一休.com Developers Blog

一休のエンジニア、デザイナー、ディレクターが情報を発信していきます

Rendertron導入でDynamic Renderingしている話

こんにちは。 一休.comの開発基盤を担当しています、akasakasです。

今回は、Rendertronを導入してDynamic Renderingをしている話をしたいと思います。

ここでお話しする内容

  • Dynamic Renderingについて
  • 一休.com/一休レストランでDynamic Renderingが必要になった背景
  • Rendertron とは
  • Rendertron にした理由
  • Rendertron 導入イメージ
  • クローキングの懸念
  • 苦労話
    • Rendertronのモバイル対応がバグってた
    • Rendertronのメモリリーク
    • AMPページに対してDynamic Renderingを適用するとレンダリング後が評価されてしまって正常なAMPとして認識されない
  • 学び
    • できたてのライブラリは不完全(どこかしらにバグは潜んでいる)
    • Dynamic Renderingさせるべき画面・させないほうがいい画面を明確にする
  • おまけ:Dynamic Renderingについて思うこと

Dynamic Renderingについて

Dynamic Renderingは、ユーザ向けのリクエストは正常に処理し、bot向けのリクエストはレンダラを経由し、静的HTMLを配信する方法です。

f:id:akasakas:20190308205632p:plain

Dynamic Renderingについては、いろんなところで言及されているので、詳細については割愛します。

詳しくはこちらに書かれているので、興味のある方はご覧ください。

ダイナミック レンダリングの使用方法  |  検索  |  Google Developers

Google ウェブマスター向け公式ブログ: Rendertron によるダイナミック レンダリング

一休.com/一休レストランでDynamic Renderingが必要になった背景

一休.comも一休レストランもSPA化が進んできたというが大きいです。

一休.comの場合

ホテルリストページ スマホ版の速度改善でmetaタグ等をJSで書いて、Full CSRにして、ページスピードを上げていきたいという背景がありました。

詳しくはこちらで書かれていますので、興味のある方はご覧いただければと思います。

user-first.ikyu.co.jp

一休レストランの場合

  • スマホページのSPA化対応後、SEO対策のためにフロント実装が複雑化し、パフォーマンス劣化を助長する形になっていた
  • 検索結果の取得は 1 つの API で出来るのに SEO 上必要な文字列を SSR で描画するため複数の API の待ち合わせをする必要があった
  • またそれらの SSR する情報は必ずしも Above the fold で表示されるコンテンツではないためパフォーマンスの観点で言えば遅延描画するのが合理的だった
  • SEO とユーザーパフォーマンス改善の 2 つがコンフリクトしている現実を突き付けられた
  • Dynamic Rendering ならそれぞれの用途に最適化した結果を返せる

user-first.ikyu.co.jp

一休.com・一休レストランともにDynamic Rendering の必要性が増してきたため、導入を検討しました。

Rendertronとは

Rendertron は Headless Chrome (Puppeteer) をベースとしたレンダラです。

github.com

Rendertronの役割としては

  • レンダリングさせるURLを受け取る
  • 受け取ったURLのJavaScriptまで実行と描画
  • 静的HTMLをレスポンスとして返す

といったところです。

デモ用のエンドポイントもあるので、これを触ればRendertronのことをある程度知ることができると思います。

https://render-tron.appspot.com/

Rendertronを採用した理由

正直な話、ちゃんとした理由はないです(笑)

  • id:supercalifragilisticexpiali がサクッとDockerfileを作ってくれた
  • ST/PRDまでの環境もサクッとできた
  • とりあえずできたから、本番投入して試してみよう

という勢いです。

Redertron以外の選択肢として、以下の2つもアリだと思うので、興味のある方は試してみていいと思います。

github.com

prerender.io

Rendertron 導入イメージ

導入イメージは下記になります。

f:id:akasakas:20190308205321p:plain

やっていることは2つです。

  • Fastlyでルーティングとレスポンスキャッシュ
  • レンダラはRendertronに任せる

という流れです

クローキングの懸念

Dynamic Rendering自体がGoogleお墨付きの手法なので、問題ないとは思いつつも不安でした。

モバイルフレンドリーテストや Fetch As Googleで問題ないのは確認済みだったのですが、それでもちょっと不安だったので、部分導入でSEO面で問題ないかどうかという検証を行いました。

結果としては、問題なかったです。

苦労話

Rendertronのモバイル対応がバグってた

Rendertron導入検討時はモバイル対応がバグってました。

現在は解消中ですが、下記のプルリクエストがマージされる前は、これを取りこんでいました

Fix mobile rendering by danielpoonwj · Pull Request #234 · GoogleChrome/rendertron · GitHub

Rendertronのメモリリーク

Redertronを数日間、運用してみると、メモリ使用量がどんどん増えていくのがわかりました。

http status code 400 か 403 の場合は puppeteerが起動したままになり、プロセスが残り続け、メモリを食いつぶしていくということになってました。

下記のプルリクエストで対応はしておりますが、 2019/03/12 時点ではまだマージされてないので、これを取り込んで、なんとか乗り切ってます。

Always close page before return to prevent memory leak by ramadimasatria · Pull Request #268 · GoogleChrome/rendertron · GitHub

AMPページに対してDynamic Renderingを適用するとレンダリング後が評価されてしまって正常なAMPとして認識されない

Rendertron導入当初、AMPページもDynamic Renderingの対象ページとして含めていました。

しかし、AMPページに対してDynamic Renderingを適用するとレンダリング後が評価されてしまって正常なAMPとして認識されないので、AMPページはDynamic Renderingさせないようにしました。

学び

できたてのライブラリは不完全(どこかしらにバグは潜んでいる)

単純に rendertronを git clone すれば、バグはないし、当然のように運用できるだろうと思ってましたが、その認識が甘かったです。

Dynamic Renderingさせるべき画面・させないほうがいい画面を明確にする

AMPページもそうですが、Dynamic Renderingさせるべき画面・させないほうがいい画面を明確にして、ルーティングを設定するのが重要だなと思いました。

Dynamice Rendering する必要のない画面に対してやっても、ダウンロード時間が余計にかかるため、SEOのスコアを落としかねないです。

Dynamic Rendering の使用方法 でも書かれています。

ダイナミック レンダリングは、JavaScript で生成される変更頻度の高いインデックス登録可能な一般公開コンテンツや、サイト運営が重視するクローラではサポートされていない JavaScript の機能を使用するコンテンツに適しています。 すべてのサイトでダイナミック レンダリングを使用する必要はありません。 ダイナミック レンダリングはクローラ向けの回避策であることに注意してください。

おまけ:Dynamic Renderingについて思うこと

Dynamic Renderingという手法自体が過渡期の技術という印象を受けました。

個人的に思うDynamic Renderingに関する違和感として

  • ユーザーに見せる画面とクローラに見せる画面を異なるように扱う
  • Googleが技術的にできないことを、こちら側でカバーしなければいけない

というのがあるのかなと思います。

Chrome Dev Summit 2018 でFuture Enhancement として古い(Chrome41相当)レンダリングエンジンを解消すると言ってましたが、将来的には、Googlebotが最新のChromeになって、普通にJSを実行しているという未来が早く来て欲しいです。