GithubHelp home page GithubHelp logo

HTTP/2 server push support about fetch HOT 22 OPEN

whatwg avatar whatwg commented on July 16, 2024 4
HTTP/2 server push support

from fetch.

Comments (22)

annevk avatar annevk commented on July 16, 2024 1

@DanielBaulig I think we'd want to give full control, yes. The main tricky point is how to layer H/2 push.

from fetch.

rektide avatar rektide commented on July 16, 2024 1

Please help. This deserves to be worked upon. This issue speaks to one of the best, most interesting, most enabling new capabilities of http 2, and leaving it chronically un-usable is so sad.

from fetch.

annevk avatar annevk commented on July 16, 2024

You'll have to be a bit more concrete with what kind of API you're expecting for this.

from fetch.

martinthomson avatar martinthomson commented on July 16, 2024

Sure. I was thinking that an event handler on Request, maybe called onpush might work. You get pushes before and during response delivery. Each push turns up in the form of a Request, and you need to actually fetch that to get the actual response.

from fetch.

annevk avatar annevk commented on July 16, 2024

So what are the use cases for this? I wonder if this should be part of the fetch registry proposal https://www.w3.org/Bugs/Public/show_bug.cgi?id=23878#c16 and some kind of associated network observer API.

from fetch.

martinthomson avatar martinthomson commented on July 16, 2024

Not understanding the full scope of what your registry proposal is, it seems plausible, but I'd have to trust your judgment in this case.

The use cases I can think of, without getting into too much detail:

  • HTTP APIs that use server push
  • replacing long-polling (webpush uses server push)

from fetch.

brendanlong avatar brendanlong commented on July 16, 2024

This bug report has a lot of information about use-cases. Copying it here for convenience: https://www.w3.org/Bugs/Public/show_bug.cgi?id=28083

http://lists.w3.org/Archives/Public/public-whatwg-archive/2015Feb/0030.html

The use-case I have in mind is MPEG DASH or HLS live streaming:

A server updates the manifest (MPD or m3u8) and pushes it. The client browser will cache it, but JavaScript applications don’t know that it exists. For newly generated segments, we need the MPD to use them anyway, but for adaptive streaming we need to know when the request started and when it finished so we can estimate bandwidth. If a server is pushing MPD updates, we want a way to tell it to stop (RST_STREAM on a pushed stream to end the transfer, or RST_STREAM on the original client request to prevent future pushes for that request).

The obvious question to ask is “why not just poll the server”? The answer its that live streaming latency depends (among other things) on how quickly you poll. Unless you can perfectly predict when the server will have an update available, you need to either poll slightly late (introducing latency) or poll significantly more often than the server creates updates. Using server push is equivalent to to polling infinitely fast, while simultaneously reducing load on the server by making fewer requests (win/win).

I imagine that this would be useful for JavaScript implementations of HTTP/2 REST API’s, especially API’s using something like ATOM or RSS. Firefox has an API for addons to detect pushed streams, so presumably they think there is some use for this (but they didn’t propose this as a public API, so maybe not?).

What's needed:

  • Event when PUSH_PROMISE is detected, containing a new Response.
  • Ability to signal to a UA that a stream should left in the "half closed" state (to allow server pushes).

I'm not sure fetch is the best API for this, since there's currently no way to cancel fetches or use a partial response before it finishes, but it seems to be the only API anyone wants to make changes to.

from fetch.

igrigorik avatar igrigorik commented on July 16, 2024

@annevk +1 on registry overlap. I think this is another instance of "observer use case": #65. Specifically, in this instance the receipt of the PUSH_PROMISE would register the request in the registry... which would trigger appropriate observer callbacks, etc.

from fetch.

rektide avatar rektide commented on July 16, 2024

I have an example of this usage pattern in a server-to-server case- I stream IRC messages from one microservice to another.
https://github.com/rektide/tele-pump/blob/master/tele-muc-pump.js#L17

There's also an earlier implemented of this capability that I created by recording all push_promises i'd sent, then attaching an X-Associated-Content header to any replies made to the client with this list. Then I polyfilled XMLHttpRequest to read these headers, and postMessage to to the window to inform any listeners. By periodically issuing requests to the server, the client gets notice of what has been pushed.
https://github.com/rektide/pushchannel

This latter technique was something inspired by Jetty, who also has X-associated-content: in that implementation, the header informs the server to push that resource to the client; I took it one step further. This should be a readily available capability for the browser, without polyfilling XHR. I would love for the first project, tele-muc-pump, to be usable from the client (without having to devise an out of band signalling like the pushchannel XHR monkeypatching, or using a Server-Sent-Events or websockets).

from fetch.

jakearchibald avatar jakearchibald commented on July 16, 2024

I don't think this API fits on request objects, as far as I can tell PUSH_PROMISE frames aren't linked to another request.

I don't think this API should be on pages because the lifecycle doesn't match up. As far as I know one H2 connection can cover many pages. Are H2 connections even per origin?

from fetch.

martinthomson avatar martinthomson commented on July 16, 2024

@jakearchibald, actually PUSH_PROMISE is tied to a request and that binding is sometimes (often maybe) important.

That an h2 connection can cover multiple origins makes this less easy, I agree. In some cases you will be receiving a cross-grained request-response without a pre-flight. We have to ask whether we even want to surface the existence of something like that.

from fetch.

rektide avatar rektide commented on July 16, 2024

I appreciate @martinthomson pointing out that PUSH_PROMISE is affiliated with a specific request (and that's super important as in the case with protocol specs like his WebPush Protocol). That makes fetch a sensible place to expose push events.

As a developer, it would also be convenient to have one high level place where I could perform observations on pushed data. If Service Workers also offered a way to see PUSH_PROMISES for their domain, for example, that would be useful and handy. It would both prevent developers from having to explicitly set up each fetch to listen, and secondarily, it would be answer to how to handle PUSH_PROMISES sent to non-AJAX/non-fetch-based PUSH_PROMISES.

from fetch.

martinthomson avatar martinthomson commented on July 16, 2024

Trying to record the result of in-person discussion...

Two options seem to be most attractive:

  1. A fetch-group-local service that provides events when requests are made. See #65.
  2. Attaching events to Response that surface when a server push is made.

In both these cases, a Request would be generated for each server push. These could then be passed to fetch() to attach to the existing request and acquire the answer. This would likely need to build on Response.clone() to deal with the fact that multiple clients could consume the answer.

The main shortcoming of the second option is that you would delay the receipt of pushes until the response header fields are populated. h2 permits PUSH_PROMISE to be sent prior to the generation of the response header block, but fetch() depends on the header block to construct the Response.

from fetch.

igrigorik avatar igrigorik commented on July 16, 2024

In favor of (1): some RUM vendors wrap all the JS APIs + attach onload / onerror's to all new elements that initiate fetches via MutationObserver to capture "start of request". Exposing an event would eliminate that overhead.. which would be nice.

from fetch.

annevk avatar annevk commented on July 16, 2024

There's also some discussion on the semantics of server push and @mnot might write a draft on that. Fetch-wise the semantics would roughly be:

  1. All push promises end up in the HTTP cache (effectively). This way they can be used for navigation. (There's many ways to put something in the HTTP cache already so that wasn't really a valid concern.)
  2. Noncacheable push promises disappear together with the fetch group.

from fetch.

DanielBaulig avatar DanielBaulig commented on July 16, 2024

Is there any consideration of being able to cancel/abort an ongoing push from a future API through a reset stream? I don't think the proposed solutions in this thread allow for this.

from fetch.

rektide avatar rektide commented on July 16, 2024

@slightlyoff providing a more tangible discussion point here:
https://gist.github.com/slightlyoff/18dc42ae00768c23fbc4c5097400adfb#gistcomment-2227534

[ed: jake archibald has also reiterated some ideas begat in fetch observer in second comment, and it's worth reviewing!! see: comment#2]

from fetch.

jakearchibald avatar jakearchibald commented on July 16, 2024

A lot of PUSH stuff was removed from Chrome https://groups.google.com/a/chromium.org/g/blink-dev/c/K3rYLvmQUBY/m/vOWBKZGoAQAJ

from fetch.

mitar avatar mitar commented on July 16, 2024

Nothing has been removed from Chrome (yet).

from fetch.

jakearchibald avatar jakearchibald commented on July 16, 2024

I'm pretty sure we never enabled PUSH over HTTP/3

from fetch.

mitar avatar mitar commented on July 16, 2024

So? Your comment was that that PUSH was removed from Chrome, referencing a mailing list post where nothing to that effect was posted, but only that there is an intend and that they are conducting an experiment. So, what exactly has been already removed?

from fetch.

rektide avatar rektide commented on July 16, 2024

This should still be followed up on, even if it's winter-cg that can use it & the browsers remain unmoved about letting dev's ever explore what the world could do with push.

from fetch.

Related Issues (20)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.