Migrating to Express.js v3

I’ve been working on a Node.js web application for a couple of months now.  A few days ago I ran npm update on my project without really thinking about it (d’oh), and my Express.js install was upgraded to v3.  There are a lot of changes in v3, and it took the best part of a day for me to work through them all.  I’ve outlined some of the issues I encountered below. Some of them aren’t particularly easy to find fixes for, so hopefully this will help someone out.

Getting started

Your first port of call should be the migration guide:  There is also a wiki article on the new features (, but there’s no need to read through this until you’ve got everything fixed and working again.

‘Layout’ removed

The first thing that will be immediately apparent is that none of your views are rendering properly.  The default way to render views in Express v2.x was to have a master layout template that all other views inherited from. If you were using Jade as your template engine, a layout template used to look something like this:

!!! 5
    title Title
    link(rel='stylesheet', '/style.css')
  body!= body

This template would be applied to all other views – all other views inheriting from this template would be rendered as != body.

Both ‘layout’ and partials have been removed in Express v3, so when you first load your site or application after the upgrade, you’ll see that only the body of your view template is being rendered to the page.  The fix for this is dependent upon which template engine you use.  I’m using Jade, so I’ve outlined the fix below, but if you’re using EJS or similar, you’ll need to look it up.

Layouts in Jade

In the latest version of Jade, the way in which views are rendered has been ‘reversed’ as it were – rather than views inheriting from layouts, a view will specify the layout it wants to extend. This gives you greater flexibility with your views, as you can have different layouts for different purposes.

To get your views to render again, you’ll firstly need to go through all your views and specify the layout you want to extend at the top of each template file, using the keyword extends. The path to layout is relative, so if your views are nested in folders, don’t forget ../.  One thing I haven’t figured out yet is if you can set a fixed path to layout, so that any deeply nested views can inherit from extends layout rather than extends ../../../layout. Answers on a postcard please :p

The second thing you’ll have to do is designate blocks in your layout – chunks of code to be replaced with the content in the view template:

// layout.jade
!!! 5
    title Title
    link(rel='stylesheet', '/style.css')
    block content
    block scripts


// view.jade
extends layout

block content
  h1 Content
  p Some content here 
block scripts

This should fix your view rendering problems.

req.flash removed

Req.flash was removed in favour of attaching messages to req.session.messages.  I’ve made extensive use of req.flash in my application, so it would have taken me a long time to rewrite all my message code.  Luckily, the migration guide points us towards connect-flash, a middleware that implements req.flash in Express v3 – very handy if you don’t want to do a big refactor.

Dynamic helpers

Dynamic helpers have been removed in favour of app.locals.use(callback).  Now, instead of assigning view helpers to an object, you assign them directly to res.locals:

Express v2.x

  session: function(req, res){
    return req.session;

Express v.3

app.locals.use(function(req, res) {
  res.locals.session = req.session;
}); not serving client

There are a number of reasons why might not be serving the client, and just as many proffered solutions on stackoverflow to try.  After a bit of digging, I discovered that the bug in my application was related an issue with Connect:

Long story short, you have to call app.listen() before io.listen() – this wasn’t the case before. It’s annoying how the simplest bugs can sometimes take the longest time to track down 🙂 and sessions

In my application, has access to session data.  When I was initially developing this functionality, I leaned heavily on the code from Daniel Baulig’s excellent blog post on passing session information to via the handshake/authorisation method (  As Daniel has now noted at the top of his guide, it requires a few tweaks to work with Express v3.

The first thing that you’ll need to change is where you put your application’s session secret. Formerly, you specified this in express.session – you’ll need to move it to reside in express.cookieparser:

app.configure(function() {

If you make the above change and run your application, you’ll notice that the session cookie is now being transmitted, but we get another 500 error instead. If we take a look at Daniel’s code:

sio.set('authorization', function (data, accept) {
    if (data.headers.cookie) {
        data.cookie = parseCookie(data.headers.cookie);
        data.sessionID = data.cookie['express.sid'];
        // save the session store to the data object
        // (as required by the Session constructor)
        data.sessionStore = sessionStore;
        sessionStore.get(data.sessionID, function (err, session) {
            if (err || !session) {
                accept('Error', false);
            } else {
                // create a session object, passing data as request and our
                // just acquired session data
                data.session = new Session(data, session);
                accept(null, true);
    } else {
       return accept('No cookie transmitted.', false);

With a bit of debugging, you’ll find that the line that starts sessionStore.get is failing and throwing an error on the next line.  This is because the way that cookie signing is implemented in Connect has changed, and sessionStore.get is being passed the long session id from the cookie, rather than the short (24 character) session id it’s expecting (for more information see this thread).  In order to get the short session id, you need to split the long session id at the dot:

data.sessionID = data.cookie['express.sid'].split('.')[0];

Data.sessionID should now contain the short SID – this will be evaluated against the SID contained in the sessionStore as normal.  No more pesky 500 errors!

If you have any comments or suggestions, please feel free to comment below.  Thanks!

The following two tabs change content below.
Nicola Hibbert is a mobile game developer based in Guildford, Surrey.

Latest posts by Nicola (see all)


  1. kenshiro says:

    Great post Nikki! I had spent the last few evenings wondering why the hell I could not get and express v3 sessions to work.
    Thanks to you I have not broken any keyboards nor tables due to rage;)

  2. Marcus Pope says:

    To answer your question about ways to avoid deeply nested relative paths in layouts, you can use “extends /layout” to grab a layout from your base view path. Basically a root relative path.

    Thanks for the rest of the info it was all I needed to upgrade.

  3. mwq27 says:

    I ran across some problems when trying to get to work with the sessions. Thanks for posting the above fixes, it really helped a lot. But it wasn’t completely working for me, and after some debugging, it seemed that I had to do one more step after the

    “handshakeData.sessionID = handshakeData.cookie[‘express.sid’].split(‘.’)[0];”
    I’m using MemoryStore (var sessionStore = new MemoryStore(); ) for sessions, and if I print out sessionStore i get
    { sessions : {‘000000000000000000’}} (thats a fake sessionid),
    but if i print out handshakeData.sessionID i get s:000000000000000. It has the “s:” in front of it. So once I did handshakeData.sessionID = handshakeData.sessionID.split(‘:’)[1]; , everything worked for me, since now it returned the actual session ID and not the s:sessionID. Hopefully this helps people having the same issue as me 🙂

  4. codewarrioraq says:

    How can u access and set cookie inside of Like this?

    sio.sockets.on(‘connection’, function (socket) {
    socket.on(‘X’, function (data) {
    data.test = ‘1’;


    app.get(‘/’, function (req, res) {
    console.log(req.cookies.test); // 1

    • nikki says:

      Urm, no? I just documented a few of the problems I encountered with my migration. I just happen to use Jade as my templating engine. Why would you be screwed?

  5. Buritica says:

    One note: app.locals.use() has been removed since 3.0.0beta6, you should use app.use() with middleware instead. For example:

    app.use(function(req, res, next) {
    res.locals.session = req.session;

  6. TJ says:

    Good post, I think that part will help people a lot. It still really surprises me though that no one has taken that blog post snippet and made it a module yet though to abstract things out, everyone painfully tries to duplicate the same thing instead.

    req.session.messages isn’t necessarily preferred, it’s just that req.flash() was a bit of an odd level of abstraction and didn’t quite fit with my goals in Express. It’s very rails-like in name which is sort of awkward and people didn’t understand that it was simply stuffing some data in the session. So I think having them just stuff things in the session simplifies things nicely our you can stub your own methods like req.error(‘msg’) to populate them etc