Skip to content

Commit

Permalink
worker: add support for platformData
Browse files Browse the repository at this point in the history
The `worker.platformData` and `worker.setPlatformData()` APIs allow
an arbitrary, cloneable JavaScript value to be set and passed to all
new Worker instances spawned from the current context. It is similar
to `workerData` except that `platformData` is set independently of
the `new Worker()` constructor, and the the value is passed
automatically to all new Workers.

This is a *partial* fix of nodejs#30992
but does not implement a complete fix.

Signed-off-by: James M Snell <jasnell@gmail.com>
  • Loading branch information
jasnell committed Mar 11, 2021
1 parent 8283373 commit 1fb5359
Show file tree
Hide file tree
Showing 5 changed files with 71 additions and 0 deletions.
40 changes: 40 additions & 0 deletions doc/api/worker_threads.md
Expand Up @@ -176,6 +176,32 @@ if (isMainThread) {
}
```

## `worker.platformData`
<!-- YAML
added: REPLACEME
-->

An arbitrary JavaScript value that contains a clone of the data passed
to the spawning threads `worker.setPlatformData()` function. The
`worker.platformData` is similar to `worker.workerData` except that
every new `Worker` receives it's own copy of `platformData` automatically.

```js
const {
Worker,
isMainThread,
setPlatformData,
platformData
} = require('worker_threads');

if (isMainThread) {
setPlatformData('Hello World!');
const worker = new Worker(__filename);
} else {
console.log(platformData); // Prints 'Hello, world!'.
}
```

## `worker.receiveMessageOnPort(port)`
<!-- YAML
added: v12.3.0
Expand Down Expand Up @@ -246,6 +272,20 @@ new Worker('process.env.SET_IN_WORKER = "foo"', { eval: true, env: SHARE_ENV })
});
```

## `worker.setPlatformData(value)`
<!--YAML
added: REPLACEME
-->

* `value` {any} Any arbitrary, cloneable JavaScript value that will be cloned
and passed automatically to all new `Worker` instances.

The `worker.setPlatformData()` API sets the value of the `worker.platformData`
in all new `Worker` instances spawned from the current context.

Calling `worker.setPlatformData()` will have no impact on the value of
`worker.platformData` on existing threads.

## `worker.threadId`
<!-- YAML
added: v10.5.0
Expand Down
2 changes: 2 additions & 0 deletions lib/internal/main/worker_thread.js
Expand Up @@ -105,6 +105,7 @@ port.on('message', (message) => {
filename,
doEval,
workerData,
platformData,
publicPort,
manifestSrc,
manifestURL,
Expand All @@ -126,6 +127,7 @@ port.on('message', (message) => {
}
publicWorker.parentPort = publicPort;
publicWorker.workerData = workerData;
publicWorker.platformData = platformData;

// The counter is only passed to the workers created by the main thread, not
// to workers created by other workers.
Expand Down
7 changes: 7 additions & 0 deletions lib/internal/worker.js
Expand Up @@ -90,6 +90,8 @@ let debug = require('internal/util/debuglog').debuglog('worker', (fn) => {

let cwdCounter;

let platformData;

if (isMainThread) {
cwdCounter = new Uint32Array(new SharedArrayBuffer(4));
const originalChdir = process.chdir;
Expand All @@ -99,6 +101,9 @@ if (isMainThread) {
};
}

function setPlatformData(value) {
platformData = value;
}
class Worker extends EventEmitter {
constructor(filename, options = {}) {
super();
Expand Down Expand Up @@ -228,6 +233,7 @@ class Worker extends EventEmitter {
doEval,
cwdCounter: cwdCounter || workerIo.sharedCwdCounter,
workerData: options.workerData,
platformData,
publicPort: port2,
manifestURL: getOptionValue('--experimental-policy') ?
require('internal/process/policy').url :
Expand Down Expand Up @@ -493,6 +499,7 @@ module.exports = {
SHARE_ENV,
resourceLimits:
!isMainThread ? makeResourceLimits(resourceLimitsRaw) : {},
setPlatformData,
threadId,
Worker,
};
3 changes: 3 additions & 0 deletions lib/worker_threads.js
Expand Up @@ -4,6 +4,7 @@ const {
isMainThread,
SHARE_ENV,
resourceLimits,
setPlatformData,
threadId,
Worker
} = require('internal/worker');
Expand Down Expand Up @@ -33,5 +34,7 @@ module.exports = {
Worker,
parentPort: null,
workerData: null,
platformData: null,
BroadcastChannel,
setPlatformData,
};
19 changes: 19 additions & 0 deletions test/parallel/test-worker-platform-data.js
@@ -0,0 +1,19 @@
'use strict';

require('../common');
const {
Worker,
isMainThread,
platformData,
setPlatformData,
} = require('worker_threads');

const { strictEqual } = require('assert');

if (isMainThread) {
setPlatformData('foo');
strictEqual(platformData, null);
new Worker(__filename);
} else {
strictEqual(platformData, 'foo');
}

0 comments on commit 1fb5359

Please sign in to comment.