mdmark

索引と用語集を書く

索引に文書と用語を書き、表から用語集に用語を入れる手順

文書の用語に意味のツールチップを付けるとき、文書を参照している文書を文書の末尾に出すとき、索引と文書のずれを見つけるときに実行する。

前提

手順

索引に文書と用語を書く

索引の YAML を書く

schema: 1
docs:
  - id: arch
    path: 設計/arch.md
    title: アーキテクチャ
  - id: api
    path: api.md
    title: API
    description: mount と render の引数
    aliases: [公開関数]
    related:
      - to: arch
        type: requires
        when: 公開関数の前提の構成を確かめるとき
terms:
  - id: workspace
    term: ワークスペース
    aliases: [WS]
    meaning: 話し合いの記録を置くフォルダ
    avoid: [作業場]

path は索引のファイルからの相対パスで書く。 avoid に、使わないことにした言い方を並べる。 本文に出ると、描いた文書では波線のマーカーとツールチップが付き、点検も知らせる(索引と文書のずれを点検する)。 キーと型は 索引。 索引の場所は、設定の index に書く(索引の場所)。

索引と文書の id を渡して描く

使う側のサーバーが索引の YAML を読み、読んだオブジェクトと描く文書の id を mount に渡す。

mount(document.querySelector("#doc"), { markdown, index, docId: "arch" });

本文に出た用語の語・別名に破線の下線が付く。 下線は、同じ用語(語と別名を合わせた用語の id)の、節ごとに最初に出たところだけに付く。 語の始まりと終わりが本文の語の区切りに揃うところだけを照合するため、印刷 の中の 印 には付かない。 Intl.Segmenter を持たないブラウザ(Firefox 124 以前)では、英数字の連なりを 1 語とし、それ以外の文字を 1 文字ずつ区切って照合する。 英字の語の一部(WSL の中の WS)には付かないが、印刷 の中の 印 には付く。 コード・リンク・見出し・用語集の表の中の語には付かない。

照合の前に、索引・用語集の表の語と本文の文字の両方を、NFKC・英字の小文字化・前後の空白の除去で正規化する。 全角と半角(API と API)、英字の大文字と小文字(Api と API)だけが違う語は同じ語として照合し、下線は本文に記載したままの文字に付く。 活用形・送り仮名・別の言い方のように、正規化しても同じにならない揺れは、aliases に記載する。

ポインターを乗せるかフォーカスすると、見出し「用語」に意味を出したツールチップが開く。 ツールチップの上へポインターを移しても開いたままで、Esc で閉じる。 索引を渡さないときは、用語集の表から入れた用語だけが付く。

索引の用語の avoid と用語集の表の avoid= の列に並べたやめた言い方が本文に出ると、波線のマーカーが付く。 やめた言い方も、用語と同じ正規化をして照合する。 マーカーは、同じやめた言い方の、節ごとに最初に出たところだけに付き、用語の下線とは別に数える。 ポインターを乗せるかフォーカスすると、見出し「代わりの用語」に代わりの用語の語と意味を出したツールチップが開き、開閉の操作は用語のツールチップと同じ。 同じやめた言い方を複数の用語が持つときは、次の順で先の用語が代わりの用語になる(点検の avoided_term と同じ順)。

優先 やめた言い方を持つ場所 代わりの用語
先 索引の terms の用語の avoid その用語
後 索引の docs の順の文書の用語集の表の行。描く文書が docs に無いときは、描く文書の表をほかの文書の表より先にする その行の用語の列と意味の列の文字

用語の語・別名の一部として出たところ(ワーク をやめた言い方にしたときの ワークスペース)には付かず、コード・リンク・見出し・用語集の表の中にも付かない。 色は CSS 変数 --mdmark-color-avoided-underline で変える(テーマの CSS 変数)。 glossary をオフにすると、マーカーもツールチップも付かない。

文書の関連を書く

関連に相手・関係の種類・いつ読むかを書く

docs:
  - id: api
    path: api.md
    title: API
    related:
      - to: arch
        type: requires
        when: 公開関数の前提の構成を確かめるとき

to に相手の文書の id、type に関係の種類、when にいつ読むかの 1 文を記載する。 type は requires(前提)・references(参照)・replaces(置き換え)・part_of(一部)・change_together(一緒に直す)のどれか。 関連が当たるファイルを絞るときは、paths に glob の並びを記載する。 キーと型は 索引。

関連は片側だけに記載する。 逆向きは、Claude Code が find_docs の related_to で引くときに、向きと逆向きの名前つきで出る(MCP のツールを使う)。 change_together だけは、両側に記載する。 片側にしか記載していない change_together は、点検が知らせる。 本文でリンクしている相手は、related と本文のリンクのどちらか一方にする(change_together を除く)。 文字列の要素(related: [arch])も読めるが、type と when を持たない関連として扱い、点検がオブジェクトへの書き換えを求める。

タグの語彙と主題のタグを書く

索引の最上位にタグの語彙を書く

tags:
  - name: topic:mcp
    group: topic
    description: "含める: MCP のツールの作り方。含めない: Claude Code の設定。例: find_docs の引数"
    aliases: [MCP]
  - name: topic:old-mcp
    deprecated: topic:mcp

name はタグの名前で、語彙の中で一意にする。 group にタグのグループ(topic・kind・scope・tool など)、description にタグを付ける文書の「含める / 含めない / 例」、aliases にタグの別名を書く。 やめたタグは、deprecated に代わりに使うタグの name を書く。 語彙は索引に 1 つだけ置き、同じ name をグループごとに別に書かない。 キーと型は 索引。

文書に主題のタグを付ける

文書の tags に、タグの名前の文字列か、name と main を持つオブジェクトを書く。 その文書の主題を表すタグは、main: true を付けたオブジェクトで書く。

docs:
  - id: arch
    path: 設計/arch.md
    title: アーキテクチャ
    tags: [設計, { name: topic:mcp, main: true }]

文字列で書いたタグは、main: false と同じ。 find_docs は、絞り込みのタグが主題のタグに当たる文書を上に並べる(MCP のツールを使う)。 語彙の aliases に当たる別名は、語彙の name のタグとして扱う。

語彙を記載した索引では、checkIndex と mdmark check が、語彙に無いタグ・やめたタグ・語彙の重なりと振り替え先の切れを知らせる(索引と文書のずれを点検する)。 語彙を記載していない索引では、タグのずれを知らせない。 Claude Code から語彙を書き換えるときは、MCP の update_index の kind に tag を渡す。

表から用語集に用語を入れる

表を glossary の印で囲む

<!-- glossary: term=用語 aliases=別名 meaning=意味 -->

| 用語 | 別名 | 意味 |
| --- | --- | --- |
| 印 | マーク、オン・オフの印 | HTML コメントで書く指定 |

<!-- /glossary -->

term=・meaning= に、用語と意味の列の見出しの文字を書く。 別名の列は aliases= に書き、別名のセルは「、」か「,」で区切る。 「・」は別名の中の文字として扱うため、オン・オフの印 は 1 つの別名になる。 やめた言い方の列は avoid= に書き、セルは別名と同じく区切る。 索引の文書の本文にやめた言い方が出ると、点検が知らせる(索引と文書のずれを点検する)。 この列のやめた言い方にも、索引の用語の avoid と同じく、描いた文書で波線のマーカーと、その行の用語を代わりの用語にしたツールチップが付く。 ほかの文書の表のやめた言い方は、collectReferences の戻り値を references に渡したときに効く。 表は普通の表として描き、表の中の語には下線を付けない。

索引に同じ語があるときは、索引の意味をツールチップに出す。 同じ語かどうかは、正規化した後で判定する。 索引を渡し、collectReferences の戻り値を references に渡すと、ほかの文書の用語集の表から入れた用語も効く。

列名が表に無いときも、表と本文は描かれる。 その箇所に書き方の警告が出て、この表からは用語を入れない。

被参照と関連文書を出す

参照の表を作って渡す

使う側のサーバーが、索引と全ての文書の本文から参照の表を作る。

const references = collectReferences({ index, documents });
mount(document.querySelector("#doc"), { markdown, index, docId: "arch", references });

documents は、文書のパスから Markdown を引く表で、パスは索引のファイルからの相対パスで書く。 文書を書き換えたら、参照の表を作り直す。

文書の末尾に、その文書を参照している文書が、題「関連文書」のリンクの一覧で並ぶ。 文書を参照しているのは、次のどれかに当たる文書で、自分自身は並ばない。

aliases は、全角と半角・英字の大文字と小文字の違いを無視して照合する。 参照されていない文書には、一覧を置かない。 参照の表を渡さないときは、索引の related だけから出す。

文書の別名を書く

索引の文書の aliases に書いた語が本文に出ると、用語と同じ規則で下線が付く。 ツールチップの見出し「関連文書」に、一致した文書の題・リンク・description が並ぶ。 描いた文書自身は並ばない。 用語にも一致する語は、「用語」→「関連文書」の順に並ぶ。 関連文書のリンクはキーボードで、語の次の Tab から中へ移れる。 関連文書が多いときは、ツールチップの中をスクロールする。

文書の別名の数え方は用語とは別で、文書の id ごとに、節で最初に出たところだけに下線が付く。 用語を数え終えた語でも、文書の別名として節で初めて出たなら、「関連文書」だけのツールチップで下線が付く。

画面を出さずに本文の参照を取り出す

collectMatches を呼ぶ

使う側の処理(AI へ本文を返すサーバーなど)が、索引と文書の本文を渡し、本文に出た用語・文書の別名の一致を受け取る。

const { byDocument, avoided, targets } = collectMatches({ index, documents });

documents は collectReferences と同じ、文書のパスから Markdown を引く表。 複数の文書を渡せる。

byDocument は、文書の id から、その文書の本文の一致の並びを引く表。 要素は、参照先の種類(kind)・id・title・description と、一致した文字列(text)・本文の位置(line・start・end)を持つ。 avoided は、文書の id から、その文書の本文に出たやめた言い方の並びを引く表。 要素は、代わりの用語の種類(kind)・id・title・description と、一致したやめた言い方(text)・本文の位置(line・start・end)を持つ。 glossary がオフの文書は、空の並びになる。 targets は、渡した全ての文書の参照先を、重なりを除いてまとめた並び。 キーと型は 本文の参照を取り出す。

一致の規則は、描いた文書の下線とツールチップと同じ。 照合の前の正規化も同じで、text は照合した索引・用語集の表に記載した表記のまま返す。 本文に記載した表記は、本文の位置(line・start・end)から引く。 同じ実行環境で、mount に同じ索引・設定と、同じ documents から collectReferences で作った参照の表(references)を渡して描いた下線と、同じ語が一致する。 語の区切りは実行環境に依る(Intl.Segmenter の有無と辞書で決まる)ため、サーバーで取り出してブラウザで描くときは、一致が変わることがある。 ただし、ツールチップの、節ごとに最初の 1 回だけに下線を付ける制限は効かず、同じ参照先の出現を全て並べる。 やめた言い方のマーカーの、節ごとに最初の 1 回だけに付ける制限も効かず、avoided には同じやめた言い方の出現を全て並べる。 位置は、本文の Markdown の行(1 から)と、その行の中の UTF-16 の位置(0 から)で、本文に記載したままの範囲を指す。

索引と文書のずれを点検する

checkIndex を呼ぶ

const issues = checkIndex({ index, documents, indexFile: "docs/index.yaml" });

index は読んだ値をそのまま渡す。 documents に、索引のフォルダにある文書のパスと本文を渡す。 索引に無い文書・索引にあって消えた文書・related の切れた id・文字列の関連・片側だけの change_together・本文のリンクと重なる関連・用語の重複・本文に出た用語のやめた言い方・語彙に無いタグ・やめたタグ・タグの語彙のずれ(タグの語彙を記載した索引のとき)・Schema に合わない索引が、ファイル・場所・種類・内容の一覧で返る。 ずれが無ければ、空の一覧が返る。 用語の重複は、語と別名を正規化した後に同じになるものも数え、本文に出たやめた言い方も正規化して照合する。 changedPaths に、比べる基準から変わった文書のパスを渡すと、change_together の組のうち片方の文書だけが変わった組が、直し忘れとして missed_change_together で返る。 パスの引き方は呼ぶ側が決める(mdmark check --base は git の merge-base から引く。点検する)。 種類は 点検が返すずれ。

反映

即時。mount を呼ぶと、その場で描かれる。 update は、mount に渡した索引と参照の表で本文を描き直す。 索引や文書を書き換えたときは、参照の表を作り直し、読み直した値を渡して mount を呼び直す。

確認

用語のツールチップが出る

下線の付いた語にポインターを乗せる。 意味のツールチップが出て、ツールチップの上へポインターを移しても出たままになる。 Tab で下線の付いた語へフォーカスしても出て、Esc で消える。

被参照の一覧が出る

文書の末尾に、題 関連文書 の一覧がある。

document.querySelector(".mdmark .mdmark-backlinks-title").textContent

関連文書 が出る。 一覧のリンクの href は、描いた文書の path から見た相対パスになっている。

本文の参照が返る

本文に索引の用語の語を含めた文書を渡して collectMatches を呼ぶ。

collectMatches({ index, documents }).byDocument["arch"].map((m) => m.text)

本文に出た用語・文書の別名の text が、本文の頭からの順に並ぶ。

点検がずれを返す

索引から文書を 1 つ消した状態で checkIndex を呼ぶ。 その文書の行が orphan_doc で返る。

元に戻す

mount から index・docId・references を外すと、索引を渡さない文書と同じに描く。 用語集の表の印を消すと、表は普通の表に戻る。 機能を止めるときは、機能をオン・オフする で glossary・backlinks をオフにする。