mirror of https://github.com/lukechilds/node.git
Browse Source
* Add multiple comments. * Switch to a persistent fixture for subprocess. * Assert that `send` queue is drained. PR-URL: https://github.com/nodejs/node/pull/15186 Fixes: https://github.com/nodejs/node/issues/15176 Reviewed-By: James M Snell <jasnell@gmail.com>canary-base
1 changed files with 47 additions and 17 deletions
@ -1,28 +1,58 @@ |
|||||
'use strict'; |
'use strict'; |
||||
const common = require('../common'); |
const common = require('../common'); |
||||
|
|
||||
|
// subprocess.send() will return false if the channel has closed or when the
|
||||
|
// backlog of unsent messages exceeds a threshold that makes it unwise to send
|
||||
|
// more. Otherwise, the method returns true.
|
||||
|
|
||||
const assert = require('assert'); |
const assert = require('assert'); |
||||
const net = require('net'); |
const net = require('net'); |
||||
const { fork, spawn } = require('child_process'); |
const { fork, spawn } = require('child_process'); |
||||
const fixtures = require('../common/fixtures'); |
const fixtures = require('../common/fixtures'); |
||||
|
|
||||
const emptyFile = fixtures.path('empty.js'); |
// Just a script that stays alive (does not listen to `process.on('message')`).
|
||||
|
const subScript = fixtures.path('child-process-persistent.js'); |
||||
|
|
||||
|
{ |
||||
|
// Test `send` return value on `fork` that opens and IPC by deafult.
|
||||
|
const n = fork(subScript); |
||||
|
// `subprocess.send` should always return `true` for the first send.
|
||||
|
const rv = n.send({ h: 'w' }, (err) => { if (err) assert.fail(err); }); |
||||
|
assert.strictEqual(rv, true); |
||||
|
n.kill(); |
||||
|
} |
||||
|
|
||||
const n = fork(emptyFile); |
{ |
||||
|
// Test `send` return value on `spawn` and saturate backlog with handles.
|
||||
|
// Call `spawn` with options that open an IPC channel.
|
||||
|
const spawnOptions = { stdio: ['pipe', 'pipe', 'pipe', 'ipc'] }; |
||||
|
const s = spawn(process.execPath, [subScript], spawnOptions); |
||||
|
|
||||
const rv = n.send({ hello: 'world' }); |
const server = net.createServer(common.mustNotCall()).listen(0, () => { |
||||
assert.strictEqual(rv, true); |
const handle = server._handle; |
||||
|
|
||||
const spawnOptions = { stdio: ['pipe', 'pipe', 'pipe', 'ipc'] }; |
// Sending a handle and not giving the tickQueue time to acknoladge should
|
||||
const s = spawn(process.execPath, [emptyFile], spawnOptions); |
// create the internal backlog, but leave it empty.
|
||||
let handle = null; |
const rv1 = s.send('one', handle, (err) => { if (err) assert.fail(err); }); |
||||
s.on('exit', function() { |
assert.strictEqual(rv1, true); |
||||
handle.close(); |
// Since the first `send` included a handle (should be unackoladged),
|
||||
}); |
// we can safly queue up only one more message.
|
||||
|
const rv2 = s.send('two', (err) => { if (err) assert.fail(err); }); |
||||
|
assert.strictEqual(rv2, true); |
||||
|
// The backlog should now be indicate to backoff.
|
||||
|
const rv3 = s.send('three', (err) => { if (err) assert.fail(err); }); |
||||
|
assert.strictEqual(rv3, false); |
||||
|
const rv4 = s.send('four', (err) => { |
||||
|
if (err) assert.fail(err); |
||||
|
// `send` queue should have been drained.
|
||||
|
const rv5 = s.send('5', handle, (err) => { if (err) assert.fail(err); }); |
||||
|
assert.strictEqual(rv5, true); |
||||
|
|
||||
net.createServer(common.mustNotCall()).listen(0, function() { |
// End test and cleanup.
|
||||
handle = this._handle; |
s.kill(); |
||||
assert.strictEqual(s.send('one', handle), true); |
handle.close(); |
||||
assert.strictEqual(s.send('two', handle), true); |
server.close(); |
||||
assert.strictEqual(s.send('three'), false); |
}); |
||||
assert.strictEqual(s.send('four'), false); |
assert.strictEqual(rv4, false); |
||||
}); |
}); |
||||
|
} |
||||
|
Loading…
Reference in new issue