LoginSignup
2
0

More than 1 year has passed since last update.

denoでMarkdown内コードのテストをしてみる(ちょっといい感じに)

Last updated at Posted at 2022-12-11

はじめに

モジュールを作成する際、使いやすいようにREADMEにコードブロックで使用例などを載せることが多いと思います。
しかしその使用例、きちんと動きますか?

コードブロックのコードはべた書きが多いので、タイポがあったり、モジュールに変更があった場合、更新し忘れることが多々あります。

「使用例が動かない」 ということは、せっかくあなたが作ったモジュールの評価が下がることにも繋がりかねません。

ということで、deno testコマンドを駆使して、Markdownのコードをテストできるようにしましょう!
(※型チェックのみ)

テスト方法

本記事では以下のコードをテストします。

mod.ts
export function add(a: number, b: number) {
  return a + b;
}
README.md
# Usage

```ts
import { add } from "./mod.ts";

const a = add(1, 2);
console.log(a);
```

deno test --doc

$ deno test --help
deno-test 
~~~~~~~~~~ 省略 ~~~~~~~~~~
        --doc
            UNSTABLE: type-check code blocks
~~~~~~~~~~ 省略 ~~~~~~~~~~

コードブロックの型チェックを行ってくれます。これを使うことで、例のコードをチェックすると、

running 0 tests from ./README.md
running 0 tests from ./mod.ts

ok | 0 passed | 0 failed (47ms)

0 tests0 passedとはなっていますが、きちんとチェックできています。

証拠に、import文のところを./hoge.tsとしてみると、

error: Module not found "file:///C:/test-doc/hoge.ts".
    at file:///C:/test-doc/README.md$3-9.ts:1:21

とエラーになります。

改善してみよう!

前章でコードブロックの型チェックをすることは"一応"できました。
しかし、例のREADME、不親切ではありませんか?
importのURLが相対パスになっています。使う側からしたらコピペするだけでは使えないので不便です。

使いやすいようにURLインポートにしてあげましょう。

README.md
# Usage

```ts
import { add } from "https://example.com/mod.ts";

const a = add(1, 2);
console.log(a);
```

こうなります。example.comは適当な配布先になりますね。deno 3rd Partyモジュールならdeno.land/x/(モジュール名) とかでしょうか。

これで先ほどのテストを行うと...

error: Module not found "https://example.com/mod.ts".
    at file:///C:/test-doc/README.md$3-9.ts:1:21

という風に、https://example.com/mod.tsがないって怒られます。

この問題をImport Mapsで解決しましょう!

test-import-map.jsonに以下のように設定します。

test-import-map.json
{
  "imports": {
    "https://example.com/": "./"
  }
}

そして、テスト時のコマンドを次のようにして、Import Mapsを指定してあげます。

$ deno test --doc --import-map ./test-import-map.json

すると、

running 0 tests from ./README.md
running 0 tests from ./mod.ts

ok | 0 passed | 0 failed (46ms)

テストが成功しました🎊

deno.jsonを使う

テストするたびに毎回、上のようなコマンドを打つのは面倒くさいので、タスクに登録します。

deno.json
{
  "tasks": {
    "test": "deno test --doc --import-map ./test-import-map.json"
  }
}

実行するときには、

$ deno task test

これだけです!

問題点(懸念点)

いくつか考慮しておくべき点があるので書いておきます。

  • .md以外のファイルにもImport Mapsが適用されてしまう。
    • チェックしたいファイル毎にテストコマンドを用意する必要あり。
    • deno test --doc --import-map test-import-map.json README.md のようにファイルごとに実行
    • deno_task_shellのissueにglob対応したいと書いてあるのでアップデートに期待
  • 既にImportMapを使用している場合に実行用とテスト用の2つのファイルを管理する必要がある
    • 2つのファイル間で整合性を保つのが大変
  • import-map.jsonをテスト用に作る必要がある。
    • deno.json内にも書けるがそこに書くと通常実行時にも読み込んでしまう。
    • 本記事ではtest-import-map.jsonとはしたものの、もっとスマートな名前が決めれるといい。testディレクトリ内とかに作ってもいいかも
  • 実行はしてくれない
    • あくまでも--docオプションは型チェックだけなので実行はしてくれない。

さいごに

--docについて書かれている記事はいくつかあったものの、importのURLが相対パスになってしまうのが嫌いで避けていました。
なんとかならないかなと考えた結果Import Mapを使用する方法に行きつきました。
もっとスマートな方法あるよ!って方いたら遠慮なく教えてください🙇

Denoアドベントカレンダー、参加3年目。今年は忙しくて書けないかなぁと思いながらも、軽めの題が見つかったので課題の合間に急いで書いてます笑

大分早いですが、メリークリスマス & よいお年を!

2
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
2
0