Experimenting with Express: Node.js day two
Day one was figuring out how to install node, express, and npm on Ubuntu and to get it to work, as well as some furtive experiments with a DIY module. Now I am trying to get Epress to do things my way.
I have three goals for buggering with Express:
- Figuring out what a module is in the whole Node.js framework
- Figuring out how to pass information around inside Node, and templates
- Trying to figure out why I always pre-designate how many items I want in a list before writing them out
Add a breadcrumb to the MVC example of express
express has a default page layout file, views/layout.html; in the mvc example, as in most of the examples, body is inserted inside an HTML layout. I want to add a 'breadcrumb' variable and insert it into the layout as in:
<html>
<head>
<title>Express - MVC Example</title>
<link rel="stylesheet" href="/style.css" />
</head>
<body>
<% if (breadcrumb) { %><div id="breadcrumb"><%- breadcrumb %></div>
<% } else { %>No Breadcrumb<% } %>
<%- body %>
</body>
</html>
body is a special layout variable - the first value passed to res.render is set as the body. Where do you get any other layout variables you want to send to a layout? That's what the second (often omitted ) object is for.
For instance, for the example above to work every render has to be written as
res.render('my body', {breadcrumb: foo});
There may be another way to seed all responses with a default value but in this case, its kind of okay that each response needs a new breadcrumb value, becuase you kind of want a custom breadcrumb for each url responder anyway.
Creating a breadcrumb handling library
Although you could hand code each and every breadcrumb, I want a little more elegance so I write a breadcrumb library to have relevant functions and constants. Actually I want it to put some constants into the global space without reference to the module. To do that I take advantage of the global variable called 'global'. This is a little confusing; in node.js global is a value that when found in a module, transfers all values attached to it to the global space. It may be a CommonJS feature - not sure; but the upshot is that when you write a module - as in my init.js module - as such
global.BC_HOME = '<a href="/">HOME</a>';
global.BC_SEP = ' ~ ';
exports.link = function (ref, text, opts){
return '<a href="' + ref + '">' + text + '</a>';
}
you can then use the values BC_HOME and BC_SEP in any module that requires 'init'. as in:
var init = require('./../init');
...
module.exports = {
// /users
index: function(req, res){
req.breadcrumb = 'bc_req';
res.render(users, {breadcrumb: BC_HOME + BC_SEP + 'users'});
},
// /users/:id
show: function(req, res, next){
get(req.params.id, function(err, user){
if (err) return next(err);
res.render(user, {breadcrumb: BC_HOME + BC_SEP
+ init.link('/users', 'users') + BC_SEP + 'show'});
});
},
The above example also has a function 'link' that is used in the second function in the object block. Because it is attached to exports, it must be referred to from the module object by name.

Post new comment