Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement the Service Worker API #5957

Closed
lucidNTR opened this issue May 29, 2020 · 14 comments
Closed

Implement the Service Worker API #5957

lucidNTR opened this issue May 29, 2020 · 14 comments
Labels
cli related to cli/ dir suggestion suggestions for new features (yet to be agreed)

Comments

@lucidNTR
Copy link

lucidNTR commented May 29, 2020

To build a production ready cloudflare worker/ faas alternative with deno it would be very hard to use the current deno web worker implementation. (basically starting one webworker per handler and then dispatching messages from the main script)
i see some pain points implementing the registration / update workflows that browsers have in the main script, but i think finding a good solution there would REALLY pay of well:

  • custom caching strategies for fetch events
  • resourceful lifetime management of external 'processes' like browsers do with service workers, without having to manually start and stop the web workers
  • handling, rewriting, transforming, monitoring the requests that imported files make (huge number of possibilities here)

would love to help, but i dont know rust (yet) and not even at what point in the architecture this would need to be implemented

@bartlomieju bartlomieju added cli related to cli/ dir suggestion suggestions for new features (yet to be agreed) labels Jun 7, 2020
@ry
Copy link
Member

ry commented Nov 5, 2020

Service worker API is on the roadmap. It's just not clear if the fetch event should be available in the main worker - which would make it compatible with CF - or if we should somehow register a service worker.

We will be killing two birds with one stone when we introduce this API. We will be using the hyper web server to implement it. That means we'll have support for modern HTTP protocols #3995

@kitsonk kitsonk changed the title support service workers for fetch Implement the Service Worker API Nov 5, 2020
@kitsonk
Copy link
Contributor

kitsonk commented Nov 5, 2020

For clarity too, this issue is for tracking service workers as a whole, since we had several part issues about that we wanted to consolidate.

@kitsonk kitsonk added feat new feature (which has been agreed to/accepted) and removed suggestion suggestions for new features (yet to be agreed) labels Nov 5, 2020
@Schoude
Copy link

Schoude commented Dec 6, 2020

Will this also enable the usage of the Push API spec and a Deno implementation of libraries like web-push?
If there is currently already a method to implement push notifications in a similar way I would love to be enlightened on that topic. :)

@ghost
Copy link

ghost commented Feb 7, 2021

The service worker API could also allow to replace the current import map implementation by defining its logic in code rather than via a CLI argument, which is a requested feature (#3585).

Any application-specific, arbitrary file other than json could also have its own import logic defined in a service worker.

@qwtel
Copy link

qwtel commented Mar 15, 2021

For those interested in the Cloudflare Workers-alternative use case, I've implemented a module that "polyfills" the global fetch event by running a Deno http server in the background and converting between the different response/request reader/writer types: deno-fetch-event-adapter.

The implementation is pretty short and works surprisingly well, at least for my use case. Feedback is welcome!

@lucidNTR
Copy link
Author

lucidNTR commented Apr 24, 2021

there is now also the "official" deployctl that implements a mostly service worker compatible api https://github.com/denoland/deployctl however this should be really in core and part of official deno software architectures. :)

@lucidNTR
Copy link
Author

@qwtel I really like your worker-tools project and your approach of combining good documentation and modular tools. 1000 Kudos to you!

@kitsonk kitsonk added suggestion suggestions for new features (yet to be agreed) and removed feat new feature (which has been agreed to/accepted) labels Aug 5, 2021
@kitsonk
Copy link
Contributor

kitsonk commented Aug 5, 2021

This is complicated, as there are a lot of unanswered questions. Currently there isn't a compelling need for the core team to work on it. We would not be opposed to someone working on it, but we see it is a non-trivial piece of work and reaching out to a core team member before embarking on it would be strongly recommended.

@amithm7 amithm7 mentioned this issue Oct 18, 2021
17 tasks
@mimbrown
Copy link

mimbrown commented Nov 6, 2021

I would be highly interested in this feature. It's the best way I can think of to enable something like native imports of single-file .vue components for SSR. What's currently blocking the implementation? Is it API details or something else?

@bartlomieju
Copy link
Member

The core team discussed this feature during design meeting and we agreed that Service Worker API doesn't make sense in context of server side runtime.

Due to how the API works (service workers are installed after first startup, plus imperative API) it's not a valid solution to custom module loaders or rewriting fetch requests (ie. the rewrites wouldn't work the first time you try to run it, they would only work on subsequent process runs).

I'm going to close this issue for now. If you come up with different use cases we'll be happy to reevaluate, but for now it's not something we want to implement.

@rektide
Copy link

rektide commented Dec 6, 2021

I'm not sure what the team had in mind here but I think we're not speaking the same language. In my mind, CloudFlare Workers have proven a simple, enjoyable, web-platform-ish like model for handling incoming HTTP requests. Service Workers themselves had a specification which I dearly believe needs to be revived, Foreign Fetch, for Service Workers serving cross-origin traffic, demonstrating their use not just as an intercepting proxy but as a serving framework. The concerns listed sound like some technical nuance around life-cycles that are more applicable to Service Workers as intercepting proxies.

As I said in Discord, I simply cannot imagine doing HTTP endpoint development in anything that is not at least somewhat web platform compliant. CloudFlare did indeed drop a good bit of the web platform to make Workers but that is fine with me. My sense from @bartlomieju's reply is that the team is thinking in terms of Service Workers as a way to intercept requests in the serverside environment, not to establish a Service Worker like platform for serving incoming requests. I'm still interested in trying to do a lo-fi pass at this, but I'm a very very slow developer, I have no recommendations for implementation (a recommendation not to implement, actually), and whatever I produce will likely be experimental at best. So don't except much at all, but I hope I do get at least some prototype going. [Edit: oh this might be done/semi-done already: https://github.com/worker-tools/deno-fetch-event-adapter ]

I do believe this is an enormously compelling future for http serving. The good news is, I don't think I really need to do much Deno development per se- I was hoping maybe for some good tips/tricks/strategies that a more than naive user-land implementation might arrive at, but simply making a userland adaption is going to work fine.

I'm not sure why the somewhat weird lifecycle of Service Workers (which web developers don't seem to like either) would be such a source of hang-ups to the team. The act of installing service workers doesn't have to be a perfect match; let not the perfect be the enemy of the good.

@lucacasonato
Copy link
Member

lucacasonato commented Dec 6, 2021

@rektide I think you are mistaking Service Workers (which are outgoing request interceptors), which "edge workers" which are rather incoming request interceptors. This distinction is very important.

The core team is not in favor of implementing service workers in Deno (outgoing request interceptors) like they are implemented in the browser, because we do not see enough user value to justify the significant time and architecture complexity investment.

As for "edge workers" (incoming request interceptors - also known as HTTP servers): these are already very well supported in Deno, with a very web platform centric API. Deno.serveHttp provides the low level interface to build complex HTTP server, using the same primitives as used for fetch and Service Workers (Request and Response). We have reservations about addEventListener("fetch") as a first class HTTP server primitive as it can result in significant foot guns (due to event lifecycle and FetchEvent#waitUntil). We instead provide a high level serve function in std/http that is compatible with code written for addEventListener("fetch"), but with a simplified interface and less foot guns.

If you have code written for Cloudflare Workers that uses addEventListener("fetch"), using it in Deno should be a matter of updating 3-4 lines.

For a platform to run "edge workers" using Deno, see https://deno.com/deploy.

@frank-dspeed
Copy link

@lucacasonato i remember you from the wintercg i think your assumption is wrong i guess the service worker api and even the web worker api is a core feature the most best would be to implement it all under one umbrella web-context (simple url based isolated context) offers fetch and web workers as also service workers bound to the web-context.

this would enable real cross platform apps.

@lrowe
Copy link
Contributor

lrowe commented May 11, 2023

@bartlomieju Could you expand on why service workers would only work on subsequent process runs?

Due to how the API works (service workers are installed after first startup, plus imperative API) it's not a valid solution to custom module loaders or rewriting fetch requests (ie. the rewrites wouldn't work the first time you try to run it, they would only work on subsequent process runs).

On the browser you can activate a service worker for the current page using the Clients: claim() method. I imagine on the server one would await the service worker startup before a dynamic import of the main application.

Apart from custom module loaders they would also be useful for testing. On the browser I've been using Mock Service Worker.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
cli related to cli/ dir suggestion suggestions for new features (yet to be agreed)
Projects
None yet
Development

No branches or pull requests