在Yeoman生成器完成后,同步执行命令行操作
我正在构build一个Yeoman生成器,完成之后我想执行一些命令行操作,如'npm install','bower install'和'grunt less'。 我使用spawnCommand为此,我嵌套使用事件侦听器的所有操作,以同步执行它们。 但是,为了避免这种无休止的嵌套,我正在寻找一个更清洁的实现,使其易于扩展。 完美的,我想有一个命令的数组(如['npm install','grunt install','less:dev']),并通过正确的错误检测同步处理。
// Install npm packages this.spawnCommand('npm', ['install']) .on('exit', function (err) { if (err) { this.log.error('npm package installation failed. Please run \'npm install\' and \'bower install\'. Error: ' + err); } else { // Install bower packages this.spawnCommand('bower', ['install']) .on('exit', function (err) { if (err) { this.log.error('bower package installation failed. Please run \'bower install\'. Error: ' + err); } else { this.spawnCommand('grunt', ['less']) .on('exit', function (err) { if (err) { this.log.error('Less compilation failed. Please run \'grunt less:dev\'. Error: ' + err); } else { } }.bind(this)); } }.bind(this)); } }.bind(this));
像这样的东西? (未经testing):
this.processTask = function (task) { this.spawnCommand(task.cmd, task.args) .on('exit', function (err) { if (err) { this.log.error('task failed. Error: ' + err); } else { this.emit('nextTask'); } }); }; this.on('nextTask' function(){ var next = this.tasks.shift(); if (next){ this.processTask(next); } else { console.log('we are done'); } }.bind(this)); //preparing the list of tasks: this.tasks = []; this.tasks.push({cmd: 'npm', args:['install']}); this.tasks.push({cmd: 'bower', args:['install']}); this.tasks.push({cmd: 'grunt', args:['less']}); //start first task this.processTask(this.tasks.shift());
我使用从Node.js的execSync似乎工作,例如:
var child_process = require('child_process'); var result = execSync('grunt less');
Node.js 0.12和io.js 1.10支持execSync:
child_process.execSync(command[, options])
并返回“Buffer | String来自命令的stdout”,这可能是一个错误代码。 API文档。
关于同步API的背后故事 。
你可以创build一个像init.sh
这样的脚本,并将你需要按顺序运行的命令放在里面,如:
#!/usr/bin/env bash npm install your-funky-command gulp something-special gulp
…然后无论你需要把spawnCommand
代码(我在end
方法中),添加somehting像这样:
var done = this.async(); this.spawnCommand('sh', ['init.sh'], /* maybe cwd? {cwd: 'src'} */) .on('close', done);
不漂亮或者什么都行,但是很明显。
或者,如果您需要一个命令只在prev成功时运行,请执行以下操作:
#!/usr/bin/env bash npm install \ && your-funky-command \ && gulp something-special \ && gulp
(奖金的好处是,现在你的应用程序初始化逻辑不再与哟。)