mirror of
https://github.com/nodejs/node.git
synced 2024-11-21 10:59:27 +00:00
03fb789fb9
This will improve the Web compatibility. Passing null as the signal should throw an error. WPT says "Passing null as the signal should throw". Please see https://github.com/web-platform-tests/wpt/blob/master/dom/events/AddEventListenerOptions-signal.any.js PR-URL: https://github.com/nodejs/node/pull/43153 Reviewed-By: Luigi Pinca <luigipinca@gmail.com> Reviewed-By: Antoine du Hamel <duhamelantoine1995@gmail.com> Reviewed-By: Tobias Nießen <tniessen@tnie.de> Reviewed-By: Colin Ihrig <cjihrig@gmail.com> Reviewed-By: James M Snell <jasnell@gmail.com>
169 lines
4.9 KiB
JavaScript
169 lines
4.9 KiB
JavaScript
'use strict';
|
|
|
|
require('../common');
|
|
|
|
const {
|
|
strictEqual,
|
|
throws,
|
|
} = require('assert');
|
|
|
|
// Manually ported from: wpt@dom/events/AddEventListenerOptions-signal.any.js
|
|
|
|
{
|
|
// Passing an AbortSignal to addEventListener does not prevent
|
|
// removeEventListener
|
|
let count = 0;
|
|
function handler() {
|
|
count++;
|
|
}
|
|
const et = new EventTarget();
|
|
const controller = new AbortController();
|
|
et.addEventListener('test', handler, { signal: controller.signal });
|
|
et.dispatchEvent(new Event('test'));
|
|
strictEqual(count, 1, 'Adding a signal still adds a listener');
|
|
et.dispatchEvent(new Event('test'));
|
|
strictEqual(count, 2, 'The listener was not added with the once flag');
|
|
controller.abort();
|
|
et.dispatchEvent(new Event('test'));
|
|
strictEqual(count, 2, 'Aborting on the controller removes the listener');
|
|
// See: https://github.com/nodejs/node/pull/37696 , adding an event listener
|
|
// should always return undefined.
|
|
strictEqual(
|
|
et.addEventListener('test', handler, { signal: controller.signal }),
|
|
undefined);
|
|
et.dispatchEvent(new Event('test'));
|
|
strictEqual(count, 2, 'Passing an aborted signal never adds the handler');
|
|
}
|
|
|
|
{
|
|
// Passing an AbortSignal to addEventListener works with the once flag
|
|
let count = 0;
|
|
function handler() {
|
|
count++;
|
|
}
|
|
const et = new EventTarget();
|
|
const controller = new AbortController();
|
|
et.addEventListener('test', handler, { signal: controller.signal });
|
|
et.removeEventListener('test', handler);
|
|
et.dispatchEvent(new Event('test'));
|
|
strictEqual(count, 0, 'The listener was still removed');
|
|
}
|
|
|
|
{
|
|
// Removing a once listener works with a passed signal
|
|
let count = 0;
|
|
function handler() {
|
|
count++;
|
|
}
|
|
const et = new EventTarget();
|
|
const controller = new AbortController();
|
|
const options = { signal: controller.signal, once: true };
|
|
et.addEventListener('test', handler, options);
|
|
controller.abort();
|
|
et.dispatchEvent(new Event('test'));
|
|
strictEqual(count, 0, 'The listener was still removed');
|
|
}
|
|
|
|
{
|
|
let count = 0;
|
|
function handler() {
|
|
count++;
|
|
}
|
|
const et = new EventTarget();
|
|
const controller = new AbortController();
|
|
const options = { signal: controller.signal, once: true };
|
|
et.addEventListener('test', handler, options);
|
|
et.removeEventListener('test', handler);
|
|
et.dispatchEvent(new Event('test'));
|
|
strictEqual(count, 0, 'The listener was still removed');
|
|
}
|
|
|
|
{
|
|
// Passing an AbortSignal to multiple listeners
|
|
let count = 0;
|
|
function handler() {
|
|
count++;
|
|
}
|
|
const et = new EventTarget();
|
|
const controller = new AbortController();
|
|
const options = { signal: controller.signal, once: true };
|
|
et.addEventListener('first', handler, options);
|
|
et.addEventListener('second', handler, options);
|
|
controller.abort();
|
|
et.dispatchEvent(new Event('first'));
|
|
et.dispatchEvent(new Event('second'));
|
|
strictEqual(count, 0, 'The listener was still removed');
|
|
}
|
|
|
|
{
|
|
// Passing an AbortSignal to addEventListener works with the capture flag
|
|
let count = 0;
|
|
function handler() {
|
|
count++;
|
|
}
|
|
const et = new EventTarget();
|
|
const controller = new AbortController();
|
|
const options = { signal: controller.signal, capture: true };
|
|
et.addEventListener('test', handler, options);
|
|
controller.abort();
|
|
et.dispatchEvent(new Event('test'));
|
|
strictEqual(count, 0, 'The listener was still removed');
|
|
}
|
|
|
|
{
|
|
// Aborting from a listener does not call future listeners
|
|
let count = 0;
|
|
function handler() {
|
|
count++;
|
|
}
|
|
const et = new EventTarget();
|
|
const controller = new AbortController();
|
|
const options = { signal: controller.signal };
|
|
et.addEventListener('test', () => {
|
|
controller.abort();
|
|
}, options);
|
|
et.addEventListener('test', handler, options);
|
|
et.dispatchEvent(new Event('test'));
|
|
strictEqual(count, 0, 'The listener was still removed');
|
|
}
|
|
|
|
{
|
|
// Adding then aborting a listener in another listener does not call it
|
|
let count = 0;
|
|
function handler() {
|
|
count++;
|
|
}
|
|
const et = new EventTarget();
|
|
const controller = new AbortController();
|
|
et.addEventListener('test', () => {
|
|
et.addEventListener('test', handler, { signal: controller.signal });
|
|
controller.abort();
|
|
}, { signal: controller.signal });
|
|
et.dispatchEvent(new Event('test'));
|
|
strictEqual(count, 0, 'The listener was still removed');
|
|
}
|
|
|
|
{
|
|
// Aborting from a nested listener should remove it
|
|
const et = new EventTarget();
|
|
const ac = new AbortController();
|
|
let count = 0;
|
|
et.addEventListener('foo', () => {
|
|
et.addEventListener('foo', () => {
|
|
count++;
|
|
if (count > 5) ac.abort();
|
|
et.dispatchEvent(new Event('foo'));
|
|
}, { signal: ac.signal });
|
|
et.dispatchEvent(new Event('foo'));
|
|
}, { once: true });
|
|
et.dispatchEvent(new Event('foo'));
|
|
}
|
|
{
|
|
const et = new EventTarget();
|
|
[1, 1n, {}, [], null, true, 'hi', Symbol(), () => {}].forEach((signal) => {
|
|
throws(() => et.addEventListener('foo', () => {}, { signal }), {
|
|
name: 'TypeError',
|
|
});
|
|
});
|
|
}
|