fix(web): handle unhandled promise rejection in CancellableTask (#27553)

When a concurrent caller awaits `this.complete` inside `execute()` and
`cancel()` is called, the promise rejects with `undefined` outside of any
try/catch, causing "Uncaught (in promise) undefined" console spam during
rapid timeline scrolling.

- Wrap the `await this.complete` path in try/catch, returning 'CANCELED'
- Guard the `finally` block to only null `cancelToken` if it still belongs
  to this call, preventing a race condition with `cancel()` to `init()`

Change-Id: I65764dd664eb408433fc6e5fc2be4df56a6a6964
This commit is contained in:
Min Idzelis
2026-04-07 10:22:29 -04:00
committed by GitHub
parent 7f784952eb
commit de9ec95db1
2 changed files with 33 additions and 3 deletions
+9 -3
View File
@@ -64,8 +64,12 @@ export class CancellableTask {
if (this.cancellable && !cancellable) {
this.cancellable = cancellable;
}
await this.complete;
return 'WAITED';
try {
await this.complete;
return 'WAITED';
} catch {
return 'CANCELED';
}
}
this.cancellable = cancellable;
const cancelToken = (this.cancelToken = new AbortController());
@@ -86,7 +90,9 @@ export class CancellableTask {
this.#transitionToErrored(error);
return 'ERRORED';
} finally {
this.cancelToken = null;
if (this.cancelToken === cancelToken) {
this.cancelToken = null;
}
}
}