Gulp.js is a JavaScript task runner which can carry out various tasks in a web project automatically. For example, it can condense multiple JavaScript files down into one, reduce image sizes, watch files when they change and compile SASS into CSS files for you. It takes a little bit of effort to set up, but once configured, it can save you so much time…

I aim to provide a tutorial to people who are perhaps from a more design-orientated rather than development background, for whom using the command line isn’t second nature. By the end of this tutorial, you should have a grasp of what Gulp.js can do for your web projects and how to set up some basic, but very useful tasks.

Install Node & npm

The very first thing you should do is install Node.js onto your machine. Node is an environment upon which applications can be run; Gulp being one of them. npm stands for node package manager, and it is used to manage Node.js libraries via the command line.

Set up your project

The next thing you should do is create a folder for your project. I’d suggest setting up your folder structure similar to this:

├── projectname/
│   ├── assets/
│   │   ├── css/
│   │   ├── js/
│   ├── index.html
│   ├── src/
│   │   ├── scss/
│   │   │   ├── style.scss
│   │   │   ├── _partial.scss
│   │   ├── js/
│   │   │   ├── jsfile1.js
│   │   │   ├── jsfile2.js
│   │   │   ├── jsfile3.js

Within the src folder, you would place your SCSS and JavaScript source files which, when passed through Gulp, will be processed and placed in appropriate folders within the assets folder.

Create package.json

Before installing Gulp, a file called package.json needs to be created which will hold all of your devDependencies. devDependencies are packages which will allow your project to run. You can create this file automatically by typing the following into the command prompt:

npm init

If you go back to look at your project file structure, you should notice that it will contain a new package.json file. Open it in a text editor and you will see something like this:

{
  "name": "projectname",
  "version": "1.0.0",
  "description": "This is a trial project",
  "main": "index.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "author": "Createful",
  "license": "ISC"
}

Install Gulp globally & locally

Install Gulp globally to your machine by typing the following into the command line (you don’t need to be in a specific directory):

npm install gulp --global

Navigate to your project folder via the command line (obviously replace with your correct path!). A good tip is to navigate to the folder using Finder, then drag that folder into Terminal, and it will provide you with the correct path.

cd /your/projectname

Install Gulp locally to your project by typing the following into the command line:

npm install gulp --save-dev

The --save-dev part ensures that the package will appear in your devDependencies. You might have noticed that a node_modules folder was created in the root of your project automatically – this is where all the dependency files are placed, so there should be a gulp folder within it now too. As you add more modules, folders for them will show up next to the gulp one.

Your package.json folder should now look something like this – notice where gulp has been added to the devDependencies:

{
  "name": "projectname",
  "version": "1.0.0",
  "description": "This is a trial project",
  "main": "index.js",
  "scripts": {
    "test": "echo \"Error: no test specified\" && exit 1"
  },
  "author": "Createful",
  "license": "ISC",
  "devDependencies": {
    "gulp": "^3.9.0"
  }
}

Create gulpfile.js

In the root of your project, create a blank file and save it as gulpfile.js. This file is where we instruct Gulp on what to do with our project. All that needs to be placed into this file at the moment is the Gulp dependency and to set up a basic default task; so for now, paste the following into your gulpfile.js:

// Require Gulp
var gulp  = require('gulp');

// Default task
gulp.task('default', []);

Lint, concatenate and minify JavaScript files

The first useful thing Gulp can do for us is to take our JavaScript files within the src/js folder and do a number of things with them simultaneously:

  • Lint them (scan them for possible errors);
  • Concatenate them (combine them all into one file) to reduce server load;
  • Minify the concatenated file to shrink its final size.

To do these things, we need to install a number of plugins for Gulp. Type the following commands into the command prompt and press enter after each one to install each plugin separately:

npm install gulp-jshint --save-dev
npm install jshint-stylish --save-dev
npm install gulp-concat --save-dev
npm install gulp-uglify --save-dev
npm install gulp-rename --save-dev

Then we need to add the new dependencies and set up the tasks within gulpfile.js:

// Require Gulp and plugins
var gulp  = require('gulp'),
    jshint = require('gulp-jshint'),
    concat = require('gulp-concat'),
    uglify = require('gulp-uglify'),
    rename = require('gulp-rename');

// Scripts task
gulp.task('scripts', function() {
  return gulp.src('src/js/**/*.js')
    .pipe(jshint())
    .pipe(jshint.reporter('jshint-stylish'))
    .pipe(concat('scripts.js'))
    .pipe(gulp.dest('assets/js'))
    .pipe(rename({suffix: '.min'}))
    .pipe(uglify())
    .pipe(gulp.dest('assets/js'))
});

// Default task
gulp.task('default', ['scripts']);

You’ll see I have added the list of plugins just installed underneath the Gulp dependency, then added a scripts task, which contains a list of things that it will do when processed.

It should be relatively clear what the scripts task is doing:

  • return gulp.src('src/js/**/*.js') is looking for any .js files within the src/js folder and in any additional folders within;
  • .pipe(jshint())
    .pipe(jshint.reporter('jshint-stylish'))
    runs a linting process on the files to check for errors and display them in a ‘stylish’ manner;
  • .pipe(concat('scripts.js')) concatenates all of those files into a single file called scripts.js;
  • .pipe(gulp.dest('assets/js')) saves the concatenated file down in the assets/js folder;
  • .pipe(rename({suffix: '.min'})) renames the concatenated file to scripts.min.js;
  • .pipe(uglify()) runs the file through the uglify plugin, which will minify the file;
  • .pipe(gulp.dest('assets/js')) This minified file is also saved down into the assets/js folder.

At the very bottom, you’ll see I have added the scripts task to the default task – which means if you now type gulp into the command prompt, any files you have in the src/js folder will be run through the steps outlined above and saved out into the assets/js folder, ready to be used in your project.

Compile & autoprefix SCSS files, minify CSS files

The next extremely useful thing Gulp can do is to take our SCSS files and compile them into CSS files for production. At the same time, we are going to autoprefix the files, which means that instead of having to include all of the browser-specific rules for more modern CSS, they will be added automatically.

Again, we need to install a few plugins before we can set this up, so type the following commands into the command prompt and press return after each one to initiate the install:

npm install gulp-sass --save-dev
npm install gulp-autoprefixer --save-dev
npm install gulp-minify-css --save-dev

So, a similar procedure as with the scripts task, we are going to first add the plugin dependencies we just installed to the top of the file, and then add a styles task below the scripts task we created earlier:

// Require Gulp and plugins
var gulp  = require('gulp'),
    jshint = require('gulp-jshint'),
    concat = require('gulp-concat'),
    uglify = require('gulp-uglify'),
    rename = require('gulp-rename'),
    sass = require('gulp-sass'),
    autoprefixer = require('gulp-autoprefixer'),
    minifycss = require('gulp-minify-css');

// Scripts task
gulp.task('scripts', function() {
  return gulp.src('src/js/**/*.js')
    .pipe(jshint('.jshintrc'))
    .pipe(jshint.reporter('jshint-stylish'))
    .pipe(concat('scripts.js'))
    .pipe(gulp.dest('assets/js'))
    .pipe(rename({suffix: '.min'}))
    .pipe(uglify())
    .pipe(gulp.dest('assets/js'))
});

// Styles task
gulp.task('styles', function() {
  return gulp.src('src/scss/**/*.scss')
    .pipe(sass())
    .pipe(autoprefixer(
        {browsers: ['last 2 version', 'safari 5', 'ie 8', 'ie 9', 'opera 12.1']
    }))
    .pipe(gulp.dest('assets/css'))
    .pipe(rename({suffix: '.min'}))
    .pipe(minifycss())
    .pipe(gulp.dest('assets/css'))
});

// Default task
gulp.task('default', ['scripts', 'styles']);

The styles task is doing the following:

  • return gulp.src('src/scss/**/*.scss') is looking for any .scss files within the src/scss folder and in any additional folders within;
  • .pipe(sass()) compiles CSS files from the SCSS files we just specified;
  • .pipe(autoprefixer('last 2 version', 'safari 5', 'ie 8', 'ie 9', 'opera 12.1')) runs the autoprefixer on the files and will autoprefix any CSS rules that require it;
  • .pipe(gulp.dest('assets/css')) saves the compiled and autoprefixed CSS file style.css in the assets/css folder;
  • .pipe(rename({suffix: '.min'})) renames the CSS file to style.min.css;
  • .pipe(minifycss()) minifies the CSS file;
  • .pipe(gulp.dest('assets/css')) This minified file is also saved down into the assets/css folder.

The styles task also needs to be added to the default task, as above. So now, if you type gulp into the command prompt, both the JavaScript and SCSS files will be processed and placed into their respective folders within the assets directory.

Watch SCSS and JavaScript files for changes

When we are working on a project, it would get very annoying if we had to type gulp into the command prompt every five minutes to compile the changed files that we need for our project. So, we should set a watch task to detect when we have changed a file and run our tasks immediately.

The watch task doesn’t require any additional plugins to use; we just need to add an additional watch task to our gulpfile.js and add that task to our default task.

Our gulpfile.js should now look like this:

// Require Gulp and plugins
var gulp  = require('gulp'),
    jshint = require('gulp-jshint'),
    concat = require('gulp-concat'),
    uglify = require('gulp-uglify'),
    rename = require('gulp-rename'),
    sass = require('gulp-sass'),
    autoprefixer = require('gulp-autoprefixer'),
    minifycss = require('gulp-minify-css');

// Scripts task
gulp.task('scripts', function() {
  return gulp.src('src/js/**/*.js')
    .pipe(jshint('.jshintrc'))
    .pipe(jshint.reporter('jshint-stylish'))
    .pipe(concat('scripts.js'))
    .pipe(gulp.dest('assets/js'))
    .pipe(rename({suffix: '.min'}))
    .pipe(uglify())
    .pipe(gulp.dest('assets/js'))
});

// Styles task
gulp.task('styles', function() {
  return gulp.src('src/scss/**/*.scss')
    .pipe(sass())
    .pipe(autoprefixer(
        {browsers: ['last 2 version', 'safari 5', 'ie 8', 'ie 9', 'opera 12.1']
    }))
    .pipe(gulp.dest('assets/css'))
    .pipe(rename({suffix: '.min'}))
    .pipe(minifycss())
    .pipe(gulp.dest('assets/css'))
});

// Watch task
gulp.task('watch', function() {
    gulp.watch('src/js/**/*.js', ['scripts']);
    gulp.watch('src/scss/**/*.scss', ['styles']);
});

// Default task
gulp.task('default', ['scripts', 'styles', 'watch']);

The watch task is doing the following:

  • gulp.watch('src/js/**/*.js', ['scripts']); is watching all of the .js files within the src/js folder and in any additional folders within, and if any of them change, it will go ahead and run the scripts task;
  • gulp.watch('src/scss/**/*.scss', ['styles']); is watching all of the .scss files within the src/scss folder and in any additional folders within, and if any of them change, it will go ahead and run the styles task.

The watch task also needs to be added to the default task, as above. So now, if you type gulp into the command prompt, the scripts task will be run first, followed by the styles task, then the watch task is started which will run continuously to watch files and run their associated tasks until you stop it manually.

Conclusion: Gulp is useful!

So there we go; a simple but useful set of Gulp tasks which, when set up, will make running your project an absolute breeze. There are so many other tasks Gulp can carry out such as shrinking image sizes, auto-refreshing your browser and creating source maps for your JS and CSS files, but this should be enough to get you started. Happy Gulping!

[clickandtweet handle=”” hashtag=”” related=”” layout=”card” position=””]There are so many tasks Gulp can carry out, such as shrinking images and creating source maps.[/clickandtweet]

Sample project

I have set up a sample project on GitHub which you can clone and explore/tinker with yourself. When you have the project on your machine, navigate to it via the command line and then type:

npm install

This will install gulp to your project automatically, along with all other dependencies listed in the package.json file. Then typing gulp will set the processes outlined in gulpfile.js running to build all files and start the watch task.

Useful Resources