UNPKG

mockserver-node

Version:

Node.js module and Grunt plugin to start and stop MockServer

309 lines (260 loc) 9.07 kB
/* * mockserver * http://mock-server.com * * Copyright (c) 2014 James Bloom * Licensed under the Apache License, Version 2.0 */ const glob = require("glob"); module.exports = (function () { var mockServer; var logLevel; var artifactoryHost = 'oss.sonatype.org'; var artifactoryPath = '/content/repositories/releases/org/mock-server/mockserver-netty/'; var mockServerVersion = '5.15.0'; var Q = require('q'); var http = require('http'); function defer() { var promise = (global.protractor && protractor.promise.USE_PROMISE_MANAGER !== false) ? protractor.promise : Q; var deferred = promise.defer(); if (deferred.fulfill && !deferred.resolve) { deferred.resolve = deferred.fulfill; } return deferred; } function checkStarted(request, retries, promise, verbose) { var deferred = promise || defer(); var req = http.request(request); req.setTimeout(2000); req.once('response', function (response) { var body = ''; response.on('data', function (chunk) { body += chunk; }); response.on('end', function () { deferred.resolve({ statusCode: response.statusCode, body: body }); }); }); req.once('error', function (error) { if (retries > 0) { setTimeout(function () { if (verbose) { console.log("waiting for MockServer to start retries remaining: " + retries); } checkStarted(request, retries - 1, promise, verbose); }, 100); } else { if (verbose) { console.log("MockServer failed to start"); } deferred.reject(error); } }); req.end(); return deferred.promise; } function checkStopped(request, retries, promise, verbose) { var deferred = promise || defer(); var req = http.request(request); req.once('response', function (response) { var body = ''; response.on('data', function (chunk) { body += chunk; }); response.on('end', function () { if (retries > 0) { if (verbose) { console.log("waiting for MockServer to stop retries remaining: " + retries); } setTimeout(function () { checkStopped(request, retries - 1, promise, verbose); }, 100); } else { if (verbose) { console.log("MockServer failed to stop"); } deferred.reject(); } }); }); req.once('error', function () { deferred.resolve(); }); req.end(); return deferred.promise; } function sendRequest(request) { var deferred = defer(); var callback = function (response) { var body = ''; if (response.statusCode === 400 || response.statusCode === 404) { deferred.reject(response.statusCode); } response.on('data', function (chunk) { body += chunk; }); response.on('end', function () { deferred.resolve({ statusCode: response.statusCode, headers: response.headers, body: body }); }); }; var req = http.request(request, callback); req.once('error', function (err) { deferred.reject(err); }); req.end(); return deferred.promise; } function stop_mockserver(options) { var port; var deferred = defer(); if (options && options.serverPort) { if (options.serverPort) { port = port || options.serverPort; } if (options.verbose) { console.log('Using port \'' + port + '\' to stop MockServer and MockServer Proxy'); } sendRequest({ method: 'PUT', host: "localhost", path: "/stop", port: port }).then( function () { if (mockServer) { mockServer.kill(); } checkStopped({ method: 'PUT', host: "localhost", path: "/reset", port: port }, 100, deferred, options && options.verbose); // wait for 10 seconds }, function (err) { if (err && err.code === "ECONNREFUSED") { deferred.resolve(); } else { deferred.reject(err); } } ); } else { deferred.reject("Please specify \"serverPort\", for example: \"stop_mockserver({ serverPort: 1080 })\""); } return deferred.promise; } function start_mockserver(options) { var port; var deferred = defer(); if (!(options && options.serverPort)) { deferred.reject('Please specify "serverPort", for example: "start_mockserver({ serverPort: 1080 })"'); return deferred.promise; } if ((options.systemProperties)) { deferred.reject('The option "systemProperties" was renamed to "jvmOptions" in 5.4.1. Please migrate to the new option name'); return deferred.promise; } if (options.artifactoryHost) { artifactoryHost = options.artifactoryHost; } if (options.artifactoryPath) { artifactoryPath = options.artifactoryPath; } if (options.mockServerVersion) { mockServerVersion = options.mockServerVersion; } if (options.trace) { logLevel = 'TRACE'; options.verbose = true; } else if (options.verbose) { logLevel = 'DEBUG'; } var startupRetries = options.startupRetries || options.javaDebugPort ? 500 : 110; // double check the jar has already been downloaded require('./downloadJar').downloadJar(mockServerVersion, artifactoryHost, artifactoryPath, logLevel).then(function () { var spawn = require('child_process').spawn; var glob = require('glob'); var commandLineOptions = ['-Dfile.encoding=UTF-8']; if (options.initializationJsonPath) { commandLineOptions.push('-Dmockserver.initializationJsonPath=' + options.initializationJsonPath); } if (options.javaDebugPort) { commandLineOptions.push('-agentlib:jdwp=transport=dt_socket,server=y,suspend=y,address=' + options.javaDebugPort); } if (options.jvmOptions) { if (Array.isArray(options.jvmOptions)) { commandLineOptions.push(...options.jvmOptions); } else { commandLineOptions.push(...options.jvmOptions.split(' ')); } } commandLineOptions.push('-jar'); let items = glob.sync('node_modules/mockserver-node/mockserver-netty-*-jar-with-dependencies.jar'); if (items.length === 0) { items = glob.sync('**/mockserver-netty-*-jar-with-dependencies.jar'); } commandLineOptions.push(items); if (options.serverPort) { commandLineOptions.push("-serverPort"); commandLineOptions.push(options.serverPort); port = port || options.serverPort; } if (options.proxyRemotePort) { commandLineOptions.push("-proxyRemotePort"); commandLineOptions.push(options.proxyRemotePort); } if (options.proxyRemoteHost) { commandLineOptions.push("-proxyRemoteHost"); commandLineOptions.push(options.proxyRemoteHost); } if (logLevel) { commandLineOptions.push("-logLevel"); commandLineOptions.push(logLevel); } if (options.verbose) { console.log('Running \'java ' + commandLineOptions.join(' ') + '\''); } if (!options.runForked) { var exitHandler = function(config, err) { return stop_mockserver(config.options).then(function () { if (err) { console.log(err.stack); } if (config.exit) { process.exit(); } }); }; // stop mockserver for uncaught exceptions process.on('uncaughtException', exitHandler.bind(null, {exit: true, options: options})); } mockServer = spawn('java', commandLineOptions, { stdio: ['ignore', (options.verbose ? process.stdout : 'ignore'), process.stderr] }); }).then(function () { return checkStarted({ method: 'PUT', host: "localhost", path: "/mockserver/retrieve?type=ACTIVE_EXPECTATIONS", port: port }, startupRetries, deferred, options.verbose); }, function (error) { deferred.reject(error); }); return deferred.promise; } return { start_mockserver: start_mockserver, stop_mockserver: stop_mockserver }; })();