CA MOBILE TECH BLOG

株式会社シーエー・モバイルのエンジニア・デザイナーの活動を綴るブログです

株式会社シーエー・モバイルの技術広報による、
技術に特化したブログです。
エンジニアとデザイナーの活動や思想を綴ってゆきます。

【ボルトチャレンジ】DDTサイト表示速度 爆速化のしかけ

f:id:cam-engineer:20180606172757p:plain

シーエー・モバイルでは、社内啓蒙活動の一環として、運営するサービスの表示速度を競うキャンペーン「ボルトチャレンジ」を実施しています。

開始から半年ほどたった5月のある日、突如参戦したあるサイトが、短期間で一気に爆速化し、周囲をざわつかせる事態に。

一体、何が起こったのか・・・。



ボルトチャレンジを始めたきっかけ

まずはこのキャンペーンの実施に至った背景を、推進担当者にヒアリングしました。

安藤: きっかけは、去年(2017年秋)のGoogle Growth Campですね。

モバイルページの表示速度の1秒の差が、利益やブランドへの信頼に大きく影響する事実はよく知られていますが、同じ1秒でも、特に3.5秒から2.5秒に改善した時、CV(コンバージョン)が27%もアップするという衝撃のデータがgoogleから提示されたのです。

f:id:cam-engineer:20180605215541p:plain
▲ ボルトチャレンジ推進担当・安藤

Google Growth Campに参加した役員が、その情報を役員会で共有したところ、”うちのサイトってどの程度なんだろうね?”という流れになって、TestMySitepagespeed insightsで社内のいくつかのサービスの表示速度を試しに調べてみたんです。

そうしたら、調べたサイトの半数以上が「要改善」という衝撃の結果で。

その結果を受けて始まったのが「ボルトチャレンジ」なんです。あの“最速の男”の名前を冠して、サイトの最速化を目指そうという呼びかけです。

ボルトチャレンジのルール

安藤:  当社の運営するサービスの中から、規模の大きい約20サイトをピックし、それぞれのトップページの完全表示にかかる秒数を、半月ごとに集計して、結果のランキングをポスターにして発表しています。

f:id:cam-engineer:20180608163630p:plain
▲ A0サイズのポスターを月に2回更新

速度レンジを表すランクは「ボルト級」「タイソン・ゲイ級」「ガトリン級」「ケンブリッジ飛鳥級」「高校生級」「中学生級」の6つ。

最速レンジの「ボルト級」は、先の「3.5秒から2.5秒に〜」の情報をふまえ、「3秒以内」という条件になっています。

一番最初の集計時は、ボルト級はおろか、タイソン・ゲイ級もわずか1サイト、全体的にボトムが厚い状態でしたので、担当者の意識を高める意図も込めて、もともと想定していなかった「中学生級」ランクを新たに加えたくらいです。

キャンペーンの効果もあってか、始めてしばらくは全体的に数値が向上しました。ボルト級を維持するサイトも出てきました。

しかしながら、継続的に数値改善に取り組むことは少なく、事業のKPIに直結する施策などに作業時間を費やす傾向が見受けられました。

先ほどのデータが示す通り、表示スピードが業績に直結するという意識を浸透させるために、何か刺激が必要だなと感じていました。

DDTが「ボルト級」にチャレンジ!

そんな折、DDT のWEBサイトが2018年5月にリニューアルオープン。ボルトチャレンジの対象サイトにピックアップされました。

しかし初回の計測で、表示速度は15.8秒、順位は21サイト中18位。ランクは中学生級です。

この結果に、奮い立ったDDTチームは、最速で“ボルト級”へ到達することを誓い、DDT最速化プロジェクトが始動したのです。

そして半月の奮闘の結果・・・。

f:id:cam-engineer:20180608163633p:plain
▲ わずか2週間で、DDTが一気にトップに!

なんと、表示速度は1.7秒!18位から一気にトップへと駆け上がり、見事に「CAM最速のサービス」の座を勝ち取りました!

一体、DDTチームはどうやって爆速化を実現したのか?功労者の2人のエンジニアにヒアリングをしました。

「最速化」のしかけ

(1)計測環境を用意する

f:id:cam-engineer:20180605215608p:plain
▲ フロントエンド担当の大谷(左)とサーバサイド担当の岡田(右)
大谷: まず最初に、計測条件を安藤さんに聞いて、WebPagetest というツールを使って同じ条件で計測できる環境を用意しました。

今回でいうと、具体的には以下のような条件でした。


WebPagetestを使用して定期的(毎日10時と20時の計2回)に計測。
計測設定は以下の通り。

  • ブラウザ: Chrome
  • 計測サーバ: ec2-ap-northeast-1:Chrome.Cable(東京)

  • 端末: Mobileエミュレート(iPhone6plus or Nexus5)

  • 計測回数: 1回

  • 順位付けに用いられる指標はFully Loadedの値。 (WebPagetest Documentation の 「Fully Loaded」項)


これでいつでもボルトチャレンジできる条件が整いました。

(2)計測結果を分析して対応する

f:id:cam-engineer:20180605215545p:plain

大谷:WebPagetestの計測結果から、修正すべきポイントを探しました。 こちらが対策前のWebPagetestの結果です。

f:id:cam-engineer:20180607120736p:plain

これにより、DDTの課題点が把握できました。その中でインパクトが大きいものを選び、一つ一つ対応しました。以下は、実際に見つけた問題点と対応になります。



1.画像最適化

1.a 画像容量

10KBとか2MB等で表現される画像のファイルサイズのこと。運用者(外部)が入稿する画像容量が大きすぎる。入稿レギュレーションは存在するが、実際に運用が始まるとレギュレーション通りに入稿されることは稀だった。大きいものだと2MBの画像があった。

対応:

入稿時にサーバーサイドで加工。圧縮処理には「jpegtran」と「pngquant」を用いた。



1.b 画像サイズ

100x200(px)等で表現される画像の大きさのこと。運用者(外部)が入稿する画像容量サイズが大きすぎる。入稿レギュレーションは存在するが、実際に運用が始まるとレギュレーション通りに入稿されることは稀だった。大きいものだと横幅1920pxの画像があった。

対応:

入稿時にサーバーサイドで加工。リサイズ処理には「ImageMagick」を用いた。



1.c 画像形式

jpgが最適な形式であるにも関わらず、png形式になっている画像が入稿されていた。

対応:

とりあえず、クリティカルな箇所のみ手動で形式を変更した。運用フロー調整が必要なので、今回の改善施策ではシステマチックに対応しないことに。



1.d 画像読み込み振り分け

ブラウザのScreen要件(幅、高さ、ピクセル密度等)に応じて読み込む画像を振り分ける。 例えば、画面サイズの小さいモバイル端末では小さいサイズの画像を読み込む等。 (キーワード: picture要素やsrcset属性)

対応:

運用コストが大きくなる & 次回ボルトチャレンジ計測日までに実装が終わらないので、今回の改善施策では対応しない。



2. テキストファイルの圧縮

圧縮されていないリソースが見つかった。

対応:

APIレスポンス(JSON)とテキスト静的ファイル(HTML/JS/CSS)に対して、AWS CloudFrontにてgzip配信の設定を行った。



3. Resource Hints API

「次に必要となるリソースを事前にブラウザに伝える」ことが出来るAPI群。

主に以下の4項目がある。

  • dns-prefetch: 事前にDNS問い合わせを事前に行い、名前解決コストを下げる。
  • preconnect: TCP接続を事前に確立しておく。
  • prefetch: 事前にリソースを取得してキャッシュに貯める。
  • prerender: 事前にページ取得&描画を行う。

対応:

DDTに適した「dns-prefetch」と「preconnect」を設定した。



4. HTTP/2対応

通信コストの削減や並列コネクション数が増える。…が、良し悪しについては賛否両論あります!!

対応:

AWS CloudFrontにて設定した。 計測したら改善が見込めたのでDDTでは導入することに。



5. クリティカルレンダリングパス最適化

「ページ読み込み」から「画面描画完了(ユーザ操作可能になるタイミング)」に至るまでにブラウザが行う工程を最適化すること。

対応:

ソースコード内のひとつひとつの処理を細かく見直した。 不適切なタイミングでAPIコールをしていたので修正した。 それ以外は特に問題なかった。



6. 遅延読み込み/実行

適切なタイミングで画像読み込みや描画等を行う技術。 (キーワード: LazyLoad / ATF / Intersection Observer)

対応:

LazyLoad機能を実装し、

  • 画面内に要素が現れたタイミングで画像の読み込み&レンダリングを行う。
  • 外部SNS関連スクリプトを読み込み&実行する。
  • ServiceWorkerの登録処理を遅延実行する。

ように修正。



(7. キャッシュ関連)

ボルトチャレンジでは計測回数が1回なので順位付けには影響しませんが、キャッシュに関わる改善も行いました。

対応:

ServiceWorkerを介してCacheStorageに静的ファイル群をキャッシュ。

これらの対応をしたら、どのサイトも、うんと早くなるのは間違いないと思います。



成功のポイント

f:id:cam-engineer:20180605215604p:plain

岡田: 何よりも、計測できる環境を作って「改善を見える化」すること、これが全てと言っていいほど、大事です。計測環境がないのに、改善だけ進めてもダメです。

また、今回は計測方法の条件をボルトチャレンジに合わせましたが、「読み込みが終わるまで」とか「ボタンを押されるまで」とか「動画が再生されるまで」とか、色々あるので、サービスの性質や内容に適した計測方法をおさえておくべきですね。

そして、関係者を巻き込むこと。サーバ(サイドエンジニア)とフロント(エンドエンジニア)と、プロデューサと、みんなで一緒に目標を追うことが大事です。

結果

岡田: 先ほどと同じWebPagetestの結果が、対策後、このように変化しました。

f:id:cam-engineer:20180607120636p:plain

無駄が省かれ、数値が格段に向上しました。

今回は、ボルトチャレンジ用の計測でしたが、こういった数値はサイトの健康状態のチェックに使えるため、日頃から見ておききたいですね。

数値をずっとグラフ形式で追える speedcurveもおすすめのツールです。

f:id:cam-engineer:20180605215536p:plain
▲ 爆速化大成功でチームの雰囲気も◎


メンテナンスやアップデートは、地味な作業に見えますが、実はサービスレベルを維持するために重要な作業です。

シーエー・モバイルでは、毎月、半日営業の プレミアムフライデー を実施していますが、この半日を、普段後回しになりがちなサイトのメンテナンスや整理整頓、情報のアップデートに充てることを推奨する「アップデート・フライデー」の呼びかけも同時に行っています。

もし同様のキャンペーンを実施する場合、「これをやろう!」のメッセージとともに「この時間でやろう!」もセットで提示すると、浸透しやすいかもしれませんね。

(技術広報/桑田)