Skip to content

Commit

Permalink
option to prevent session save when unmodified
Browse files Browse the repository at this point in the history
fixes #7
closes #38
  • Loading branch information
joewagner authored and dougwilson committed May 19, 2014
1 parent 198ad7a commit 6cc95c9
Show file tree
Hide file tree
Showing 4 changed files with 118 additions and 7 deletions.
5 changes: 5 additions & 0 deletions History.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,8 @@
unreleased
==========

* Add `resave` option to control saving unmodified sessions

1.1.0 / 2014-05-12
==================

Expand Down
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ middleware _before_ `session()`.
- `cookie` - session cookie settings.
- (default: `{ path: '/', httpOnly: true, secure: false, maxAge: null }`)
- `rolling` - forces a cookie reset on response. The reset affects the expiration date. (default: `false`)
- `resave` - forces session to be saved even when unmodified. (default: `true`)


#### Cookie options
Expand Down
29 changes: 22 additions & 7 deletions index.js
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,11 @@ function session(options){
, storeReady = true
, rollingSessions = options.rolling || false;

// TODO: switch default to false on next major
var resaveSession = options.resave === undefined
? true
: false;

// notify user that this store is not
// meant for a production environment
if ('production' == env && store instanceof MemoryStore) {
Expand Down Expand Up @@ -153,7 +158,7 @@ function session(options){
return
}
// compare hashes and ids
} else if (originalHash == hash(req.session) && originalId == req.session.id) {
} else if (!isModified(req.session)) {
debug('unmodified session');
return
}
Expand All @@ -170,20 +175,30 @@ function session(options){
res.end = function(data, encoding){
res.end = end;
if (!req.session) return res.end(data, encoding);
debug('saving');
req.session.resetMaxAge();
req.session.save(function(err){
if (err) console.error(err.stack);
debug('saved');
res.end(data, encoding);
});

if (resaveSession || isModified(req.session)) {
debug('saving');
return req.session.save(function(err){
if (err) console.error(err.stack);
debug('saved');
res.end(data, encoding);
});
}

res.end(data, encoding);
};

// generate the session
function generate() {
store.generate(req);
}

// check if session has been modified
function isModified(sess) {
return originalHash != hash(sess) || originalId != sess.id;
}

// get the sessionID from the cookie
req.sessionID = unsignedCookie;

Expand Down
90 changes: 90 additions & 0 deletions test/session.js
Original file line number Diff line number Diff line change
Expand Up @@ -113,6 +113,96 @@ describe('session()', function(){
})
})

describe('resave option', function(){
it('should default to true', function(done){
var count = 0;
var app = express();
app.use(cookieParser());
app.use(session({ secret: 'keyboard cat', cookie: { maxAge: min }}));
app.use(function(req, res, next){
var save = req.session.save;
res.setHeader('x-count', count);
req.session.user = 'bob';
req.session.save = function(fn){
res.setHeader('x-count', ++count);
return save.call(this, fn);
};
res.end();
});

request(app)
.get('/')
.expect('x-count', '1')
.expect(200, function(err, res){
if (err) return done(err);
request(app)
.get('/')
.set('Cookie', 'connect.sid=' + sid(res))
.expect('x-count', '2')
.expect(200, done);
});
});

it('should prevent save on unmodified session', function(done){
var count = 0;
var app = express();
app.use(cookieParser());
app.use(session({ resave: false, secret: 'keyboard cat', cookie: { maxAge: min }}));
app.use(function(req, res, next){
var save = req.session.save;
res.setHeader('x-count', count);
req.session.user = 'bob';
req.session.save = function(fn){
res.setHeader('x-count', ++count);
return save.call(this, fn);
};
res.end();
});

request(app)
.get('/')
.expect('x-count', '1')
.expect(200, function(err, res){
if (err) return done(err);
request(app)
.get('/')
.set('Cookie', 'connect.sid=' + sid(res))
.expect('x-count', '1')
.expect(200, done);
});
});

it('should still save modified session', function(done){
var count = 0;
var app = express();
app.use(cookieParser());
app.use(session({ resave: false, secret: 'keyboard cat', cookie: { maxAge: min }}));
app.use(function(req, res, next){
var save = req.session.save;
res.setHeader('x-count', count);
req.session.count = count;
req.session.user = 'bob';
req.session.save = function(fn){
res.setHeader('x-count', ++count);
return save.call(this, fn);
};
res.end();
});

request(app)
.get('/')
.expect('x-count', '1')
.expect(200, function(err, res){
if (err) return done(err);
request(app)
.get('/')
.set('Cookie', 'connect.sid=' + sid(res))
.expect('x-count', '2')
.expect(200, done);
});
});
});

it('should retain the sid', function(done){
var n = 0;

Expand Down

0 comments on commit 6cc95c9

Please sign in to comment.