6 May 2009

Namespacing in JavaScript

To structure my javascript code I've developed a namespace scheme ((Javascript doesn't really have namespaces so we need to fake them)). Namespace is used in languages like C++ to group functionality and data, it's also used in Java but referred to as packages.

Coming from a C++ background with structure I wanted to impose a kind of order to my JavaScript code. Prior the using namespace almost all my functions were global functions and they had longer and longer names like this:
data_sentences_get( sent_id ) {...}

To get some structure on this I decided to have two global objects:

	var UI = [];
	var Data = [];

UI is the top-level namespace for all my UI functions.
Data is the top-level namespace for all data-processing and retrival functions.

In this scheme the above mentioned function would be defined like this:

( function( Data ) {
	if ( Data.sentences ) {
		return; // Already defined, don't do it again.

	// Create the sentences namespace object.
	Data.sentences = [];

	// Create a short hand reference to it.
	var ref = Data.sentences;

	ref.get = function( sent_id ) {
		// TODO
} )( Data );

In this example I create the namespace Data.sentences (I know this is actually an object) and create the function “Data.sentences.get( sent_id )”.

This structure gives me some benefits. The first is the grouping of functions which help me structure my code, the second is that I can have private data and functions for each namespace ((Covered in the article
Reintroducing a little sanity in working with JavaScript)) and the third is that I can use dynamic load functions as needed.

Jquery have a useful function called $.getScript, it's used to dynamically load JavaScript-files to the webpage. Since we have the namespace objects and JavaScript allows us to extend already initiated objects, we have an easy way to load new functions and to check if they have been loaded.

	if ( Data.sentences ) {
		Data.sentences.get( 1 );
	} else {
		$.getScript( “data_sentences.js”, function( ) {
			Data.sentences.get( 1 );
		} );

If you have a large web application, you might want to save memory or bandwidth by only loading functionality as needed. You might need 100kB+ of JavaScript code for a component your users might use less then 1% of the time, this costs bandwidth and load time.

But if you do this you need to consider what could go wrong. If the server or connection is slow, loading code might make the interface fell slow since the user will have to wait for the code to be loaded. There is the possibility that the request fails or times out, you need to handle this problem or the interface might be appear to have frozen. There is also the possibility, that the version of code on the server is incompatible with the version of code the browser has (this shouldn't happen. If it does something is wrong with you development process).