Simon Priet e69a613a37 feat: Created a mini nodeJS server with NewMan for testing without PostMan GUI.
This will mimic a run in a CD/CI environment or docker container.
2021-09-08 14:01:19 +02:00

151 lines
7.4 KiB
JavaScript

#!/usr/bin/env node
require('../lib/node-version-check'); // @note that this should not respect CLI --silent
const _ = require('lodash'),
waterfall = require('async/waterfall'),
{ Command } = require('commander'),
program = new Command(),
version = require('../package.json').version,
newman = require('../'),
util = require('./util');
program
.name('newman')
.addHelpCommand(false)
.version(version, '-v, --version');
// The `run` command allows you to specify a collection to be run with the provided options.
program
.command('run <collection>')
.description('Initiate a Postman Collection run from a given URL or path')
.usage('<collection> [options]')
.option('-e, --environment <path>', 'Specify a URL or path to a Postman Environment')
.option('-g, --globals <path>', 'Specify a URL or path to a file containing Postman Globals')
.option('-r, --reporters [reporters]', 'Specify the reporters to use for this run', util.cast.csvParse, ['cli'])
.option('-n, --iteration-count <n>', 'Define the number of iterations to run', util.cast.integer)
.option('-d, --iteration-data <path>', 'Specify a data file to use for iterations (either JSON or CSV)')
.option('--folder <path>',
'Specify the folder to run from a collection. Can be specified multiple times to run multiple folders',
util.cast.memoize, [])
.option('--global-var <value>',
'Allows the specification of global variables via the command line, in a key=value format',
util.cast.memoizeKeyVal, [])
.option('--env-var <value>',
'Allows the specification of environment variables via the command line, in a key=value format',
util.cast.memoizeKeyVal, [])
.option('--export-environment <path>', 'Exports the final environment to a file after completing the run')
.option('--export-globals <path>', 'Exports the final globals to a file after completing the run')
.option('--export-collection <path>', 'Exports the executed collection to a file after completing the run')
.option('--postman-api-key <apiKey>', 'API Key used to load the resources from the Postman API')
.option('--bail [modifiers]',
'Specify whether or not to gracefully stop a collection run on encountering an error' +
' and whether to end the run with an error based on the optional modifier', util.cast.csvParse)
.option('--ignore-redirects', 'Prevents Newman from automatically following 3XX redirect responses')
.option('-x , --suppress-exit-code', 'Specify whether or not to override the default exit code for the current run')
.option('--silent', 'Prevents Newman from showing output to CLI')
.option('--disable-unicode', 'Forces Unicode compliant symbols to be replaced by their plain text equivalents')
.option('--color <value>', 'Enable/Disable colored output (auto|on|off)', util.cast.colorOptions, 'auto')
.option('--delay-request [n]', 'Specify the extent of delay between requests (milliseconds)', util.cast.integer, 0)
.option('--timeout [n]', 'Specify a timeout for collection run (milliseconds)', util.cast.integer, 0)
.option('--timeout-request [n]', 'Specify a timeout for requests (milliseconds)', util.cast.integer, 0)
.option('--timeout-script [n]', 'Specify a timeout for scripts (milliseconds)', util.cast.integer, 0)
.option('--working-dir <path>', 'Specify the path to the working directory')
.option('--no-insecure-file-read', 'Prevents reading the files situated outside of the working directory')
.option('-k, --insecure', 'Disables SSL validations')
.option('--ssl-client-cert-list <path>', 'Specify the path to a client certificates configurations (JSON)')
.option('--ssl-client-cert <path>', 'Specify the path to a client certificate (PEM)')
.option('--ssl-client-key <path>', 'Specify the path to a client certificate private key')
.option('--ssl-client-passphrase <passphrase>', 'Specify the client certificate passphrase (for protected key)')
.option('--ssl-extra-ca-certs <path>', 'Specify additionally trusted CA certificates (PEM)')
.option('--cookie-jar <path>', 'Specify the path to a custom cookie jar (serialized tough-cookie JSON) ')
.option('--export-cookie-jar <path>', 'Exports the cookie jar to a file after completing the run')
.option('--verbose', 'Show detailed information of collection run and each request sent')
.action((collection, command) => {
let options = util.commanderToObject(command),
// parse custom reporter options
reporterOptions = util.parseNestedOptions(program._originalArgs, '--reporter-', options.reporters);
// Inject additional properties into the options object
options.collection = collection;
options.reporterOptions = reporterOptions._generic;
options.reporter = _.transform(_.omit(reporterOptions, '_generic'), (acc, value, key) => {
acc[key] = _.assignIn(value, reporterOptions._generic); // overrides reporter options with _generic
}, {});
newman.run(options, function (err, summary) {
const runError = err || summary.run.error || summary.run.failures.length;
if (err) {
console.error(`error: ${err.message || err}\n`);
err.friendly && console.error(` ${err.friendly}\n`);
}
runError && !_.get(options, 'suppressExitCode') && process.exit(1);
});
});
program.addHelpText('after', `
To get available options for a command:
newman <command> -h`);
// Warn on invalid command and then exits.
program.on('command:*', (command) => {
console.error(`error: invalid command \`${command}\`\n`);
program.help();
});
/**
* Starts the script execution.
* callback is required when this is required as a module in tests.
*
* @param {String[]} argv - Argument vector.
* @param {?Function} callback - The callback function invoked on the completion of execution.
*/
function run (argv, callback) {
waterfall([
(next) => {
// cache original argv, required to parse nested options later.
program._originalArgs = argv;
// omit custom nested options, otherwise commander will throw unknown options error
next(null, util.omitNestedOptions(argv, '--reporter-'));
},
(args, next) => {
let error = null;
try {
program.parse(args);
}
catch (err) {
error = err;
}
next(error);
},
(next) => {
// throw error if no argument is provided.
next(program.args.length ? null : new Error('no arguments provided'));
}
], (error) => {
// invoke callback if this is required as module, used in tests.
if (callback) { return callback(error); }
// in case of an error, log error message and print help message.
if (error) {
console.error(`error: ${error.message || error}\n`);
program.help();
}
});
}
// This hack has been added from https://github.com/nodejs/node/issues/6456#issue-151760275
// @todo: remove when https://github.com/nodejs/node/issues/6456 has been fixed
(Number(process.version[1]) >= 6) && [process.stdout, process.stderr].forEach((s) => {
s && s.isTTY && s._handle && s._handle.setBlocking && s._handle.setBlocking(true);
});
// Run this script if this is a direct stdin.
!module.parent && run(process.argv);
// Export to allow debugging and testing.
module.exports = run;