🌊

Zenn 記事の目次をターミナル内でプレビュー

2021/12/28に公開

作成した Zenn 記事を実環境にデプロイしてみたところ「目次(章)のバランスがよくなかったかな」ということがありました。

本来ならばエディターのアウトラインなどで確認しておけばよいのですが、現在は CMS 上で編集しているのでそれも少し難しい。

エディターでアウトラインを表示させているスクリーンショットエディターのアウトライン表示

そのようなわけで簡単な目次のプレビュー機能を作ってみました。

対応案

2 つほど思いついた案があったのですが、最終的には「記事を CMS からローカルへ保存するスクリプトの表示の中に目次も含める」という方法になりました。

実装方法

FrontMatter + Markdown を扱うので本来ならば gray-matter + remark などを使うのが固いのですが、今回は grep などを組み合わせることにしました。

見出しの抽出

grep で先頭の # を検索することで対応します。

以下のような懸念点はありますが、今回はとりあえず保留にしておきます。

  • FrontMatter 中のコメント
  • コードブロック内の # 形式のコメント
  • コードブロック内の Markdown
  • --- を使った見出し

追記: remark-cli を使う方法も試してみたので問題が多いようなら切り替えることにします。

見出しの整形

sed と Bash の文字列操作で対応します。

grep + sed
$ grep -e '^##\{1,2\} ' -- tmp/articles/native-esm-with-typescript-jest.md | sed -e 's/^## /+ /' -e 's/^### /| /'
+ モジュールの native ESM 対応
+ ts-jest の ESM 対応設定
+ Jest の native ESM 対応設定
+ native ESM での jest モックモジュール
+ VSCode 関連
| 構文チェック
| デバッグ
| コード補完と動的インポート
+ とりあえず

表示幅の確認

これは以下のように「実環境での表示で折り返される」行を検出したいというものです。

環境によって表示は異なるので、それほど気にするものではありませんが「長すぎる見出しもよくないかな」ということで。

目次の項目が折り返されているスクリーンショット折り返されている項目

この部分はターミナル上だと難しいので(Puppeteer でいけるかもですがそこまでは)、Fullwidth などを考慮した値を wc --max-line-length で取得し簡易的に使います[1]

wc
$ echo '👀 Preview:'| wc --max-line-length
11

作ってみた

上記の内容を組み合わせて作ったのもが以下になります。

script(toc.sh)
toc.sh
#!/bin/bash
set -e

WARN_LEN="33"

COLOR_RESET='\e[0m'
COLOR_DEPTH2='\e[0m'
COLOR_DEPTH3='\e[2m'
COLOR_WARN='\e[33m'

grep -e '^\(##\|###\) ' -- | sed -e 's/^## /+ /' -e 's/^### /| /' | while read -r LINE
do
  HEADDING="${LINE::1}"
  TITLE="${LINE:2}"
  LEN="$(echo "${TITLE}" | wc --max-line-length)"

  # ヘッディング文字
  echo -n "${HEADDING} " 

  # 装飾
  if test "${LEN}" -gt "${WARN_LEN}" ; then
    echo -n -e "${COLOR_WARN}"
  elif test "${HEADDING}" = "+" ;then
    echo -n -e "${COLOR_DEPTH2}"
  else
    echo -n -e "${COLOR_DEPTH3}"
  fi

  # タイトル
  echo -n "${TITLE}"

  # 装飾リセット
  echo -n -e "${COLOR_RESET}"
  echo ""
done 
$ bash scripts/toc.sh < articles/native-esm-with-typescript-jest.md

スクリプトを実行して長いタイトルが警告色で表示されているスクリーンショット実行結果

簡単な装飾と長い行は警告色で表示されるようになっています。

おわりに

とりあえず動作するようになったので CMS からローカルへ保存するスクリプトにも組み込んで記事作成時に利用しています。

CMS のコンテンツをローカルへ保存する時に目次をプレビューしているスクリーンショットCMS からの保存時に目次プレビュー

やはり目次を事前に確認できるのは良い感じです。

ちなみに

本筋とは関係ないのですが、現在スクラップの使い方の練習もしています。

その一環として、この記事は以下のスクラップを作成してからそれを元に記述しています。

脚注
  1. https://unix.stackexchange.com/a/258551 ↩︎

GitHubで編集を提案

Discussion