X-Git-Url: https://git.josue.xyz/?p=VSoRC%2F.git;a=blobdiff_plain;f=node_modules%2Fnode-pty%2Fsrc%2FwindowsTerminal.test.ts;fp=node_modules%2Fnode-pty%2Fsrc%2FwindowsTerminal.test.ts;h=90441621d81dea49597f40cc73817bf2e7380a45;hp=0000000000000000000000000000000000000000;hb=e79e4a5a87f3e84f7c1777f10a954453a69bf540;hpb=4339da12467b75fb8b6ca831f4bf0081c485ed2c diff --git a/node_modules/node-pty/src/windowsTerminal.test.ts b/node_modules/node-pty/src/windowsTerminal.test.ts new file mode 100644 index 0000000..9044162 --- /dev/null +++ b/node_modules/node-pty/src/windowsTerminal.test.ts @@ -0,0 +1,205 @@ +/** + * Copyright (c) 2017, Daniel Imms (MIT License). + * Copyright (c) 2018, Microsoft Corporation (MIT License). + */ + +import * as fs from 'fs'; +import * as assert from 'assert'; +import { WindowsTerminal } from './windowsTerminal'; +import * as path from 'path'; +import * as psList from 'ps-list'; + +interface IProcessState { + // Whether the PID must exist or must not exist + [pid: number]: boolean; +} + +interface IWindowsProcessTreeResult { + name: string; + pid: number; +} + +function pollForProcessState(desiredState: IProcessState, intervalMs: number = 100, timeoutMs: number = 2000): Promise { + return new Promise(resolve => { + let tries = 0; + const interval = setInterval(() => { + psList({ all: true }).then(ps => { + let success = true; + const pids = Object.keys(desiredState).map(k => parseInt(k, 10)); + pids.forEach(pid => { + if (desiredState[pid]) { + if (!ps.some(p => p.pid === pid)) { + success = false; + } + } else { + if (ps.some(p => p.pid === pid)) { + success = false; + } + } + }); + if (success) { + clearInterval(interval); + resolve(); + return; + } + tries++; + if (tries * intervalMs >= timeoutMs) { + clearInterval(interval); + const processListing = pids.map(k => `${k}: ${desiredState[k]}`).join('\n'); + assert.fail(`Bad process state, expected:\n${processListing}`); + resolve(); + } + }); + }, intervalMs); + }); +} + +function pollForProcessTreeSize(pid: number, size: number, intervalMs: number = 100, timeoutMs: number = 2000): Promise { + return new Promise(resolve => { + let tries = 0; + const interval = setInterval(() => { + psList({ all: true }).then(ps => { + const openList: IWindowsProcessTreeResult[] = []; + openList.push(ps.filter(p => p.pid === pid).map(p => { + return { name: p.name, pid: p.pid }; + })[0]); + const list: IWindowsProcessTreeResult[] = []; + while (openList.length) { + const current = openList.shift(); + ps.filter(p => p.ppid === current.pid).map(p => { + return { name: p.name, pid: p.pid }; + }).forEach(p => openList.push(p)); + list.push(current); + } + const success = list.length === size; + if (success) { + clearInterval(interval); + resolve(list); + return; + } + tries++; + if (tries * intervalMs >= timeoutMs) { + clearInterval(interval); + assert.fail(`Bad process state, expected: ${size}, actual: ${list.length}`); + resolve(); + } + }); + }, intervalMs); + }); +} + +if (process.platform === 'win32') { + describe('WindowsTerminal', () => { + describe('kill', () => { + it('should not crash parent process', (done) => { + const term = new WindowsTerminal('cmd.exe', [], {}); + term.kill(); + // Add done call to deferred function queue to ensure the kill call has completed + (term)._defer(done); + }); + it('should kill the process tree', function (done: Mocha.Done): void { + this.timeout(5000); + const term = new WindowsTerminal('cmd.exe', [], {}); + // Start sub-processes + term.write('powershell.exe\r'); + term.write('notepad.exe\r'); + term.write('node.exe\r'); + pollForProcessTreeSize(term.pid, 4, 500, 5000).then(list => { + assert.equal(list[0].name, 'cmd.exe'); + assert.equal(list[1].name, 'powershell.exe'); + assert.equal(list[2].name, 'notepad.exe'); + assert.equal(list[3].name, 'node.exe'); + term.kill(); + const desiredState: IProcessState = {}; + desiredState[list[0].pid] = false; + desiredState[list[1].pid] = false; + desiredState[list[2].pid] = true; + desiredState[list[3].pid] = false; + pollForProcessState(desiredState).then(() => { + // Kill notepad before done + process.kill(list[2].pid); + done(); + }); + }); + }); + }); + + describe('resize', () => { + it('should throw a non-native exception when resizing an invalid value', () => { + const term = new WindowsTerminal('cmd.exe', [], {}); + assert.throws(() => term.resize(-1, -1)); + assert.throws(() => term.resize(0, 0)); + assert.doesNotThrow(() => term.resize(1, 1)); + }); + it('should throw an non-native exception when resizing a killed terminal', (done) => { + const term = new WindowsTerminal('cmd.exe', [], {}); + (term)._defer(() => { + term.on('exit', () => { + assert.throws(() => term.resize(1, 1)); + done(); + }); + term.destroy(); + }); + }); + }); + + describe('Args as CommandLine', () => { + it('should not fail running a file containing a space in the path', (done) => { + const spaceFolder = path.resolve(__dirname, '..', 'fixtures', 'space folder'); + if (!fs.existsSync(spaceFolder)) { + fs.mkdirSync(spaceFolder); + } + + const cmdCopiedPath = path.resolve(spaceFolder, 'cmd.exe'); + const data = fs.readFileSync(`${process.env.windir}\\System32\\cmd.exe`); + fs.writeFileSync(cmdCopiedPath, data); + + if (!fs.existsSync(cmdCopiedPath)) { + // Skip test if git bash isn't installed + return; + } + const term = new WindowsTerminal(cmdCopiedPath, '/c echo "hello world"', {}); + let result = ''; + term.on('data', (data) => { + result += data; + }); + term.on('exit', () => { + assert.ok(result.indexOf('hello world') >= 1); + done(); + }); + }); + }); + + describe('env', () => { + it('should set environment variables of the shell', (done) => { + const term = new WindowsTerminal('cmd.exe', '/C echo %FOO%', { env: { FOO: 'BAR' }}); + let result = ''; + term.on('data', (data) => { + result += data; + }); + term.on('exit', () => { + assert.ok(result.indexOf('BAR') >= 0); + done(); + }); + }); + }); + + describe('On close', () => { + it('should return process zero exit codes', (done) => { + const term = new WindowsTerminal('cmd.exe', '/C exit'); + term.on('exit', (code) => { + assert.equal(code, 0); + done(); + }); + }); + + it('should return process non-zero exit codes', (done) => { + const term = new WindowsTerminal('cmd.exe', '/C exit 2'); + term.on('exit', (code) => { + assert.equal(code, 2); + done(); + }); + }); + }); + }); +}