🐔

【esa.io】カテゴリ全体の移動後にカテゴリへのリンクを切れさせない方法

2024/09/26に公開

課題

esa.ioにはカテゴリというディレクトリのような多層の整理システムがあります。
esaのポスト(記事)はこのカテゴリ内を自由に移動させることができます。

このカテゴリ間でポストを移動させた場合ですが、ポストへのリンクは切れません。
というのも、ポストのURLはユニークなIDしか含んでおらず、カテゴリのIDや文字列を含んでいないためです。

https://docs.esa.io/posts/251

ですが、カテゴリのそのものへのリンクは別です。これには次のようにカテゴリ自体の表記文字列を含んでおり、カテゴリ全体を移動させるとリンク切れになります。

https://docs.esa.io/#path=%2FReleaseNotes%2F2024

このリンク切れを回避する方法を紹介します。

方法1: マニュアルリダイレクトのためのREADME

例えば ReleaseNotes/2024 というカテゴリを esa/ReleaseNotes/2024 へ移動させるとします。
この場合、各記事中に https://docs.esa.io/#path=%2FReleaseNotes%2F2024 のリンクが存在すると、移動後は次のように真っ白なページしか表示されません。

そこで、すでに移動して中身が空っぽの元のカテゴリ位置にREADMEを追加して、移動先へのリンクを書いておきます。

こうすると行き先不明にならずに目的のカテゴリへ移動できます。
いわば人力で解決する301 Moved Permanentlyですね。

この方法の欠点は、移動したにも関わらず古い元のカテゴリにREADMEの1ポストが残り続けてしまうことと毎回ワンクッション挟まってしまうことですが、簡単で安全性も高いです。

方法2: スクリプトでの全ポスト中での書き換え

esa内のリンク切れであれば、次のスクリプトを使うことで修正できます。

このスクリプトの機能は非常にシンプルで、esaチーム全体のポストから特定の文字列を見つけ出し、記事中のその文字列を別の文字列へ置換するだけです(まさにfind grep replace)。

前述の例を使うと、カテゴリ移動前のリンクは

  • https://bigwheel.esa.io/#path=%2FReleaseNotes%2F2024

で、カテゴリ移動後はそれを

  • https://bigwheel.esa.io/#path=%2Fesa%2FReleaseNotes%2F2024

にすればよいです。なので、

./esa-findgrepreplace.sh $pat bigwheel 'https://bigwheel.esa.io/#path=%2FReleaseNotes%2F2024' 'https://bigwheel.esa.io/#path=%2Fesa%2FReleaseNotes%2F2024'

としてやればチーム内の全ポストの全リンクを書き換えることができます。

この方法の欠点は、API呼び出し制限のため、デフォルトでは書き換えの処理速度が 150ポスト/Hour と比較的低速なことです[1]。あとは機械的な置換であるためバグや誤った文字列指定で大規模な書き換えミスが発生しうるので慎重に行う必要があります。

備考: この方法で8000ポストの移動と1000ポスト以上の書き換えを行いましたが正常に実行できました

個人的なおすすめ

個人的には、スクリプトでesa内のリンクはすべて移動後のページへ直接飛ぶようにしつつ、esa外に書かれたリンクがリンク切れにならないよう、マニュアルリダイレクトREADMEも置くのが良いと思います。

備考

これはリンク切れとは無関係な注意点ですが、カテゴリ内のポストの一括移動は、アーカイブ内およびテンプレート内のポストは移動してくれません。
少なくともテンプレート内のポストは同様の移動をしたほうが良いでしょう。

謝辞

本記事の手法、特に前者については esa.io のサポートへの問い合わせをもとにしております(許可を得て掲載させていただきました)。

脚注
  1. https://docs.esa.io/posts/102#利用制限 に書かれた制限を回避するためsleepを設定しています。底に書かれている通りサポートに連絡することでこの制限は一時的に緩和することができるそうなので、緩和をしてからスクリプトの引数でsleep時間をより短くすればもっと早くすることができます ↩︎

株式会社エス・エム・エス

Discussion