- From: Stuart P. Bentley <notifications@github.com>
- Date: Wed, 25 Jan 2017 16:21:55 -0800
- To: whatwg/fetch <fetch@noreply.github.com>
- Cc: Subscribed <subscribed@noreply.github.com>
- Message-ID: <whatwg/fetch/issues/448/275274933@github.com>
So, when I initially wrote this, it's not that I wasn't considering fetch on a separate thread from JavaScript - I was, if maybe a bit simplistically: ![Figure 1](https://cloud.githubusercontent.com/assets/572196/22314304/b01e2cb0-e315-11e6-97a4-4e8050360ea7.png) Here's an example of a "normal" fetch being aborted in my model, where the JS thread keeps a local state of the fetch, [as Anne described](https://github.com/whatwg/fetch/issues/448#issuecomment-270606993) (here represented by the pink "Sync-fetch-aborted zone", where the JS thread's local state reflects the fetch having been aborted): ![Figure 2](https://cloud.githubusercontent.com/assets/572196/22314398/19a70a1c-e316-11e6-8543-b6672c5bb76e.png) The idea here was that aborting a fetch would be synchronous, as nothing coming after the line calling `abort()` would ever encounter the fetch in any other state. Of course, I was aware that inter-thread communication isn't strictly lock-step, and it'd be possible for a fetch that had been *aborted* by JS to *complete normally* before that abort had been reflected (shown here with the darker-pink "Fetch aborting" section of the Network thread, representing all such overhead). The point was that, if a fetch had been aborted, *even if the fetch reached a successful conclusion after that point*, the successful conclusion would be *discarded* as no longer relevant, as JS had declared the fetch to be Aborted, and any such progress after that point would have been irrelevant: ![Figure 3](https://cloud.githubusercontent.com/assets/572196/22314556/0de9e9e6-e317-11e6-8083-2ce913492756.png) The aspect of all this that I hadn't fully been considering, is that the event for completion of a fetch is something that gets *scheduled*, not visited, *as* the JS thread runs - as I knew, a fetch that completes while the JS thread isn't idle will be scheduled to run once the current sync block cedes back to the event loop: ![Figure 4](https://cloud.githubusercontent.com/assets/572196/22314824/11dced36-e318-11e6-82e9-f1070e747cd9.png) What I'd been overlooking, though, was that this event can be *scheduled for execution* at the completion of a fetch that arrives *before* the JS thread aborts the fetch: ![Figure 5](https://cloud.githubusercontent.com/assets/572196/22314910/862448ec-e318-11e6-9588-5b5d8c50ed9e.png) Because, the fetch having already completed in this scenario, this event is already "in the pipe" at the point where we call `abort()`, we'd have scheduled an event that we declared would never come in the synchronous model. We could throw in some kind of overhead on the event to *suppress* it after the fact, or remove it from the queue somehow at the point where the red arrow above crosses the blue, but there's never been, as far as I know, any need for a facility in JS to have an event "un-happen" like this, and I don't want to be the asshead who obliviously introduced a cause for one. --- So, yeah: I'm coming around to the idea that `abort()` should be async, and mostly-harmless if aborted redundantly (with some kind of boolean returning whether the abort was effectively recognized or not, as suggested in [Jake's meeting summary](https://github.com/whatwg/fetch/issues/455#issuecomment-274869169). Furthermore, I think it's important that we note that this will be a pattern that will likely be *repeated* for *other* kinds of fetch control: if *aborting* a fetch that's already ended is an errorless nop, then *modifying its priority* should be treated as errorless as well, for the same reasons (ie. because it can happen as a routine part of normal operation). -- You are receiving this because you are subscribed to this thread. Reply to this email directly or view it on GitHub: https://github.com/whatwg/fetch/issues/448#issuecomment-275274933
Received on Thursday, 26 January 2017 00:22:58 UTC