5 Grunt Tasks that Improve the Performance of Your Website
Many times on SitePoint I’ve mentioned how achieving good performance is a main concern today and how you should strive for fast web pages. In some articles of mine about JavaScript APIs, such as Introduction to the Resource Timing API and Discovering the User Timing API, I gave you all the power you need to know what’s slowing down your project. Earlier this year, Craig Buckler covered this topic too, with his article The Complete Guide to Reducing Page Weight.
If you aren’t stuck in the past, you’re likely using a task runner like Grunt or Gulp to improve your workflow by automating a lot of operations we used to perform manually. In this article I’ll describe five Grunt tasks that help us enhance the performance of our web pages.
grunt-contrib-imagemin
The first task I want to mention is grunt-contrib-imagemin. The reason why I want to discuss it first is that images are killing the web. Seriously!
If you take a look at HTTParchive.org statistics you’ll see that images represent more than 63% of the total size of a page. The reason for such bloat is that often images aren’t compressed to have a weight as low as possible. grunt-contrib-imagemin is one of the tasks you can use to solve this issue.
This task comes with the following optimizers to be able to compress most of the image formats employed on the web:
- gifsicle to compress GIF images
- jpegtran to compress JPEG images
- optipng to compress PNG images
- svgo to compress SVG images
An example of configuration for this task is shown below:
imagemin: {
dist: {
options: {
optimizationLevel: 5
},
files: [{
expand: true,
cwd: 'src/images',
src: ['**/*.{png,jpg,gif}'],
dest: 'dist/'
}]
}
}
This configuration allows for a high level of optimizations by using the optimizationLevel
option. This value ranges from 0 to 7, with 3 as the default. In this case the images optimized are those with the extension png, jpg, or gif, and located in the “src/images” folder and all its subfolders. The result of the optimization will be stored in the “dist” folder.
grunt-contrib-uglify
The grunt-contrib-uglify task is used to minify JavaScript files. This task removes all the unnecessary whitespace that your source code has, and renames the variables and functions consistently to use a name as short as possible.
Some options that you’ll often use for this task are sourceMap
and banner
. The former creates a source map file in the same directory as the destination file. To enable this option you have to set it to true
(the default value is false
). banner
is a string to prepend to the minified output in which you usually write the name of the file/library/framework, its version, your name as the author, and the license. Its default value is an empty string.
To give you an idea of what a minified source looks like, let’s say that you have the following JavaScript code:
var MyApplication = function() {
var data = 'hello';
this.sum = function(first, second) {
return first + second;
}
this.showData = function() {
return data;
}
};
The minification process will convert it to the following code:
var MyApplication=function(){var a="hello";this.sum=function(a,b){return a+b},this.showData=function(){return a}};
An example configuration of this tool is shown below:
uglify: {
dist: {
options: {
sourceMap: true,
banner: '/*! MyLib.js 1.0.0 | Aurelio De Rosa (@AurelioDeRosa) | MIT Licensed */'
},
files: {
'dest/output.min.js': ['src/input.js'],
}
}
}
grunt-contrib-cssmin
As the name suggests, grunt-contrib-cssmin compresses CSS files. Like the grunt-contrib-uglify task, this one provides a banner
option.
A simple configuration for this task is:
cssmin: {
dist: {
options: {
banner: '/*! MyLib.js 1.0.0 | Aurelio De Rosa (@AurelioDeRosa) | MIT Licensed */'
},
files: {
'dist/css/style.min.css': ['src/css/**/*.css']
}
}
}
This example minifies all the CSS files stored in “src/css” and its subfolders, and stores the result in a single style sheet called “style.min.css” that is placed in the folder “dist/css”. In addition, the configuration adds a banner at the top of the minified file.
grunt-uncss
Another task that deals with CSS is grunt-uncss. This task removes unused CSS from a project, so it reduces the size of the final CSS file, and thus improves the download time. It’s particularly well suited if you’re developing using a framework like Boostrap or Foundation. This task has some important limitations that you can read on the official documentation.
Some nice options worth mentioning are ignore
, that allows us to specify a list of selectors that should not be removed, and ignoreSheets
, that allows us to specify style sheets to ignore.
An example use of this task is shown below:
uncss: {
dist: {
options: {
ignore: [/js-.+/, '.special-class'],
ignoreSheets: [/fonts.googleapis/],
},
files: {
'dist/css/unused-removed.css': ['src/index.html', 'src/contact.html', 'src/service.html']
}
}
}
grunt-contrib-htmlmin
The last Grunt task I want to discuss in this article is grunt-contrib-htmlmin, a task to minify HTML code. It doesn’t speed up your website a lot because it often saves just a few Kbs, and if you’re serving your content using gzip compression, the gain is even lower. Therefore, if you’re looking to minify your HTML, well… compliments; it means your website was already pretty optimized.
Nonetheless, the philosophy to follow when dealing with performance on the web is that every Kb counts. So, let’s see a simple configuration that integrates this task into our workflow:
htmlmin: {
dist: {
options: {
removeComments: true,
collapseWhitespace: true
},
files: [{
expand: true,
cwd: 'src',
src: '**/*.html',
dest: 'dist/'
}]
}
}
The code above processes all the pages placed in the “src” directory and its subfolders. For each of these pages, the task removes all the comments and collapses the spaces it finds, storing the results in the “dist” directory.
Conclusion
In this article I introduced you to five Grunt tasks to easily improve the performance of your website. They’re so simple that you really have no excuses to avoid using them and offer your users a better experience through a faster service. I hope you liked this article and you’ll employ these tasks soon.
Have you ever used them? How much did they improve your website? Are there any tasks you love and want to share with us?