Bundles request returning Cache-Control response header as no-cahe when deployed on Azure Web APP - bundling-and-minification

We are using CDN for bundling in Azure Web APP. We have implemented approach given in below article.But it seems that for every bundle request to CDN, CDN is only forwarding this request to Azure Web-App,instead of delivering it from its own cache making it more time consuming
https://azure.microsoft.com/en-us/documentation/articles/cdn-websites-with-cdn/#integrate-aspnet-bundling-and-minification-with-azure-cdn
On debugging, found that Cache-Control value is set to no-Cache from azure-web-app. In Bundle Request URL we are using build number for Querystring value.
URL looks like - ~/bundles/lib?v=26948
Caveat is ,this works well when deployed on local.Somehow azure web app is sending wrong value for Cache-Control
Below is fiddler trace for bundle request on webapp.
GET /bundles/lib?v=26948 HTTP/1.1
Accept: text/html, application/xhtml+xml, image/jxr, */*
Host: mseventsdevtertiary.azurewebsites.net
Connection: Keep-Alive
Accept-Language: en-IN,en;q=0.5
Accept-Encoding: gzip, deflate, peerdist
X-P2P-PeerDist: Version=1.1
X-P2P-PeerDistEx: MinContentInformation=1.0, MaxContentInformation=2.0
HTTP/1.1 200 OK
Cache-Control: no-cache
Pragma: no-cache
Transfer-Encoding: chunked
Content-Type: text/javascript; charset=utf-8
Content-Encoding: gzip
Expires: -1
Vary: Accept-Encoding
Server: Microsoft-IIS/8.0
X-AspNet-Version: 4.0.30319
Access-Control-Allow-Origin: *
Date: Mon, 27 Jun 2016 09:02:28 GMT

Related

How does a browser force loading non-cached data in the request header?

I'm building a little application that loads fresh data from the OpenStreetMap project. For my app, it's very important to request the freshest data possible, so I don't want to be served cached data. Now, since OpenStreetMap has a lot of data requests to handle, they have some kind of caching on their side too. Simply sending a GET request isn't enough, because this will likely serve a pre-cached tile:
x-served-by: cache-ams21054-AMS
x-cache: HIT
x-cache-hits: 1
x-timer: S1652643221.620976,VS0,VE1
This led me to inspect the requests sent by Firefox on the official website. This is the header that is sent on a normal refresh:
Host: tile.openstreetmap.org
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:100.0) Gecko/20100101 Firefox/100.0
Accept: image/avif,image/webp,*/*
Accept-Language: en-GB,en;q=0.5
Accept-Encoding: gzip, deflate, br
Referer: https://www.openstreetmap.org/
Connection: keep-alive
Sec-Fetch-Dest: image
Sec-Fetch-Mode: no-cors
Sec-Fetch-Site: same-site
And this is the request sent on a force-refresh (ctrl+f5):
GET /14/8033/6198.png HTTP/2
Host: tile.openstreetmap.org
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:100.0) Gecko/20100101 Firefox/100.0
Accept: image/avif,image/webp,*/*
Accept-Language: en-GB,en;q=0.5
Accept-Encoding: gzip, deflate, br
Referer: https://www.openstreetmap.org/
Connection: keep-alive
Sec-Fetch-Dest: image
Sec-Fetch-Mode: no-cors
Sec-Fetch-Site: same-site
Pragma: no-cache
Cache-Control: no-cache
The only two additional header fields are Cache-Control: no-cache and Pragma: no-cache.
This led me to implement the same in my own application. I added the same header fields to my requests. However, this did not fix my problem and I was still getting served cached content (x-cache: HIT) in the response. After some googling and experimenting, I tried adding max-age=0 to Cache-Control and this did stop the servers from sending me cached content.
Here's my question: how come that my app needs the max-age=0 value, while a browser can get non-cached content reliably with just the no-cache values?
What other fields control that behavior, if all the fields I have are these:
User-Agent: MyApp-v1
Cache-Control: no-cache, max-age=0
Pragma: no-cache
For reference, here are the response headers for a standard refresh and a force-refresh:
Refresh:
HTTP/2 200 OK
server: Apache/2.4.41 (Ubuntu)
strict-transport-security: max-age=31536000; includeSubDomains; preload
expect-ct: max-age=0
etag: "afa1fdc623f5ea600b40ebd27c27f97a"
cache-control: max-age=33407, stale-while-revalidate=604800, stale-if-error=604800
expires: Thu, 12 May 2022 16:47:46 GMT
access-control-allow-origin: *
x-tilerender: odin.openstreetmap.org
content-type: image/png
accept-ranges: bytes
date: Sun, 15 May 2022 20:01:23 GMT
via: 1.1 varnish
age: 304223
x-served-by: cache-ams21051-AMS
x-cache: HIT
x-cache-hits: 1
x-timer: S1652644883.024001,VS0,VE1
content-length: 8290
X-Firefox-Spdy: h2
Forced refresh:
HTTP/2 200 OK
server: Apache/2.4.41 (Ubuntu)
strict-transport-security: max-age=31536000; includeSubDomains; preload
expect-ct: max-age=0
etag: "1e2555621fd6e9da0c35d0ab5440d2e5"
cache-control: max-age=8170, stale-while-revalidate=604800, stale-if-error=604800
expires: Sun, 15 May 2022 22:03:15 GMT
access-control-allow-origin: *
x-tilerender: nidhogg.openstreetmap.org
content-type: image/png
accept-ranges: bytes
date: Sun, 15 May 2022 19:47:05 GMT
via: 1.1 varnish
age: 0
x-served-by: cache-ams21083-AMS
x-cache: MISS
x-cache-hits: 0
x-timer: S1652644026.595670,VS0,VE97
content-length: 14499
X-Firefox-Spdy: h2
A server can emit data however it wishes, including from its own caches. The Cache-Control: no-cache mostly pertain to the browser-side caches.
For a browser to do a 'fresh' request, the most important this is mainly just not sending an ETag or If-Modified-Since header.
There's no standard header/instruction to tell a server to get a 'fresher' version of an item and not use its own internal caches. It's possible that for the API you're using they do have a mechanism to request uncached responses, but it's not standard.

set-cookie not working for IE11/10 after clearing cache

I'm currently experiencing a problem where after clearing cache/cookies IE10 & IE11 will not set the cookie again. The requests and responses look almost identical but after clearing the cache the cookie is never passed up even though it appears to be set correctly.
Heres how my login method flows:
1. VerifyLogin() -> Fail: Go To Login page
-> Pass: Call rest of the AJAX Methods // Enter Login Credentials and submit
2. Authentication() -> Fail: Prompt the user
-> Pass: set forms auth cookie and navigate back to original page, where it will call VerifyLogin() again
This once Authentication() passes they should then slip through VerifyLogin() with no problem and continue using the product. All the calls will now have the forms authentication cookie passed up.
In the instance im seeing it fail, the Authentication() call passes and gets a 200 OK (and has a set-cookie response header) however, the VerifyLogin() then fails because it hasn't passed up the cookie.
I have had a real hard time reproducing this but so far the reproduction steps i have are as follows. This is starting with no instance of IE running. I'm not 100% sure this is the exact same issue my customers are experiencing however it seems to reveal the same problem they are seeing.
Start IE
Browse to the index page of the site and get bounced to the login (verify failed)
Login with credentials, Authentication() returns a 200 OK and has a set-cookie response header. It then navigates you and calls VerifyLogin() which passes. The cookie is sent up in the request and its all successful. Subsequent calls all work.
Clear my cache and cookies
Browse to the index page of the site and get bounced to the login (verify failed as it should)
Login with credentials, Authentication() returns a 200 OK and has a set-cookie response header. It then navigates you and calls VerifyLogin() at this point fails. The cookie isn't passed up in the request, even though it was previously set in the response of Authentication(). If i close and reopen IE it will work again.
So, its like the second time round the set-cookie response is just not setting the cookie.
Firstly, Heres the relevent sections of my web.config and how i set my forms cookie.
web.config:
<authentication mode="Forms">
<forms enableCrossAppRedirects="true" name="Gator.Express.Auth" timeout="2880" />
</authentication>
setAuthenticationCookie method:
public void SetAuthenticationCookie(string userName, CookieData cookieData)
{
//In order to pickup the settings from config, we create a default cookie and use its values to create a
//new one.
var cookie = FormsAuthentication.GetAuthCookie(userName, true);
var ticket = FormsAuthentication.Decrypt(cookie.Value);
if (ticket == null)
throw new Exception("Error setting authorisation cookie. Decryption of default cookie failed.");
var jsonToken = JsonConvert.SerializeObject(cookieData);
var newTicket = new FormsAuthenticationTicket(ticket.Version, ticket.Name, ticket.IssueDate, ticket.Expiration,
ticket.IsPersistent, jsonToken, ticket.CookiePath);
var encTicket = FormsAuthentication.Encrypt(newTicket);
cookie.Value = encTicket;
HttpContext.Current.Response.Cookies.Add(cookie);
}
Now below here are the requests and responses in order.
Working Authentication Request
POST http://localhost:55733/api/Authentication HTTP/1.1
Accept: application/json, text/javascript, */*; q=0.01
Content-Type: application/x-www-form-urlencoded; charset=UTF-8
Referer: http://localhost:61496/Login.html
Accept-Language: en-GB
Accept-Encoding: gzip, deflate
User-Agent: Mozilla/5.0 (Windows NT 6.3; WOW64; Trident/7.0; rv:11.0) like Gecko
Connection: Keep-Alive
Content-Length: 35
DNT: 1
Host: localhost:55733
Pragma: no-cache
Username=michaelGator&Password=XXXX
# Working Authentication Response
HTTP/1.1 200 OK
Cache-Control: no-cache
Pragma: no-cache
Content-Type: application/json; charset=utf-8
Expires: -1
Server: Microsoft-IIS/8.0
X-AspNet-Version: 4.0.30319
Set-Cookie: Gator.Express.Auth=01020FCCF4658183D208FE0F4CC8BA1385D208000C6D00690063006800610065006C004700610074006F00720000012F00FF; path=/; HttpOnly
Set-Cookie: Gator.Express.Auth=0102054E17668183D208FE05CEEABA1385D208010C6D00690063006800610065006C004700610074006F007200377B002200530073006F004100630063006F0075006E0074004900640022003A002200300030003000300030003000300030002D0030003000300030002D0030003000300030002D0030003000300030002D0030003000300030003000300030003000300030003000300022007D00012F00FF; expires=Sun, 05-Jul-2015 08:28:39 GMT; path=/; HttpOnly
X-SourceFiles: =?UTF-8?B?QzpcV29ya2luZ1xnYXRvci5nYXRvcndlYnNlcnZpY2VcU291cmNlXEdhdG9yV2ViU2VydmljZVxhcGlcQXV0aGVudGljYXRpb24=?=
Access-Control-Allow-Origin: http://localhost:61496
Access-Control-Allow-Headers: Origin, X-Requested-With, Content-Type, Accept, Authorization, token
Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS
Access-Control-Allow-Credentials: true
Date: Fri, 03 Jul 2015 08:28:39 GMT
Content-Length: 14
"michaelGator"
# Working VerifyLogin Request
GET http://localhost:55733/api/VerifyLogin HTTP/1.1
Referer: http://localhost:61496/
Accept: */*
Accept-Language: en-GB
Accept-Encoding: gzip, deflate
User-Agent: Mozilla/5.0 (Windows NT 6.3; WOW64; Trident/7.0; rv:11.0) like Gecko
Connection: Keep-Alive
DNT: 1
Host: localhost:55733
Cookie: Gator.Express.Auth=0102054E17668183D208FE05CEEABA1385D208010C6D00690063006800610065006C004700610074006F007200377B002200530073006F004100630063006F0075006E0074004900640022003A002200300030003000300030003000300030002D0030003000300030002D0030003000300030002D0030003000300030002D0030003000300030003000300030003000300030003000300022007D00012F00FF
# Working VerifyLogin response
HTTP/1.1 200 OK
Cache-Control: no-cache
Pragma: no-cache
Expires: -1
Server: Microsoft-IIS/8.0
X-AspNet-Version: 4.0.30319
X-SourceFiles: =?UTF-8?B?QzpcV29ya2luZ1xnYXRvci5nYXRvcndlYnNlcnZpY2VcU291cmNlXEdhdG9yV2ViU2VydmljZVxhcGlcVmVyaWZ5TG9naW4=?=
Access-Control-Allow-Origin: http://localhost:61496
Access-Control-Allow-Headers: Origin, X-Requested-With, Content-Type, Accept, Authorization, token
Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS
Access-Control-Allow-Credentials: true
Date: Fri, 03 Jul 2015 08:28:39 GMT
Content-Length: 0
Below here is the non-working set of requests and responses. Note that the Authentication method returns a 200 OK and a set-cookie command but in the next verify login call, the coookie is gone.
# Authentication Request - Returns as it should but part of the non-working set of requests
POST http://localhost:55733/api/Authentication HTTP/1.1
Accept: application/json, text/javascript, */*; q=0.01
Content-Type: application/x-www-form-urlencoded; charset=UTF-8
Referer: http://localhost:61496/Login.html
Accept-Language: en-GB
Accept-Encoding: gzip, deflate
User-Agent: Mozilla/5.0 (Windows NT 6.3; WOW64; Trident/7.0; rv:11.0) like Gecko
Connection: Keep-Alive
Content-Length: 35
DNT: 1
Host: localhost:55733
Pragma: no-cache
Username=michaelGator&Password=XXXX
# Authentication Response- Returns as it should but part of the non-working set of requests
HTTP/1.1 200 OK
Cache-Control: no-cache
Pragma: no-cache
Content-Type: application/json; charset=utf-8
Expires: -1
Server: Microsoft-IIS/8.0
X-AspNet-Version: 4.0.30319
Set-Cookie: Gator.Express.Auth=01022054EB9B8183D208FE20D4BEF01385D208000C6D00690063006800610065006C004700610074006F00720000012F00FF; path=/; HttpOnly
Set-Cookie: Gator.Express.Auth=01028447109C8183D208FE84C7E3F01385D208010C6D00690063006800610065006C004700610074006F007200377B002200530073006F004100630063006F0075006E0074004900640022003A002200300030003000300030003000300030002D0030003000300030002D0030003000300030002D0030003000300030002D0030003000300030003000300030003000300030003000300022007D00012F00FF; expires=Sun, 05-Jul-2015 08:30:10 GMT; path=/; HttpOnly
X-SourceFiles: =?UTF-8?B?QzpcV29ya2luZ1xnYXRvci5nYXRvcndlYnNlcnZpY2VcU291cmNlXEdhdG9yV2ViU2VydmljZVxhcGlcQXV0aGVudGljYXRpb24=?=
Access-Control-Allow-Origin: http://localhost:61496
Access-Control-Allow-Headers: Origin, X-Requested-With, Content-Type, Accept, Authorization, token
Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS
Access-Control-Allow-Credentials: true
Date: Fri, 03 Jul 2015 08:30:10 GMT
Content-Length: 14
"michaelGator"
# Non-Working VerifyLogin Request - note, no cookie passes up
GET http://localhost:55733/api/VerifyLogin HTTP/1.1
Referer: http://localhost:61496/
Accept: */*
Accept-Language: en-GB
Accept-Encoding: gzip, deflate
User-Agent: Mozilla/5.0 (Windows NT 6.3; WOW64; Trident/7.0; rv:11.0) like Gecko
Connection: Keep-Alive
DNT: 1
Host: localhost:55733
# Non-Working VerifyLogin response - Fails as no Forms Cookie was passed up
HTTP/1.1 401 Unauthorized
Cache-Control: no-cache
Pragma: no-cache
Content-Type: application/json; charset=utf-8
Expires: -1
Server: Microsoft-IIS/8.0
X-AspNet-Version: 4.0.30319
X-SourceFiles: =?UTF-8?B?QzpcV29ya2luZ1xnYXRvci5nYXRvcndlYnNlcnZpY2VcU291cmNlXEdhdG9yV2ViU2VydmljZVxhcGlcVmVyaWZ5TG9naW4=?=
Access-Control-Allow-Origin: http://localhost:61496
Access-Control-Allow-Headers: Origin, X-Requested-With, Content-Type, Accept, Authorization, token
Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONS
Access-Control-Allow-Credentials: true
Date: Fri, 03 Jul 2015 08:30:10 GMT
Content-Length: 71
{"$id":"1","Message":"Authorization has been denied for this request."}
Any one have any ideas on this?
You seem to get getting two authentication cookies, which suggests that your implementation is clashing with something that ASP.Net is trying to automate for you.
There is a FormsAuthentication.SetAuthCookie that creates and sets the cookie, and I think this has already applied, so:
FormsAuthentication.SetAuthCookie gets the cookie (already set in the same response).
Your SetAuthenticationCookie fires.
This calls FormsAuthentication.GetAuthCookie and processes (embeds JSON serialised data into a new cookie) the original.
You call HttpContext.Current.Response.Cookies.Add to create a second cookie.
Both cookies are delivered in the header with the same name
You haven't cleared the original cookie, and .Net doesn't know how to process your processed cookie.
I think you have two options:
Split out your JSON data into a completely separate cookie with a different name.
Roll your own cookies from scratch and don't use any of .Net's FormsAuthentication methods.
I'd personally go with the former as the simplest and quickest to implement.
It might also be worth experimenting with cookie names - I'm not sure all browsers support periods in cookie names, but they are all case sensitive.
Finally something else worth checking - it's almost never worth setting a cookie's path in .Net, as IIS treats URL as case insensitive, but browsers all treat cookie names as case-sensitive.
Why is the response sending two SetCookie headers with the same cookie name? That seems… wrong and confusing.
Be careful not to give IE too much data in cookies. Your cookie values are pretty long! There is a cookie limit of ~4k. That’s total cookies for your domain. If it is longer than that, IE will not send it back.
HTH

Servlet response ETag Cache

I want to use ETag to cache the version of a request and return 304 not modifed response to the client so the client can use last cached page.
So my url is like this which returns a json response
"http://server/WEB_GWT/prmCall?prmName=PRM_SIS_PROG_REG_STATUS"
In my servlet handling this request, I am always putting ETag information to store its value to be the version of url param PRM_SIS_PROG_REG_STATUS.
So response header returning to client is
HTTP/1.1 200 OK
Date: Sat, 07 Dec 2013 16:07:49 GMT
Server: IBM_HTTP_Server
ETag: "5"
Last-Modified: Sat, 07 Dec 2013 16:07:49 GMT
Content-Length: 356
Keep-Alive: timeout=10, max=99
Connection: Keep-Alive
Content-Type: application/json
Content-Language: tr-TR
In my next request, I am expecting this request header to include "If-None-Match" header to return the version of the request but I cannot get this header param. Any idea why I cannot get my ETag back.
My next request header is
GET /OZU_GWT/prmCall?prmName=PRM_SIS_PROG_REG_STATUS HTTP/1.1
Host: 10.100.199.103
Connection: keep-alive
Cache-Control: max-age=0
If-Modified-Since: Thu, 01 Jan 1970 00:00:00 GMT
User-Agent: Mozilla/5.0 (Windows NT 6.2; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/31.0.1650.57 Safari/537.36
Accept: */*
Referer: http://10.100.199.103/OZU_GWT/
Accept-Encoding: gzip,deflate,sdch
Accept-Language: tr-TR,tr;q=0.8,en-US;q=0.6,en;q=0.4
Cookie: JSESSIONID=0000kvocMBmjoWPbpKt_VAsDUMv:-1
Inoder to cache your request you need to include "Cache-Control" directive and specify the way in which the response should be cached and for what period.
HTTP/1.1 200 OK
Date: Sat, 07 Dec 2013 16:07:49 GMT
Server: IBM_HTTP_Server
ETag: "5"
Cache-Control : public, max-age=86400
Content-Length: 356
Keep-Alive: timeout=10, max=99
Connection: Keep-Alive
Content-Type: application/json
Content-Language: tr-TR
Here the Cache-Control header says that the content can be stored by "public" caching servers and the duration after which it needs to revalidate the content is 86400 seconds. And so when you refresh the page again "If-None-Match" and "If-Modified-Since" conditional headers will kick in and use the cached data.
After some investigation,I found out SmartGWT framework requests are sent to server with bypassCache:true flag which was sending my xhr request without any cache header. I managed to fixed it by overriding following method in DataSource class.
#Override
protected Object transformRequest(DSRequest dsRequest) {
dsRequest.setBypassCache(false);

Why could a browser not caching a resource with Cache-Control HTTP headers?

I've read all the caching documentation for HTTP, and this are the headers for my file:
Edit: I am now using amazon S3 to see if it helps and still the same problem! Here go the request and the response> What am I missing? Even thought the response asks for the browser to cache the file, it doesn't! I've checked the Google Chrome cache and the file is not there.
Request URL:https://s3-sa-east-1.amazonaws.com/combo-combat-release/WebPlayer.unity3d
Request Method:GET
Status Code:200 OK
**Request Headers**
GET /combo-combat-release/WebPlayer.unity3d HTTP/1.1
Host: s3-sa-east-1.amazonaws.com
Connection: keep-alive
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.17 (KHTML, like Gecko) Chrome/24.0.1312.52 Safari/537.17
Accept: */*
Accept-Encoding: gzip,deflate,sdch
Accept-Language: es,en-US;q=0.8,en;q=0.6
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.3
**Response Headers**
HTTP/1.1 200 OK
x-amz-id-2: xu/RKgR4Xt6G3jQ1qkdO5rzd4TlngDYYERZ+bbGlalitJFMDjAgiLAoP4GXhmkeo
x-amz-request-id: 6A9389D16407D28D
Date: Wed, 16 Jan 2013 22:42:26 GMT
Cache-Control: max-age=2592000, public, must-revalidate
Last-Modified: Wed, 16 Jan 2013 22:29:55 GMT
ETag: "0f8d22257da9fcae61f21fd30b7a1fd4"
Accept-Ranges: bytes
Content-Type: application/octet-stream
Content-Length: 39222189
Server: AmazonS3
But the browser doesn't cache the file. Each time, the request is sent and all the data transferred from scratch (200 OK instead of 304). :(
File size is 37.4 MB
Any tip on what could be wrong?
Thanks,
Manuel
Try HTTP 1.1 instead of 1.0.
http://www.w3.org/Protocols/rfc2616/rfc2616-sec14.html states:
Note that HTTP/1.0 caches might not implement Cache-Control and
might only implement Pragma: no-cache

LiveHttpHeaders: which cache-control info is right

Using LiveHttpHeaders for Firefox 6 I was trying to see if my css, JS files being cached using Headers Module from Apache using htaccess. But I confuse, there are 2 values from the 'Cache-Control' data:
GET /proz/css/global.css HTTP/1.1
Host: localhost
User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:5.0) Gecko/20100101 Firefox/5.0
Accept: text/css,*/*;q=0.1
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
Connection: keep-alive
Referer: http://localhost/proz/
Cookie: PHPSESSID=el34de37pe3bnp4rdtbst1kd43
If-Modified-Since: Fri, 16 Sep 2011 21:15:32 GMT
If-None-Match: "400000000b06a-2999-4ad157e5b4583"
Cache-Control: max-age=0
HTTP/1.1 304 Not Modified
Date: Sat, 17 Sep 2011 03:04:50 GMT
Server: Apache/2.2.17 (Win32) PHP/5.2.8
Connection: Keep-Alive
Keep-Alive: timeout=5, max=99
Etag: "400000000b06a-2999-4ad157e5b4583"
Cache-Control: max-age=604800, public
Vary: Accept-Encoding
Which one is the true data, the first Cache-Control data (max-age=0) or the latter one.
I also would like to know how do I make sure that my JS, CSS, HTML files being compress after I use deflate module in htaccess. And yes, both headers and deflate modules are turn on.
There are two parts in this listing:
The part before the blank line is the request, sent by your browser
The part after the blank line is the response, sent by the server
The Cache-Control: max-age=0 sent by the client (your browser) tells the server (or any proxy in the middle) to send the most fresh version of the file. The browser usually sends this when you hit the refresh button.
The Cache-Control: max-age=604800, public sent by the server tells the client (your browser or a proxy) that the file is valid for 604800 seconds and can be cached for that time. (The browser won't even attemps to ask the server if a newer version exists, unless you hit refresh, as you did in this case.)
The server replied 304 Not Modified, this means that your browser already has the most recent version and it doesn't need to download it again (it did not downloaded it again).
The Vary: Accept-Encoding header indicate that the server taken some decisions based on the client's Accent-Encoding header. This may indicate that, if the server didn't replied 304 Not Modified, it would have compressed the file.
To verify this last point, clear your cache, and request the file again, and look at the content of the Content-Encoding header (must be gzip or deflate if the data is compressed).

Resources