Reusing require.js modules in Node.js

May 21, 2014 10:23 am 4 comments

Using the same code in the browser and in the server is something that every developer dream of. The solution of that problem is known as the Holy Grail of javascript and there are different approaches to trying to get it. Probably we will be much closer to find the Grail when ECMAScript 6 modules are supported by every browser, but until that day, people try to find their ways to reuse as much as possible.

A lot of developers are using the awesome tool Browserify nowadays to make node modules work in the browser. Browserify is great, and I think that the way of requiring modules in a Node way is much cleaner than the one used in the browser by AMD modules. But it needs to ‘compile’ the node source code to a browser version in order to be used in the client side, so actually it is not the same code that runs in the server.

Currently it is not possible to require scripts in a CommonJS style (node style) in the browser

because the script execution can’t be halted until the module is ready to use it. That is why Browserify needs to transform the code to be used by the client.

On the other hand, browser javascript modules are defined using the AMD notation (for example, the ones used by require.js) and Node.js would be perfectly able to load the modules with a defined in that way.

 Introducing AMDrequire

AMDrequire is a npm package that makes Node.js able to load AMD modules like if they were native Node modules. Let’s say we have the following require.js module in mymodule.js

Using AMDrequire it is possible to load it in your Node.js the way it would be loaded in the browser:

That means that all the modules written for require.js are suddenly available for their use in Node.js. Isn’t it great? And the best part of it that there is no need to modify one line of code, the same exact code is being reused by the client and the server.

And what is even better, you can still use Node.js modules as usual, requiring them in a synchronous way.

Notice that AMD modules are loaded using require.js notation, with an array as the first parameter (named define are not supported yet), and Node modules are loaded using standard Node.js notation, with the path or name string as the first parameter.

How can I use AMDrequire?

AMDrequire is available as NPM package, so, to use it, the first thing to do is add it to your project

Then, make it the first require in your application’s entry file

Once this is done, it is possible to load AMD modules in any of the application files. Also it is possible to create modules with the define method to be used in the server and the client.

Configuring AMDrequire

To make the configuration easier, AMDrequire can directly receive require.js configuration object to use the same named requires than the client.

As it is seen in the example, the config method accepts almost the same parameters of require.js one. That method is only available in the require object returned when amdrequire is loaded. There are two different parameters :

  • basePath:  It is equivalent to require.js baseUrl option, so it should point to the local path of that URL. All the relative paths used in AMD’s require and define calls, that don’t start with ./ or ../ will be relative to this directory. In the example, the world module should be in __dirname + '/public/assets/js/somedir/world.js' .
  • publicPath: Defines the path of the root URL directory. In the browser it is possible to require modules using root routes, they start with a slash /like/route/from/the/root and they are relative to the domain URL. publicPath  tells what is the equivalent to that /  route to AMDrequire, so it can handle that kind of requires.

 Want to collaborate?

AMDrequire is a young module, so any help in its development would be great. In the AMDrequire git page it is possible to find deeper documentation and some suggestions on what to improve, and of course, any comment is really welcome.

javi

Let’s push your website a bit further

My name is Javier Márquez and I have more than 10 years of web programming and web designing experience. If you have a difficult development to complete, maybe you can stop by and see what I can do for you. You can find me on and Twitter.

4 Comments - Leave yours

  • Kevin Dangoor

    How does this compare with RequireJS’s own support for Node?

    http://requirejs.org/docs/node.html

    It seems very similar…

    • Javi Marquez

      The main difference is in the way the files are required. As you can see in their example, requirejs module is loaded as any other node.js module, creating a new object:

      You can use the requirejs object now to fetch your amd modules in your file, but, of course you need to do the same in every file you want to use an AMD require. If your AMD modules require other ones, you will need to modify them to use requirejs function in order to work in Node.js.

      With amdrequire you add AMD module capabilities to Node’s require function, that means that once you have required amdrequire, you can use ‘require’ and ‘define’ functions in a AMD way anywhere.

      If your AMD modules require other ones, they will work with no modifications, because the require function will know how to fetch the modules.

Leave a reply


contact meAnything related to web development like javascript and CSS to create responsive designs, or PHP and node.js to make your website work properly, is my pleasure. If you have an interesting project in mind, I can help to make it real.