304 Not Modified in HTTP Caching
A 304 Not Modified response tells a client that its cached representation is still valid, so the server does not resend the representation body. It is used with conditional requests and helps reduce bandwidth and latency.
A client can cache an HTTP response and later ask whether its cached copy is still current. It does this with a conditional request, commonly using `If-None-Match` with an entity tag (`ETag`) or `If-Modified-Since` with a timestamp.
If the server determines that the cached representation has not changed, it returns `304 Not Modified`. The response normally has no message body, and the client reuses its stored representation rather than downloading the resource again.
`ETag` validation is generally more precise than timestamp validation because an entity tag identifies a particular representation. A server can respond with `304` when the supplied validator still matches the current representation and the request semantics permit cache reuse.
A `304` is not the same as returning the resource with status `200`. A `200` response normally carries the representation, while `304` tells a cache to continue using its existing stored representation. A cache can then update relevant metadata according to HTTP caching rules.
For Java backend engineers, the important implementation point is that conditional requests are part of HTTP caching semantics, not simply an application-level optimization. Frameworks and web servers may generate validators and handle conditional requests automatically, but application code should avoid defeating caching with unnecessary changes to validators or cache headers.
Key points
- `304 Not Modified` validates an existing cached representation instead of resending it.
- Conditional requests commonly use `If-None-Match`/`ETag` or `If-Modified-Since`/`Last-Modified`.
- A 304 response normally does not contain the representation body.
- `304` differs from `200`: the client reuses its cached representation after successful validation.
- Cache validators and cache-control metadata determine whether cached content can be reused.
Interview questions
What problem does HTTP 304 Not Modified solve?
It allows a client or cache to validate a stored response without downloading the representation again. The client sends a conditional request containing a validator such as an `ETag`. If the representation is still valid for that cache entry, the server returns `304 Not Modified`. The client then uses its existing cached representation.
How do ETag and If-None-Match work together?
The server can associate an `ETag` with a representation. A client that has cached that representation can later send the value in `If-None-Match`. If the validator matches the current representation under the applicable HTTP comparison rules, the server can return `304 Not Modified` for a cacheable retrieval request. Otherwise, the server returns the current representation, commonly with `200 OK`.
What is the difference between a fresh cache hit and a 304 response?
With a fresh cache hit, the cache can use its stored response without asking the origin server for validation. With a 304 response, the cache has made a conditional request and the origin has confirmed that the stored representation remains valid. Both can avoid transferring the representation body from the origin. The 304 path still involves a validation request and response.
Why should a backend engineer understand cache-control directives when implementing 304 support?
Validators alone do not determine the complete caching behavior of a response. Cache-control directives can specify freshness requirements, whether storage is permitted, and when revalidation is necessary. A backend that emits inconsistent validators or cache directives can cause unnecessary requests or incorrect reuse of representations. Correct HTTP caching therefore requires considering validators together with the response's caching metadata.