So you are a Joomla! developer and you build packages. I'm sure you have built your own zipfiles at least once. I've done this for quite a while which consumes alot of time you could've used to develop your new and awesome extension! Next to that, Gruntjs and her packages offer a lot more then creating zip-files only.

So what is this "NodeJS" and "Grunt", you say? NodeJS is Javascript as a process outside the browser. It allows you to run Javascript and access the host machine which combined leads to very useful applications, such as a webserver. Grunt is a Javascript package that can run tasks, which we will discuss later.

To start saving insane amounts of time (not lying!) you'll need;

  1. NodeJS
  2. Grunt

That's all! Install NodeJS using the installer and after that install Grunt using its manual (http://gruntjs.com/getting-started). Once you've done that we can start by explaining the useful taskrunner named Grunt. Grunt is a taskrunner meaning you can program it to do certain tasks. A task can be minifying a file or building a zip-file of files. To start programming Grunt we'll need a basic setup. Create a folder and create the following structure;

MyProject
|- Gruntfile.js
|- package.json
|- server.bat (optional)
|- dest
|- src
|- script.js

When you've created these files (or downloaded) we can start building our automatisation. The Gruntfile.js is the file in which we explain to Grunt what to do. Take a look at the basic example below;

// Gruntfile.js
module.exports = function(grunt) {
	'use strict';

	grunt.initConfig({
		pkg: grunt.file.readJSON('package.json'),

		/**
		 * Watch Task
		 */
		watch: {
			// Subtask
			project: {
				files: ['src/**/*.js'],
				tasks: ['uglify']
			}
		},

		/**
		 * Uglify Task
		 */
		uglify: {
			// Subtask
			js: {
				files: {
					'dest/script.min.js': ['src/script.js']
				}
			}
		}
	});

	/**
	 * Load Plugins
	 */
	grunt.loadNpmTasks('grunt-contrib-watch');
	grunt.loadNpmTasks('grunt-contrib-uglify');

	/**
	 * Setup Tasks
	 */
	grunt.registerTask('default', ['watch']);
};

This is a very basic example of Grunt to minify a Javascript file once saved. The "watch" task triggers the "uglify" task whenever a file with the ".js" file extension has been altered in the "src" folder. The uglify task then minifies the file and writes its output to the dest folder in a file called "script.min.js". But, this won't work yet. We need a package.json!

{
  "name": "GruntDemo",
  "version": "0.0.1",
  "license": "GNU/GPLv3",
  "description": "Demo for Grunt",
  "author": "Snoeren Development",
  "contributors": {
    "name": "Michael Snoeren",
    "email": ""
  },
  "private": true,
  "devDependencies": {
    "grunt": "~0.4.5",
    "grunt-contrib-watch": "^1.0.0",
    "grunt-contrib-uglify": "^2.0.0"
  }
}

The package.json describes your project and contains the packages you want to use. Any package you'll install will be saved to this file if done correctly. This way, you can replicate the environment on a new pc with just one command. You can change the name, version, license, description, author and contributors to your liking or your project needs. But, this does nothing yet. You'll need to run the following command in the command prompt after you navigated to the folder your project is in;

npm install

This command will install all packages found in your package.json. You'll need this command too if you want to install additional packages.

Now for the magic part! After installing the packages you may have noted a "node_modules" folder. This folder contains all the software you've installed (packages). You may recognize uninstalled environments by checking if the node_modules folder is present. To run your environment you use the command following command in your console;

grunt

That's all! We've specified a default task which contains the watch task. The Watch task will watch all files matched in the "files" parameter of the task and run the specified tasks. You may also add additional subtasks for a more advanced program. Try to add some Javascript code to the script.js file while running the Grunt software in the console. If you've set it up correctly a new file should appear in the dest folder named "script.min.js". Open it and view its content. Minified?

Now you've setup your environment we can program a bat file to ease up the progress!

@echo off
CMD /K "cd %CD% && cls && npm update && cls && grunt watch"

Put the code above in the server.bat file to automate the start of your automated environment. Save the file and run it! The server will automaticly keep your packages up to date with "npm update". Then, Grunt will take over and run the watch task (make sure its present). You can also put a "git pull" command before the "npm update" command to make sure you use your latest software.

Now you know how to automate your programming environment with Grunt. I suggest you look at more packages for Grunt at https://www.npmjs.com/ and try them out. Noticable packages are;

  • grunt-contrib-clean
    Clean your console output before running new tasks
  • grunt-contrib-compress
    Compress files into zip-files (very useful for building Joomla! extensions)
  • grunt-http-upload
    Upload files using a HTTP request. Use this together with MS PackageUpload to automate the process even more! More information about this in the component itself.
  • grunt-joomlaindexer
    My own Grunt software! Creates index.html files in every directory found as required by Joomla!
  • load-grunt-tasks
    Replaces the grunt.loadNpmTasks rows with one simple line.

To learn more about Grunt and how to setup more tasks, take a look at their website; http://gruntjs.com/getting-started. Download the files for this post here (1,5kb).