diff --git a/lib/config.js b/lib/config.js index 008e981b0..243b54525 100644 --- a/lib/config.js +++ b/lib/config.js @@ -199,6 +199,10 @@ var normalizeConfig = function (config, configFilePath) { throw new TypeError('Invalid configuration: formatError option must be a function.') } + if (config.processKillTimeout && !helper.isNumber(config.processKillTimeout)) { + throw new TypeError('Invalid configuration: processKillTimeout option must be a number.') + } + var defaultClient = config.defaultClient || {} Object.keys(defaultClient).forEach(function (key) { var option = config.client[key] @@ -321,6 +325,7 @@ var Config = function () { this.browserDisconnectTimeout = 2000 this.browserDisconnectTolerance = 0 this.browserNoActivityTimeout = 10000 + this.processKillTimeout = 2000 this.concurrency = Infinity this.failOnEmptyTestSuite = true this.retryLimit = 2 diff --git a/lib/helper.js b/lib/helper.js index 0356edc2f..7c317cb9d 100644 --- a/lib/helper.js +++ b/lib/helper.js @@ -80,6 +80,7 @@ exports.isFunction = _.isFunction exports.isString = _.isString exports.isObject = _.isObject exports.isArray = _.isArray +exports.isNumber = _.isNumber var ABS_URL = /^https?:\/\// exports.isUrlAbsolute = function (url) { diff --git a/lib/launcher.js b/lib/launcher.js index 67c0ebe56..be15dcf56 100644 --- a/lib/launcher.js +++ b/lib/launcher.js @@ -14,13 +14,14 @@ var baseBrowserDecoratorFactory = function ( baseLauncherDecorator, captureTimeoutLauncherDecorator, retryLauncherDecorator, - processLauncherDecorator + processLauncherDecorator, + processKillTimeout ) { return function (launcher) { baseLauncherDecorator(launcher) captureTimeoutLauncherDecorator(launcher) retryLauncherDecorator(launcher) - processLauncherDecorator(launcher) + processLauncherDecorator(launcher, processKillTimeout) } } @@ -39,7 +40,7 @@ var Launcher = function (server, emitter, injector) { return null } - this.launchSingle = function (protocol, hostname, port, urlRoot, upstreamProxy) { + this.launchSingle = function (protocol, hostname, port, urlRoot, upstreamProxy, processKillTimeout) { var self = this return function (name) { if (upstreamProxy) { @@ -53,6 +54,7 @@ var Launcher = function (server, emitter, injector) { var locals = { id: ['value', Launcher.generateId()], name: ['value', name], + processKillTimeout: ['value', processKillTimeout], baseLauncherDecorator: ['factory', baseDecorator], captureTimeoutLauncherDecorator: ['factory', captureTimeoutDecorator], retryLauncherDecorator: ['factory', retryDecorator], @@ -157,7 +159,8 @@ var Launcher = function (server, emitter, injector) { this.launch.$inject = [ 'config.browsers', - 'config.concurrency' + 'config.concurrency', + 'config.processKillTimeout' ] this.launchSingle.$inject = [ @@ -165,7 +168,8 @@ var Launcher = function (server, emitter, injector) { 'config.hostname', 'config.port', 'config.urlRoot', - 'config.upstreamProxy' + 'config.upstreamProxy', + 'config.processKillTimeout' ] this.kill = function (id, callback) { diff --git a/lib/launchers/process.js b/lib/launchers/process.js index e079a53af..97f137aa0 100644 --- a/lib/launchers/process.js +++ b/lib/launchers/process.js @@ -2,10 +2,10 @@ var path = require('path') var log = require('../logger').create('launcher') var env = process.env -var ProcessLauncher = function (spawn, tempDir, timer) { +var ProcessLauncher = function (spawn, tempDir, timer, processKillTimeout) { var self = this var onExitCallback - var killTimeout = 2000 + var killTimeout = processKillTimeout this._tempDir = tempDir.getPath('/karma-' + this.id.toString()) @@ -134,7 +134,7 @@ var ProcessLauncher = function (spawn, tempDir, timer) { } ProcessLauncher.decoratorFactory = function (timer) { - return function (launcher) { + return function (launcher, processKillTimeout) { var spawn = require('child_process').spawn var spawnWithoutOutput = function () { @@ -145,7 +145,7 @@ ProcessLauncher.decoratorFactory = function (timer) { return proc } - ProcessLauncher.call(launcher, spawnWithoutOutput, require('../temp_dir'), timer) + ProcessLauncher.call(launcher, spawnWithoutOutput, require('../temp_dir'), timer, processKillTimeout) } }