2008-08-07 9 views
9

私は様々なファイルへのアクセスを制御するリソース処理メソッドを作成しています。ブラウザのキャッシュを利用できるようにしたいと考えています。私は304応答を送信するかどうかを確実に知るためにチェックする必要が決定的なHTTPヘッダをしている304未修正の応答を送信する方法を知る方法

  1. は、と私はそれらをチェックしないときのために何を探しています:私の質問は2倍です?

  2. さらに、最初にファイルを(Last-Modifiedのように)200回の応答として送信する必要があるヘッダーがありますか?

おそらく擬似コードが最も有用な答えでしょう。


キャッシュ制御ヘッダーはどうなりますか?さまざまな可能な値があなたがクライアントに送るもの(つまり最大年齢)に影響を及ぼしたり、変更された場合にのみ従うべきですか?

+1

私は304レスポンスを送信するときに追加したいのですが、ヘッダーのみを送信し、コンテンツは送信しないでください。 – GateKiller

答えて

8

私はそれをどのように実装しましたか?コードは1年以上、複数のブラウザで動作しているので、かなり信頼できると思います。これはRFC 2616に基づいており、さまざまなブラウザが何時に何を送信していたかを観察することによって行われます。ここでは、これを処理する私のサーバー・ロジックの抜粋です

 
server_etag = gen_etag_for_this_file(myfile) 
etag_from_browser = get_header("Etag") 

if etag_from_browser does not exist: 
    etag_from_browser = get_header("If-None-Match") 
if the browser has quoted the etag: 
    strip the quotes (e.g. "foo" --> foo) 

set server_etag into http header 

if etag_from_browser matches server_etag 
    send 304 return code to browser 

はここで擬似コードです。

 
/* the client should set either Etag or If-None-Match */ 
/* some clients quote the parm, strip quotes if so */ 
mketag(etag, &sb); 

etagin = apr_table_get(r->headers_in, "Etag"); 
if (etagin == NULL) 
    etagin = apr_table_get(r->headers_in, "If-None-Match"); 
if (etag != NULL && etag[0] == '"') { 
    int sl; 
    sl = strlen(etag); 
    memmove(etag, etag+1, sl+1); 
    etag[sl-2] = 0; 
    logit(2,"etag=:%s:",etag); 
} 
... 
apr_table_add(r->headers_out, "ETag", etag); 
... 
if (etagin != NULL && strcmp(etagin, etag) == 0) { 
    /* if the etag matches, we return a 304 */ 
    rc = HTTP_NOT_MODIFIED; 
} 

あなたがetag generationに関するいくつかの助けをしたいのであれば、別の質問を投稿してください。 HTH!キャッシュ制御に関する

+0

リクエストに 'ETag'ヘッダーを送るクライアントに本当に出くわしましたか?それはただ応答で使用されることになっています。また、仕様に従って常に引用する必要があります。 –

+0

マットでは、クライアントは以前に受信したエタグを返送するので、サーバーはHTTP_NOT_MODIFIEDが適切な応答であるかどうかを判断できます。私がこれをしたときの私の主な仕事は、FirefoxとSafariでした。指定されたリソースに対する以前の要求がクライアントにエタグを与えていた場合、両方とも格納されたetagを含みます。 http://en.wikipedia.org/wiki/HTTP_ETag –

+0

クライアントは 'If-None-Match' /' If-Match'ヘッダにetag(s)を含めます。私はUAが 'ETag:" ... "ヘッダーを要求に送信したことはありませんでしたか? –

3

クライアントが既にそのページをキャッシュに保持していると明示的に述べている場合は、304を送信する必要があります。これは条件付きGETと呼ばれ、if-modified-ヘッダーが要求に含まれている必要があります。

基本的に、このリクエストヘッダーには、クライアントがキャッシュされたコピーを持つと主張する日付が含まれています。この日以降に内容が変更されているかどうかを確認し、内容が変更されていない場合は304を送信してください。

RFCの関連セクションについては、http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html#sec14.25を参照してください。

1

あなたはアウトサービス提供時に適切な値に設定する以外に、キャッシュ制御を心配する必要はありません。これは基本的に、キャッシュをタイムアウトするまでに経過する最大時間を、ブラウザや他の下流のエンティティ(プロキシなど)に伝えています。

4

304変更されていない応答は、If-Modified-Since( "IMS")ヘッダーまたはIf-Not-Match( "INM")ヘッダーのいずれかを使用したGETまたはHEAD要求から発生します。

これらのヘッダーを受け取ったときに何をすべきかを決めるには、これらの条件付きヘッダーなしでGETリクエストを処理しているとします。その応答にETagヘッダーとLast-Modifiedヘッダーの値が何であるかを判断し、それらを使用して決定します。うまくいけば、これを決定することが完全な応答を構成するよりもコストがかからないようにシステムを構築しておけばと思います。INMとそのヘッダの値は、あなたがたETagに置かれる値と同じであるがある場合はIMSと日付の値がある場合は、そのヘッダーがあるに

、その後、304

で応答Last-Modifiedに配置するものより後で、304で応答します。

それ以外の場合は、要求にこれらのヘッダーが含まれていないかのように処理します。

質問のパート2への最小限の取り組みで、Webアプリケーションで簡単かつ正確に作成できる(Expires、ETag、およびLast-Modified)ヘッダーを把握します。提案読み物のために

:我々はまた、キャッシュされたが、確保処理している

http://www.w3.org/Protocols/rfc2616/rfc2616.html

http://www.mnot.net/cache_docs/

2

、リソース。 ETAgヘッダー(RFC 2616のセクション13.3で推奨する必要がある)を送信/生成する場合、クライアントは条件付き要求(通常はIf-None-Match-HTTP_IF_NONE_MATCHヘッダー)でそれを使用しなければならない(MUST)。 Last-Modifiedヘッダーを送信した場合(再度SHOULDする必要があります)、If-Modified-Since - HTTP_IF_MODIFIED_SINCEヘッダーを確認する必要があります。両方を送信する場合、クライアントは両方を送信すべきであるが、ETagを送信しなければならない(MUST)。また、バリデーションは、条件付きヘッダを送信するものと厳密に等価であるかどうかをチェックすることとして定義されています。また、(リソースの一部のみが要求される)レンジ指定された要求には、強力なバリデータ(ETagなど)のみが使用されます。実際に

、我々は保護されている資源はかなり静的であるため、1秒の遅延時間が許容される、我々は次のことをやっている:

  1. 、ユーザがアクセスすることを許可されているかどうかを確認します要求されたリソース

    そうでない場合は、それらをリダイレクトするか、適切に4xx応答を送信してください。私たちは、ハック試行のような見た目やセキュリティの終了を実行しようとする欲張りなリクエストに対する404応答を生成します。

  2. は、彼らが一致した場合、304変更されていない応答と出口ページ処理を送る

    私たちは厳格な平等のために(下記参照)送信したLast-Modifiedヘッダにヘッダので場合 - 変更 - 比較

  3. 要求されたリソース

    の修正時刻はRFC 2616で

  4. をHTTPの日付形式を見上げて使用してのLast-Modifiedヘッダを作成します。

私たちの目的のために余計に使われているので、ETagヘッダーを避けることにしました。私は、ETagとして日付のタイムスタンプを使うこともできると思います。真のETagシステムに移行すれば、リソースの計算されたハッシュを格納し、それらをETagとして使用するでしょう。

あなたのリソースがデータベースコンテンツから動的に生成されている場合、ETagsは必要に応じてより適切かもしれません。

関連する問題