• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1'use strict';
2const common = require('../common');
3const assert = require('assert');
4const spawnSync = require('child_process').spawnSync;
5const signals = require('os').constants.signals;
6const rootUser = common.isWindows ? false :
7  common.isIBMi ? true : process.getuid() === 0;
8
9const invalidArgTypeError = { code: 'ERR_INVALID_ARG_TYPE', name: 'TypeError' };
10const invalidRangeError = { code: 'ERR_OUT_OF_RANGE', name: 'RangeError' };
11
12function pass(option, value) {
13  // Run the command with the specified option. Since it's not a real command,
14  // spawnSync() should run successfully but return an ENOENT error.
15  const child = spawnSync('not_a_real_command', { [option]: value });
16
17  assert.strictEqual(child.error.code, 'ENOENT');
18}
19
20function fail(option, value, message) {
21  assert.throws(() => {
22    spawnSync('not_a_real_command', { [option]: value });
23  }, message);
24}
25
26{
27  // Validate the cwd option
28  pass('cwd', undefined);
29  pass('cwd', null);
30  pass('cwd', __dirname);
31  fail('cwd', 0, invalidArgTypeError);
32  fail('cwd', 1, invalidArgTypeError);
33  fail('cwd', true, invalidArgTypeError);
34  fail('cwd', false, invalidArgTypeError);
35  fail('cwd', [], invalidArgTypeError);
36  fail('cwd', {}, invalidArgTypeError);
37  fail('cwd', common.mustNotCall(), invalidArgTypeError);
38}
39
40{
41  // Validate the detached option
42  pass('detached', undefined);
43  pass('detached', null);
44  pass('detached', true);
45  pass('detached', false);
46  fail('detached', 0, invalidArgTypeError);
47  fail('detached', 1, invalidArgTypeError);
48  fail('detached', __dirname, invalidArgTypeError);
49  fail('detached', [], invalidArgTypeError);
50  fail('detached', {}, invalidArgTypeError);
51  fail('detached', common.mustNotCall(), invalidArgTypeError);
52}
53
54if (!common.isWindows) {
55  {
56    // Validate the uid option
57    if (!rootUser) {
58      pass('uid', undefined);
59      pass('uid', null);
60      pass('uid', process.getuid());
61      fail('uid', __dirname, invalidArgTypeError);
62      fail('uid', true, invalidArgTypeError);
63      fail('uid', false, invalidArgTypeError);
64      fail('uid', [], invalidArgTypeError);
65      fail('uid', {}, invalidArgTypeError);
66      fail('uid', common.mustNotCall(), invalidArgTypeError);
67      fail('uid', NaN, invalidArgTypeError);
68      fail('uid', Infinity, invalidArgTypeError);
69      fail('uid', 3.1, invalidArgTypeError);
70      fail('uid', -3.1, invalidArgTypeError);
71    }
72  }
73
74  {
75    // Validate the gid option
76    if (process.getgid() !== 0) {
77      pass('gid', undefined);
78      pass('gid', null);
79      pass('gid', process.getgid());
80      fail('gid', __dirname, invalidArgTypeError);
81      fail('gid', true, invalidArgTypeError);
82      fail('gid', false, invalidArgTypeError);
83      fail('gid', [], invalidArgTypeError);
84      fail('gid', {}, invalidArgTypeError);
85      fail('gid', common.mustNotCall(), invalidArgTypeError);
86      fail('gid', NaN, invalidArgTypeError);
87      fail('gid', Infinity, invalidArgTypeError);
88      fail('gid', 3.1, invalidArgTypeError);
89      fail('gid', -3.1, invalidArgTypeError);
90    }
91  }
92}
93
94{
95  // Validate the shell option
96  pass('shell', undefined);
97  pass('shell', null);
98  pass('shell', false);
99  fail('shell', 0, invalidArgTypeError);
100  fail('shell', 1, invalidArgTypeError);
101  fail('shell', [], invalidArgTypeError);
102  fail('shell', {}, invalidArgTypeError);
103  fail('shell', common.mustNotCall(), invalidArgTypeError);
104}
105
106{
107  // Validate the argv0 option
108  pass('argv0', undefined);
109  pass('argv0', null);
110  pass('argv0', 'myArgv0');
111  fail('argv0', 0, invalidArgTypeError);
112  fail('argv0', 1, invalidArgTypeError);
113  fail('argv0', true, invalidArgTypeError);
114  fail('argv0', false, invalidArgTypeError);
115  fail('argv0', [], invalidArgTypeError);
116  fail('argv0', {}, invalidArgTypeError);
117  fail('argv0', common.mustNotCall(), invalidArgTypeError);
118}
119
120{
121  // Validate the windowsHide option
122  pass('windowsHide', undefined);
123  pass('windowsHide', null);
124  pass('windowsHide', true);
125  pass('windowsHide', false);
126  fail('windowsHide', 0, invalidArgTypeError);
127  fail('windowsHide', 1, invalidArgTypeError);
128  fail('windowsHide', __dirname, invalidArgTypeError);
129  fail('windowsHide', [], invalidArgTypeError);
130  fail('windowsHide', {}, invalidArgTypeError);
131  fail('windowsHide', common.mustNotCall(), invalidArgTypeError);
132}
133
134{
135  // Validate the windowsVerbatimArguments option
136  pass('windowsVerbatimArguments', undefined);
137  pass('windowsVerbatimArguments', null);
138  pass('windowsVerbatimArguments', true);
139  pass('windowsVerbatimArguments', false);
140  fail('windowsVerbatimArguments', 0, invalidArgTypeError);
141  fail('windowsVerbatimArguments', 1, invalidArgTypeError);
142  fail('windowsVerbatimArguments', __dirname, invalidArgTypeError);
143  fail('windowsVerbatimArguments', [], invalidArgTypeError);
144  fail('windowsVerbatimArguments', {}, invalidArgTypeError);
145  fail('windowsVerbatimArguments', common.mustNotCall(), invalidArgTypeError);
146}
147
148{
149  // Validate the timeout option
150  pass('timeout', undefined);
151  pass('timeout', null);
152  pass('timeout', 1);
153  pass('timeout', 0);
154  fail('timeout', -1, invalidRangeError);
155  fail('timeout', true, invalidRangeError);
156  fail('timeout', false, invalidRangeError);
157  fail('timeout', __dirname, invalidRangeError);
158  fail('timeout', [], invalidRangeError);
159  fail('timeout', {}, invalidRangeError);
160  fail('timeout', common.mustNotCall(), invalidRangeError);
161  fail('timeout', NaN, invalidRangeError);
162  fail('timeout', Infinity, invalidRangeError);
163  fail('timeout', 3.1, invalidRangeError);
164  fail('timeout', -3.1, invalidRangeError);
165}
166
167{
168  // Validate the maxBuffer option
169  pass('maxBuffer', undefined);
170  pass('maxBuffer', null);
171  pass('maxBuffer', 1);
172  pass('maxBuffer', 0);
173  pass('maxBuffer', Infinity);
174  pass('maxBuffer', 3.14);
175  fail('maxBuffer', -1, invalidRangeError);
176  fail('maxBuffer', NaN, invalidRangeError);
177  fail('maxBuffer', -Infinity, invalidRangeError);
178  fail('maxBuffer', true, invalidRangeError);
179  fail('maxBuffer', false, invalidRangeError);
180  fail('maxBuffer', __dirname, invalidRangeError);
181  fail('maxBuffer', [], invalidRangeError);
182  fail('maxBuffer', {}, invalidRangeError);
183  fail('maxBuffer', common.mustNotCall(), invalidRangeError);
184}
185
186{
187  // Validate the killSignal option
188  const unknownSignalErr = { code: 'ERR_UNKNOWN_SIGNAL', name: 'TypeError' };
189
190  pass('killSignal', undefined);
191  pass('killSignal', null);
192  pass('killSignal', 'SIGKILL');
193  fail('killSignal', 'SIGNOTAVALIDSIGNALNAME', unknownSignalErr);
194  fail('killSignal', true, invalidArgTypeError);
195  fail('killSignal', false, invalidArgTypeError);
196  fail('killSignal', [], invalidArgTypeError);
197  fail('killSignal', {}, invalidArgTypeError);
198  fail('killSignal', common.mustNotCall(), invalidArgTypeError);
199
200  // Invalid signal names and numbers should fail
201  fail('killSignal', 500, unknownSignalErr);
202  fail('killSignal', 0, unknownSignalErr);
203  fail('killSignal', -200, unknownSignalErr);
204  fail('killSignal', 3.14, unknownSignalErr);
205
206  Object.getOwnPropertyNames(Object.prototype).forEach((property) => {
207    fail('killSignal', property, unknownSignalErr);
208  });
209
210  // Valid signal names and numbers should pass
211  for (const signalName in signals) {
212    pass('killSignal', signals[signalName]);
213    pass('killSignal', signalName);
214    pass('killSignal', signalName.toLowerCase());
215  }
216}
217