Clientside is a tool for converting a node.js library (CommonJS) into a library that is compatible in the browser. It will parse your library, find all its dependencies, wrap all files in a closure, concatinate them and replace all require() calls with variable references.
Clientside is designed for people that want to write a library and release it to the node community and the client-side javascript community. Nodejs developers shouldn't assume that everybody is running node, so we need to provide a way for other people to use our libraries without installing something like browserify.
Note this is still an early release, so it might not work in every case. If you run into an issue, please add it here.
Here's a comparison ClientSide and Browserify with a couple different libraries, written CommonJS style, converted to run in the browser:
Tool | Tiny Library (220b) | Medium Library (10k) |
---|---|---|
ClientSite | 423b | 10.8k |
Browserify | 9.7k | 22k |
I think what Browserify does is fine if you are running it on your entire website where you have 100s of kb of javascript and you only add the ~9k overhead once. But in my workflow, that doesn't work for me. I want to write small libraries and be able to reuse them in a nodejs enviornment at home and a php enviornment at work.
Install via npm
npm install -g clientside
Usage: clientside [file]
Options:
-h, --help output usage information
-V, --version output the version number
-e, --export <name> Module Name
-v, --verify Verifies your code in a sandbox
-s, --stats Displays file size stats of all files
Examples:
Pass in params
$ clientside --export module index.js > dist/module.js
Read from package.json
$ clientside > dist/module.js
var ClassA = require('./a');
var ClassB = function() {
this.a = new ClassA();
console.log('ClassB init');
};
module.exports = ClassB;
var ClassA = function() {
console.log('ClassA init');
}
module.exports = ClassA;
clientside --export ClassB index.js
As you can see in the output, a.js got wrapped in a closure and set to cs1 and index.js's require('./a') call got replaced by cs1. The entire file also got wrapped in a closure, set to the export name that was passed in, which is set to the output from the main file (index.js).
var ClassB = (function(exports) {
var cs1 = (function(exports) {
var ClassA = function() {
console.log('ClassA init');
}
exports = ClassA;
return exports;
})({});
var cs0 = (function(exports) {
var ClassA = cs1;
var ClassB = function() {
this.a = new ClassA();
console.log('ClassB init');
};
exports = ClassB;
return exports;
})({});
return cs0;
})({});
ClientSide will read your package.json if no arguments are passed in.
{
"name": "SomeAwesomePackage",
"main": "index.js",
"clientside": {
"shim": {
"http": "ajax.js"
}
}
}
You can also add a clientside object to your package.json. This is handy if, for example, your library makes some http requests using the http module. In the clientside object, you can define a shim that will replace the http object with another file (in this case, replace http client with one that uses XMLHttpRequest).
var http = require('http');
var ClassA = function() {
console.log('ClassA init');
};
module.exports = ClassA;
var ClassA = require('./a');
var ClassB = function() {
this.a = new ClassA();
console.log('ClassB init');
};
module.exports = ClassB;
module.exports = function() {
console.log("this will make ajax calls");
};
var SomeAwesomePackage = (function(exports) {
var cs0 = (function(exports) {
exports = function() {
console.log("this will make ajax calls");
};
return exports;
})({});
var cs2 = (function(exports) {
var http = cs0;
var ClassA = function() {
console.log('ClassA init');
};
exports = ClassA;
return exports;
})({});
var cs1 = (function(exports) {
var ClassA = cs2;
var ClassB = function() {
this.a = new ClassA();
console.log('ClassB init');
};
exports = ClassB;
return exports;
})({});
return cs1;
})({});