Today I've created a custom jQuery package for Kanso. It's not only containing a much later jQuery version but also all the jQuery extensions I normally use. My goal was to compile all of them into one single file so that applications using it don't have to contain a column of script tags just to get all the extensions in.
Initial effort
I begun by creating a new package with a `kanso.json` file like this:
{
"name": "jquery2",
"version": "2.0.3",
"categories": ["utils"],
"attachments": [
"jquery.js"
],
"maintainers": [
{
"name": "Arthur McFlint",
"url": "https://github.com/arthurmcflint"
}
],
"url": "http://jquery.com/",
"dependencies": {
"attachments": null,
"modules": ">=0.0.8"
},
"description": "Contains the jQuery core as well as some extensions used commonly used by my projects."
}
By adding the `jquery2` extension to an app it automatically adds jquery.js.
Fine Tuning
Even so the above solution works like a charm it has a massive flaw. I couldn't care less about manually maintaining one big file containing the jQuery core as well as the extensions. After a while it would be beyond repair.
Instead I added build processors and some JavaScript files executed by node when running kanso. The new `kanso.json` file looks a bit like this:
{
"name": "nexus-jquery",
"version": "2.0.3",
"categories": ["utils"],
"attachments": [
"jquery.js"
],
"maintainers": [
{
"name": "Arthur McFlint",
"url": "https://github.com/arthurmcflint"
}
],
"preprocessors": {
"merge": "build/merge"
},
"postprocessors": {
"cleanup": "build/cleanup"
},
"url": "http://jquery.com/",
"dependencies": {
"attachments": null,
"modules": ">=0.0.8"
},
"description": "Contains the jQuery core as well as some extensions used commonly used by my projects."
}
Whenever kanso is pushing an app to the server it first goes through the process of building the app. By adding 'hooks' in the shape of preprocessors and postprocessors it's possible to alter the standard behavior quite a bit.
First of all I've created a new file calles `build_config.json`:
{
"jsfiles": [
"jquery-2.0.3.js",
"extensions/misc/jquery.ba-serializeobject.js"
]
}
Then I've added `build/merge.js`:
var uglify = require('uglify-js');
module.exports = function(root, path, settings, doc, callback) {
// Read the extensions config file
var build_config = JSON.parse(fs.readFileSync(__dirname + '/../build_config.json', 'ascii'));
// Fix pathes to js files
var jsfiles = [];
build_config.jsfiles.forEach(function(path) {
jsfiles.push(__dirname + '/../' + path);
});
// This is where the output will go to
var target_file = __dirname + '/../jquery.js';
// Init output buffer
var output = '';
// Combine JS files into one string
jsfiles.forEach(function(path) {
output += fs.readFileSync(path, 'ascii');
});
// Add newline at the end of file
output += "\n";
// If compression is active, minify the code
if (settings.jscompression) {
output += uglify.minify(output, {fromString: true})
}
// Write jquery.js
fs.writeFileSync(target_file, output);
// Carry on :)
callback(null, doc);
};
And of course `build/cleanup.js`:
var fs = require('fs');
module.exports = function(root, path, settings, doc, callback) {
fs.unlinkSync(__dirname + '/../jquery.js');
callback(null, doc);
}
To make it all work, I've finally added a `package.json` file adding `uglify-js` to the requirements and installed it with npm.
The result
As a result the code is now automatically merged from the files I've added in the `build_config.json` file. If I turn on `jscompression` in the `kanso.json` file of my main application using the jquery2 package, kanso automatically minifies the code during the build.
All in all that's a very nice result and shows how much tweaking is possible within the kanso framework. The only thing you have to be cautious about is async code. I ran into big trouble using minify or node-minify to do the job. However as long as the functions run in sync mode you're good to go.
No comments :
Post a Comment