HTTP/2 Server Push Reference

HTTP/2 PUSH_PROMISE frame mechanics with deprecation notes and 103 Early Hints

Reference for HTTP/2 Server Push: the PUSH_PROMISE frame, RST_STREAM cancellation, the SETTINGS_ENABLE_PUSH flag, why browsers removed it, and 103 Early Hints with rel=preload as the modern replacement.

Is HTTP/2 Server Push still usable?

No, not in practice. Chrome removed support in version 106 (2022) and other engines followed, citing poor real-world performance and frequent over-pushing of already-cached resources. HTTP/3 never specified push at all. Treat it as deprecated and use 103 Early Hints instead.

HTTP/2 Server Push let a server send resources to a client before they were requested, using a PUSH_PROMISE frame. In practice it under-delivered and is now removed from browsers. This reference documents how it worked and what to use instead.

How it works

A pushed resource follows this lifecycle on an HTTP/2 connection:

  1. The server sends a PUSH_PROMISE frame on the client’s request stream, reserving a new server-initiated (even-numbered) stream ID and carrying the promised request header block.
  2. The server then sends HEADERS + DATA for that pushed response on the reserved stream.
  3. The client may accept it, or send RST_STREAM with CANCEL / REFUSED_STREAM to decline — useful when the resource is already in cache.
  4. A client can disable push for the whole connection with SETTINGS_ENABLE_PUSH = 0.

The fatal flaw: servers routinely pushed resources the browser had already cached, wasting bandwidth, and push interacted badly with prioritization. Chrome removed it in v106 (2022), and HTTP/3 never specified push at all.

The modern replacement — 103 Early Hints

Instead of pushing bytes, the server sends an informational 103 Early Hints response carrying Link headers with rel=preload while it prepares the real response:

HTTP/2 103 Early Hints
Link: </app.css>; rel=preload; as=style
Link: </app.js>; rel=preload; as=script

HTTP/2 200 OK
Content-Type: text/html
...

The browser starts fetching the hinted resources immediately but stays in control of caching, so it never re-downloads something it already has. This is the recommended path on HTTP/2 and HTTP/3.