これまでHeartRails Captureを使ってきたブログ内リンクを自前の実装とショートコードに置き換えました。

以前使っていたはてなブログのリンクの表示形式が気に入っていたので、それをリスペクトする形でほぼ同じような見た目で表示できるようにしました。

ある記事内のリンクの見た目はどうなったのか。BeforeとAfterで見比べてみましょう。

Before

After

新旧の違い

新旧で見た目が異なるのはもちろんですが、より詳しい情報を得られるように仕組みも変更しました。

Heartrails Captureを使ったリンクではブラウザで表示したときに見える画面のキャプチャを表示していましたが、今回のリンクではOGPを利用します。

最近は多くのサイトでOGPの画像やDescriptionが設定されていることが多いです。Hugoに移行した時からOGPを使って表示したいなと思っていました。

ショートコードとHTML

ショートコードは例えばこんな感じにしました。

{{< link url=“https://blog.piyo.tech/posts/2018-03-27-deploy-go/" >}}

ショートコードに対応したHTMlは以下のようになってます。(ほぼはてなブログと一緒)

{{- $url := .Get "url" -}}
{{- $json := getJSON .Site.Params.OgpJsonBaseUrl $url -}}
{{- $title := $json.Title -}}
{{- $siteName := $json.SiteName -}}
{{- $description := $json.Description -}}
{{- $favicon := $json.Favicon -}}
{{- $image := index $json.Image 0 -}}
{{- $imageUrl := $image.URL -}}
{{- $urlInfo := $json.URL -}}
{{- $host := $urlInfo.Host -}}

<div class="embed-wrapper">
  <div class="embed-wrapper-inner">
    <div class="embed-content with-thumb">
      <div class="thumb-wrapper">
        <a href="{{ $url }}" target="_blank">
          <img src="{{ $imageUrl }}" class="thumb">
        </a>
      </div>

      <div class="entry-body">
        <div class="entry-title">
          <a href="{{ $url }}" target="_blank">{{ $title }}</a>
        </div>
        <div class="entry-content">
          {{ $description }}
        </div>
      </div>
    </div>
    <div class="embed-footer">
      <a href="{{ $url }}" target="_blank">
	<img src="{{ $favicon }}" alt="" title="{{ $host }}" class="favicon">
	{{ $host }}
      </a>
      <a href="http://b.hatena.ne.jp/entry/{{ $url | safeURL }}" target="_blank"><img src="https://b.hatena.ne.jp/entry/image/{{ $url | safeURL }}" class="bookmark-count"></a>
    </div>
  </div>
</div>

HugoにはData Driven Contentの仕組みがあります。これはAmazonのAdvertising APIのときにも利用したのですが、JSON APIから戻ってきた値をベースにしてHTMLを組み立てられるというものです。

Data Templates | Hugo

コードのこの部分で、JSON APIを呼び出してOGPをJSONで取得します。

{{- $json := getJSON .Site.Params.OgpJsonBaseUrl $url -}}

OgpJsonBaseUrlについては、Hugoのconfig.tomlにこのように書いておきました。

[params]
  OgpJsonBaseURL = "https://myapi.xxxxx.yyy/ogp?url="

今回はURLに対応するOGPをJSONで返すサーバーを自前で用意しました。 config.tomlにはその自前サーバーのパスを書いておき、ショートコードの中でURLを渡してAPI呼び出します。そして得られたJSONの中身をもってHTMLを組み立てるということを行いました。

ちなみに、OGPをJSONで取得する方法は、最初FacebookのかOpen Graphオブジェクトデバッガーあたりからできるのではないかと考えていました。ですがどうもそんなものがないのか探し方が悪いのか、見つかりませんでした。

次回はOGPのJSONを返すサーバーについて書きまーす。