Using Gulp to manage opening and closing MongoDB - node.js

So far I have a child_process that executes 'mongod --dbpath db' and another child_process which can kill it with 'mongod --dbpath db --shutdown'. How do I listen for the user to enter ctrl-c or exit the gulp runner, and then run the gulp task to shutdown mongo?

I was trying something similar and came across this answer. I refactored it a little to just be the run command function. Functionally there should be no difference between --shutdown and the command I'm using.
var gulp = require('gulp');
var exec = require('child_process').exec;
function runCommand(command) {
return function (cb) {
exec(command, function (err, stdout, stderr) {
console.log(stdout);
console.log(stderr);
cb(err);
});
}
}
//Running mongo
//https://stackoverflow.com/a/28048696/46810
gulp.task('start-mongo', runCommand('mongod --dbpath ./data/'));
gulp.task('stop-mongo', runCommand('mongo --eval "use admin; db.shutdownServer();"'));
gulp.task('start-app', runCommand('node app.js'));

#QueueHammer's response was very helpful, but to get this running for my particulars (OSX, MongoDB 3.0.1) it took the following:
var exec = require('child_process').exec;
var mkdirs = require('mkdirs');
var runCommand = function(command) {
exec(command, function (err, stdout, stderr) {
console.log(stdout);
console.log(stderr);
if (err !== null) {
console.log('exec error: ' + err);
}
});
}
gulp.task("mongo-start", function() {
var command = "mongod --fork --dbpath "+paths.dbDir+"/ --logpath "+paths.dbLogs+"/mongo.log";
mkdirs(paths.dbDir);
mkdirs(paths.dbLogs);
runCommand(command);
});
gulp.task("mongo-stop", function() {
var command = 'mongo admin --eval "db.shutdownServer();"'
runCommand(command);
});

To further add on to the above answers, if you'd like a platform-independent solution that works in any OS/environment. You can use docker.
So you're gulp task would be something like:
const Gulp = require('gulp');
const exec = require('child_process').exec;
function runCommand(command) {
return function (cb) {
exec(command, function (err, stdout, stderr) {
console.log(stdout);
console.log(stderr);
cb(err);
});
};
}
// Database tasks
Gulp.task('start-mongo', runCommand('docker run --rm --name mongo-dev -p 27017:27017 mongo'));
Gulp.task('start-mongo-viewer', runCommand('docker run --rm --name mongo-express-dev --link mongo-dev:mongo -p 8081:8081 mongo-express'));

Related

How to handle mysql command-line password prompt using exec function

I don't know how id pipe the password variable in the exec function.
I've tried running it, but no prompt appears.
const {user,password,database} = require('./config.js');
const { exec } = require('child_process');
const comm = `mysql -u ${user} -p ${database} < ${QUERY_PATH} `
exec(comm)
I guess the only part missing is to use the callback, as recommended by Node in https://nodejs.org/api/child_process.html#child_process_child_process_exec_command_options_callback .
Replace:
exec(comm)
by:
exec(comm, (error, stdout, stderr) => {
console.log(stdout);
})
This way, you need to type the password manually. If you don't want to type the password manually (not recommended, mySQL warns about safety concerns using this second method), then the code would be:
const comm = `mysql -u${user} -p${password} ${database} < ${QUERY_PATH}`
If you want to check what is the error happening to you, and that's how I debugged, use the callback function to log the errors:
exec(comm, (error, stdout, stderr) => {
if (error) {
console.error(`exec error: ${error}`);
return;
}
console.log(`stdout: ${stdout}`);
console.error(`stderr: ${stderr}`);
});

Run Bash-Script within Electron App using child_process.exec

I'm struggling with running a bash-script within main.html.
const exec = require("child_process").exec;
// Execute bash script
exec("/c/workspace/_edu_zone/Proxy_Manager/filemover.sh", shellCallback);
// Callback
function shellCallback(error, stdout, stderr) {
console.log(error, stdout)
}
I'm always getting the error: no such file or directory. What am i doing wrong?
Any help is highly appreciated.
change
/c/workspace/_edu_zone/Proxy_Manager/filemover.sh
to
c:/workspace/_edu_zone/Proxy_Manager/filemover.sh
or
your could try using node-powershell to execute the command directly
const shell = require('node-powershell')
let ps = new shell({
executionPolicy: 'Bypass',
noProfile: true
});
function lunchnode() {
process.stdout.write('logging');
ps.addCommand('node run.js')
ps.invoke()
.then(function (output) {
process.stdout.write(output)
}).catch(function (err) {
process.stdout.write(err)
ps.dispose()
})
}

nodejs child_process spawn command input file

I would like to run the following code in nodejs
$ ./a.out < inputfile.txt
So I wrote the following code.
var run = spawn('./a.out', ['< input.txt']);
var run = spawn('./a.out < input.txt');
I tried this, but it did not work.
What I want to do is to input input.txt ina.out
how can i do?
Since < (redirection) is a shell construct, you need to run your command line with a shell. That's what child_process.exec() is for:
const exec = require('child_process').exec;
exec('./a.out < inputfile.txt', function(err, stdout, stderr) {
if (err) {
return console.error('exec error:', err);
}
console.log('stdout:', stdout);
console.log('stderr:', stderr);
});

NodeJS exec() command for both Windows and Ubuntu

Using NodeJS, NPM, and Gulp.
I want to build a gulp task to run JSDoc that works on Ubuntu and Windows.
This works on Ubuntu...
var exec = require('child_process').exec;
return function(cb) {
exec('node node_modules/.bin/jsdoc -c jsdoc-conf.json', function(err, stdout, stderr) {
cb(err);
});
};
And this works on Windows...
var exec = require('child_process').exec;
return function(cb) {
exec('node_modules\\.bin\\jsdoc -c jsdoc-conf.json', function(err, stdout, stderr) {
cb(err);
});
};
Needless to say, neither works on the other. How do others solve this type of problem?
Try using path.resolve, which should provide you with a full path to the file regardless of the platform.
Node has process.platform, which... "returns a string identifying the operating system platform on which the Node.js process is running. For instance darwin, freebsd, linux, sunos or win32"
https://nodejs.org/api/process.html#process_process_platform
var exec = require('child_process').exec;
return function(cb) {
if (process.platform === 'win32') {
// Windows OS
} else {
// everything else
}
};
Using path.resolve:
const exec = require('child_process').exec;
const path = require('path');
return function(cb) {
let command = `node ${path.resolve('node_modules/.bin/jsdoc')} -c jsdoc-conf.json`;
exec(command, function(err, stdout, stderr) {
cb(err);
});
};

I want to run npm install and grunt in the background

So I have code in node, I want to run npm install and grunt in the background. npm install should run before grunt runs. Both both should run in the asynchronously. How can I get this done using node?
Shelling out the commands from within node, it will look like this:
const exec = require('child_process').exec;
exec('npm install && grunt', (err, stdout, stderr) => {
if (err) {
console.error(err);
return;
}
console.log(stdout);
});
If you want to run both as described, in the background from you shell just run
npm install && grunt &
To write the output to a file, you could do
const exec = require('child_process').exec;
exec('npm install && grunt', (err, stdout, stderr) => {
fs.writeFile('outputOfNpmInstallPlusGrunt.txt', stdout, () => { ... })
}
Conversely, using spawn this would look something like:
const spawn = require('child_process').spawn;
function makeRunner(name, cb) {
var ls = spawn(name, []);
var output = '';
ls.stdout.on('data', (data) => { output += data; });
ls.on('close', (code) => {
fs.writeFile(name.split(' ').join('-'), output, cb);
});
}
makeRunner('npm install', () => makeRunner('grunt'));

Resources