diff --git a/.eslintrc.js b/.eslintrc.js index 8464945125b678..99f7196ffc8158 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -287,6 +287,11 @@ module.exports = { BigInt: 'readable', BigInt64Array: 'readable', BigUint64Array: 'readable', + Event: 'readable', + EventTarget: 'readable', + MessageChannel: 'readable', + MessageEvent: 'readable', + MessagePort: 'readable', TextEncoder: 'readable', TextDecoder: 'readable', queueMicrotask: 'readable', diff --git a/doc/api/events.md b/doc/api/events.md index 5de7e06840ef5e..11e13e6d852ea6 100644 --- a/doc/api/events.md +++ b/doc/api/events.md @@ -1069,9 +1069,15 @@ const ac = new AbortController(); process.nextTick(() => ac.abort()); ``` + ## `EventTarget` and `Event` API > Stability: 1 - Experimental @@ -1082,7 +1088,7 @@ Neither the `EventTarget` nor `Event` classes are available for end user code to create. ```js -const target = getEventTargetSomehow(); +const target = new EventTarget(); target.addEventListener('foo', (event) => { console.log('foo event happened!'); @@ -1168,7 +1174,7 @@ const handler4 = { } }; -const target = getEventTargetSomehow(); +const target = new EventTarget(); target.addEventListener('foo', handler1); target.addEventListener('foo', handler2); @@ -1189,6 +1195,10 @@ The `EventTarget` does not implement any special default handling for ### Class: `Event` The `Event` object is an adaptation of the [`Event` Web API][]. Instances @@ -1341,6 +1351,11 @@ The event type identifier. ### Class: `EventTarget` #### `eventTarget.addEventListener(type, listener[, options])` @@ -1374,7 +1389,7 @@ a `listener`. Any individual `listener` may be added once with ```js function handler(event) {} -const target = getEventTargetSomehow(); +const target = new EventTarget(); target.addEventListener('foo', handler, { capture: true }); // first target.addEventListener('foo', handler, { capture: false }); // second diff --git a/doc/api/globals.md b/doc/api/globals.md index 8b279a21715e6b..4191c1e017afc7 100644 --- a/doc/api/globals.md +++ b/doc/api/globals.md @@ -169,6 +169,30 @@ added: v0.1.100 Used to print to stdout and stderr. See the [`console`][] section. +## `Event` + + + + +> Stability: 1 - Experimental + +A browser-compatible implementation of the `Event` class. See +[`EventTarget` and `Event` API][] for more details. + +## `EventTarget` + + + + +> Stability: 1 - Experimental + +A browser-compatible implementation of the `EventTarget` class. See +[`EventTarget` and `Event` API][] for more details. + ## `exports` This variable may appear to be global but is not. See [`exports`][]. @@ -187,6 +211,33 @@ within the browser `var something` will define a new global variable. In Node.js this is different. The top-level scope is not the global scope; `var something` inside a Node.js module will be local to that module. +## `MessageChannel` + + + + +The `MessageChannel` class. See [`MessageChannel`][] for more details. + +## `MessageEvent` + + + + +The `MessageEvent` class. See [`MessageEvent`][] for more details. + +## `MessagePort` + + + + +The `MessagePort` class. See [`MessagePort`][] for more details. + ## `module` This variable may appear to be global but is not. See [`module`][]. @@ -322,6 +373,10 @@ The object that acts as the namespace for all W3C [Mozilla Developer Network][webassembly-mdn] for usage and compatibility. [`AbortController`]: https://developer.mozilla.org/en-US/docs/Web/API/AbortController +[`EventTarget` and `Event` API]: events.md#event-target-and-event-api +[`MessageChannel`]: worker_threads.md#worker_threads_class_messagechannel +[`MessageEvent`]: https://developer.mozilla.org/en-US/docs/Web/API/MessageEvent/MessageEvent +[`MessagePort`]: worker_threads.md#worker_threads_class_messageport [`TextDecoder`]: util.md#util_class_util_textdecoder [`TextEncoder`]: util.md#util_class_util_textencoder [`URLSearchParams`]: url.md#url_class_urlsearchparams diff --git a/lib/internal/bootstrap/node.js b/lib/internal/bootstrap/node.js index 551367583e55a8..bb4689d0d342e8 100644 --- a/lib/internal/bootstrap/node.js +++ b/lib/internal/bootstrap/node.js @@ -140,6 +140,21 @@ if (!config.noBrowserGlobals) { exposeInterface(global, 'AbortController', AbortController); exposeInterface(global, 'AbortSignal', AbortSignal); + const { + EventTarget, + Event, + } = require('internal/event_target'); + exposeInterface(global, 'EventTarget', EventTarget); + exposeInterface(global, 'Event', Event); + const { + MessageChannel, + MessagePort, + MessageEvent, + } = require('internal/worker/io'); + exposeInterface(global, 'MessageChannel', MessageChannel); + exposeInterface(global, 'MessagePort', MessagePort); + exposeInterface(global, 'MessageEvent', MessageEvent); + // https://html.spec.whatwg.org/multipage/webappapis.html#windoworworkerglobalscope const timers = require('timers'); defineOperation(global, 'clearInterval', timers.clearInterval); diff --git a/src/node_external_reference.h b/src/node_external_reference.h index f332103c3f5a27..0544979dd9a6f1 100644 --- a/src/node_external_reference.h +++ b/src/node_external_reference.h @@ -64,7 +64,8 @@ class ExternalReferenceRegistry { V(string_decoder) \ V(trace_events) \ V(timers) \ - V(types) + V(types) \ + V(worker) #if NODE_HAVE_I18N_SUPPORT #define EXTERNAL_REFERENCE_BINDING_LIST_I18N(V) V(icu) diff --git a/src/node_worker.cc b/src/node_worker.cc index 4159a6efeda780..cdaeefb7897794 100644 --- a/src/node_worker.cc +++ b/src/node_worker.cc @@ -2,6 +2,7 @@ #include "debug_utils-inl.h" #include "memory_tracker-inl.h" #include "node_errors.h" +#include "node_external_reference.h" #include "node_buffer.h" #include "node_options-inl.h" #include "node_perf.h" @@ -860,9 +861,20 @@ void InitWorker(Local target, NODE_DEFINE_CONSTANT(target, kTotalResourceLimitCount); } -} // anonymous namespace +void RegisterExternalReferences(ExternalReferenceRegistry* registry) { + registry->Register(GetEnvMessagePort); + registry->Register(Worker::New); + registry->Register(Worker::StartThread); + registry->Register(Worker::StopThread); + registry->Register(Worker::Ref); + registry->Register(Worker::Unref); + registry->Register(Worker::GetResourceLimits); + registry->Register(Worker::TakeHeapSnapshot); +} +} // anonymous namespace } // namespace worker } // namespace node NODE_MODULE_CONTEXT_AWARE_INTERNAL(worker, node::worker::InitWorker) +NODE_MODULE_EXTERNAL_REFERENCE(worker, node::worker::RegisterExternalReferences) diff --git a/test/parallel/test-bootstrap-modules.js b/test/parallel/test-bootstrap-modules.js index ee9a62fbfa6455..23e2f534a73183 100644 --- a/test/parallel/test-bootstrap-modules.js +++ b/test/parallel/test-bootstrap-modules.js @@ -31,6 +31,7 @@ const expectedModules = new Set([ 'Internal Binding types', 'Internal Binding url', 'Internal Binding util', + 'Internal Binding worker', 'NativeModule buffer', 'NativeModule events', 'NativeModule fs', @@ -76,6 +77,17 @@ const expectedModules = new Set([ 'NativeModule internal/process/warning', 'NativeModule internal/querystring', 'NativeModule internal/source_map/source_map_cache', + 'NativeModule internal/streams/buffer_list', + 'NativeModule internal/streams/destroy', + 'NativeModule internal/streams/duplex', + 'NativeModule internal/streams/end-of-stream', + 'NativeModule internal/streams/legacy', + 'NativeModule internal/streams/passthrough', + 'NativeModule internal/streams/pipeline', + 'NativeModule internal/streams/readable', + 'NativeModule internal/streams/state', + 'NativeModule internal/streams/transform', + 'NativeModule internal/streams/writable', 'NativeModule internal/timers', 'NativeModule internal/url', 'NativeModule internal/util', @@ -84,8 +96,10 @@ const expectedModules = new Set([ 'NativeModule internal/util/types', 'NativeModule internal/validators', 'NativeModule internal/vm/module', + 'NativeModule internal/worker/io', 'NativeModule internal/worker/js_transferable', 'NativeModule path', + 'NativeModule stream', 'NativeModule timers', 'NativeModule url', 'NativeModule util', diff --git a/test/parallel/test-event-on-async-iterator.js b/test/parallel/test-event-on-async-iterator.js index d9817ff15e0701..276a6f62d37e33 100644 --- a/test/parallel/test-event-on-async-iterator.js +++ b/test/parallel/test-event-on-async-iterator.js @@ -5,9 +5,7 @@ const common = require('../common'); const assert = require('assert'); const { on, EventEmitter } = require('events'); const { - EventTarget, - NodeEventTarget, - Event + NodeEventTarget } = require('internal/event_target'); async function basic() { diff --git a/test/parallel/test-events-once.js b/test/parallel/test-events-once.js index be3ed794e19eb9..ea1963f0e58c1b 100644 --- a/test/parallel/test-events-once.js +++ b/test/parallel/test-events-once.js @@ -1,5 +1,5 @@ 'use strict'; -// Flags: --expose-internals --no-warnings +// Flags: --no-warnings const common = require('../common'); const { once, EventEmitter } = require('events'); @@ -9,7 +9,6 @@ const { fail, rejects, } = require('assert'); -const { EventTarget, Event } = require('internal/event_target'); async function onceAnEvent() { const ee = new EventEmitter(); diff --git a/test/parallel/test-eventtarget-whatwg-passive.js b/test/parallel/test-eventtarget-whatwg-passive.js index 5e33ec5c6c2e47..5399d19da45943 100644 --- a/test/parallel/test-eventtarget-whatwg-passive.js +++ b/test/parallel/test-eventtarget-whatwg-passive.js @@ -1,13 +1,7 @@ -// Flags: --expose-internals 'use strict'; const common = require('../common'); -const { - Event, - EventTarget, -} = require('internal/event_target'); - const { fail, ok, diff --git a/test/parallel/test-worker-message-event.js b/test/parallel/test-worker-message-event.js index 6bb90a993ea0b4..bbc2e3b612686e 100644 --- a/test/parallel/test-worker-message-event.js +++ b/test/parallel/test-worker-message-event.js @@ -1,8 +1,6 @@ -// Flags: --expose-internals 'use strict'; require('../common'); const assert = require('assert'); -const { MessageEvent, MessageChannel } = require('internal/worker/io'); const dummyPort = new MessageChannel().port1; @@ -90,3 +88,7 @@ const dummyPort = new MessageChannel().port1; message: /The "init\.ports\[0\]" property must be an instance of MessagePort/, }); } + +{ + assert(new MessageEvent('message') instanceof Event); +}