27 comments

[ 4.8 ms ] story [ 69.1 ms ] thread
Anyone who uses CloudFlare for their web site can experiment with HTTP/2 Server Push. https://blog.cloudflare.com/announcing-support-for-http-2-se...

It's simply a matter of adding appropriate Link headers to responses and we can push stuff to clients. This makes it easy to run experiments without having to have a server that already supports push.

https://blog.cloudflare.com/http-2-server-push-with-multiple...

We rolled this out precisely so people can experiment and we are very interested to understand how people are using it and what performance improvements and problems they run into.

That image there seems strange. Did you run it by your PR and Legal team before posting it? You wouldn't want offend anyone.
The day CloudFlare forces me to run a blog post by the PR and Legal team for approval because of worry that I might offend someone will be a pitifully sad day. That would be ridiculous.

Which image are you talking about? Is it https://commons.wikimedia.org/wiki/File:They_started_our_car... which depicts people help restart a car by pushing it?

Are you offended by pictures of brown people?
No, I'm not. But, it might take on a different meaning to other people. Most blog posts are run by the PR and Legal team and big companies because they could be a liability to the corporate image.
What meaning could that image take on? I'm baffled.
I reduced Server Push to these rules for my HTML pages:

* Push only when I can guarantee that they don't have it in cache

* Push only assets included in the <head>

Which, for me, means I push a single CSS file for a page when I know that the visitor is a new visitor. After that, I never push again.

The implementation is essentially:

* For a HTML page request

* Check for the existence of a pushed=true cookie

* If cookie does not exist (new user/session) push the CSS needed

* And add a Set-Cookie for pushed=true with the same cache expiry time as the CSS resource

That's it.

Of course... if we could move away from sending the CSS for a whole site when people just request a page then I'd revisit this, but until then a single CSS file needs a single cookie and a single push.

Thanks. I haven't explored HTTP/2 Push yet and this example looks like a good starting point.
I am a bit surprised that client side caching seems to be an afterthought of http2. It was the first thing that jumped to my mind the day I first heard of http2 push.

And this caching can become a privacy issue. The client producing a list of what it has in cache can become a new form of cookie. The cache would have to be cleared at the end of each session to mitigate this risk.

> And this caching can become a privacy issue.

I am shocked — shocked! — that Google would develop a standard with built-in privacy attacks.

Caching is already a privacy issue with etags. HTTP2 doesn't make that situation worse. Besides the web has become so complex and offers so much for fingerprinting, that this battle has been lost long ago.

In order to have actual privacy you'd need to redesign the web from the ground up and consider privacy implications at every step. Even then you might come to the conclusion that it's just not possible to guarantee privacy.

> And this caching can become a privacy issue. The client producing a list of what it has in cache can become a new form of cookie. The cache would have to be cleared at the end of each session to mitigate this risk.

Is this really a significant privacy issue? Server can deduce which items (I use word "item" to refer to a resource cache entry) are missing from client cache just by monitoring follow-up requests by the client. Of course this way server can't know anything about the items client has but are not present on the page.

Maybe some cryptography can be used here, so that client can tell the server items it has, but in such a way that server can't know anything more than what it strictly needs.

Client could for example hash each item signature with salt and send this information to the server, salt + a list of hashed items. This would prevent direct lookups, but of course the server could still compute same value (hash of signature + salt) for all items in a database.

Maybe it's somehow possible to have even stronger privacy guarantees while still allowing server to compute which items have a high probability to be needed by the client based on some information client included in the request?

Another idea: client could send a bloom filter [1] of the related items it already has plus random hashing data to compute it. Server would use client provided hashing parameters to compute bloom filter bit index for each item and push it if the bit wasn't set. Of course this would sometimes cause server not to push needed data. Frequency when this happens would depend on the bloom filter size the client chooses versus number of potential items.

Because the client chooses bloom filter hashing parameters, this would mask the set of items the client possesses. This makes the data about already cached items almost useless for fingerprinting purposes, while still keeping some of the server push performance gain. Client can pick the tradeoff between performance and privacy with bloom filter size.

[1]: https://en.wikipedia.org/wiki/Bloom_filter

> Is this really a significant privacy issue? Server can deduce which items (I use word "item" to refer to a resource cache entry) are missing from client cache just by monitoring follow-up requests by the client.

Conceivably, a server could generate random null resources which are cached by the client and can then be used, as the GP indicates, to identify it — yet another supercookie.

I think the only way not to leak any information through caching is not to cache anything.

What do you think about my bloom filter idea?

> What do you think about my bloom filter idea?

It sounds interesting, but I suspect that you're right that caching leaks no matter what — I wonder if it's almost like compression in that sense (and we remember how compression impacts HTTPS!).

I have very fast mobile internet (4G, so I can download megabytes of traffic in one second) yet this traffic might cost a lot. And my pings to US server might easily be second or more. So basically I risk to download an entire website which is already in the my cache for each HTTP request.

Honestly I'm not sure that I like this server push. I think, the only appropriate use is: server push if client misses some cookie and set this cookie immediately.

We're working on a draft that will allow clients to signal what resources are already in their cache. This should allow us to reduce the bandwidth risk of unnecessary pushes.
(comment deleted)
I appreciate in-depth analysis, the numbers, and the actual case studies, and resulting recommendations. This is a very good resource that puts actual numbers to the issue.

In my opinion, this reveals that HTTP/2 Server Push is essentially one huge microoptimization, proper use of which requires even more effort from both the server (and the client):

[1] watch and aggressively respond to network utilization

[2] construct a dependency graph of resources (presumably by actually parsing the HTML on server-side, or beforehand out-of-band and store it some other place)

[3] have the client communicate the state of its cache! [ref-1]

[4] have custom, conditional logic for cookies

----

[ref-1] https://tools.ietf.org/html/draft-ietf-httpbis-cache-digest-...

Anyone have a good HTTP/2 web server that supports Push as well as WSGI?

NGINX doesn't support push it seems, and looking around for an HTTP/2 server that does support push, the only one I found was h2o (https://h2o.examp1e.net) but that doesn't support WSGI, for dynamic python apps.