javascript - node - ¿Cómo ejecutar una tarea Grunt después de que mi generador Yeoman finalice la instalación?
yo angular (3)
Estoy creando un generador Yeoman personalizado que instala muchos compiladores de lenguaje preprocesados como CoffeeScript, LESS y Jade. En el archivo Gruntfile que crea mi generador, tengo una tarea de compilación que compila todo. Sin embargo, hasta que la tarea de compilación se ejecute al menos una vez, los archivos HTML, CSS y Javascript compilados no existen, lo que puede resultar confuso si trato de ejecutar el servidor Grunt Watch / Connect después de un nuevo andamio.
¿Cuál es la mejor manera de hacer que mi generador ejecute el paso de compilación Grunt al final de la instalación? El evento end
que ya se está utilizando para llamar a esto. this.installDependencies
parece ser el lugar correcto para hacerlo, pero ¿cómo debo comunicarme con Grunt?
Esta pregunta ya es un poco antigua, pero aún quiero hacer esta adición si alguien la omite. Los procesos posteriores a la instalación son ahora mucho más fáciles de implementar. Eche un vistazo al bucle de ejecución y use el método end
donde puede ejecutar todas las cosas posteriores a la instalación.
He usado la gran respuesta de Stephen, implementada de la siguiente manera con un evento personalizado para mantener las cosas ordenadas.
MyGenerator = module.exports = function MyGenerator(args, options, config) {
this.on(''end'', function () {
this.installDependencies({
skipInstall: options[''skip-install''],
callback: function() {
// Emit a new event - dependencies installed
this.emit(''dependenciesInstalled'');
}.bind(this)
});
});
// Now you can bind to the dependencies installed event
this.on(''dependenciesInstalled'', function() {
this.spawnCommand(''grunt'', [''build'']);
});
};
Si sigues la pila, this.installDependencies
eventualmente se this.installDependencies
paso hasta https://github.com/yeoman/generator/blob/45258c0a48edfb917ecf915e842b091a26d17f3e/lib/actions/install.js#L36 :
this.spawnCommand(installer, args, cb)
.on(''error'', cb)
.on(''exit'', this.emit.bind(this, installer + ''Install:end'', paths))
.on(''exit'', function (err) {
if (err === 127) {
this.log.error(''Could not find '' + installer + ''. Please install with '' +
''`npm install -g '' + installer + ''`.'');
}
cb(err);
}.bind(this));
Persiguiendo esto, this.spawnCommand
proviene de https://github.com/yeoman/generator/blob/master/lib/actions/spawn_command.js :
var spawn = require(''child_process'').spawn;
var win32 = process.platform === ''win32'';
/**
* Normalize a command across OS and spawn it.
*
* @param {String} command
* @param {Array} args
*/
module.exports = function spawnCommand(command, args) {
var winCommand = win32 ? ''cmd'' : command;
var winArgs = win32 ? [''/c''].concat(command, args) : args;
return spawn(winCommand, winArgs, { stdio: ''inherit'' });
};
En otras palabras, en el código de su Generador, puede llamar a this.spawnCommand
cualquier momento, y pasarle los argumentos que desea que ejecute el terminal. Como en, this.spawnCommand(''grunt'', [''build''])
.
Entonces la siguiente pregunta es ¿dónde pones eso? Pensando de forma lineal, solo puede confiar en que la grunt build
funcionará después de que se hayan instalado todas sus dependencias.
Desde https://github.com/yeoman/generator/blob/45258c0a48edfb917ecf915e842b091a26d17f3e/lib/actions/install.js#L67-69 , this.installDependencies
acepta una devolución de llamada, por lo que su código puede tener este aspecto:
this.on(''end'', function () {
this.installDependencies({
skipInstall: this.options[''skip-install''],
callback: function () {
this.spawnCommand(''grunt'', [''build'']);
}.bind(this) // bind the callback to the parent scope
});
});
¡Dale un tiro! Si todo va bien, debe agregar algo de manejo de errores sobre esa nueva llamada a this.spawnCommand
para estar seguro.