Explain Codes LogoExplain Codes Logo

How to run Gulp tasks sequentially one after the other

javascript
gulp
task-management
streaming
Anton ShumikhinbyAnton Shumikhin·Dec 6, 2024
TLDR

Using the series() function in Gulp 4 is the default way to run tasks sequentially. Simply put your tasks within the series() call to enforce this order.

Example:

const { series } = require('gulp'); function clean(done) { // Pretend cleaning your room is this easy (*wink*); done(); } function build(done) { // Building as though it's a LEGO set (*hint: It's more complicated*); done(); } exports.build = series(clean, build);

Just call series(clean, build) to make sure clean precedes build.

For those still clinging on to Gulp < 4, you might want to get on the "run-sequence" train:

npm install --save-dev run-sequence

Then, in the gulpfile.js, do this:

var runSequence = require('run-sequence'); gulp.task('default', function(callback) { runSequence('task1', 'task2', 'task3', callback); });

Signalling task conclusion

It's essential that tasks indicate their completion, either by returning a stream or promise, or receiving a callback.

// The stream way gulp.task('styles', function() { return gulp.src('styles/**/*.css') .pipe(gulp.dest('dist/styles')); }); // The promise way gulp.task('scripts', function() { return new Promise(resolve => { // Code so that promises aren't simply meant to be broken! resolve(); }); });

Completion with a callback:

gulp.task('clean', function(done) { // Cleaning time! No, not your room - the code! done(); });

Handling errors: The unsung hero

You might encounter errors while running tasks. Better prepare for that eventuality:

gulp.task('lint', function() { return gulp.src('scripts/**/*.js') .pipe(plugin1()) .on('error', handleErrors) .pipe(gulp.dest('output')); });

You could define handleErrors to gracefully handle errors, or demonstrate your high pitch scream.

Streamlining your workflow: The Gulp way

Combine the series() for sequential tasks with parallel() for concurrent tasks.

const { parallel, series } = require('gulp'); // 'clean' happens first, followed by 'styles' and 'scripts' concurrently exports.build = series(clean, parallel(styles, scripts));

Modular task organization: Because "divide and conquer" isn't just for empires

You can utilize Yeoman generators and plugins for simplified workflows to avoid repetitively reinventing the wheel.

npm install -g yo npm install -g generator-gulp-webapp yo gulp-webapp

This sets up tasks nearly as fast as your microwave reheats last night's pizza.

Managing task dependencies: Because nobody likes a domino effect

When the task plot thickens, define dependencies to ensure the correct task order - because dependencies are not just for TV series episodes!

gulp.task('pre-build', gulp.series('clean', 'lint')); gulp.task('build', gulp.series('pre-build', 'compile'));

Here, both 'clean' and 'lint' tasks must complete before 'compile' begins - because who wants a dirty compile?

What's next: The future (of Gulp)

Stay tuned for Gulp's release notes. They're the Gulp equivalent of your favourite show's next episode teasers.

Listener Overload? No, thank you!

While listeners can make your tasks super dynamic, removing them when they're not needed prevents memory leaks and keeps your Gulp happy.

gulp.task('watch', function() { let watcher = gulp.watch('scripts/**/*.js', gulp.series('build')); watcher.on('change', function(path, stats) { console.log(`File ${path} was changed, but do not fear - watcher is here!`); }); // When you no longer need the watcher watcher.close(); });