Skip to content

Commit eea8f04

Browse files
committed
test_runner: align mock timeout api
Expose Timeout.close() and Timeout[Symbol.dispose]() from MockTimers. This keeps fake setTimeout() handles aligned with the public Timeout API so disposal-based patterns do not throw. Add targeted coverage for Timeout.close() and Timeout[Symbol.dispose]().
1 parent 58a8e1d commit eea8f04

File tree

2 files changed

+39
-0
lines changed

2 files changed

+39
-0
lines changed

lib/internal/test_runner/mock/mock_timers.js

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,12 +69,15 @@ const TIMERS_DEFAULT_INTERVAL = {
6969
};
7070

7171
class Timeout {
72+
#clear;
73+
7274
constructor(opts) {
7375
this.id = opts.id;
7476
this.callback = opts.callback;
7577
this.runAt = opts.runAt;
7678
this.interval = opts.interval;
7779
this.args = opts.args;
80+
this.#clear = opts.clear;
7881
}
7982

8083
hasRef() {
@@ -92,6 +95,15 @@ class Timeout {
9295
refresh() {
9396
return this;
9497
}
98+
99+
close() {
100+
this.#clear(this);
101+
return this;
102+
}
103+
104+
[SymbolDispose]() {
105+
this.#clear(this);
106+
}
95107
}
96108

97109
class MockTimers {
@@ -310,6 +322,7 @@ class MockTimers {
310322
runAt: this.#now + delay,
311323
interval: isInterval ? delay : undefined,
312324
args,
325+
clear: this.#clearTimeout,
313326
};
314327

315328
const timer = new Timeout(opts);

test/parallel/test-runner-mock-timers.js

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -266,6 +266,32 @@ describe('Mock Timers Test Suite', () => {
266266
assert.deepStrictEqual(fn.mock.calls[0].arguments, args);
267267
});
268268

269+
it('should expose Timeout.prototype[Symbol.dispose]', (t) => {
270+
t.mock.timers.enable({ apis: ['setTimeout'] });
271+
const fn = t.mock.fn();
272+
const timeout = globalThis.setTimeout(fn, 2000);
273+
274+
assert.strictEqual(typeof timeout[Symbol.dispose], 'function');
275+
276+
timeout[Symbol.dispose]();
277+
t.mock.timers.tick(2000);
278+
279+
assert.strictEqual(fn.mock.callCount(), 0);
280+
});
281+
282+
it('should expose Timeout.prototype.close()', (t) => {
283+
t.mock.timers.enable({ apis: ['setTimeout'] });
284+
const fn = t.mock.fn();
285+
const timeout = globalThis.setTimeout(fn, 2000);
286+
287+
assert.strictEqual(typeof timeout.close, 'function');
288+
assert.strictEqual(timeout.close(), timeout);
289+
290+
t.mock.timers.tick(2000);
291+
292+
assert.strictEqual(fn.mock.callCount(), 0);
293+
});
294+
269295
it('should keep setTimeout working if timers are disabled', (t, done) => {
270296
const now = Date.now();
271297
const timeout = 2;

0 commit comments

Comments
 (0)