diff --git a/.travis.yml b/.travis.yml index 8a9a661f7f..56346bd3b5 100644 --- a/.travis.yml +++ b/.travis.yml @@ -3,8 +3,6 @@ before_install: - "npm install -g npm && npm install" before_script: - - "./build.py serve &" - "rm src/ol/renderer/webgl/*shader.js" - - "sleep 3" script: "./build.py ci" diff --git a/build.py b/build.py index 1872fdd0cd..cf7ff7a6b7 100755 --- a/build.py +++ b/build.py @@ -690,8 +690,7 @@ def proj4js_zip(t): @target('test', PROJ4JS, phony=True) def test(t): - t.run('%(PHANTOMJS)s', 'test/mocha-phantomjs.js', - 'http://localhost:3000/test/index.html') + t.run('node', 'tasks/test.js') @target('fixme', phony=True) diff --git a/package.json b/package.json index da8a8b18b7..a1c8336ac3 100644 --- a/package.json +++ b/package.json @@ -4,7 +4,8 @@ "description": "Mapping library", "scripts": { "postinstall": "node tasks/parse-examples.js", - "start": "node tasks/serve.js" + "start": "node tasks/serve.js", + "test": "node tasks/test.js" }, "repository": { "type": "git", diff --git a/tasks/readme.md b/tasks/readme.md index 2e6dcb99f9..5b1b902bdf 100644 --- a/tasks/readme.md +++ b/tasks/readme.md @@ -104,3 +104,8 @@ Called after install to generate an example index. After new examples are added Run a debug server that provides all library sources unminified. Provides a static server for examples and tests. See the `--help` option for more detail. node tasks/serve.js --help + + +## `test.js` + +Run the tests once in a headless browser. Note that you can also run the tests by running the `serve.js` task and then visiting the root of the test directory in your browser. diff --git a/tasks/serve.js b/tasks/serve.js index 23118a5959..219ce69a5f 100644 --- a/tasks/serve.js +++ b/tasks/serve.js @@ -12,62 +12,88 @@ var nomnom = require('nomnom'); var log = closure.log; -var options = nomnom.options({ - port: { - abbr: 'p', - default: 3000, - help: 'Port for incoming connections', - metavar: 'PORT' - }, - loglevel: { - abbr: 'l', - choices: ['silly', 'verbose', 'info', 'warn', 'error'], - default: 'info', - help: 'Log level', - metavar: 'LEVEL' - } -}).parse(); - -/** @type {string} */ -log.level = options.loglevel; - -log.info('ol', 'Parsing dependencies ...'); -var manager = new closure.Manager({ - closure: true, // use the bundled Closure Library - lib: [ - 'src/**/*.js', - 'test/spec/**/*.test.js' - ], - main: 'examples/*.js' -}); -manager.on('error', function(e) { - log.error('ol', e.message); -}); -manager.on('ready', function() { - var server = new closure.Server({ - manager: manager, - loader: /^\/\w+\/loader.js/, - getMain: function(req) { - var main; - var query = url.parse(req.url, true).query; - if (query.id) { - var referer = req.headers.referer; - if (referer) { - var from = path.join(process.cwd(), - path.dirname(url.parse(referer).pathname)); - main = path.resolve(from, query.id + '.js'); - } - } - return main; +/** + * Create a debug server for ol and Closure Library sources. + * @param {function(Error, closure.Server)} callback Callback. + */ +var createServer = exports.createServer = function(callback) { + var server; + var manager = new closure.Manager({ + lib: [ + 'src/**/*.js', + 'test/spec/**/*.test.js' + ], + main: 'examples/*.js' + }); + manager.on('error', function(err) { + if (server) { + log.error('serve', err.message); + } else { + callback(err); } }); - server.listen(options.port, function() { - log.info('ol', 'Listening on http://localhost:' + - options.port + '/ (Ctrl+C to stop)'); + manager.on('ready', function() { + server = new closure.Server({ + manager: manager, + loader: /^\/\w+\/loader.js/, + getMain: function(req) { + var main; + var query = url.parse(req.url, true).query; + if (query.id) { + var referer = req.headers.referer; + if (referer) { + var from = path.join(process.cwd(), + path.dirname(url.parse(referer).pathname)); + main = path.resolve(from, query.id + '.js'); + } + } + return main; + } + }); + callback(null, server); }); - server.on('error', function(err) { - log.error('ol', 'Server failed to start: ' + err.message); - process.exit(1); +}; + + +/** + * If running this module directly start the server. + */ +if (require.main === module) { + var options = nomnom.options({ + port: { + abbr: 'p', + default: 3000, + help: 'Port for incoming connections', + metavar: 'PORT' + }, + loglevel: { + abbr: 'l', + choices: ['silly', 'verbose', 'info', 'warn', 'error'], + default: 'info', + help: 'Log level', + metavar: 'LEVEL' + } + }).parse(); + + /** @type {string} */ + log.level = options.loglevel; + + log.info('serve', 'Parsing dependencies ...'); + createServer(function(err, server) { + if (err) { + log.error('serve', 'Parsing failed'); + log.error('serve', err.message); + process.exit(1); + } + server.listen(options.port, function() { + log.info('serve', 'Listening on http://localhost:' + + options.port + '/ (Ctrl+C to stop)'); + }); + server.on('error', function(err) { + log.error('serve', 'Server failed to start: ' + err.message); + process.exit(1); + }); + }); -}); +} diff --git a/tasks/test.js b/tasks/test.js new file mode 100644 index 0000000000..f082b468a5 --- /dev/null +++ b/tasks/test.js @@ -0,0 +1,68 @@ +/** + * This task starts a dev server that provides a script loader for OpenLayers + * and Closure Library and runs tests in PhantomJS. + */ + +var path = require('path'); +var spawn = require('child_process').spawn; + +var phantomjs = require('phantomjs'); + +var serve = require('./serve'); + +/** + * Try listening for incoming connections on a range of ports. + * @param {number} min Minimum port to try. + * @param {number} max Maximum port to try. + * @param {http.Server} server The server. + * @param {function(Error)} callback Callback called with any error. + */ +function listen(min, max, server, callback) { + function _listen(port) { + server.once('error', function(err) { + if (err.code === 'EADDRINUSE') { + ++port; + if (port < max) { + _listen(port); + } else { + callback(new Error('Could not find an open port')); + } + } else { + callback(err); + } + }); + server.listen(port, callback); + } + _listen(min); +} + + +/** + * Create the debug server and run tests. + */ +serve.createServer(function(err, server) { + if (err) { + console.error(err.message); + process.exit(1); + } + + listen(3001, 3005, server, function(err) { + if (err) { + console.error('Server failed to start: ' + err.message); + process.exit(1); + } + + var address = server.address(); + var url = 'http://' + address.address + ':' + address.port; + var args = [ + path.join(__dirname, '..', 'test', 'mocha-phantomjs.js'), + url + '/test/index.html' + ]; + + var child = spawn(phantomjs.path, args, {stdio: 'inherit'}); + child.on('exit', function(code) { + process.exit(code); + }); + }); + +});