Skip to content

Commit a519aa4

Browse files
committed
workaround a V8 AsyncDisposableStack bug
tc39/proposal-explicit-resource-management#256
1 parent 15b70e3 commit a519aa4

File tree

6 files changed

+46
-4
lines changed

6 files changed

+46
-4
lines changed

CHANGELOG.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -18,8 +18,9 @@
1818
- Extracted from [old `Math` extensions proposal](https://github.com/rwaldron/proposal-math-extensions), [February 2025 TC39 meeting](https://github.com/tc39/proposals/commit/0c24594aab19a50b86d0db7248cac5eb0ae35621)
1919
- Added arguments validation
2020
- Added new entries
21+
- Added a workaround of a V8 `AsyncDisposableStack` bug, [tc39/proposal-explicit-resource-management/256](https://github.com/tc39/proposal-explicit-resource-management/issues/256)
2122
- Compat data improvements:
22-
- [`DisposableStack`, `AsyncDisposableStack`, `SuppressedError` and `Iterator.prototype[@@dispose]`](https://github.com/tc39/proposal-explicit-resource-management) marked as [shipped from V8 ~ Chromium 134](https://issues.chromium.org/issues/42203506#comment24)
23+
- [`DisposableStack`, `SuppressedError` and `Iterator.prototype[@@dispose]`](https://github.com/tc39/proposal-explicit-resource-management) marked as [shipped from V8 ~ Chromium 134](https://issues.chromium.org/issues/42203506#comment24)
2324
- [`Error.isError`](https://github.com/tc39/proposal-is-error) added and marked as [shipped from V8 ~ Chromium 134](https://issues.chromium.org/issues/382104870#comment4)
2425
- [`Math.f16round` and `DataView.prototype.{ getFloat16, setFloat16 }`](https://github.com/tc39/proposal-float16array) marked as [shipped from V8 ~ Chromium 135](https://issues.chromium.org/issues/42203953#comment36)
2526
- [`Iterator` helpers proposal](https://github.com/tc39/proposal-iterator-helpers) features marked as [shipped from Safari 18.4](https://developer.apple.com/documentation/safari-release-notes/safari-18_4-release-notes#New-Features)

packages/core-js-compat/src/data.mjs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2287,8 +2287,9 @@ export const data = {
22872287
// TODO: Remove from `core-js@4`
22882288
'esnext.array-buffer.transfer-to-fixed-length': null,
22892289
'esnext.async-disposable-stack.constructor': {
2290-
// reverted in https://issues.chromium.org/issues/42203506#comment25
2291-
chrome: '134', // '133',
2290+
// added in 133, reverted in 134, https://issues.chromium.org/issues/42203506#comment25
2291+
// https://github.com/tc39/proposal-explicit-resource-management/issues/256, fixed in early 135
2292+
chrome: '136',
22922293
deno: false,
22932294
},
22942295
'esnext.async-iterator.constructor': {

packages/core-js/modules/esnext.async-disposable-stack.constructor.js

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,7 @@ var defineBuiltInAccessor = require('../internals/define-built-in-accessor');
1111
var wellKnownSymbol = require('../internals/well-known-symbol');
1212
var InternalStateModule = require('../internals/internal-state');
1313
var addDisposableResource = require('../internals/add-disposable-resource');
14+
var V8_VERSION = require('../internals/environment-v8-version');
1415

1516
var Promise = getBuiltIn('Promise');
1617
var SuppressedError = getBuiltIn('SuppressedError');
@@ -125,6 +126,10 @@ if (DESCRIPTORS) defineBuiltInAccessor(AsyncDisposableStackPrototype, 'disposed'
125126
defineBuiltIn(AsyncDisposableStackPrototype, ASYNC_DISPOSE, AsyncDisposableStackPrototype.disposeAsync, { name: 'disposeAsync' });
126127
defineBuiltIn(AsyncDisposableStackPrototype, TO_STRING_TAG, ASYNC_DISPOSABLE_STACK, { nonWritable: true });
127128

128-
$({ global: true, constructor: true }, {
129+
// https://github.com/tc39/proposal-explicit-resource-management/issues/256
130+
// can't be detected synchronously
131+
var SYNC_DISPOSE_RETURNING_PROMISE_RESOLUTION_BUG = V8_VERSION && V8_VERSION < 136;
132+
133+
$({ global: true, constructor: true, forced: SYNC_DISPOSE_RETURNING_PROMISE_RESOLUTION_BUG }, {
129134
AsyncDisposableStack: $AsyncDisposableStack
130135
});

tests/compat/tests.js

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1653,6 +1653,9 @@ GLOBAL.tests = {
16531653
return [].uniqueBy;
16541654
},
16551655
'esnext.async-disposable-stack.constructor': function () {
1656+
// https://github.com/tc39/proposal-explicit-resource-management/issues/256
1657+
// can't be detected synchronously
1658+
if (V8_VERSION && V8_VERSION < 136) return;
16561659
return typeof AsyncDisposableStack == 'function';
16571660
},
16581661
'esnext.async-iterator.constructor': function () {

tests/unit-global/esnext.async-disposable-stack.constructor.js

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -184,3 +184,19 @@ QUnit.test('AsyncDisposableStack#3', assert => {
184184
assert.same(error.suppressed.message, '3');
185185
});
186186
});
187+
188+
// https://github.com/tc39/proposal-explicit-resource-management/issues/256
189+
QUnit.test('AsyncDisposableStack#256', assert => {
190+
const resume = assert.async();
191+
assert.expect(1);
192+
let called = false;
193+
const stack = new AsyncDisposableStack();
194+
const neverResolves = new Promise(() => { /* empty */ });
195+
stack.use({ [Symbol.dispose]() { return neverResolves; } });
196+
stack.disposeAsync().then(() => {
197+
called = true;
198+
assert.required('It should be called');
199+
resume();
200+
});
201+
setTimeout(() => called || resume(), 3e3);
202+
});

tests/unit-pure/esnext.async-disposable-stack.constructor.js

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -184,3 +184,19 @@ QUnit.test('AsyncDisposableStack#3', assert => {
184184
assert.same(error.suppressed.message, '3');
185185
});
186186
});
187+
188+
// https://github.com/tc39/proposal-explicit-resource-management/issues/256
189+
QUnit.test('AsyncDisposableStack#256', assert => {
190+
const resume = assert.async();
191+
assert.expect(1);
192+
let called = false;
193+
const stack = new AsyncDisposableStack();
194+
const neverResolves = new Promise(() => { /* empty */ });
195+
stack.use({ [Symbol.dispose]() { return neverResolves; } });
196+
stack.disposeAsync().then(() => {
197+
called = true;
198+
assert.required('It should be called');
199+
resume();
200+
});
201+
setTimeout(() => called || resume(), 3e3);
202+
});

0 commit comments

Comments
 (0)