@theia/process 1.67.0-next.56 → 1.67.0-next.86
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/common/process-common-module.d.ts +4 -0
- package/lib/common/process-common-module.d.ts.map +1 -0
- package/lib/common/process-common-module.js +23 -0
- package/lib/common/process-common-module.js.map +1 -0
- package/lib/common/process-manager-types.d.ts +36 -0
- package/lib/common/process-manager-types.d.ts.map +1 -0
- package/lib/common/process-manager-types.js +24 -0
- package/lib/common/process-manager-types.js.map +1 -0
- package/lib/common/shell-command-builder.d.ts +50 -0
- package/lib/common/shell-command-builder.d.ts.map +1 -0
- package/lib/common/shell-command-builder.js +170 -0
- package/lib/common/shell-command-builder.js.map +1 -0
- package/lib/common/shell-command-builder.slow-spec.d.ts +10 -0
- package/lib/common/shell-command-builder.slow-spec.d.ts.map +1 -0
- package/lib/common/shell-command-builder.slow-spec.js +405 -0
- package/lib/common/shell-command-builder.slow-spec.js.map +1 -0
- package/lib/common/shell-quoting.d.ts +92 -0
- package/lib/common/shell-quoting.d.ts.map +1 -0
- package/lib/common/shell-quoting.js +146 -0
- package/lib/common/shell-quoting.js.map +1 -0
- package/lib/common/shell-quoting.spec.d.ts +2 -0
- package/lib/common/shell-quoting.spec.d.ts.map +1 -0
- package/lib/common/shell-quoting.spec.js +171 -0
- package/lib/common/shell-quoting.spec.js.map +1 -0
- package/lib/node/dev-null-stream.d.ts +18 -0
- package/lib/node/dev-null-stream.d.ts.map +1 -0
- package/lib/node/dev-null-stream.js +42 -0
- package/lib/node/dev-null-stream.js.map +1 -0
- package/lib/node/index.d.ts +7 -0
- package/lib/node/index.d.ts.map +1 -0
- package/lib/node/index.js +25 -0
- package/lib/node/index.js.map +1 -0
- package/lib/node/multi-ring-buffer.d.ts +71 -0
- package/lib/node/multi-ring-buffer.d.ts.map +1 -0
- package/lib/node/multi-ring-buffer.js +300 -0
- package/lib/node/multi-ring-buffer.js.map +1 -0
- package/lib/node/multi-ring-buffer.spec.d.ts +2 -0
- package/lib/node/multi-ring-buffer.spec.d.ts.map +1 -0
- package/lib/node/multi-ring-buffer.spec.js +423 -0
- package/lib/node/multi-ring-buffer.spec.js.map +1 -0
- package/lib/node/process-backend-module.d.ts +4 -0
- package/lib/node/process-backend-module.d.ts.map +1 -0
- package/lib/node/process-backend-module.js +52 -0
- package/lib/node/process-backend-module.js.map +1 -0
- package/lib/node/process-manager.d.ts +34 -0
- package/lib/node/process-manager.d.ts.map +1 -0
- package/lib/node/process-manager.js +103 -0
- package/lib/node/process-manager.js.map +1 -0
- package/lib/node/process.d.ts +96 -0
- package/lib/node/process.d.ts.map +1 -0
- package/lib/node/process.js +146 -0
- package/lib/node/process.js.map +1 -0
- package/lib/node/pseudo-pty.d.ts +24 -0
- package/lib/node/pseudo-pty.d.ts.map +1 -0
- package/lib/node/pseudo-pty.js +40 -0
- package/lib/node/pseudo-pty.js.map +1 -0
- package/lib/node/raw-process.d.ts +47 -0
- package/lib/node/raw-process.d.ts.map +1 -0
- package/lib/node/raw-process.js +104 -0
- package/lib/node/raw-process.js.map +1 -0
- package/lib/node/raw-process.spec.d.ts +2 -0
- package/lib/node/raw-process.spec.d.ts.map +1 -0
- package/lib/node/raw-process.spec.js +163 -0
- package/lib/node/raw-process.spec.js.map +1 -0
- package/lib/node/task-terminal-process.d.ts +11 -0
- package/lib/node/task-terminal-process.d.ts.map +1 -0
- package/lib/node/task-terminal-process.js +43 -0
- package/lib/node/task-terminal-process.js.map +1 -0
- package/lib/node/terminal-process.d.ts +61 -0
- package/lib/node/terminal-process.d.ts.map +1 -0
- package/lib/node/terminal-process.js +252 -0
- package/lib/node/terminal-process.js.map +1 -0
- package/lib/node/terminal-process.spec.d.ts +2 -0
- package/lib/node/terminal-process.spec.d.ts.map +1 -0
- package/lib/node/terminal-process.spec.js +104 -0
- package/lib/node/terminal-process.spec.js.map +1 -0
- package/lib/node/test/process-test-container.d.ts +3 -0
- package/lib/node/test/process-test-container.d.ts.map +1 -0
- package/lib/node/test/process-test-container.js +29 -0
- package/lib/node/test/process-test-container.js.map +1 -0
- package/lib/node/utils.d.ts +17 -0
- package/lib/node/utils.d.ts.map +1 -0
- package/lib/node/utils.js +78 -0
- package/lib/node/utils.js.map +1 -0
- package/package.json +3 -3
|
@@ -0,0 +1,405 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// *****************************************************************************
|
|
3
|
+
// Copyright (C) 2020 Ericsson and others.
|
|
4
|
+
//
|
|
5
|
+
// This program and the accompanying materials are made available under the
|
|
6
|
+
// terms of the Eclipse Public License v. 2.0 which is available at
|
|
7
|
+
// http://www.eclipse.org/legal/epl-2.0.
|
|
8
|
+
//
|
|
9
|
+
// This Source Code may also be made available under the following Secondary
|
|
10
|
+
// Licenses when the conditions for such availability set forth in the Eclipse
|
|
11
|
+
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
|
12
|
+
// with the GNU Classpath Exception which is available at
|
|
13
|
+
// https://www.gnu.org/software/classpath/license.html.
|
|
14
|
+
//
|
|
15
|
+
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
|
16
|
+
// *****************************************************************************
|
|
17
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
18
|
+
/**
|
|
19
|
+
* This test suite assumes that we run in a NodeJS environment!
|
|
20
|
+
*/
|
|
21
|
+
const child_process_1 = require("child_process");
|
|
22
|
+
const path_1 = require("path");
|
|
23
|
+
const shell_command_builder_1 = require("./shell-command-builder");
|
|
24
|
+
const chalk = require("chalk"); // tslint:disable-line:no-implicit-dependencies
|
|
25
|
+
const isWindows = process.platform === 'win32';
|
|
26
|
+
/**
|
|
27
|
+
* Extra debugging info (very verbose).
|
|
28
|
+
*/
|
|
29
|
+
const _debug = Boolean(process.env['THEIA_PROCESS_TEST_DEBUG']);
|
|
30
|
+
/**
|
|
31
|
+
* On Windows, some shells simply mess up the terminal's output.
|
|
32
|
+
* Enable if you still want to test those.
|
|
33
|
+
*/
|
|
34
|
+
const _runWeirdShell = Boolean(process.env['THEIA_PROCESS_TEST_WEIRD_SHELL']) || undefined;
|
|
35
|
+
/**
|
|
36
|
+
* You might only have issues with a specific shell (`cmd.exe` I am looking at you).
|
|
37
|
+
*/
|
|
38
|
+
const _onlyTestShell = process.env['THEIA_PROCESS_TEST_ONLY'] || undefined;
|
|
39
|
+
/**
|
|
40
|
+
* Only log if environment variable is set.
|
|
41
|
+
*/
|
|
42
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
43
|
+
function debug(...parts) {
|
|
44
|
+
if (_debug) {
|
|
45
|
+
console.debug(...parts);
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
const testResources = (0, path_1.join)(__dirname, '../../src/common/tests');
|
|
49
|
+
const spawnOptions = {
|
|
50
|
+
// We do our own quoting, don't rely on the one done by NodeJS:
|
|
51
|
+
windowsVerbatimArguments: true,
|
|
52
|
+
stdio: ['pipe', 'pipe', 'pipe'],
|
|
53
|
+
};
|
|
54
|
+
// Formatting options, used with `scanLines` for debugging.
|
|
55
|
+
const stdoutFormat = (prefix) => (data) => `${chalk.bold(chalk.yellow(`${prefix} STDOUT:`))} ${chalk.bgYellow(chalk.black(data))}`;
|
|
56
|
+
const stderrFormat = (prefix) => (data) => `${chalk.bold(chalk.red(`${prefix} STDERR:`))} ${chalk.bgRed(chalk.white(data))}`;
|
|
57
|
+
// Default error scanner
|
|
58
|
+
const errorScanner = (handle) => {
|
|
59
|
+
if (/^\s*\w+Error:/.test(handle.line) ||
|
|
60
|
+
/^\s*Cannot find /.test(handle.line)) {
|
|
61
|
+
throw new Error(handle.text);
|
|
62
|
+
}
|
|
63
|
+
};
|
|
64
|
+
// Yarn mangles the PATH and creates some proxy script around node(.exe),
|
|
65
|
+
// which messes up our environment, failing the tests.
|
|
66
|
+
const hostNodePath = process.env['npm_node_execpath'] ||
|
|
67
|
+
process.env['NODE'];
|
|
68
|
+
if (!hostNodePath) {
|
|
69
|
+
throw new Error('Could not determine the real node path.');
|
|
70
|
+
}
|
|
71
|
+
const shellCommandBuilder = new shell_command_builder_1.ShellCommandBuilder();
|
|
72
|
+
const shellConfigs = [{
|
|
73
|
+
name: 'bash',
|
|
74
|
+
path: isWindows
|
|
75
|
+
? _runWeirdShell && execShellCommand('where bash.exe')
|
|
76
|
+
: execShellCommand('command -v bash'),
|
|
77
|
+
nodePath: isWindows && 'node' // Good enough
|
|
78
|
+
}, {
|
|
79
|
+
name: 'wsl',
|
|
80
|
+
path: isWindows
|
|
81
|
+
? _runWeirdShell && execShellCommand('where wsl.exe')
|
|
82
|
+
: undefined,
|
|
83
|
+
nodePath: isWindows && 'node' // Good enough
|
|
84
|
+
}, {
|
|
85
|
+
name: 'cmd',
|
|
86
|
+
path: isWindows
|
|
87
|
+
? execShellCommand('where cmd.exe')
|
|
88
|
+
: undefined,
|
|
89
|
+
}, {
|
|
90
|
+
name: 'powershell',
|
|
91
|
+
path: execShellCommand(isWindows
|
|
92
|
+
? 'where powershell'
|
|
93
|
+
: 'command -v pwsh'),
|
|
94
|
+
}];
|
|
95
|
+
/* eslint-disable max-len */
|
|
96
|
+
// 18d/12m/19y - Ubuntu 16.04:
|
|
97
|
+
// Powershell sometimes fails when running as part of an npm lifecycle script.
|
|
98
|
+
// See following error:
|
|
99
|
+
//
|
|
100
|
+
//
|
|
101
|
+
// FailFast:
|
|
102
|
+
// The type initializer for 'Microsoft.PowerShell.ApplicationInsightsTelemetry' threw an exception.
|
|
103
|
+
//
|
|
104
|
+
// at System.Environment.FailFast(System.String, System.Exception)
|
|
105
|
+
// at System.Environment.FailFast(System.String, System.Exception)
|
|
106
|
+
// at Microsoft.PowerShell.UnmanagedPSEntry.Start(System.String, System.String[], Int32)
|
|
107
|
+
// at Microsoft.PowerShell.ManagedPSEntry.Main(System.String[])
|
|
108
|
+
//
|
|
109
|
+
// Exception details:
|
|
110
|
+
// System.TypeInitializationException: The type initializer for 'Microsoft.PowerShell.ApplicationInsightsTelemetry' threw an exception. ---> System.ArgumentException: Item has already been added. Key in dictionary: 'SPAWN_WRAP_SHIM_ROOT' Key being added: 'SPAWN_WRAP_SHIM_ROOT'
|
|
111
|
+
// at System.Collections.Hashtable.Insert(Object key, Object nvalue, Boolean add)
|
|
112
|
+
// at System.Environment.ToHashtable(IEnumerable`1 pairs)
|
|
113
|
+
// at System.Environment.GetEnvironmentVariables()
|
|
114
|
+
// at Microsoft.ApplicationInsights.Extensibility.Implementation.Platform.PlatformImplementation..ctor()
|
|
115
|
+
// at Microsoft.ApplicationInsights.Extensibility.Implementation.Platform.PlatformSingleton.get_Current()
|
|
116
|
+
// at Microsoft.ApplicationInsights.Extensibility.Implementation.TelemetryConfigurationFactory.Initialize(TelemetryConfiguration configuration, TelemetryModules modules)
|
|
117
|
+
// at Microsoft.ApplicationInsights.Extensibility.TelemetryConfiguration.get_Active()
|
|
118
|
+
// at Microsoft.PowerShell.ApplicationInsightsTelemetry..cctor()
|
|
119
|
+
// --- End of inner exception stack trace ---
|
|
120
|
+
// at Microsoft.PowerShell.ApplicationInsightsTelemetry.SendPSCoreStartupTelemetry()
|
|
121
|
+
// at Microsoft.PowerShell.ConsoleHost.Start(String bannerText, String helpText, String[] args)
|
|
122
|
+
// at Microsoft.PowerShell.ConsoleShell.Start(String bannerText, String helpText, String[] args)
|
|
123
|
+
// at Microsoft.PowerShell.UnmanagedPSEntry.Start(String consoleFilePath, String[] args, Int32 argc)
|
|
124
|
+
/* eslint-enable max-len */
|
|
125
|
+
let id = 0;
|
|
126
|
+
for (const shellConfig of shellConfigs) {
|
|
127
|
+
let skipMessage;
|
|
128
|
+
if (typeof _onlyTestShell === 'string' && shellConfig.name !== _onlyTestShell) {
|
|
129
|
+
skipMessage = `only testing ${_onlyTestShell}`;
|
|
130
|
+
}
|
|
131
|
+
else if (!shellConfig.path) {
|
|
132
|
+
// For each shell, skip if we could not find the executable path.
|
|
133
|
+
skipMessage = 'cannot find shell';
|
|
134
|
+
}
|
|
135
|
+
else {
|
|
136
|
+
// Run a test in the shell to catch runtime issues.
|
|
137
|
+
// CI seems to have issues with some shells depending on the environment...
|
|
138
|
+
try {
|
|
139
|
+
const debugName = `${shellConfig.name}/test`;
|
|
140
|
+
const shellTest = (0, child_process_1.spawnSync)(shellConfig.path, {
|
|
141
|
+
input: 'echo abcdefghijkl\n\n',
|
|
142
|
+
timeout: 5000,
|
|
143
|
+
});
|
|
144
|
+
debug(stdoutFormat(debugName)(shellTest.stdout.toString()));
|
|
145
|
+
debug(stderrFormat(debugName)(shellTest.stderr.toString()));
|
|
146
|
+
if (!/abcdefghijkl/m.test(shellTest.output.toString())) {
|
|
147
|
+
skipMessage = 'wrong test output';
|
|
148
|
+
}
|
|
149
|
+
}
|
|
150
|
+
catch (error) {
|
|
151
|
+
console.error(error);
|
|
152
|
+
skipMessage = 'error occurred';
|
|
153
|
+
}
|
|
154
|
+
}
|
|
155
|
+
/**
|
|
156
|
+
* If skipMessage is set, we should skip the test and explain why.
|
|
157
|
+
*/
|
|
158
|
+
const describeOrSkip = (callback) => {
|
|
159
|
+
const describeMessage = `test ${shellConfig.name} commands`;
|
|
160
|
+
if (typeof skipMessage === 'undefined') {
|
|
161
|
+
describe(describeMessage, callback);
|
|
162
|
+
}
|
|
163
|
+
else {
|
|
164
|
+
describe.skip(`${describeMessage} - skip: ${skipMessage}`, callback);
|
|
165
|
+
}
|
|
166
|
+
};
|
|
167
|
+
describeOrSkip(function () {
|
|
168
|
+
this.timeout(10000);
|
|
169
|
+
let nodePath;
|
|
170
|
+
let cwd;
|
|
171
|
+
let submit;
|
|
172
|
+
let processInfo;
|
|
173
|
+
let context;
|
|
174
|
+
beforeEach(() => {
|
|
175
|
+
// In WSL, the node path is different than the host one (Windows vs Linux).
|
|
176
|
+
nodePath = shellConfig.nodePath || hostNodePath;
|
|
177
|
+
// On windows, when running bash we need to convert paths from Windows
|
|
178
|
+
// to their mounting point, assuming bash is running within WSL.
|
|
179
|
+
if (isWindows && /bash|wsl/.test(shellConfig.name)) {
|
|
180
|
+
cwd = convertWindowsPath(testResources);
|
|
181
|
+
}
|
|
182
|
+
else {
|
|
183
|
+
cwd = testResources;
|
|
184
|
+
}
|
|
185
|
+
// When running powershell, it seems like good measure to send `\n` twice...
|
|
186
|
+
if (shellConfig.name === 'powershell') {
|
|
187
|
+
submit = '\n\n';
|
|
188
|
+
}
|
|
189
|
+
// TestContext holds all state for a given test.
|
|
190
|
+
const testContextName = `${shellConfig.name}/${++id}`;
|
|
191
|
+
context = new TestCaseContext(testContextName, submit);
|
|
192
|
+
processInfo = createShell(context, shellConfig.path);
|
|
193
|
+
});
|
|
194
|
+
afterEach(() => {
|
|
195
|
+
processInfo.shell.kill();
|
|
196
|
+
context.finalize();
|
|
197
|
+
});
|
|
198
|
+
it('use simple environment variables', async () => {
|
|
199
|
+
const envName = 'SIMPLE_NAME';
|
|
200
|
+
const envValue = 'SIMPLE_VALUE';
|
|
201
|
+
await testCommandLine(context, processInfo, {
|
|
202
|
+
cwd, args: [nodePath, '-p', `\`[\${process.env['${envName}']}]\``],
|
|
203
|
+
env: {
|
|
204
|
+
[envName]: envValue,
|
|
205
|
+
}
|
|
206
|
+
}, [
|
|
207
|
+
// stderr
|
|
208
|
+
scanLines(context, processInfo.shell.stderr, errorScanner, stderrFormat(context.name)),
|
|
209
|
+
// stdout
|
|
210
|
+
scanLines(context, processInfo.shell.stdout, handle => {
|
|
211
|
+
errorScanner(handle);
|
|
212
|
+
if (handle.line.includes(`[${envValue}]`)) {
|
|
213
|
+
handle.resolve();
|
|
214
|
+
}
|
|
215
|
+
}, stdoutFormat(context.name)),
|
|
216
|
+
]);
|
|
217
|
+
});
|
|
218
|
+
it('use problematic environment variables', async () => {
|
|
219
|
+
const envName = 'A?B_C | D $PATH';
|
|
220
|
+
const envValue = 'SUCCESS';
|
|
221
|
+
await testCommandLine(context, processInfo, {
|
|
222
|
+
cwd, args: [nodePath, '-p', `\`[\${process.env['${envName}']}]\``],
|
|
223
|
+
env: {
|
|
224
|
+
[envName]: envValue,
|
|
225
|
+
}
|
|
226
|
+
}, [
|
|
227
|
+
// stderr
|
|
228
|
+
scanLines(context, processInfo.shell.stderr, errorScanner, stderrFormat(context.name)),
|
|
229
|
+
// stdout
|
|
230
|
+
scanLines(context, processInfo.shell.stdout, handle => {
|
|
231
|
+
errorScanner(handle);
|
|
232
|
+
if (handle.line.includes(`[${envValue}]`)) {
|
|
233
|
+
handle.resolve();
|
|
234
|
+
}
|
|
235
|
+
if (handle.line.includes('[undefined]')) {
|
|
236
|
+
handle.reject(new Error(handle.text));
|
|
237
|
+
}
|
|
238
|
+
}, stdoutFormat(context.name)),
|
|
239
|
+
]);
|
|
240
|
+
});
|
|
241
|
+
it('command with complex arguments', async () => {
|
|
242
|
+
const left = 'ABC';
|
|
243
|
+
const right = 'DEF';
|
|
244
|
+
await testCommandLine(context, processInfo, {
|
|
245
|
+
cwd, args: [nodePath, '-e', `{
|
|
246
|
+
const left = '${left}';
|
|
247
|
+
const right = '${right}';
|
|
248
|
+
console.log(\`[\${left}|\${right}]\`);
|
|
249
|
+
}`],
|
|
250
|
+
}, [
|
|
251
|
+
// stderr
|
|
252
|
+
scanLines(context, processInfo.shell.stderr, errorScanner, stderrFormat(context.name)),
|
|
253
|
+
// stdout
|
|
254
|
+
scanLines(context, processInfo.shell.stdout, handle => {
|
|
255
|
+
errorScanner(handle);
|
|
256
|
+
if (handle.line.includes(`[${left}|${right}]`)) {
|
|
257
|
+
handle.resolve();
|
|
258
|
+
}
|
|
259
|
+
}, stdoutFormat(context.name)),
|
|
260
|
+
]);
|
|
261
|
+
});
|
|
262
|
+
});
|
|
263
|
+
}
|
|
264
|
+
/**
|
|
265
|
+
* Allow `command` to fail and return undefined instead.
|
|
266
|
+
*/
|
|
267
|
+
function execShellCommand(command) {
|
|
268
|
+
try {
|
|
269
|
+
// If trimmed output is an empty string, return `undefined` instead:
|
|
270
|
+
return (0, child_process_1.execSync)(command).toString().trim() || undefined;
|
|
271
|
+
}
|
|
272
|
+
catch (error) {
|
|
273
|
+
console.error(command, error);
|
|
274
|
+
return undefined;
|
|
275
|
+
}
|
|
276
|
+
}
|
|
277
|
+
/**
|
|
278
|
+
* When executing `bash.exe` on Windows, the `C:`, `D:`, etc drives are mounted under `/mnt/<drive>/...`
|
|
279
|
+
*/
|
|
280
|
+
function convertWindowsPath(windowsPath) {
|
|
281
|
+
return windowsPath
|
|
282
|
+
// Convert back-slashes to forward-slashes
|
|
283
|
+
.replace(/\\/g, '/')
|
|
284
|
+
// Convert drive-letter to usual mounting point in WSL
|
|
285
|
+
.replace(/^[A-Za-z]:\//, s => `/mnt/${s[0].toLowerCase()}/`);
|
|
286
|
+
}
|
|
287
|
+
/**
|
|
288
|
+
* Display trailing whitespace in a string, such as \r and \n.
|
|
289
|
+
*/
|
|
290
|
+
function displayWhitespaces(line) {
|
|
291
|
+
return line
|
|
292
|
+
.replace(/\r?\n/, s => s.length === 2 ? '<\\r\\n>\r\n' : '<\\n>\n');
|
|
293
|
+
}
|
|
294
|
+
/**
|
|
295
|
+
* Actually run `prepareCommandLine`.
|
|
296
|
+
*/
|
|
297
|
+
async function testCommandLine(context, processInfo, options,
|
|
298
|
+
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
299
|
+
firstOf) {
|
|
300
|
+
const commandLine = shellCommandBuilder.buildCommand(processInfo, options);
|
|
301
|
+
debug(`${chalk.bold(chalk.white(`${context.name} STDIN:`))} ${chalk.bgWhite(chalk.black(displayWhitespaces(commandLine)))}`);
|
|
302
|
+
processInfo.shell.stdin.write(commandLine + context.submit);
|
|
303
|
+
return Promise.race(firstOf);
|
|
304
|
+
}
|
|
305
|
+
/**
|
|
306
|
+
* Creates a `(Test)ProcessInfo` object by spawning the specified shell.
|
|
307
|
+
*/
|
|
308
|
+
function createShell(context, shellExecutable, shellArguments = []) {
|
|
309
|
+
const shell = (0, child_process_1.spawn)(shellExecutable, shellArguments, spawnOptions);
|
|
310
|
+
debug(chalk.magenta(`${chalk.bold(`${context.name} SPAWN:`)} ${shellExecutable} ${shellArguments.join(' ')}`));
|
|
311
|
+
shell.on('close', (code, signal) => debug(chalk.magenta(`${chalk.bold(`${context.name} CLOSE:`)} ${shellExecutable} code(${code}) signal(${signal})`)));
|
|
312
|
+
return {
|
|
313
|
+
executable: shellExecutable,
|
|
314
|
+
arguments: [],
|
|
315
|
+
shell,
|
|
316
|
+
};
|
|
317
|
+
}
|
|
318
|
+
/**
|
|
319
|
+
* Fire `callback` once per new detected line.
|
|
320
|
+
*/
|
|
321
|
+
async function scanLines(context, stream, callback, debugFormat = (s) => s) {
|
|
322
|
+
return new Promise((resolve, reject) => {
|
|
323
|
+
let line = '';
|
|
324
|
+
let text = '';
|
|
325
|
+
stream.on('close', () => {
|
|
326
|
+
debug(debugFormat('<CLOSED>'));
|
|
327
|
+
});
|
|
328
|
+
// The `data` listener will be collected on 'close', which will happen
|
|
329
|
+
// once we kill the process.
|
|
330
|
+
stream.on('data', data => {
|
|
331
|
+
if (context.resolved) {
|
|
332
|
+
return;
|
|
333
|
+
}
|
|
334
|
+
const split = data.toString().split('\n');
|
|
335
|
+
while (!context.resolved && split.length > 1) {
|
|
336
|
+
line += split.shift() + '\n';
|
|
337
|
+
text += line;
|
|
338
|
+
debug(debugFormat(displayWhitespaces(line)));
|
|
339
|
+
try {
|
|
340
|
+
callback({
|
|
341
|
+
resolve: (value) => {
|
|
342
|
+
if (!context.resolved) {
|
|
343
|
+
context.resolve();
|
|
344
|
+
resolve(value);
|
|
345
|
+
debug(chalk.bold(chalk.green(`${context.name} SCANLINES RESOLVED`)));
|
|
346
|
+
}
|
|
347
|
+
},
|
|
348
|
+
reject: (reason) => {
|
|
349
|
+
if (!context.resolved) {
|
|
350
|
+
context.resolve();
|
|
351
|
+
reject(reason);
|
|
352
|
+
debug(chalk.bold(chalk.red(`${context.name} SCANLINES REJECTED`)));
|
|
353
|
+
}
|
|
354
|
+
},
|
|
355
|
+
line,
|
|
356
|
+
text,
|
|
357
|
+
});
|
|
358
|
+
}
|
|
359
|
+
catch (error) {
|
|
360
|
+
debug(chalk.bold(chalk.red(`${context.name} SCANLINES THROWED`)));
|
|
361
|
+
context.resolve();
|
|
362
|
+
reject(error);
|
|
363
|
+
break;
|
|
364
|
+
}
|
|
365
|
+
line = '';
|
|
366
|
+
}
|
|
367
|
+
line += split[0];
|
|
368
|
+
});
|
|
369
|
+
});
|
|
370
|
+
}
|
|
371
|
+
/**
|
|
372
|
+
* We need a test case context to help with catching listeners that timed-out,
|
|
373
|
+
* and synchronize multiple listeners so that when one resolves the test case,
|
|
374
|
+
* the others can be put in "sleep mode" until destruction.
|
|
375
|
+
*/
|
|
376
|
+
class TestCaseContext {
|
|
377
|
+
constructor(
|
|
378
|
+
/**
|
|
379
|
+
* A name associated with this context, to help with debugging.
|
|
380
|
+
*/
|
|
381
|
+
name,
|
|
382
|
+
/**
|
|
383
|
+
* The characters to send in order to submit a command (mostly
|
|
384
|
+
* powershell is causing issues).
|
|
385
|
+
*/
|
|
386
|
+
submit = '\n',
|
|
387
|
+
/**
|
|
388
|
+
* @internal Current state of the test case, if it is finished or not.
|
|
389
|
+
*/
|
|
390
|
+
resolved = false) {
|
|
391
|
+
this.name = name;
|
|
392
|
+
this.submit = submit;
|
|
393
|
+
this.resolved = resolved;
|
|
394
|
+
}
|
|
395
|
+
resolve() {
|
|
396
|
+
this.resolved = true;
|
|
397
|
+
}
|
|
398
|
+
finalize() {
|
|
399
|
+
if (!this.resolved) {
|
|
400
|
+
this.resolve();
|
|
401
|
+
debug(chalk.red(`${chalk.bold(`${this.name} CONTEXT:`)} context wasn't resolved when finalizing, resolving!`));
|
|
402
|
+
}
|
|
403
|
+
}
|
|
404
|
+
}
|
|
405
|
+
//# sourceMappingURL=shell-command-builder.slow-spec.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"shell-command-builder.slow-spec.js","sourceRoot":"","sources":["../../src/common/shell-command-builder.slow-spec.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Defines how an argument should be quoted if it contains
|
|
3
|
+
* spaces or unsupported characters.
|
|
4
|
+
*/
|
|
5
|
+
export declare const enum ShellQuoting {
|
|
6
|
+
/**
|
|
7
|
+
* Character escaping should be used. This for example
|
|
8
|
+
* uses \ on bash and ` on PowerShell.
|
|
9
|
+
*/
|
|
10
|
+
Escape = "escape",
|
|
11
|
+
/**
|
|
12
|
+
* Strong string quoting should be used. This for example
|
|
13
|
+
* uses " for Windows cmd and ' for bash and PowerShell.
|
|
14
|
+
* Strong quoting treats arguments as literal strings.
|
|
15
|
+
* Under PowerShell echo 'The value is $(2 * 3)' will
|
|
16
|
+
* print `The value is $(2 * 3)`
|
|
17
|
+
*/
|
|
18
|
+
Strong = "strong",
|
|
19
|
+
/**
|
|
20
|
+
* Weak string quoting should be used. This for example
|
|
21
|
+
* uses " for Windows cmd, bash and PowerShell. Weak quoting
|
|
22
|
+
* still performs some kind of evaluation inside the quoted
|
|
23
|
+
* string. Under PowerShell echo "The value is $(2 * 3)"
|
|
24
|
+
* will print `The value is 6`
|
|
25
|
+
*/
|
|
26
|
+
Weak = "weak"
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* A string that will be quoted depending on the used shell.
|
|
30
|
+
*/
|
|
31
|
+
export interface ShellQuotedString {
|
|
32
|
+
/**
|
|
33
|
+
* The actual string value.
|
|
34
|
+
*/
|
|
35
|
+
value: string;
|
|
36
|
+
/**
|
|
37
|
+
* The quoting style to use.
|
|
38
|
+
*/
|
|
39
|
+
quoting: ShellQuoting;
|
|
40
|
+
}
|
|
41
|
+
/**
|
|
42
|
+
* Functions that provide shell quoting capabilities.
|
|
43
|
+
*/
|
|
44
|
+
export interface ShellQuotingFunctions {
|
|
45
|
+
characters: {
|
|
46
|
+
/** Characters that require quotes, white space is always implied. */
|
|
47
|
+
needQuotes?: string;
|
|
48
|
+
/** The character used to escape sequences. */
|
|
49
|
+
escape?: string;
|
|
50
|
+
/** The character used to quote sequences, preventing variable expansion. */
|
|
51
|
+
strong?: string;
|
|
52
|
+
/** The character used to quote sequences, allowing variable expansion. */
|
|
53
|
+
weak?: string;
|
|
54
|
+
};
|
|
55
|
+
/**
|
|
56
|
+
* Should add escape-characters in front of forbidden characters.
|
|
57
|
+
*/
|
|
58
|
+
escape?(this: any, arg: string): string;
|
|
59
|
+
/**
|
|
60
|
+
* Should quote the argument in such a way that variables CANNOT be expanded.
|
|
61
|
+
*/
|
|
62
|
+
strong?(this: any, arg: string): string;
|
|
63
|
+
/**
|
|
64
|
+
* Should quote the argument in such a way that variables CAN be expanded.
|
|
65
|
+
*/
|
|
66
|
+
weak?(this: any, arg: string): string;
|
|
67
|
+
}
|
|
68
|
+
/**
|
|
69
|
+
* Converts a list of args into an escaped shell command.
|
|
70
|
+
*
|
|
71
|
+
* There are two main use cases when handling command/arguments for a shell:
|
|
72
|
+
* 1. User already wrote the escaped commandline, then just use that.
|
|
73
|
+
* 2. User wants a specific process to be invoked with some arguments.
|
|
74
|
+
*
|
|
75
|
+
* The `createShellCommandLine` function is useful for the latter.
|
|
76
|
+
*
|
|
77
|
+
* @param args Standard list of spawn/exec arguments, first item is the command.
|
|
78
|
+
* @param quotingFunctions Collection of functions to process arguments.
|
|
79
|
+
*/
|
|
80
|
+
export declare function createShellCommandLine(args: Array<string | ShellQuotedString>, quotingFunctions?: ShellQuotingFunctions): string;
|
|
81
|
+
/**
|
|
82
|
+
* Escape (or quote) a given input.
|
|
83
|
+
*
|
|
84
|
+
* @param arg Input to escape.
|
|
85
|
+
* @param quotingFunctions Collection of functions to process the given `arg`.
|
|
86
|
+
* @param quotingType Override the quoting type specified by the given `arg`.
|
|
87
|
+
*/
|
|
88
|
+
export declare function escapeForShell(arg: string | ShellQuotedString, quotingFunctions?: ShellQuotingFunctions, quotingType?: ShellQuoting): string;
|
|
89
|
+
export declare const BashQuotingFunctions: Required<ShellQuotingFunctions>;
|
|
90
|
+
export declare const CmdQuotingFunctions: Required<ShellQuotingFunctions>;
|
|
91
|
+
export declare const PowershellQuotingFunctions: Required<ShellQuotingFunctions>;
|
|
92
|
+
//# sourceMappingURL=shell-quoting.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"shell-quoting.d.ts","sourceRoot":"","sources":["../../src/common/shell-quoting.ts"],"names":[],"mappings":"AAyBA;;;GAGG;AACH,0BAAkB,YAAY;IAE1B;;;OAGG;IACH,MAAM,WAAW;IAEjB;;;;;;OAMG;IACH,MAAM,WAAW;IAEjB;;;;;;OAMG;IACH,IAAI,SAAS;CAChB;AAED;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAC9B;;OAEG;IACH,KAAK,EAAE,MAAM,CAAC;IAEd;;OAEG;IACH,OAAO,EAAE,YAAY,CAAC;CACzB;AAID;;GAEG;AACH,MAAM,WAAW,qBAAqB;IAElC,UAAU,EAAE;QACR,qEAAqE;QACrE,UAAU,CAAC,EAAE,MAAM,CAAA;QACnB,8CAA8C;QAC9C,MAAM,CAAC,EAAE,MAAM,CAAA;QACf,4EAA4E;QAC5E,MAAM,CAAC,EAAE,MAAM,CAAA;QACf,0EAA0E;QAC1E,IAAI,CAAC,EAAE,MAAM,CAAA;KAChB,CAAA;IAED;;OAEG;IAEH,MAAM,CAAC,CAAC,IAAI,EAAE,GAAG,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAAA;IAEvC;;OAEG;IAEH,MAAM,CAAC,CAAC,IAAI,EAAE,GAAG,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAAC;IAExC;;OAEG;IAEH,IAAI,CAAC,CAAC,IAAI,EAAE,GAAG,EAAE,GAAG,EAAE,MAAM,GAAG,MAAM,CAAC;CACzC;AAED;;;;;;;;;;;GAWG;AACH,wBAAgB,sBAAsB,CAAC,IAAI,EAAE,KAAK,CAAC,MAAM,GAAG,iBAAiB,CAAC,EAAE,gBAAgB,CAAC,EAAE,qBAAqB,GAAG,MAAM,CAEhI;AAED;;;;;;GAMG;AACH,wBAAgB,cAAc,CAAC,GAAG,EAAE,MAAM,GAAG,iBAAiB,EAAE,gBAAgB,CAAC,EAAE,qBAAqB,EAAE,WAAW,CAAC,EAAE,YAAY,GAAG,MAAM,CAkB5I;AAED,eAAO,MAAM,oBAAoB,EAAE,QAAQ,CAAC,qBAAqB,CAyBhE,CAAC;AAEF,eAAO,MAAM,mBAAmB,EAAE,QAAQ,CAAC,qBAAqB,CA8B/D,CAAC;AAEF,eAAO,MAAM,0BAA0B,EAAE,QAAQ,CAAC,qBAAqB,CAyBtE,CAAC"}
|
|
@@ -0,0 +1,146 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
// *****************************************************************************
|
|
3
|
+
// Copyright (C) 2020 Ericsson and others.
|
|
4
|
+
//
|
|
5
|
+
// This program and the accompanying materials are made available under the
|
|
6
|
+
// terms of the Eclipse Public License v. 2.0 which is available at
|
|
7
|
+
// http://www.eclipse.org/legal/epl-2.0.
|
|
8
|
+
//
|
|
9
|
+
// This Source Code may also be made available under the following Secondary
|
|
10
|
+
// Licenses when the conditions for such availability set forth in the Eclipse
|
|
11
|
+
// Public License v. 2.0 are satisfied: GNU General Public License, version 2
|
|
12
|
+
// with the GNU Classpath Exception which is available at
|
|
13
|
+
// https://www.gnu.org/software/classpath/license.html.
|
|
14
|
+
//
|
|
15
|
+
// SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-only WITH Classpath-exception-2.0
|
|
16
|
+
// *****************************************************************************
|
|
17
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
18
|
+
exports.PowershellQuotingFunctions = exports.CmdQuotingFunctions = exports.BashQuotingFunctions = exports.escapeForShell = exports.createShellCommandLine = void 0;
|
|
19
|
+
/**
|
|
20
|
+
* Converts a list of args into an escaped shell command.
|
|
21
|
+
*
|
|
22
|
+
* There are two main use cases when handling command/arguments for a shell:
|
|
23
|
+
* 1. User already wrote the escaped commandline, then just use that.
|
|
24
|
+
* 2. User wants a specific process to be invoked with some arguments.
|
|
25
|
+
*
|
|
26
|
+
* The `createShellCommandLine` function is useful for the latter.
|
|
27
|
+
*
|
|
28
|
+
* @param args Standard list of spawn/exec arguments, first item is the command.
|
|
29
|
+
* @param quotingFunctions Collection of functions to process arguments.
|
|
30
|
+
*/
|
|
31
|
+
function createShellCommandLine(args, quotingFunctions) {
|
|
32
|
+
return args.map(arg => escapeForShell(arg, quotingFunctions)).join(' ');
|
|
33
|
+
}
|
|
34
|
+
exports.createShellCommandLine = createShellCommandLine;
|
|
35
|
+
/**
|
|
36
|
+
* Escape (or quote) a given input.
|
|
37
|
+
*
|
|
38
|
+
* @param arg Input to escape.
|
|
39
|
+
* @param quotingFunctions Collection of functions to process the given `arg`.
|
|
40
|
+
* @param quotingType Override the quoting type specified by the given `arg`.
|
|
41
|
+
*/
|
|
42
|
+
function escapeForShell(arg, quotingFunctions, quotingType) {
|
|
43
|
+
let value;
|
|
44
|
+
let quoting = quotingType;
|
|
45
|
+
if (typeof arg === 'string') {
|
|
46
|
+
if (!quoting) {
|
|
47
|
+
return arg;
|
|
48
|
+
}
|
|
49
|
+
value = arg;
|
|
50
|
+
}
|
|
51
|
+
else {
|
|
52
|
+
if (!quoting) {
|
|
53
|
+
quoting = arg.quoting;
|
|
54
|
+
}
|
|
55
|
+
value = arg.value;
|
|
56
|
+
}
|
|
57
|
+
if (quotingFunctions && typeof quotingFunctions[quoting] === 'function') {
|
|
58
|
+
return quotingFunctions[quoting](value);
|
|
59
|
+
}
|
|
60
|
+
return value;
|
|
61
|
+
}
|
|
62
|
+
exports.escapeForShell = escapeForShell;
|
|
63
|
+
exports.BashQuotingFunctions = {
|
|
64
|
+
characters: {
|
|
65
|
+
needQuotes: '()',
|
|
66
|
+
escape: '\\',
|
|
67
|
+
strong: '\'',
|
|
68
|
+
weak: '"',
|
|
69
|
+
},
|
|
70
|
+
escape(arg) {
|
|
71
|
+
return arg
|
|
72
|
+
.replace(/[\s\\|(){}<>$&;"']/g, '\\$&');
|
|
73
|
+
},
|
|
74
|
+
strong(arg) {
|
|
75
|
+
// ('+) becomes ('"'+"')
|
|
76
|
+
return `'${arg
|
|
77
|
+
.replace(/'+/g, '\'"$&"\'')}'`;
|
|
78
|
+
},
|
|
79
|
+
weak(arg) {
|
|
80
|
+
return `"${arg
|
|
81
|
+
// Escape escape-characters.
|
|
82
|
+
.replace(/\\"/g, '\\\\"')
|
|
83
|
+
// Escape user-specified double-quotes.
|
|
84
|
+
.replace(/"/g, '\\"')
|
|
85
|
+
// Escape trailing (\), we don't want the user to escape our last quote.
|
|
86
|
+
.replace(/\\$/g, '\\\\')}"`;
|
|
87
|
+
},
|
|
88
|
+
};
|
|
89
|
+
exports.CmdQuotingFunctions = {
|
|
90
|
+
characters: {
|
|
91
|
+
weak: '"',
|
|
92
|
+
},
|
|
93
|
+
escape(arg) {
|
|
94
|
+
return arg
|
|
95
|
+
// Escape forbidden characters (see: cmd /?).
|
|
96
|
+
.replace(/[%&<>()@^|]/g, '^$&')
|
|
97
|
+
// Some characters must be escaped using `\`.
|
|
98
|
+
.replace(/[\\"]/g, '\\$&')
|
|
99
|
+
// Double-quote whitespaces, else we cannot escape it.
|
|
100
|
+
.replace(/\s+/g, '"$&"');
|
|
101
|
+
},
|
|
102
|
+
strong(arg) {
|
|
103
|
+
return this.weak(arg)
|
|
104
|
+
// Try to prevent variable expansion.
|
|
105
|
+
.replace(/%/g, '"%"');
|
|
106
|
+
},
|
|
107
|
+
weak(arg) {
|
|
108
|
+
return `"${arg
|
|
109
|
+
// Escape double quotes.
|
|
110
|
+
.replace(/\\"/g, '\\\\"')
|
|
111
|
+
.replace(/"/g, '\\"')
|
|
112
|
+
// Escape forbidden characters (see: cmd /?)
|
|
113
|
+
.replace(/[&<>()@^|]/g, '^$&')
|
|
114
|
+
// Escape trailing backslash, we don't want the user to escape our last quote.
|
|
115
|
+
.replace(/\\$/g, '\\\\')
|
|
116
|
+
// Escape line returns
|
|
117
|
+
.replace(/\r?\n/g, '^$&')}"`;
|
|
118
|
+
},
|
|
119
|
+
};
|
|
120
|
+
exports.PowershellQuotingFunctions = {
|
|
121
|
+
characters: {
|
|
122
|
+
needQuotes: '()',
|
|
123
|
+
escape: '`',
|
|
124
|
+
strong: '\'',
|
|
125
|
+
weak: '"',
|
|
126
|
+
},
|
|
127
|
+
escape(arg) {
|
|
128
|
+
return arg.replace(/[`|{}()<>;"' ]/g, '`$&');
|
|
129
|
+
},
|
|
130
|
+
strong(arg) {
|
|
131
|
+
// In powershell, one must write ('') for a single quote to be displayed
|
|
132
|
+
// within a single quoted string.
|
|
133
|
+
return `'${arg
|
|
134
|
+
.replace(/'/g, '\'\'')}'`;
|
|
135
|
+
},
|
|
136
|
+
weak(arg) {
|
|
137
|
+
return `"${arg
|
|
138
|
+
// Escape escape-characters.
|
|
139
|
+
.replace(/`"/g, '``"')
|
|
140
|
+
// Escape user-specified backticks.
|
|
141
|
+
.replace(/"/g, '`"')
|
|
142
|
+
// Escape trailing (`), we don't want the user to escape our last quote.
|
|
143
|
+
.replace(/`$/g, '``')}"`;
|
|
144
|
+
},
|
|
145
|
+
};
|
|
146
|
+
//# sourceMappingURL=shell-quoting.js.map
|