takanorip blog

ブログにシェア画像自動生成機能をつけた

2020年7月2日

TOC

概要

シェア画像自動生成機能をつけた。この記事を参考にした。

大体こんな感じ。

  1. タイトルからシェア画像の元になるページを生成
  2. ブログのデータにシェア画像URLをセット
  3. ベースレイアウトでURLをog:imageにセット
  4. 生成元ページのHTMLからPNGを生成

細かい話

HTML to PNG

参考にした記事ではSVGを作ってそれをPNGに変換しているけど、僕はSVGでいろいろ調整していくのがめんどくさかったのでHTMLをPNGにする方法にした。HTMLをPNGに変換するのはnode-html-to-imageを使った。このライブラリはpuppeteerを使ってHTMLを画像に変換してくれるやつ。記事数増えてビルドに時間かかりすぎるようなら考え直すかも。

CSS in puppeteer

外部CSSは反映されなかったのでインラインスタイルでCSSを書いた。Google Fontsのフォントを参照したかったんだけど無理だったのでbase64にしてHTMLに埋め込んだ。おかげでHTMLがクソ長になってしまった…。
node-html-to-imageのoptionにあるwaitUntildomcontentloadedを設定すれば外部CSSも適用される。(base64でフォント埋め込んだせいでビルドが大変遅くなっていた…。)

{
  waitUntil: 'domcontentloaded',
}

あと「ブラウザで見ると問題ないのに生成した画像だとちょっとずれる」みたいなことがあったのでCSSを調整した。margin-topがあると良くないみたいだったのでpaddingにした。

Computed Data

記事のデータにogImageUrlを持たせる必要があったので、11tyのComputed Dataという仕組みを利用した。blogディレクトリにblog.11tydata.jsを配置して下記のようなコードを書けば、blog配下にある記事すべてにogImageUrlというデータが追加される。

module.exports = {
  eleventyComputed: {
    ogImageUrl: (data) =>
      `https://takanorip.com/teasers/${data.page.fileSlug}.png`,
  },
};

その他

11tyのPaginationPermalinkはマジで便利。この2つを使えば任意のデータからページを簡単に出力できる。タグの記事一覧もこれらの機能を使って実装されてる。

感想

意外とかんたんだった。だいぶ11tyを理解してきた気がする。

takanorip

digital design engineer. X: @takanoripe