Skip to content

Commit 21864d2

Browse files
committed
lib: propagate aborted state to dependent signals before firing events
1 parent dcc2ed9 commit 21864d2

File tree

1 file changed

+24
-4
lines changed

1 file changed

+24
-4
lines changed

lib/internal/abort_controller.js

+24-4
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
// in https://github.com/mysticatea/abort-controller (MIT license)
55

66
const {
7+
ArrayPrototypePush,
78
ObjectAssign,
89
ObjectDefineProperties,
910
ObjectDefineProperty,
@@ -373,17 +374,36 @@ ObjectDefineProperty(AbortSignal.prototype, SymbolToStringTag, {
373374
defineEventHandler(AbortSignal.prototype, 'abort');
374375

375376
function abortSignal(signal, reason) {
377+
// 1. If signal is aborted, then return.
376378
if (signal[kAborted]) return;
377379
signal[kAborted] = true;
380+
// 2. Set signal's abort reason to reason if it is given;
381+
// otherwise to a new "AbortError" DOMException.
378382
signal[kReason] = reason;
383+
// 3. Let dependentSignalsToAbort be a new list.
384+
const dependentSignalsToAbort = [];
385+
// 4. For each dependentSignal of signal's dependent signals:
386+
signal[kDependantSignals]?.forEach((s) => {
387+
const dependentSignal = s.deref();
388+
// 1. If dependentSignal is not aborted, then:
389+
if (dependentSignal && !dependentSignal[kAborted]) {
390+
// 1. Set dependentSignal's abort reason to signal's abort reason.
391+
dependentSignal[kReason] = reason;
392+
// 2. Append dependentSignal to dependentSignalsToAbort.
393+
ArrayPrototypePush(dependentSignalsToAbort, dependentSignal);
394+
}
395+
});
396+
// 5. Run the abort steps for signal
379397
const event = new Event('abort', {
380398
[kTrustEvent]: true,
381399
});
382400
signal.dispatchEvent(event);
383-
signal[kDependantSignals]?.forEach((s) => {
384-
const signalRef = s.deref();
385-
if (signalRef) abortSignal(signalRef, reason);
386-
});
401+
// 6. For each dependentSignal of dependentSignalsToAbort,
402+
// run the abort steps for dependentSignal.
403+
for (let i = 0; i < dependentSignalsToAbort.length; i++) {
404+
const dependentSignal = dependentSignalsToAbort[i];
405+
if (dependentSignal) abortSignal(dependentSignal, reason);
406+
};
387407
}
388408

389409
class AbortController {

0 commit comments

Comments
 (0)