zenparsing / es-cancel-token

Cancel Tokens for ECMAScript
44 stars 1 forks source link

Parameter list pollution #2

Open zenparsing opened 8 years ago

zenparsing commented 8 years ago

A cancellation token design where the cancel token is explicitly passed into the async operation via a parameter can lead to parameter list pollution. For C#, this is perhaps mitigated somewhat by the ability to overload function signatures based on static type information. In JS, we can't do the same kind of overloading.

It appears that an async function would need to "plan ahead" to support cancel tokens by reserving a parameter position for it (unless the cancel token is passed in an options bag). This seems unfortunate and goes against the "progressive enhancement" quality of cancel tokens in general.

benjamingr commented 8 years ago

This has been a big nuisance for me in C#

zenparsing commented 8 years ago

Writing down a sketch I made at the May 2016 meeting:

let task = new Task(async () => {
    await runSomethingAsync();
});

task.cancel();

async function runSomethingAsync() {
    Task.cancelToken.throwIfRequested();
}

This could perhaps be implemented on top of zones as a way of implicitly forwarding cancel tokens through an async task or pipeline.

benjamingr commented 8 years ago

Zones automatically forwarding cancel tokens is a little similar to F#'s cancellation but I'm not sure how it would work at all.

I don't have any alternative to cancellation tokens being passed explicitly, it's just really annoying to add an extra parameter to every single method - reminds me of Java checked exceptions where adding a cancellation capability to one bit of the code requires rewriting everything around it to take cancellation tokens.

wycats commented 8 years ago

I think this is more than a minor annoyance. It takes async functions, which were pretty close to the minimal conceptual overhead necessary to compose asynchronous code ("works just like a function, but you have to write await") and adds new first class values that have to be passed around to get the basic functionality you expect.

It's not true that you can simply decide not to worry about cancellation tokens until you need them, because once an intermediate async function fails to pass through the cancellation token, there's nothing that the caller of the outer function can do to fix it.

benjamingr commented 8 years ago

@wycats the thing is - while it's easy to get the synchronous/asynchronous analogy working with regular and async functions - there is nothing similar to cancellation with non-async control flow.

Unless you want to pass cancellation implicitly around (what I wrote about zones above, for instance) I don't really see what can be done other than to pass them explicitly or expose another context-aware keyword like this.Bikeshedding something like that:

Something like that.