-
-
Notifications
You must be signed in to change notification settings - Fork 1.5k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(docz-core): auto open browser when start dev mode (#774)
* feat(docz-core): auto open browser when start dev mode * fix(docz-core): optional open browser when starting dev
- Loading branch information
1 parent
c96878d
commit c0e6c13
Showing
3 changed files
with
135 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,127 @@ | ||
/* tslint:disable */ | ||
/** | ||
* Copyright (c) 2015-present, Facebook, Inc. | ||
* | ||
* This source code is licensed under the MIT license found in the | ||
* LICENSE file in the root directory of this source tree. | ||
*/ | ||
|
||
'use strict' | ||
|
||
var chalk = require('chalk') | ||
var execSync = require('child_process').execSync | ||
var spawn = require('cross-spawn') | ||
var opn = require('opn') | ||
|
||
// https://github.com/sindresorhus/opn#app | ||
var OSX_CHROME = 'google chrome' | ||
|
||
const Actions = Object.freeze({ | ||
NONE: 0, | ||
BROWSER: 1, | ||
SCRIPT: 2, | ||
}) | ||
|
||
function getBrowserEnv() { | ||
// Attempt to honor this environment variable. | ||
// It is specific to the operating system. | ||
// See https://github.com/sindresorhus/opn#app for documentation. | ||
const value = process.env.BROWSER | ||
let action | ||
if (!value) { | ||
// Default. | ||
action = Actions.BROWSER | ||
} else if (value.toLowerCase().endsWith('.js')) { | ||
action = Actions.SCRIPT | ||
} else if (value.toLowerCase() === 'none') { | ||
action = Actions.NONE | ||
} else { | ||
action = Actions.BROWSER | ||
} | ||
return { action, value } | ||
} | ||
|
||
function executeNodeScript(scriptPath: any, url: any) { | ||
const extraArgs = process.argv.slice(2) | ||
const child = spawn('node', [scriptPath, ...extraArgs, url], { | ||
stdio: 'inherit', | ||
}) | ||
child.on('close', (code: any) => { | ||
if (code !== 0) { | ||
console.log() | ||
console.log( | ||
chalk.red( | ||
'The script specified as BROWSER environment variable failed.' | ||
) | ||
) | ||
console.log(chalk.cyan(scriptPath) + ' exited with code ' + code + '.') | ||
console.log() | ||
return | ||
} | ||
}) | ||
return true | ||
} | ||
|
||
function startBrowserProcess(browser: any, url: any) { | ||
// If we're on OS X, the user hasn't specifically | ||
// requested a different browser, we can try opening | ||
// Chrome with AppleScript. This lets us reuse an | ||
// existing tab when possible instead of creating a new one. | ||
const shouldTryOpenChromeWithAppleScript = | ||
process.platform === 'darwin' && | ||
(typeof browser !== 'string' || browser === OSX_CHROME) | ||
|
||
if (shouldTryOpenChromeWithAppleScript) { | ||
try { | ||
// Try our best to reuse existing tab | ||
// on OS X Google Chrome with AppleScript | ||
execSync('ps cax | grep "Google Chrome"') | ||
execSync('osascript openChrome.applescript "' + encodeURI(url) + '"', { | ||
cwd: __dirname, | ||
stdio: 'ignore', | ||
}) | ||
return true | ||
} catch (err) { | ||
// Ignore errors. | ||
} | ||
} | ||
|
||
// Another special case: on OS X, check if BROWSER has been set to "open". | ||
// In this case, instead of passing `open` to `opn` (which won't work), | ||
// just ignore it (thus ensuring the intended behavior, i.e. opening the system browser): | ||
// https://github.com/facebook/create-react-app/pull/1690#issuecomment-283518768 | ||
if (process.platform === 'darwin' && browser === 'open') { | ||
browser = undefined | ||
} | ||
|
||
// Fallback to opn | ||
// (It will always open new tab) | ||
try { | ||
var options = { app: browser, wait: false } | ||
opn(url, options).catch(() => {}) // Prevent `unhandledRejection` error. | ||
return true | ||
} catch (err) { | ||
return false | ||
} | ||
} | ||
|
||
/** | ||
* Reads the BROWSER environment variable and decides what to do with it. Returns | ||
* true if it opened a browser or ran a node.js script, otherwise false. | ||
*/ | ||
export function openBrowser(url: any) { | ||
const { action, value } = getBrowserEnv() | ||
switch (action) { | ||
case Actions.NONE: | ||
// Special case: BROWSER="none" will prevent opening completely. | ||
return false | ||
case Actions.SCRIPT: | ||
return executeNodeScript(value, url) | ||
case Actions.BROWSER: | ||
return startBrowserProcess(value, url) | ||
default: | ||
throw new Error('Not implemented.') | ||
} | ||
} | ||
|
||
// module.exports = openBrowser |