Skip to content

Commit 7b0e937

Browse files
cjihrigevanlucas
authored andcommitted
child_process: add public API for IPC channel
This commit adds a public channel property to ChildProcess. The existing _channel property is aliased to the new property, with the intention of deprecating and removing it in the future. Fixes: #9313 PR-URL: #9322 Reviewed-By: James M Snell <[email protected]> Reviewed-By: Sam Roberts <[email protected]>
1 parent d4b5095 commit 7b0e937

8 files changed

+51
-20
lines changed

doc/api/child_process.md

+11
Original file line numberDiff line numberDiff line change
@@ -776,6 +776,16 @@ added: v0.5.9
776776
The `'message'` event is triggered when a child process uses [`process.send()`][]
777777
to send messages.
778778

779+
### child.channel
780+
<!-- YAML
781+
added: REPLACEME
782+
-->
783+
784+
* {Object} A pipe representing the IPC channel to the child process.
785+
786+
The `child.channel` property is a reference to the child's IPC channel. If no
787+
IPC channel currently exists, this property is `undefined`.
788+
779789
### child.connected
780790
<!-- YAML
781791
added: v0.7.2
@@ -1145,6 +1155,7 @@ console.log('中文测试');
11451155
[`'error'`]: #child_process_event_error
11461156
[`'exit'`]: #child_process_event_exit
11471157
[`'message'`]: #child_process_event_message
1158+
[`child.channel`]: #child_process_child_channel
11481159
[`child.connected`]: #child_process_child_connected
11491160
[`child.disconnect()`]: #child_process_child_disconnect
11501161
[`child.kill()`]: #child_process_child_kill_signal

doc/api/process.md

+10
Original file line numberDiff line numberDiff line change
@@ -508,6 +508,16 @@ $ bash -c 'exec -a customArgv0 ./node'
508508
'customArgv0'
509509
```
510510

511+
## process.channel
512+
<!-- YAML
513+
added: REPLACEME
514+
-->
515+
516+
If the Node.js process was spawned with an IPC channel (see the
517+
[Child Process][] documentation), the `process.channel`
518+
property is a reference to the IPC channel. If no IPC channel exists, this
519+
property is `undefined`.
520+
511521
## process.chdir(directory)
512522
<!-- YAML
513523
added: v0.1.17

lib/internal/child_process.js

+20-12
Original file line numberDiff line numberDiff line change
@@ -69,7 +69,7 @@ const handleConversion = {
6969
// the slave should keep track of the socket
7070
message.key = socket.server._connectionKey;
7171

72-
var firstTime = !this._channel.sockets.send[message.key];
72+
var firstTime = !this.channel.sockets.send[message.key];
7373
var socketList = getSocketList('send', this, message.key);
7474

7575
// the server should no longer expose a .connection property
@@ -409,7 +409,15 @@ ChildProcess.prototype.unref = function() {
409409

410410

411411
function setupChannel(target, channel) {
412-
target._channel = channel;
412+
target.channel = channel;
413+
414+
// _channel can be deprecated in version 8
415+
Object.defineProperty(target, '_channel', {
416+
get() { return target.channel; },
417+
set(val) { target.channel = val; },
418+
enumerable: true
419+
});
420+
413421
target._handleQueue = null;
414422
target._pendingHandle = null;
415423

@@ -465,7 +473,7 @@ function setupChannel(target, channel) {
465473
target.disconnect();
466474
channel.onread = nop;
467475
channel.close();
468-
target._channel = null;
476+
target.channel = null;
469477
maybeClose(target);
470478
}
471479
};
@@ -491,7 +499,7 @@ function setupChannel(target, channel) {
491499
});
492500

493501
// Process a pending disconnect (if any).
494-
if (!target.connected && target._channel && !target._handleQueue)
502+
if (!target.connected && target.channel && !target._handleQueue)
495503
target._disconnect();
496504

497505
return;
@@ -547,7 +555,7 @@ function setupChannel(target, channel) {
547555
};
548556

549557
target._send = function(message, handle, options, callback) {
550-
assert(this.connected || this._channel);
558+
assert(this.connected || this.channel);
551559

552560
if (message === undefined)
553561
throw new TypeError('"message" argument cannot be undefined');
@@ -667,11 +675,11 @@ function setupChannel(target, channel) {
667675
// connected will be set to false immediately when a disconnect() is
668676
// requested, even though the channel might still be alive internally to
669677
// process queued messages. The three states are distinguished as follows:
670-
// - disconnect() never requested: _channel is not null and connected
678+
// - disconnect() never requested: channel is not null and connected
671679
// is true
672-
// - disconnect() requested, messages in the queue: _channel is not null
680+
// - disconnect() requested, messages in the queue: channel is not null
673681
// and connected is false
674-
// - disconnect() requested, channel actually disconnected: _channel is
682+
// - disconnect() requested, channel actually disconnected: channel is
675683
// null and connected is false
676684
target.connected = true;
677685

@@ -692,10 +700,10 @@ function setupChannel(target, channel) {
692700
};
693701

694702
target._disconnect = function() {
695-
assert(this._channel);
703+
assert(this.channel);
696704

697705
// This marks the fact that the channel is actually disconnected.
698-
this._channel = null;
706+
this.channel = null;
699707

700708
if (this._pendingHandle) {
701709
this._pendingHandle.close();
@@ -729,7 +737,7 @@ function setupChannel(target, channel) {
729737

730738
const INTERNAL_PREFIX = 'NODE_';
731739
function handleMessage(target, message, handle) {
732-
if (!target._channel)
740+
if (!target.channel)
733741
return;
734742

735743
var eventName = 'message';
@@ -860,7 +868,7 @@ function _validateStdio(stdio, sync) {
860868

861869

862870
function getSocketList(type, slave, key) {
863-
var sockets = slave._channel.sockets[type];
871+
var sockets = slave.channel.sockets[type];
864872
var socketList = sockets[key];
865873
if (!socketList) {
866874
var Construct = type === 'send' ? SocketListSend : SocketListReceive;

lib/internal/process/stdio.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -60,9 +60,9 @@ function setupStdio() {
6060
// sitting on fd=0, in such case the pipe for this fd is already
6161
// present and creating a new one will lead to the assertion failure
6262
// in libuv.
63-
if (process._channel && process._channel.fd === fd) {
63+
if (process.channel && process.channel.fd === fd) {
6464
stdin = new net.Socket({
65-
handle: process._channel,
65+
handle: process.channel,
6666
readable: true,
6767
writable: false
6868
});

test/parallel/test-child-process-fork-regr-gh-2847.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -44,8 +44,8 @@ var server = net.createServer(function(s) {
4444
}
4545

4646
worker.process.once('close', common.mustCall(function() {
47-
// Otherwise the crash on `_channel.fd` access may happen
48-
assert.strictEqual(worker.process._channel, null);
47+
// Otherwise the crash on `channel.fd` access may happen
48+
assert.strictEqual(worker.process.channel, null);
4949
server.close();
5050
}));
5151

test/parallel/test-child-process-fork.js

+2
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@ var fork = require('child_process').fork;
55
var args = ['foo', 'bar'];
66

77
var n = fork(common.fixturesDir + '/child-process-spawn-node.js', args);
8+
9+
assert.strictEqual(n.channel, n._channel);
810
assert.deepStrictEqual(args, ['foo', 'bar']);
911

1012
n.on('message', function(m) {

test/parallel/test-child-process-recv-handle.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -36,12 +36,12 @@ function master() {
3636
}
3737

3838
function worker() {
39-
process._channel.readStop(); // Make messages batch up.
39+
process.channel.readStop(); // Make messages batch up.
4040
process.stdout.ref();
4141
process.stdout.write('ok\r\n');
4242
process.stdin.once('data', common.mustCall((data) => {
4343
assert.strictEqual(data.toString(), 'ok\r\n');
44-
process._channel.readStart();
44+
process.channel.readStart();
4545
}));
4646
let n = 0;
4747
process.on('message', common.mustCall((msg, handle) => {

test/parallel/test-child-process-silent.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -21,8 +21,8 @@ if (process.argv[2] === 'pipe') {
2121
const child = childProcess.fork(process.argv[1], ['pipe'], {silent: true});
2222

2323
// Allow child process to self terminate
24-
child._channel.close();
25-
child._channel = null;
24+
child.channel.close();
25+
child.channel = null;
2626

2727
child.on('exit', function() {
2828
process.exit(0);

0 commit comments

Comments
 (0)