由于你的任务可能包含异步代码,你必须在任务执行完成时发出gulp信号(= "async completion")。
在Gulp 3。X,你可以不这样做。如果你没有显式地发出异步完成信号,gulp就会假设你的任务是同步的,只要你的任务函数返回,它就会完成。杯4。X在这方面更为严格。你必须明确地表示任务完成。
你可以通过六种方式做到这一点:
1. 返回一个流
如果你只是想打印一些东西,这不是一个真正的选择,但它可能是最常用的异步完成机制,因为你通常使用gulp流。下面是一个(相当做作的)例子,为你的用例演示它:
var print = require('gulp-print');
gulp.task('message', function() {
return gulp.src('package.json')
.pipe(print(function() { return 'HTTP Server Started'; }));
});
这里重要的部分是return语句。如果不返回流,gulp无法确定流何时结束。
2. 履行承诺
这是一种更适合您的用例的机制。注意,大多数时候你不需要自己创建Promise对象,它通常由一个包提供(例如,经常使用的del包返回一个Promise)。
gulp.task('message', function() {
return new Promise(function(resolve, reject) {
console.log("HTTP Server Started");
resolve();
});
});
使用async/await语法可以进一步简化。所有标记为async的函数都隐式返回一个Promise,因此以下也可以工作(如果你的node.js版本支持它):
gulp.task('message', async function() {
console.log("HTTP Server Started");
});
3.调用回调函数
对于您的用例来说,这可能是最简单的方法:gulp自动将一个回调函数作为第一个参数传递给任务。当你完成时,只需调用该函数:
gulp.task('message', function(done) {
console.log("HTTP Server Started");
done();
});
4. 返回子进程
如果你必须直接调用命令行工具,因为没有node.js包装器可用,这是非常有用的。它适用于你的用例,但显然我不推荐它(特别是因为它不是很可移植):
var spawn = require('child_process').spawn;
gulp.task('message', function() {
return spawn('echo', ['HTTP', 'Server', 'Started'], { stdio: 'inherit' });
});
5. 返回一个RxJS Observable。
我从未使用过这种机制,但如果您正在使用RxJS,它可能会有用。如果你只是想打印一些东西,这有点过头了:
var of = require('rxjs').of;
gulp.task('message', function() {
var o = of('HTTP Server Started');
o.subscribe(function(msg) { console.log(msg); });
return o;
});
6. 返回一个EventEmitter
与前一个一样,为了完整起见,我包含了它,但它并不是真正要使用的东西,除非您已经出于某种原因使用了EventEmitter。
gulp.task('message3', function() {
var e = new EventEmitter();
e.on('msg', function(msg) { console.log(msg); });
setTimeout(() => { e.emit('msg', 'HTTP Server Started'); e.emit('finish'); });
return e;
});