I am Hack Sparrow
Captain of the Internets.

Use RedisStore instead of MemoryStore – Express.js in Production

After setting the NODE_ENV environment variable to 'production', when you try to run your Express.js app with sessions support, you will be hit by this:

Warning: connection.session() MemoryStore is not
designed for a production environment, as it will leak
memory, and obviously only work within a single process.

What it means is that the MemoryStore module used for managing sessions is not meant for production. So what do you do about it? Use RedisStore.

First install Redis and run it.

Then install RedisStore:

$ npm install connect-redis

And then modify app.js to to use RedisStore instead of the default MemoryStore:

var RedisStore = require('connect-redis')(express);

app.configure(function(){
...
app.use(express.cookieParser());
app.use(express.session({ store: new RedisStore, secret: 'lolcat' }));
// app.use(express.session({ secret: 'your secret here' }));
...
});

Make sure to delete or comment out the line app.use(express.session({ secret: 'your secret here' }));.

In case, you need to pass customized options to RedisStore:

app.use(express.session({ store: new RedisStore({host:'127.0.0.1', port:6380, prefix:'chs-sess'}), secret: 'lolcat' }));

There you have it - an efficient session store for your Express.js app in production, courtesy of RedisStore.

6 Responses to “Use RedisStore instead of MemoryStore – Express.js in Production”

  1. Dan says:

    Don’t you need redis also?

    redis = require(‘redis’).createClient(); //<- Don't you need this also?
    RedisStore = require('connect-redis')(express);

  2. Captain says:

    @Dan, of course we’ll need Redis running on the local machine, that’s why I have mentioned “First install Redis and run it”.

  3. Dan says:

    I don’t think I explained myself well. Assume redis is installed and running fine. I can interact with it using redis-cli, etc.

    Now I’m building my node app. Here’s my package.json:

    {
    “name”: “”,
    “description”: “”,
    “version”: “0.0.1”,
    “author”: “”,
    “keywords”: [],
    “repository”: {
    “url”: “”
    },
    “engines”: {
    “node”: “>=0.6.17″
    },
    “dependencies”: {
    ,”express”: “2.x.x”
    ,”redis”:”0.7.x” //<- Do I need this???????????
    ,"connect-redis":"1.3.x"
    },
    "devDependencies": {},
    "optionalDependencies": {}
    }

    And here's my app.js code:

    var express = require('express')
    ,crypto = require('crypto')
    ,redis = require('redis') //<-Not sure if I need this?
    ,RedisStore = require('connect-redis')(express)
    ,sessionStore = new RedisStore({
    host: "127.0.0.1",
    port: "6379"
    });

    var app = module.exports = express.createServer();

    app.configure(function(){
    app.use(express.bodyParser());
    app.use(express.cookieParser());
    app.use(express.session({
    store: sessionStore, // Use Redis Store
    secret: salt,
    cookie: { maxAge: month }
    }));
    });

  4. Dan says:

    I figured it out. Since my app doesn’t use app.router I needed to call session.save explicitly. Only needed connect- redis for it to work.

  5. TG says:

    How can node determine if a session has expired ? I see the ttl on the redis sess key is reset on each request. Also a new cookie is generated if the previous session was lost…

    Need a hook to determine if a key is no longer valid i.e. the session expired so we can redirect back to login page. Any examples on this ?

    Currently looks like redis drops the key and express just creates a new session…

  6. sangram says:

    I’m having trouble updating express session in redis using redisClient.set explained in http://stackoverflow.com/questions/20343202/updating-req-session-outside-of-express. See if you can help out. Thanks.

Make a Comment