GitHub.com Markdown でアンカーを独自に作成したい

<!-- # GitHub.com Markdown でアンカーを独自に作成したい -->

GitHub\.com Markdown では、HTML によるアンカーの作成が可能です。これによって、見出しのように特定のパラグラフや図表、数式のような要素にジャンプすることが可能になります。

しかしながら、Markdown 内で HTML を使うには何かと面倒事が発生しがちです。

そこで本記事では、HTML によるアンカーの作成とその注意点を紹介します。

:::note warn
この方法は Qiita では使えないことに注意してください。
:::

## `<a>` タグによるアンカーの作成

HTML のアンカー作成には `<a>` タグを利用しますが、GitHub\.com Markdown でもこれが利用できます。

GitHub\.com 公式の Markdown 記法を紹介する GitHub Docs の  [カスタムアンカー][github-docs-custom-anchor] の項では、`name` 属性によるアンカーの作成が紹介されています。

[github-docs-custom-anchor]: https://docs.github.com/ja/get-started/writing-on-github/getting-started-with-writing-and-formatting-on-github/basic-writing-and-formatting-syntax#custom-anchors "カスタムアンカー | 基本的な書き方とフォーマットの構文 - GitHub Docs"

```markdown
# Section Heading

Some body text of this section.

<a name="my-custom-anchor-point"></a>
Some text I want to provide a direct link to, but which doesn't have its own heading.

(… more content…)
```

上の `<a>` タグの参照方法は普通のリンク記法を使って作成したアンカーを `#` に続く形で書けば良いです。

```markdown
[A link to that custom anchor](#my-custom-anchor-point)
```

ただし MDN によるアンカー要素の [`name` 属性の項][mdn-a-name] を参照すると、`name` 属性は非推奨であり `id` 属性を使うべきとされています。

[mdn-a-name]: https://developer.mozilla.org/ja/docs/Web/HTML/Element/a#name "<a>: アンカー要素 - HTML: ハイパーテキストマークアップ言語 | MDN"

GitHub\.com Markdown では `id` 属性も利用できるため、`id` 属性を使っても良いでしょう。

```markdown
<a id="my-custom-anchor-point"></a>
Some text I want to provide a direct link to, but which doesn't have its own heading.
```

ここではパラグラフへのアンカーの例となっていますが、他にも図表や数式等の参照のためのアンカーの利用が出来ます。

:::note info
`name` 属性は非推奨のため、本記事の例では `id` 属性を利用してアンカーを作成します。
:::

### 注意点

`<a>` タグを一行で `<a id="..."></a>` の形で利用する限り、これらは raw HTML として解釈されます。

```markdown
<a id="block-quotes"></a>
> ここはブロッククォートです。
```

しかし、これを以下のように複数行に渡って使用すると、HTML ブロックとして解釈されるようになります。
そのため、`</a>` 以降で Markdown 記法を利用しても上手く解釈されません。

```markdown
<a id="block-quotes">
</a>
> ここはブロッククォートですが Markdown として解釈されません。
```

これは、HTML ブロックの [type 7 blocks][html-blocks-7] として解釈されるためです。（HTML タグが 1 行に単体で存在する場合、HTML ブロックとして解釈される仕様）

[html-blocks-7]: https://github.github.com/gfm/#html-blocks "Start condition: line begins with a complete open tag (with any tag name other than script, style, or pre) or a complete closing tag, followed only by whitespace or the end of the line. | §4.6 HTML blocks - GitHub Flavored Markdown Spec"

一方で、`<a id="...">` のある行に `</a>` や文章があった場合には raw HTML として解釈されるため、これに続く次行は HTML ブロックとはなりません。

----------

もしも、図表やコードブロック等の GitHub Flavored Markdown (GFM) の要素全体をアンカーに含めたい場合は、HTML タグと Markdown 要素との間に空行を挟みましょう。
これによって、中の要素は Markdown 記法として解釈されます。

```markdown
<a id="image-id">

![alt](link/to/image.png)

</a>
```

## 見出しのアンカー

GitHub\.com Markdown では、自動的に見出しにアンカーを追加します。

この機能そのものは非常に有用ですが、見出しそのものが長い文のためにアンカー名が煩雑になったり、そもそも見出しアンカーが作成されない領域（Issues やそのコメント等）もあったりします。
その場合には、任意のアンカーを作成したいこともあるでしょう。

本節では `<a>` タグによる方法と HTML 見出し要素による任意のアンカーの構成方法を紹介します。

:::note info
GitHub\.com のリポジトリ内の Markdown ファイルでは、見出しの左側に :link: が表示されます。ここに自動的に作成された見出しアンカーが与えられていますが、これを変更することは出来ないことに注意してください。

本節で作成する任意のアンカーは既にあるアンカーに追加する形になります。

自動作成される見出しのアンカーに関しては、GitHub\.com 公式の Markdown 記法を紹介する GitHub Docs の [セクションリンク][github-docs-sectionlink] の項を参照してください。
:::

[github-docs-sectionlink]: https://docs.github.com/ja/get-started/writing-on-github/getting-started-with-writing-and-formatting-on-github/basic-writing-and-formatting-syntax#section-links "セクションリンク | 基本的な書き方とフォーマットの構文 - GitHub Docs"

### 見出しにアンカーを追加する

見出しのアンカーを変更するのではなく、Markdown で書かれた見出しの中にアンカーを追加します。これによって、任意のアンカーを見出しアンカーとして利用することが出来ます。

```markdown
## <a id="lipsum"></a> Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.
```

これで、自動作成されるアンカーリンクは以下のようになるのに対して、`<a>` タグで作成したアンカーリンクは `[...](#lipsum)` で済むようになります。（どちらのアンカーも機能します）

```markdown
[...](#lorem-ipsum-dolor-sit-amet-consectetur-adipiscing-elitd-sed-do-eiusmod-tempor-incididunt-ut-labore-et-dolore-magna-aliqua-Ut-enim-ad-minim-veniam-quis-nostrud-exercitation-ullamco-laboris-nisi-ut-aliquip-ex-ea-commodo-consequat-Duis-aute-irure-dolor-in-reprehenderit-in-voluptate-velit-esse-cillum-dolore-eu-fugiat-nulla-pariatur-Excepteur-sint-occaecat-cupidatat-non-proident-sunt-in-culpa-qui-officia-deserunt-mollit-anim-id-est-laborum)
```

また、この見出しへのアンカーの追加は、見出しを変更してもアンカーが変わらないと言うメリットがあります。

### HTML で見出しを作成する

GitHub\.com Markdown では HTML によって見出しを作成することも出来ます。`<h1>` 等の見出し要素には `<a>` タグと同じように `name` 属性と `id` 属性を利用できます。

```markdown
<h2 id="heading-anchor"> Heading </h2>
```

これによって作成されるアンカーは以下の 2 つです。

- 自動的に作成される見出し名によるアンカー
- `name`・`id` 属性で指定したアンカー

そのため、リポジトリ内の見出し左側の :link: に与えられているアンカーは変わらず GitHub\.com が自動的に作成するアンカーです。
HTML で見出しを作成する場合であっても、`name`・`id` 属性によるアンカーは追加的な見出しアンカーになってしまうことに注意してください。

加えて、見出しの HTML タグ内では GFM 内の記法（強調やリンク等）が使えないことに注意してください。
一方で、GFM 外の記法（絵文字や数式等）はいつもの通りに使えます。

また、見出しの HTML タグの後に空白行を挟まずにパラグラフ等が続く場合、このパラグラフ等も HTML ブロックとして解釈されます。
そのため、見出しを HTML で表現する場合は、空白行を入れることを忘れないように注意してください。

```markdown
<h2 id="custom"> ここで Markdown による**強調**は機能しません </h2>
ここも *HTML* ブロックとして解釈されます。
そのため、ここで *Markdown* 記法を用いてもリテラル表示されます。

空白行を置きましょう。（ここは *Markdown* が使える）
```

これは、HTML ブロックの [type 6 blocks][html-blocks-6] として解釈されるためです。（特定の HTML タグから行が始まる場合、HTML ブロックとして解釈される仕様）

[html-blocks-6]: https://github.github.com/gfm/#html-blocks "Start condition: line begins the string < or </ followed by one of the strings (case-insensitive) address, article, aside, base, basefont, blockquote, body, caption, center, col, colgroup, dd, details, dialog, dir, div, dl, dt, fieldset, figcaption, figure, footer, form, frame, frameset, h1, h2, h3, h4, h5, h6, head, header, hr, html, iframe, legend, li, link, main, menu, menuitem, nav, noframes, ol, optgroup, option, p, param, section, source, summary, table, tbody, td, tfoot, th, thead, title, tr, track, ul, followed by whitespace, the end of the line, the string >, or the string />. | §4.6 HTML blocks - GitHub Flavored Markdown Spec"

### 他の Markdown なら……

Markdown の中には、次のように波括弧で見出しのアンカーをカスタムすることも出来るものもあります。しかし、GitHub\.com Markdown では実装されていません。

```markdown
## Heading {#custom-id}
```

Markdown 内で HTML タグを使うとなにかとヤヤコシイことになるのでなるべく使いたくないですが、見出しのアンカーを替えたい場合は、追加的に `<a>` タグを使いましょう。

## 余談

GitHub Docs にアンカーリンクの項があることを見つけたので記事にしてみました。

https://docs.github.com/ja/get-started/writing-on-github/getting-started-with-writing-and-formatting-on-github/basic-writing-and-formatting-syntax

GitHub\.com Markdown 内で HTML が利用できることは知られていますが、HTML タグや属性のどれが利用可能なのかは明らかにされていません。
また、特にアンカーに関しては調べてみても GitHub Docs 以外の記事を見つけることが出来ませんでした。

本記事がより良い README や Issue の助けになれば幸いです。より良い GitHub\.com Markdown ライフを。