How to know when to send a 304 Not Modified response

前端 未结 5 1480
北荒
北荒 2020-12-30 07:35

I\'m writing a resource handling method where I control access to various files, and I\'d like to be able to make use of the browser\'s cache. My question is two-fold:

5条回答
  •  青春惊慌失措
    2020-12-30 08:11

    Here's how I implemented it. The code has been working for a bit more than a year and with multiple browsers, so I think it's pretty reliable. This is based on RFC 2616 and by observing what and when the various browsers were sending.

    Here's the pseudocode:

    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
    

    Here's a snippet of my server logic that handles this.

    /* 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;
    }   
    

    If you want some help with etag generation post another question and I'll dig out some code that does that as well. HTH!

提交回复
热议问题