Using Node's child_process
module, I'd like to execute commands via the cygwin shell. This is what I'm trying:
var exec = require('child_process').execSync;
exec('mkdir -p a/b/c', {shell : 'c:/cygwin64/bin/bash.exe -c'});
TypeError: invalid data at WriteStream.Socket.write (net.js:641:11) at execSync (child_process.js:503:20) at repl:1:1 at REPLServer.defaultEval (repl.js:262:27) at bound (domain.js:287:14) at REPLServer.runBound [as eval] (domain.js:300:12) at REPLServer. (repl.js:431:12) at emitOne (events.js:82:20) at REPLServer.emit (events.js:169:7) at REPLServer.Interface._onLine (readline.js:212:10)
I can see Node's child_process.js will add the /s
and /c
switches, regardless of the shell
option being set, bash.exe doesn't know what to do with these arguments.
I found a work around for this problem but it's really not ideal:
exec('c:/cygwin64/bin/bash.exe -c "mkdir -p a/b/c"');
Doing the above would obviously only work on Windows not unix systems.
How can I execute commands in the cygwin shell from NodeJS?
This is not a complete generic solution, because more would need to be done with some of the options of exec()
, but this should allow you to write code that will work on unixes, Windows and cygwin, differentiating between the later two.
This solution assumes that Cygwin is installed in a directory which name includes the string cygwin
.
var child_process = require( 'child_process' )
, home = process.env.HOME
;
function exec( command, options, next ) {
if( /cygwin/.test( home ) ) {
command = home.replace( /(cygwin[0-9]*).*/, "$1" ) + "\\bin\\bash.exe -c '" + command.replace( /\\/g, '/' ).replace( /'/g, "\'" ) + "'";
}
child_process.exec( command, options, next );
}
You could alternatively hijack child_process.exec conditionally when running under Cygwin:
var child_process = require( 'child_process' )
, home = process.env.HOME
;
if( /cygwin/.test( home ) ) {
var child_process_exec = child_process.exec
, bash = home.replace( /(cygwin[0-9]*).*/, "$1" ) + "\\bin\\bash.exe"
;
child_process.exec = function( command, options, next ) {
command = bash + " -c '" + command.replace( /\\/g, '/' ).replace( /'/g, "\'" ) + "'";
child_process_exec( command, options, next )
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With