tDiaryをAMP対応させモバイル表示を高速化した
最近、Google検索やはてなブックマークでAMPという技術が導入されている。AMPはモバイルでの表示速度を高速化するための仕様で、最初はニュースサイトから採用が始まっていた。この秋頃から、一般サイトの検索結果にもAMP対応サイトが表示されるようになってきたので、tDiaryもAMPに対応させてみた。
この日記も数日前からAMPを導入していて、ようやくGoogleの検索結果にも反映されるようになった。スマートフォンでbrowsereidと検索すると、このように検索結果に⚡AMPマークが表示される。
特にモバイル環境で試してみると分かるけど、AMP対応ページは一瞬で表示される。
AMP対応ページが高速に表示される仕組み
AMPでは、ページを高速化するためにいくつかの工夫と制約をかけている。AMPの公式ページに書かれているように、非同期のスクリプトのみ許可したり、スタイルシートを埋め込んだり、標準のHTMLに比べてできることをかなり制限している。さらに、コンテンツをCDNでキャッシュすることで、低遅延での配送を可能にしている。
tDiaryもAMP対応してみた
AMPはその制約上、静的なページに向いている。tDiaryはうってつけだろうと思い、AMP対応のプラグインを書いた。
設計の基本方針として、既存のHTMLをAMP向けにカスタマイズするか、それともAMP専用ページを作るかの2案がある。AMPはまだ仕様が変わりそうなのと、制約が多く元ページを完全再現するのは難しいだろうと判断し、AMP専用ページを作ることにした。
AMPはtDiaryのプラグインとして実装する。プラグインでは専用のコンテンツを返すための add_content_proc
という仕組みがあるので、それを使う。既存ページに ?plugin=amp
を付けるとAMPページが表示されるようにした。tDiaryの特徴であるセクションアンカーが反映されないけど、これはもう仕方ない。
- 既存ページ:
http://www.machu.jp/diary/20110722.html
- AMP対応ページ:
http://www.machu.jp/diary/20110722.html?plugin=amp
misc/plugin/amp.rbをつくり、以下の処理を書く。
add_content_proc('amp') do |date|
diary = @diaries[date]
ERB.new(File.read("views/amp.rhtml")).result(binding)
end
views/amp.rhtmlはAMP公式サイトのチュートリアルを見ながら雛形を作っていく。
<!doctype html>
<html ⚡ lang="ja">
<head>
<meta charset="utf-8">
<script async src="https://cdn.ampproject.org/v0.js"></script>
<title><%= amp_title %></title>
<link rel="canonical" href="<%= amp_canonical_url(diary) %>" />
<meta name="viewport" content="width=device-width,minimum-scale=1,initial-scale=1">
<script type="application/ld+json">
{
"@context": "http://schema.org",
"@type": "BlogPosting",
"headline": "<%= amp_headline(diary) %>",
"datePublished": "<%= amp_last_modified(diary) %>",
"dateModified": "<%= amp_last_modified(diary) %>",
"image": [
"<%= amp_logo %>"
],
"description": "<%= amp_description(diary) %>"
}
</script>
<style amp-boilerplate>中略</style></noscript>
<style amp-custom>
<%= amp_style %>
</style>
</head>
<body>
<div class="whole-content">
<div class="adminmenu">
<%= navi_user %>
</div>
<div class="content">
<h1><a href="<%= amp_canonical_url(diary) %>"><%= amp_title %></a></h1>
<div class="day">
<h2><%= amp_day_title(diary) %></h2>
<div class="body">
<%= amp_body(diary) %>
</div>
</div>
</div>
<div class="footer">
</div>
</div>
</body>
</html>
あとは、HTMLに埋め込みたいデータをプラグイン側でちょこちょこ書いていくだけ。
- スタイルシートはHTMLに埋め込まないと使えないので、プラグイン側でFile.readして埋め込んでいる
- img要素は使えないのでamp-img要素に置き換えている
まだまだ基本だけだけど、これで一通り動くようになった。
まだYouTubeなどの埋め込み系には対応できていない。Google Search Controlを使えば、どのページがAMPとして非対応なのかを教えてくれるので、それを見ながら修正していくつもり。これはボチボチやっていこう。
tDiaryをお使いの方は、ぜひAMPプラグインを導入してフィードバックいただければ。