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

Deprecate AbortSignal on resources that are not actions #48725

Open
benjamingr opened this issue Jul 10, 2023 · 9 comments
Open

Deprecate AbortSignal on resources that are not actions #48725

benjamingr opened this issue Jul 10, 2023 · 9 comments
Labels
abortcontroller Issues and PRs related to the AbortController API http Issues or PRs related to the http subsystem. stream Issues and PRs related to the stream subsystem.

Comments

@benjamingr
Copy link
Member

We currently have several APIs that support AbortSignals like:

  • http.Server
  • stream.Readable / stream.Writable
  • child_process methods returning a child (and not a promise)
  • addAbortSignal

Those APIs are resources and not actions and support Symbol.dispose Symbol.asyncDispose.

Since they are disposables, we should deprecate support for AbortSignal on APIs that are resources and not actions (while keeping AbortSignal on APIs that are actions (e.g. return promises)) and encourage the safe helper we added for addAbortListener on those updating our docs.

Basically instead of:

function foo() {
  const ac = new AbortController();
  const httpServer = /* */
  httpServer.listen(3000, { signal: ac.signal });
 
  return someAsyncAction().then(() => ac.abort()); // close the server
}

We should encourage:

async function foo() {
  using httpServer = /* */
  httpServer.listen(3000);
  await someAsyncAction()
}
@benjamingr benjamingr added http Issues or PRs related to the http subsystem. stream Issues and PRs related to the stream subsystem. abortcontroller Issues and PRs related to the AbortController API labels Jul 10, 2023
@benjamingr
Copy link
Member Author

Similarly for streams:

const ac = new AbortController()
const stream = fs.createReadStream(/* */);
addAbortSignal(stream, ac.signal);
await doStuff();
ac.abort(); // close stream

We should have:

using stream = fs.createReadStream(/* */);
await doStuff();

@benjamingr
Copy link
Member Author

cc @ronag @mcollina @atlowChemi @MoLow - I want to discuss this and:

  • Reach consensus on whether or not ideally we'd do this.
  • Reach consensus on how such a deprecation would look.

@MoLow
Copy link
Member

MoLow commented Jul 10, 2023

I will be +1 on doing this:

  • after v8 implements using
  • gradually, by adding a deprecation warning and then removing as sever major

@ronag
Copy link
Member

ronag commented Jul 10, 2023

I would be ok with deprecation without removal. I don't see much to gain by removing it (i.e. doc deprecate).

Other than that, I think it's an excellent idea.

@atlowChemi
Copy link
Member

I am +1 for this idea, but I am a little hesitant about completely removing signals support though, so I guess I would also say to doc deprecate.
I am not sure it will always be a simple swap between the 2 as in your examples 🙂

@Linkgoron
Copy link
Member

Linkgoron commented Jul 10, 2023

As someone who was part of adding AbortSignals into a few the Node APIs, I am ±0 on this.

I think that most of the use cases for AbortSignal are not really covered by using and dispose/asyncDispose. I get that there is some overlap, but I don't think that try/finally is what people should have used AbortSignal for (Although, it's quite simple now to create an AbortSignal that aborts on context end using using). AbortSignal, IMO, represents some kind of execution context, which is no longer relevant. It could have been the application lifetime (e.g. a signal when Node closes, or worker lifetime or whatever) or Request lifetime (a signal when a request is aborted, or ended or whatever) or timeout (which exists). Maybe I'm missing something, but using does not represent this kind of relationship. In one of the above examples, once you're using using you can't return the httpServer for example because that would dispose of the server, which is pretty weird (vs an abort signal that goes in an option).

Having said that, I think that the JavaScript/Node community has not really embraced AbortSignal (except mostly fetch). It's not that straightforward and easy, and we don't really have a lot of sources that provide meaningful signals. You can see it in the OP examples, where none of the sources are coming from the outside, they're coming from the same scope, which does not represent what I think signals should have been used for.

Therefore, I am ±0.

@mcollina
Copy link
Member

I'm -1 in removing them, at least for now.
The only thing this would cause is API churn, and I don't think keeping them would make the codebase any more complicated than needed.

@aduh95
Copy link
Contributor

aduh95 commented Jul 12, 2023

One thing worth mentioning is that AbortSignal.timeout is pretty neat, and I think using doesn't really let you do that. Not a problem for child_process methods which have a timeout option directly, but it could be useful when dealing with streams.

@jsumners
Copy link
Contributor

Sliding in from the linked Fastify issue...

I'm not sure if this is the right place to add this, but I'll say that the one time I really tried to add AbortSignal support to something (and I can't remember what it was at this point) I came to this conclusion:

https://twitter.com/jsumners79/status/1580168273210920962

Using AbortSignal for the first time today, and I have this feeling that it isn't quite enough. It seems to me that things that are recognizing the signal need a way to indicate they have completed their actions as a result of recognizing signal.abort === true

How that affects any decision here, I don't know. But I wouldn't be surprised if it is a contribution to:

I think that the JavaScript/Node community has not really embraced AbortSignal

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
abortcontroller Issues and PRs related to the AbortController API http Issues or PRs related to the http subsystem. stream Issues and PRs related to the stream subsystem.
Projects
None yet
Development

No branches or pull requests

8 participants