Skip to content
Gulp

A Beginners Guide to Package Manager Bower and Using Gulp to Manage Components

9 min read
Bower logo

Package managers like Composer for PHP and NPM for Node have become essential tools for simplifying a developer’s life. A package manager is a tool for keeping track of what you’ve installed, as well as installing and upgrading packages. They also check for dependencies and compatibility. Bower is a package manager for the web.

The web is built from various frameworks, libraries and plugins. Bower’s job is to make managing these “packages” easy. With Bower you can quickly download things like jQuery and plugins, as well as CSS frameworks and much more.


Let’s Install Bower

Bower uses Node, so make sure you’ve installed it before proceeding to install Bower. You can check if Node is installed by opening up a terminal and running the following command:-

$ node -v

If you get something like ‘command not found’ you will need to install it. You can get it from the Node website.

Now we should be ready to globally install Bower. To do this we’ll use the Node Package Manager (npm) from the terminal:-

$ npm install -g bower

If you’re running this from OSX or Linux you will probably need to run this as an administrator so prepend it with sudo.

Setup Bower for a Project

For each of your projects that you want to use Bower with you will need to initialise it. From the terminal navigate to a project’s folder; something like:-

$ cd ~/projects/my-project

From now on all the commands we’ll be running will be from the project’s root folder. The project needs a file called bower.json. Create one in the project’s folder, the contents of the file should be something like:-

{
  "name": "my-project"
}

Alternatively you could generate the file by running bower init and answering the questions asked. It’s up to you which method you prefer.

We should now be in a position to start installing some packages.

Finding Packages

There are a few of ways of finding Bower packages. You can search via the Bower website or alternatively you can use the command line.

To search for packages from the terminal you use Bower’s search command followed by what you’re searching for:-

$ bower search <query>

For example, to search for jQuery packages:-

$ bower search jquery

Try it yourself. You should see a very long list of available packages.

Installing a Package

To install a package you can use Bower’s install command:-

$ bower install <package> --save

This will download the specified package to a bower_components folder in the project’s root (we’ll look at changing this in a moment). The --save flag tells Bower to add the package to the bower.json file for future reference.

Let’s give it a try and install jQuery:-

$ bower install jquery --save

You should find the latest version of jQuery downloaded to bower_components and the package added to bower.json. The version installed should have been output to the terminal.

If you want to fetch a specific version you can append the version number after the package name:-

$ bower install <package>#<version> --save

So for a specific version of jQuery:-

$ bower install jquery#1.8 --save

If Bower can’t find an exact match it will attempt to offer you a choice of versions to install.

Another neat trick that Bower will perform is that if you attempt to install a package that depends on another one it will download both and make sure the packages are compatible.

Updating Packages

To update your packages simply use Bower’s update command:-

$ bower update

Uninstall a Package

To uninstall a package use Bower’s uninstall command:-

$ bower uninstall <package> --save

The --save flag will remove the package from the bower.json file as well as uninstall it.

bower_components

By default Bower is going to download everything to the bower_components folder. We can change this using the directory setting in the .bowerrc file. If this file doesn’t yet exist you will need to add it to the same folder that contains your bower.json file. This file is a JSON file for defining your Bower settings. To change the folder that Bower installs packages add the directory setting like:-

{
  "directory": "public/vendor"
}

This will cause Bower to download everything to public/vendor/ instead of bower_components.

It may be worth excluding the bower_components folder from your repository if you’re using something like Git by adding the folder to your .gitignore file. Then whenever you pull down your code you can reinstall all the Bower managed packages by running:-

$ bower install

Excluding the bower_components folder will keep the size of your repository small, but not everyone agrees with excluding this; Addy Osmani has put together something arguing for-and-against checking in front-end dependencies which is worth a look when you have time.


Using the Installed Packages

How you use the packages downloaded by Bower is left up to you. One of the neat features of Bower.

One approach is to directly link to assets in the bower_components folder (or whatever you have configured it to be in the .bowerrc file). However, you ideally want to keep the size and number of assets included in your web pages to a minimum. Using a task runner like Gulp can help achieve this.

Managing Components with Gulp

If you’re not familiar with Gulp I recommend you take a look at my Beginners Guide to the Task Runner Gulp before reading on. I’m not going to explain what Gulp is or how it works here.

What I am going to show is how you can use Gulp to take the assets from installed Bower packages and combine them into smaller files suitable for delivering to the end user on the web.

The Gulp examples that follow are going to be using the excellent gulp-load-plugins plugin so that plugins don’t need to be individually declared in the gulp file. If you haven’t come across this plugin yet take a look at my Automatically Load Gulp Plugins with gulp-load-plugins post. The top of the gulpfile will look like this:-

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

// Include plugins
var plugins = require("gulp-load-plugins")({
	pattern: ['gulp-*', 'gulp.*', 'main-bower-files'],
	replaceString: /\bgulp[\-.]/
});

// Define default destination folder
var dest = 'www/public/';

JavaScript

We’re going to be using the main-bower-files and gulp-filter plugins to grab files from the installed Bower packages. So for example, we can retrieve all the main JS files from our Bower packages like this:-

gulp.src(plugins.mainBowerFiles())
	.pipe(plugins.filter('*.js'))
	.pipe(/* doing something with the JS scripts */)
	.pipe(gulp.dest(dest + 'js'));

plugins.mainBowerFiles() returns an array of all the main files from the packages and plugins.filter('*.js') uses gulp-filter to pass only JS files.

Let’s put this in a task and combine all the JS files from the Bower packages appended with JS files from our project then minify everything:-

gulp.task('js', function() {

	var jsFiles = ['src/js/*'];

	gulp.src(plugins.mainBowerFiles().concat(jsFiles))
		.pipe(plugins.filter('*.js'))
		.pipe(plugins.concat('main.js'))
		.pipe(plugins.uglify())
		.pipe(gulp.dest(dest + 'js'));

});

plugins.mainBowerFiles().concat(jsFiles) returns an array of all the main files from the packages combined with files defined in the jsFiles array we’ve defined. Any JS files from our project will be defined in this latter array. We’re then combining and minifying the scripts with the gulp-concat and gulp-uglify plugins.

Running gulp js will create a single minified JS file, www/public/js/main.js.

CSS

We can now do the same thing for any CSS files:-

gulp.task('css', function() {

	var cssFiles = ['src/css/*'];

	gulp.src(plugins.mainBowerFiles().concat(cssFiles))
		.pipe(plugins.filter('*.css'))
		.pipe(plugins.concat('main.css'))
		.pipe(plugins.uglify())
		.pipe(gulp.dest(dest + 'css'));

});

This will output a single minified CSS file called main.css containing all the CSS rules from our Bower packages and project much like we just did for our JS files. However, what if we want to specify the order the CSS files are concatenated? For example, say we’ve installed normalize.css (bower install normalize.css --save); ideally this would be at the top of our CSS file. We can sort the filtered CSS files by piping to the gulp-order plugin:-

gulp.task('css', function() {

	var cssFiles = ['src/css/*'];

	gulp.src(plugins.mainBowerFiles().concat(cssFiles))
		.pipe(plugins.filter('*.css'))
		.pipe(plugins.order([
			'normalize.css',
			'*'
		]))
		.pipe(plugins.concat('main.css'))
		.pipe(plugins.uglify())
		.pipe(gulp.dest(dest + 'css'));

});

This will ensure normalize.css is included before all the other CSS files.

We now have one JavaScript file and one CSS file to include on our webpages.


Final Words

Bower is an excellent tool for developers looking to make life that little bit simpler. You don’t need to use Gulp to work with Bower packages, but I hope I’ve shown how it can make working with Bower easier. Other task runners like Grunt can be used instead of Gulp if that’s your thing. Otherwise you can just link directly to files downloaded by Bower, although you lose the benefits of minimising the size and number of assets to include with a page that you get from using a task runner.

I hope I’ve got you interested in Bower. Go check out Bower for yourselves!

© 2024 Andy Carter