web-dev-qa-db-ja.com

304 / If-modified-since / HEADリクエストを防ぐためのヘッダー

コンテンツがキャッシュされた後、サーバーへのすべてのリクエストを完全に停止するには、どのヘッダーを送信する必要がありますか?

非常に待ち時間の長いサーバー(Sigh、VMWare)があるため、サーバーにHEADリクエストを送信する場合でも+ 40msかかります。

現在、これらは送受信されるヘッダーです。

最初のリクエスト

クライアントが送信します。

GET http://dugong:8080/Rvi24mYJkxFRGNzq73PPvgWGh1j/IMG_2071.jpg HTTP/1.1
Host: dugong:8080
User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:9.0) Gecko/20100101 Firefox/9.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip, deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Pragma: no-cache, no-cache, no-cache
Cache-Control: no-cache, no-cache, no-cache

サーバーが応答します。

HTTP/1.1 200 OK
Server: nginx/1.0.11
Date: Wed, 01 Feb 2012 14:51:51 GMT
Content-Type: text/plain
Vary: Accept-Encoding
Last-Modified: Tue, 31 Jan 2012 10:45:11 GMT
Content-Length: 14
Expires: Thu, 31 Jan 2013 14:51:51 GMT
Cache-Control: max-age=31536000

したがって、Cache-ControlおよびExpiresヘッダーを365日先に設定して送信します。残念ながら、2回目の更新では、If-Modified-Sinceヘッダーを使用してオブジェクトを再度要求します。

第二の要求

GET http://dugong:8080/Rvi24mYJkxFRGNzq73PPvgWGh1j/IMG_2071.jpg HTTP/1.1
Host: dugong:8080
User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:9.0) Gecko/20100101 Firefox/9.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip, deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
If-Modified-Since: Tue, 31 Jan 2012 10:45:11 GMT
Cache-Control: max-age=0

応答;

HTTP/1.1 304 Not Modified
Server: nginx/1.0.11
Date: Wed, 01 Feb 2012 14:58:00 GMT
Vary: Accept-Encoding
Expires: Thu, 31 Jan 2013 14:58:00 GMT
Cache-Control: max-age=31536000

残念ながら、愚かな古いプロキシソフトウェアのため、Keep-Aliveを使用したり、他のサーバー/プロキシをアプリケーションの前に置いたりすることはできません。また、サーバーのパフォーマンスを向上させたり、ネットワークの待ち時間を短縮することもできません。 301リクエストを取り除くために送信できるヘッダーを把握しようとしています。 ETagを使用してみましたが、違いはありません。If-modified-sinceヘッダーが送信されます。また、Last-Modifiedヘッダーを削除しようとしましたが、これにより、キャッシュなしで標準のGETリクエストが発生します(ログを確認し、サーバーはまだリクエストを受信して​​います)。

クライアントは、Firefox(大部分)、IE 7、8、および(一部)9、ChromeとSafariの混合ですが、この動作はテストされたすべてのブラウザーで発生するようです。

TL; DR;

ひどいネットワーク、クライアントに伝えるためにどのヘッダーを送るべきかこれまでにないサーバーにIf-modified-sinceリクエストを送信してキャッシュを検証し、Expiresヘッダーが会った?

私はおそらく明らかな何かを見逃していますが、私が試みることはすべて同じ結果をもたらすようです。

アプリケーションサーバーの前にNGINXサーバーが配置されているため、必要に応じてヘッダーを追加/削除できます。私たちのプロキシはキープアライブをサポートしておらず、彼らのネットワークのパフォーマンスを向上させる方法はありません。ひどいソフトウェア設計により、Webアプリは各ページの読み込みごとに+100のリソースを読み込みます(ええ、エンタープライズソフトウェアは吸い込みます)。オブジェクトあたり約40〜50ミリ秒の待機時間です。

31
Smudge

ユーザーエージェントがあなたに送信することを決定するヘッダーを実際に制御することはできません。問題のファイルがブラウザのキャッシュ内にあり、新しいバージョンをチェックする必要があると判断した場合は、そうなります。 この記事 によると、これらはブラウザがIf-Modified-Sinceを使用して要求する状況です。

  • キャッシュされたエントリには有効期限がなく、ブラウザセッションで初めてコンテンツにアクセスしています
  • キャッシュされたエントリには有効期限がありますが、有効期限が切れています
  • ユーザーが[更新]ボタンをクリックするか、F5キーを押してページの更新を要求しました

したがって、キャッシュをテストするためにページをリロードしている場合、ブラウザは画像を再要求するため機能しません。リンクをクリックしてから、最初のページに戻る別のリンクをクリックしてみてください。ユーザーが定期的にページをリロードしている場合、それを防ぐためにサイト/アプリの構造を再考する必要があるかもしれません。

役立つ可能性のあることの1つは、キャッシュ制御ヘッダーに「public」、つまりCache-Control: public, max-age=31536000を追加することです。私も 最近学んだ 1年以上の有効期限は無効です。有効期限は正確に1年であるため、おそらく数日または数週間短くすることで、ファイルがブラウザーのキャッシュに残り、破棄されないようにすることができます。

25
DisgruntledGoat

必要なのは、Cache-Control行のimmutableキーワードです。 phpの例:

header('Cache-Control: public, max-age=80000, immutable');

ソース: https://code.facebook.com/posts/557147474482256/this-browser-Tweak-saved-60-of-requests-to-facebook/

5
Zdenek

少しオフトピックですが、役立つかもしれません。キャッシュされたコンテンツのリクエストに対するもう1つの改善点は、sessionStorageにキャッシュすることです。これにより、サーバーにキャッシュの検証と304の受信を要求する必要がなくなります。 sessionStorageでCSSまたはDOMをキャッシュしていることがわかります。 ofc、古いIEブラウザーでは使用できません。

1
Pablo Estornut

ソースコードを調べて、別のページに移行するためのメタ更新がないことを確認します。代わりにsendRedirectなどを使用してください。私のセットアップでは、META REFRESHはIEでは304を生成しますが、Chromeでは生成しません。 sendRedirectは、どちらのブラウザーでもこれを生成しません。

<meta http-equiv="refresh" content="0;URL='nextpage'" />    

<% response.sendRedirect("nextpage") %>
0
Richard Sandoz