How 'Last-Modified' and 'If-Modified-Since' headers work?

[Updated: Dec 18, 2017, Created: Jan 31, 2017]

Web HTTP 

'Last-Modified' response header is sent by the server to specify the last modified date of the requested resource. Example:

 Last-Modified: Tue, 20 Oct 2015 07:28:20 GMT 

'If-Modified-Since' request header is sent by the browser to specify the last modified date of the cached copy of the resource (saved in the browser). The value of this header is same as the value of the previously received 'Last-Modified' header. Example:

 If-Modified-Since: Tue, 20 Oct 2015 07:28:20 GMT 

The purpose of using above headers is to avoid unnecessary transferring of a resource if it has not been changed since the last access, hence saving bandwidth and improving performance.



How it works?

Followings are the general high level steps where the two headers are utilized:

  1. Server receives a normal HTTP request for a particular resource, say XYZ.

  2. The server side prepares the response. The server side logic wants the browser to cache XYZ locally. By default all browsers always cache the resources (specification) so no special header in the response is needed. Server may also explicitly send 'Cache-Control' to specify max age of the cache.

  3. Server includes the header 'Last-Modified' in response. It looks like this:
     Last-Modified: Tue, 20 Oct 2015 07:28:20 GMT 

    This header indicates the date time when XYZ was last modified on the server side.


  4. The server may also include following header in the response:
    Cache-Control: no-cache 

    This is an optional header. Without it, actions like accessing the resources through a link or by entering the link in the address bar uses the browser cache directly and does not send a request to the server to check the validity of the cache. Here validity means: whether the resource XYZ has changed since the first access. If we don't use this header then browser refresh/reload (usually F5 or Ctrl+r or the reload button in the browser) will still work and the validity of the cache will be checked. 'no-cache' simply forces to check the cache validity by submitting the request to the origin server before using the cached copy.


  5. Server sends the response with above headers, XYZ in the body and with status code 200. The browser displays the resource and at the same time it caches the resource along with header information.

  6. Later the same browser makes another request for the same resource XYZ. with following request header:
    If-Modified-Since: Tue, 20 Oct 2015 07:28:20 GMT

  7. On receiving the request for XYZ along with 'If-Modified-Since' header, the server side logic checks whether XYZ needs a new copy of the resource by comparing the current modified date of XYZ and the one which is received in the request header.
    • If request's If-modified-since is same as currently modified XYZ date then server sends back status code 304 (Not Modified) with the empty body. The browser uses cached copy of XYZ.
    • If request's If-modified-since value is less than the currently modified XYZ date then server sends back the new XYZ resource in the body along with status code 200. The 'Last-Modified' header with the new value is also included in the response. The browser uses the new XYZ and updates its cache with the new data.

See Also