2012-04-20 12 views
4

私のWebアプリケーションでは、HTTPキャッシュヘッダーが24時間有効なすべてのイメージとETagsを提供しています。しかし、Javascriptのクライアントアプリケーションが画像が更新された可能性があると思われることがあります。そのような場合、私は実際にキャッシュを壊すことなく、ブラウザに画像キャッシュの再検証を強制したいと思います。ブラウザでイメージを再検証する必要があります(ただし必ずしも再フェッチする必要はありません)

たとえば、最新のLastUpdated日付を持つユーザーレコード(JSON内)を取得します。 LastUpdatedの日付が変更された可能性がある理由はいくつかあります。ユーザーがニックネームを変更したり、新しいボードに参加したり、画像を変更した可能性があります。画像が変わらない可能性は高いですが、確認する必要があります。

URLにキャッシュブレーカを追加してイメージを再リクエストできることは知っています。しかし、画像が変更されたかどうかにかかわらず、画像が強制的にリロードされ、ブラウザのキャッシュに2つのエントリが表示され、新しいURLですべての画像を更新するよう強制されます。私が本当に望むのは、ブラウザが同じURLを再度要求し、If-None-MatchヘッダーまたはIf-Modified-Sinceヘッダーをリクエストに送信して、イメージが変更されていない場合は304を取得することです。

Javascriptでこれを達成する方法はありますか?

+0

あなたは思考以上のものです。_might_変更されていなくてもイメージを再取得するのは本当にひどいでしょうか? – Oded

+0

私は、数十枚の画像をチェックする可能性があります。特に携帯端末でダウンロードするのが大変なことがあります。私が毎回リロードすることなくそれらを再検証することができれば、それらを頻繁にチェックする余裕があります。プラス私はちょうどそれが面白い質問だと思う。 :) –

+0

モバイルデバイスですか?なぜあなたはあなたの質問に言及していないのですか?それはむしろ関係しているようです。 – Oded

答えて

0

イメージはサーバー上にあり、キャッシュ内に存在するため、サーバーでは照会を実行する必要があります。 ページが読み込まれる前にチェックを行い、必要に応じてサーバーが特定のイメージをキャッシュに更新するようにします。 "HTML"部分は、常にすべてのimg-tagsなどが正しいと仮定しなければなりません。

サーバーキャッシュ内の単一のファイルを更新する最良の方法は、異なるビーストIMOです。

+0

残念ながら、それは私の状況では実際には機能しません。これはシングルページのJavascriptアプリケーションなので、ページがほとんど再読み込みされません。私はページの読み込みの間に起こる変更を拾う必要があります。 –

+0

jsから送信されたリクエストであっても、私の意見では、まだetagsとレスポンスコードについてのサーバー側です。キャッシュは、画像を扱うときは友人でも敵でもありません。 – Toft

0

これは実際に達成するのが簡単です。 Cache-Controlヘッダーをmax-age=0に設定して、画像のAJAX要求を行います。

サーバは、更新された画像(及びキャッシュヘッダの新しいセット)のいずれかで応答しなければならない

、又はpublic, max-age=123Cache-Controlヘッダを含む304 を有します。

Cache-Controlヘッダーを持つ304は、ブラウザにリソースに関連付けられた最新情報を更新するように指示するため、非常に重要です。

要求が完了したら、古い<img>要素をDOMから削除し、同じsrcを指す新しい要素を再度挿入します。

要求Cache-Controlヘッダーがブラウザにキャッシュを無視し、ネットワークに移動するように指示するためです。ブラウザが応答を返すと、実際にAJAXの結果で何もしないのに、キャッシュ–が更新されます。

古い要素を削除して新しい要素を挿入すると、ブラウザは最近更新された画像をそのキャッシュから直接取得します。

Chromeのネットワークインスペクタでは、AJAXリクエストと、<img>エレメントを再挿入して生成されたリクエストの2つのリクエストが表示されます。ただし、サーバーがCache-Controlヘッダーを正しく設定している場合、2番目の「要求」はブラウザのキャッシュによって実行され、実際には何も送信されません。

function updateImage(el) { 
    el = $(el); 
    var src = el.attr('src'); 

    $.ajax({ 
     url: src, 
     headers: { 
      'Cache-Control': 'max-age=0' 
     }, 
     success: function() { 
      var parent = el.parent(); 
      el.remove(); 
      // this assumes that the <img> has no siblings and no attributes/classes/etc... 
      parent.append('<img>').attr('src',src); 
     } 
    }); 
} 
+0

+1いいえ答え@ josh3736 – sachinjain024

+0

これはFirefoxやIEでは動作しません - Chromeのみ – Nenad

関連する問題