-
-
Notifications
You must be signed in to change notification settings - Fork 105
Add --shell-auto-fallback #7
Changes from 1 commit
a7402dc
3c142b4
2a1d85a
d170146
81fe5a4
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
Generates shell code that hooks into the "command not found" mechanism and attempts to run the command with npx instead of failing. The option has an optional argument that forces generation of a particular variant, otherwise it attempts to autodetect the shell. However, autodetecting is actually very flaky, so it's better to always specify the argument. To use, place this in relevant shell config file: For Bash: source <(npx --shell-auto-fallback bash) For Zsh: source <(npx --shell-auto-fallback zsh) For Fish: source (npx --shell-auto-fallback fish | psub) As Seen On Twitter: https://twitter.com/passcod/status/869469928474107906
- Loading branch information
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,46 @@ | ||
'use strict' | ||
|
||
const POSIX = ` | ||
command_not_found_handler() { | ||
# Do not run within a pipe | ||
if test ! -t 1; then | ||
echo "command not found: $1" | ||
return 127 | ||
fi | ||
|
||
echo "Trying with npx..." | ||
npx $* | ||
return $? | ||
}` | ||
|
||
const FISH = ` | ||
function __fish_command_not_found_on_interactive --on-event fish_prompt | ||
functions --erase __fish_command_not_found_handler | ||
functions --erase __fish_command_not_found_setup | ||
|
||
function __fish_command_not_found_handler --on-event fish_command_not_found | ||
echo "Trying with npx..." | ||
npx $argv | ||
end | ||
|
||
functions --erase __fish_command_not_found_on_interactive | ||
end` | ||
|
||
module.exports = function autoFallback (shell) { | ||
const { BASH_VERSION, SHELL, ZSH_VERSION } = process.env | ||
|
||
if (shell === 'bash' || BASH_VERSION || /bash/.test(SHELL)) { | ||
return POSIX.replace('handler()', 'handle()') | ||
} | ||
|
||
if (shell === 'zsh' || ZSH_VERSION || /zsh/.test(SHELL)) { | ||
return POSIX | ||
} | ||
|
||
if (shell === 'fish' || /fish/.test(SHELL)) { | ||
return FISH | ||
} | ||
|
||
console.error('Only Bash, Zsh, and Fish shells are supported :(') | ||
process.exit(1) | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -3,6 +3,7 @@ | |
|
||
const BB = require('bluebird') | ||
|
||
const autoFallback = require('./auto-fallback.js') | ||
const cp = require('child_process') | ||
const getPrefix = require('./get-prefix.js') | ||
const parseArgs = require('./parse-args.js') | ||
|
@@ -18,6 +19,12 @@ updateNotifier({pkg}).notify() | |
main(parseArgs()) | ||
|
||
function main (argv) { | ||
const shell = argv['shell-auto-fallback'] | ||
if (shell || shell === '') { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. won't this always be true? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more.
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. doesn't having a default mean that you always get |
||
console.log(autoFallback(shell)) | ||
process.exit(0) | ||
} | ||
|
||
if (!argv.command || !argv.package) { | ||
console.error('\nERROR: You must supply a command.\n') | ||
yargs.showHelp() | ||
|
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -62,6 +62,14 @@ function parseArgs () { | |
type: 'string', | ||
describe: 'execute string as if inside `npm run-script`' | ||
}) | ||
.option('shell-auto-fallback', { | ||
choices: ['', 'bash', 'fish', 'zsh'], | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Why There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I'll re-test, but I think yargs refused to parse the option if the default wasn't in the choices. Although. Given the difficulty of figuring out the shell from a subprocess, maybe I should just remove both the autodetecting code and the default value here, and just do it based on the passed value. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Just don't give it a default? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. As to why I made the default |
||
describe: 'generate shell code to use npx as the "command not found" fallback', | ||
default: '', | ||
defaultDescription: 'detect', | ||
requiresArg: false, | ||
type: 'string' | ||
}) | ||
.version() | ||
.alias('version', 'v') | ||
|
||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We're restricted to
node@4
or latest, so was can't do destructuring assignment 😭