test: extract test runner method

This commit is contained in:
Jason Bedard 2022-05-27 14:27:09 -07:00 committed by Charles
parent f6f37821c8
commit c74bb5652c

View File

@ -70,7 +70,6 @@ function lastLogger() {
} }
const testGlob = argv.glob || 'tests/**/*.ts'; const testGlob = argv.glob || 'tests/**/*.ts';
let currentFileName = '';
const e2eRoot = path.join(__dirname, 'e2e'); const e2eRoot = path.join(__dirname, 'e2e');
const allSetups = glob.sync('setup/**/*.ts', { nodir: true, cwd: e2eRoot }).sort(); const allSetups = glob.sync('setup/**/*.ts', { nodir: true, cwd: e2eRoot }).sort();
@ -122,24 +121,58 @@ setGlobalVariable('argv', argv);
setGlobalVariable('ci', process.env['CI']?.toLowerCase() === 'true' || process.env['CI'] === '1'); setGlobalVariable('ci', process.env['CI']?.toLowerCase() === 'true' || process.env['CI'] === '1');
setGlobalVariable('package-manager', argv.yarn ? 'yarn' : 'npm'); setGlobalVariable('package-manager', argv.yarn ? 'yarn' : 'npm');
Promise.all([findFreePort(), findFreePort()]).then(async ([httpPort, httpsPort]) => { Promise.all([findFreePort(), findFreePort()])
.then(async ([httpPort, httpsPort]) => {
setGlobalVariable('package-registry', 'http://localhost:' + httpPort); setGlobalVariable('package-registry', 'http://localhost:' + httpPort);
setGlobalVariable('package-secure-registry', 'http://localhost:' + httpsPort); setGlobalVariable('package-secure-registry', 'http://localhost:' + httpsPort);
let lastTestRun: string | null = null;
// NPM registries for the lifetime of the test execution
const registryProcess = await createNpmRegistry(httpPort, httpPort); const registryProcess = await createNpmRegistry(httpPort, httpPort);
const secureRegistryProcess = await createNpmRegistry(httpPort, httpsPort, true); const secureRegistryProcess = await createNpmRegistry(httpPort, httpsPort, true);
return ( try {
testsToRun for (const [testIndex, test] of testsToRun.entries()) {
.reduce((previous, relativeName, testIndex) => { await runTest((lastTestRun = test), testIndex);
}
console.log(colors.green('Done.'));
} catch (err) {
console.log('\n');
console.error(colors.red(`Test "${lastTestRun}" failed...`));
console.error(colors.red(err.message));
console.error(colors.red(err.stack));
if (argv.debug) {
console.log(`Current Directory: ${process.cwd()}`);
console.log('Will loop forever while you debug... CTRL-C to quit.');
/* eslint-disable no-constant-condition */
while (1) {
// That's right!
}
}
throw err;
} finally {
registryProcess.kill();
secureRegistryProcess.kill();
}
})
.then(
() => process.exit(0),
() => process.exit(1),
);
async function runTest(relativeName: string, testIndex: number) {
// Make sure this is a windows compatible path. // Make sure this is a windows compatible path.
let absoluteName = path.join(e2eRoot, relativeName); let absoluteName = path.join(e2eRoot, relativeName);
if (/^win/.test(process.platform)) { if (/^win/.test(process.platform)) {
absoluteName = absoluteName.replace(/\\/g, path.posix.sep); absoluteName = absoluteName.replace(/\\/g, path.posix.sep);
} }
return previous.then(() => { const currentFileName = relativeName.replace(/\.ts$/, '');
currentFileName = relativeName.replace(/\.ts$/, '');
const start = +new Date(); const start = +new Date();
const module = require(absoluteName); const module = require(absoluteName);
@ -156,23 +189,21 @@ Promise.all([findFreePort(), findFreePort()]).then(async ([httpPort, httpsPort])
throw new Error('Invalid test module.'); throw new Error('Invalid test module.');
}; };
let clean = true; printHeader(currentFileName, testIndex);
let previousDir: string | null = null;
return Promise.resolve() let clean = true;
.then(() => printHeader(currentFileName, testIndex)) let previousDir = process.cwd();
.then(() => (previousDir = process.cwd())) try {
.then(() => logStack.push(lastLogger().createChild(currentFileName))) // Run the test function with the current file on the logStack.
.then(() => fn(() => (clean = false))) logStack.push(lastLogger().createChild(currentFileName));
.then( try {
() => logStack.pop(), await fn(() => (clean = false));
(err) => { } finally {
logStack.pop(); logStack.pop();
throw err; }
},
) console.log('----');
.then(() => console.log('----'))
.then(() => {
// If we're not in a setup, change the directory back to where it was before the test. // If we're not in a setup, change the directory back to where it was before the test.
// This allows tests to chdir without worrying about keeping the original directory. // This allows tests to chdir without worrying about keeping the original directory.
if (!allSetups.includes(relativeName) && previousDir) { if (!allSetups.includes(relativeName) && previousDir) {
@ -182,65 +213,26 @@ Promise.all([findFreePort(), findFreePort()]).then(async ([httpPort, httpsPort])
console.log(' Restoring original environment variables...'); console.log(' Restoring original environment variables...');
process.env = originalEnvVariables; process.env = originalEnvVariables;
} }
})
.then(() => {
// Only clean after a real test, not a setup step. Also skip cleaning if the test // Only clean after a real test, not a setup step. Also skip cleaning if the test
// requested an exception. // requested an exception.
if (!allSetups.includes(relativeName) && clean) { if (!allSetups.includes(relativeName) && clean) {
logStack.push(new logging.NullLogger()); logStack.push(new logging.NullLogger());
return gitClean().then( try {
() => logStack.pop(), await gitClean();
(err) => { } finally {
logStack.pop(); logStack.pop();
throw err;
},
);
} }
}) }
.then(
() => printFooter(currentFileName, start), printFooter(currentFileName, start);
(err) => { } catch (err) {
printFooter(currentFileName, start); printFooter(currentFileName, start);
console.error(err); console.error(err);
throw err; throw err;
},
);
});
}, Promise.resolve())
// Output success vs failure information.
.then(
() => console.log(colors.green('Done.')),
(err) => {
console.log('\n');
console.error(colors.red(`Test "${currentFileName}" failed...`));
console.error(colors.red(err.message));
console.error(colors.red(err.stack));
if (argv.debug) {
console.log(`Current Directory: ${process.cwd()}`);
console.log('Will loop forever while you debug... CTRL-C to quit.');
/* eslint-disable no-constant-condition */
while (1) {
// That's right!
} }
} }
return Promise.reject(err);
},
)
// Kill the registry processes before exiting.
.finally(() => {
registryProcess.kill();
secureRegistryProcess.kill();
})
.then(
() => process.exit(0),
() => process.exit(1),
)
);
});
function printHeader(testName: string, testIndex: number) { function printHeader(testName: string, testIndex: number) {
const text = `${testIndex + 1} of ${testsToRun.length}`; const text = `${testIndex + 1} of ${testsToRun.length}`;
const fullIndex = const fullIndex =