Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Original browser map refactor #16

Closed
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 0 additions & 1 deletion .jscsrc
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,6 @@
"mark": "'",
"escape": true
},
"validateIndentation": "\t",
"disallowMixedSpacesAndTabs": true,
"disallowTrailingWhitespace": true,
"disallowKeywordsOnNewLine": [ "else", "catch" ],
Expand Down
3 changes: 2 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
## Upcoming Release

#### Breaking changes
- None yet
- Type `phantom` is now `phantomjs`, which is a little more consistent
- The property "name" is more descriptive for variant channels, e.g. "chrome-canary"

#### User features
- None yet
Expand Down
6 changes: 3 additions & 3 deletions index.js
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
var path = require( 'path' ),
_ = require( 'lodash' ),
configModule = require( './lib/config' ),
detect = require( './lib/detect' ),
run = require( './lib/run' ),
pick = require('lodash/pick'),
createProfiles = require( './lib/create_profiles' );

/**
Expand Down Expand Up @@ -75,14 +75,14 @@ function getLauncher( configFile, callback ) {
getLauncher.detect = function( callback ) {
detect( function( browsers ) {
callback( browsers.map( function( browser ) {
return _.pick( browser, [ 'name', 'version', 'type', 'command' ] );
return pick( browser, [ 'name', 'version', 'type', 'command' ] );
} ) );
} );
};

/**
* Update the browsers cache and create new profiles if necessary
* @param {String} configDir Path to the configuration file
* @param {String} configFile Path to the configuration file
* @param {Function} callback Callback function
*/
getLauncher.update = function( configFile, callback ) {
Expand Down
File renamed without changes.
2 changes: 1 addition & 1 deletion lib/darwin/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,6 @@ exports.safari = require( './safari' );
exports.firefox = require( './firefox' );
exports.chrome = exports[ 'google-chrome' ] = require( './chrome' );
exports.chromium = require( './chromium' );
exports.canary = exports[ 'chrome-canary' ] = exports[ 'google-chrome-canary' ] = require( './canary' );
exports['chrome-canary'] = require( './chrome-canary' );
exports.opera = require( './opera' );
exports.phantomjs = require( './phantomjs' );
191 changes: 107 additions & 84 deletions lib/detect.js
Original file line number Diff line number Diff line change
@@ -1,68 +1,90 @@
var spawn = require( 'child_process' ).spawn,
winDetect = require( 'win-detect-browsers' ),
darwin = require( './darwin' ),
extend = require( 'lodash' ).extend,
browsers = {
'google-chrome': {
name: 'chrome',
re: /Google Chrome (\S+)/,
type: 'chrome',
profile: true
},
'google-chrome-canary': {
name: 'canary',
re: /Google Chrome (\S+)/,
type: 'chrome',
profile: true
},
'chromium': {
name: 'chromium',
re: /Chromium (\S+)/,
type: 'chrome',
profile: true
assign = require('lodash/assign'),
omit = require('lodash/omit'),
flatten = require('lodash/flatten'),
isEqual = require('lodash/isEqual'),
uniqWith = require('lodash/uniqWith');
browsers = { // List of commands and version regex for Linux and Mac
chrome: {
regex: /Google Chrome (\S+)/,
profile: true,
variants: {
'chrome': [ 'google-chrome', 'google-chrome-stable' ],
'chrome-beta': 'google-chrome-beta',
'chrome-canary': 'google-chrome-canary'
}
},
'chromium-browser': {
name: 'chromium',
re: /Chromium (\S+)/,
type: 'chrome',
profile: true
chromium: {
regex: /Chromium (\S+)/,
profile: true,
variants: {
'chromium': [ 'chromium', 'chromium-browser' ]
}
},
'firefox': {
name: 'firefox',
re: /Mozilla Firefox (\S+)/,
type: 'firefox',
profile: true
firefox: {
regex: /Mozilla Firefox (\S+)/,
profile: true,
variants: {
'firefox': 'firefox',
'firefox-developer': 'firefox-developer'
}
},
'phantomjs': {
name: 'phantomjs',
re: /(\S+)/,
type: 'phantom',
phantomjs: {
regex: /(\S+)/,
profile: false,
headless: true,
profile: false
variants: 'phantomjs'
},
'safari': {
name: 'safari',
type: 'safari',
profile: false
safari: {
profile: false,
variants: 'safari'
},
'ie': {
name: 'ie',
type: 'ie',
profile: false
ie: {
profile: false,
variants: 'ie'
},
'opera': {
name: 'opera',
re: /Opera (\S+)/,
type: 'opera',
image: 'opera.exe',
profile: true
opera: {
regex: /Opera (\S+)/,
profile: true,
variants: 'opera'
}
},
winDetectMap = {
chrome: 'google-chrome',
chromium: 'chromium-browser'
};

function getVariants(type) {
var browser = browsers[type],
variants = [];

function addVariant(name, type, command) {
variants.push(assign({
name: name,
type: type,
command: command
}, omit(browser, 'variants')));
}

if (typeof browser.variants === 'string') {

// For browsers like "phantomjs", where its only variant is the command `phantomjs`
addVariant(type, type, browser.variants);
} else {
Object.keys(browser.variants).forEach(function(name) {

// For things like "chrome", where there's "chrome", "chrome-beta", and "chrome-canary", which are all "Chromes"
if (typeof browser.variants[name] === 'string') {
addVariant(name, type, browser.variants[name]);
return;
}

// For when a variant can be launched with different commands, like `chromium` or `chromium-browser`
browser.variants[name].forEach(addVariant.bind(undefined, name, type));
});
}

return variants;
}

/**
* Detect all available browsers on Windows systems.
* Pass an array of detected browsers to the callback function when done.
Expand All @@ -71,13 +93,12 @@ var spawn = require( 'child_process' ).spawn,
function detectWindows( callback ) {
winDetect( function( found ) {
var available = found.map( function( browser ) {
var br = browsers[ winDetectMap[ browser.name ] || browser.name ];

return extend( {}, {
return {
name: browser.name,
type: browser.name,
command: browser.path,
version: browser.version
}, br || {} );
};
} );

callback( available );
Expand All @@ -87,10 +108,12 @@ function detectWindows( callback ) {
/**
* Check if the given browser is available (on OSX systems).
* Pass its version and path to the callback function if found.
* @param {String} name Name of a browser
* @param {Object} variant browser variant
* @param {Function} callback Callback function
*/
function checkDarwin( name, callback ) {
function checkDarwin( variant, callback ) {
var name = variant.name;

if ( darwin[ name ] ) {
if ( darwin[ name ].all ) {
darwin[ name ].all( function( err, available ) {
Expand All @@ -116,19 +139,18 @@ function checkDarwin( name, callback ) {
} );
}
} else {
checkOthers( name, callback );
checkOthers( variant, callback );
}
}

/**
* Check if the given browser is available (on Unix systems).
* Pass its version to the callback function if found.
* @param {String} name Name of a browser
* @param {Function} callback Callback function
* @param {Object} variant browser variant
* @param {Function} callback callback function
*/
function checkOthers( name, callback ) {
var process = spawn( name, [ '--version' ] ),
re = browsers[ name ].re,
function checkOthers( variant, callback ) {
var process = spawn( variant.command, [ '--version' ] ),
data = '';

process.stdout.on( 'data', function( buf ) {
Expand All @@ -149,10 +171,10 @@ function checkOthers( name, callback ) {
return callback( 'not installed' );
}

var m = re.exec( data );
var match = variant.regex.exec( data );

if ( m ) {
callback( null, m[ 1 ] );
if ( match ) {
callback( null, match[ 1 ] );
} else {
callback( null, data.trim() );
}
Expand All @@ -166,7 +188,7 @@ function checkOthers( name, callback ) {
*/
module.exports = function detect( callback ) {
var available = [],
names,
browserVariants,
check;

if ( process.platform === 'win32' ) {
Expand All @@ -177,37 +199,38 @@ module.exports = function detect( callback ) {
check = checkOthers;
}

names = Object.keys( browsers );

browserVariants = flatten(Object.keys( browsers ).map( getVariants ));

function next() {
var name = names.shift();
var variant = browserVariants.shift();

if ( !name ) {
return callback( available );
if ( !variant ) {
return callback(uniqWith(available, isEqual));
}

var br = browsers[ name ];

check( name, function( err, v, p ) {
check(variant, function( err, version, path ) {
if ( err === null ) {
if ( Array.isArray( v ) ) {
v.forEach( function( item ) {
available.push( extend( {}, br, {
if ( Array.isArray( version ) ) {
version.forEach( function( item ) {
available.push( assign({
command: item.path,
version: item.version
} ) );
}, variant ));
} );
} else {
available.push( extend( {}, br, {
command: p || name,
version: v
} ) );
available.push(assign({
version: version,
command: path || variant.command
}, variant));
}
}

next();
} );
});
}

next();
};

module.exports.variants = getVariants;
Loading