ブログ

記事詳細画面が新しい内容に変わらない場合のヒント

このエントリーをはてなブックマークに追加

Aplikoで現在提供しているテーマ「サイトリーダー」では記事詳細画面をWebViewで実装しており、「アプリ用記事一覧JSON」テンプレートで出力されたJSONに記載のURLにアクセスしてHTMLを表示しています。

最近社内でAplikoアドオンの一部を利用してアプリの開発を行ったのですが、なぜかHTMLが新しい内容に変わらない現象に遭遇しました。また、個人的に研究を行うために利用した私のサーバーでも同様の現象が発生しました。キャッシュが利用されていることは容易に想像がついたのですが、開発中には発生しなかった問題なので調査を実施しました。

原因はリクエストヘッダーにあり

会社のサーバーと私のサーバーで共通していたのは、Last-Modifiedヘッダーを送出していたことでした。このこと自体には何ら問題ないのですが、Last-Modifiedヘッダー付きで受信したURLについては同じURLにアクセスすると常にキャッシュが利用され、サーバーに対して全くリクエストが行われないことが分かりました。詳細はRFC 2616, Section 13を読むと分かりそうですが、有効期限が明示されていないことによる可能性があります。(参考:HTTP キャッシュ | Web | Google Developers

対策の一つとして、Last-Modifiedヘッダーと共にCache-Controlヘッダーを送出するようにすることが挙げられます。開発中であれば頻繁にHTMLが書き換えられるでしょうから、キャッシュをオフにすると作業が捗るのではないかと考えます。

Apacheの場合は設定にもよりますが、.htaccessでCache-Controlヘッダーの設定が可能です。

<Files ~ "\.html$">
    Header set Cache-Control no-cache
</Files>

nginxではserverディレクティブの中で以下のように記述します。

location ~* \.html {
    expires -1;
}

アプリ公開後の運用時はキャッシュを有効にすることで、同じリソースにアクセスするユーザーのパフォーマンス向上が期待できます。Apacheで取得したレスポンスを再使用できる最大時間を1時間とする例を示します。

<Files ~ "\.html$">
    Header set Cache-Control "max-age=3600"
</Files>

なお、Cache-Controlヘッダーを設定する前に読み込んだリソースは設定後もキャッシュが利用され続けるため、素早く新しい内容を反映するためにはアプリを一旦削除して再インストールする必要があります。この手法は開発環境でしか使えないため、アプリ公開前に本番環境のキャッシュに関係する設定を確認しておくことをお勧めいたします。