Skip to main content
Practice Problems

How does session management work in Express.js?

Session Management in Express.js

Sessions allow you to persist data across multiple HTTP requests from the same client. Since HTTP is stateless, sessions provide state by storing data on the server and identifying the client with a cookie.


How Sessions Work

Client Server β”‚ β”‚ │── GET /login ──────────>β”‚ β”‚ β”‚ Creates session, stores in memory/DB β”‚<── Set-Cookie: sid=abc──│ β”‚ β”‚ │── GET /dashboard ──────>β”‚ Cookie: sid=abc β”‚ β”‚ Looks up session by "abc" β”‚<── User dashboard ─────│

Using express-session

bash
npm install express-session
js
const session = require('express-session'); app.use(session({ secret: process.env.SESSION_SECRET, resave: false, saveUninitialized: false, cookie: { secure: process.env.NODE_ENV === 'production', // HTTPS only httpOnly: true, // Not accessible via JavaScript maxAge: 24 * 60 * 60 * 1000, // 24 hours sameSite: 'lax' // CSRF protection } }));

Using Sessions

js
// Login β€” store user in session app.post('/login', async (req, res) => { const user = await authenticate(req.body); if (user) { req.session.userId = user.id; req.session.role = user.role; res.json({ message: 'Logged in' }); } else { res.status(401).json({ error: 'Invalid credentials' }); } }); // Protected route β€” check session app.get('/dashboard', (req, res) => { if (!req.session.userId) { return res.status(401).json({ error: 'Not authenticated' }); } res.json({ message: `Welcome, user ${req.session.userId}` }); }); // Logout β€” destroy session app.post('/logout', (req, res) => { req.session.destroy((err) => { if (err) return res.status(500).json({ error: 'Logout failed' }); res.clearCookie('connect.sid'); res.json({ message: 'Logged out' }); }); });

Session Stores

By default, sessions are stored in memory (not suitable for production):

StorePackageBest For
MemoryBuilt-inDevelopment only
Redisconnect-redisProduction (fast, scalable)
PostgreSQLconnect-pg-simpleWhen you already use Postgres
MongoDBconnect-mongoWhen you already use MongoDB
js
const RedisStore = require('connect-redis').default; const { createClient } = require('redis'); const redisClient = createClient({ url: process.env.REDIS_URL }); await redisClient.connect(); app.use(session({ store: new RedisStore({ client: redisClient }), secret: process.env.SESSION_SECRET, resave: false, saveUninitialized: false }));

Sessions vs JWT

FeatureSessionsJWT
StorageServer-sideClient-side (token)
ScalabilityNeeds shared storeStateless
RevocationEasy (delete session)Hard (blacklist needed)
SizeSmall cookieLarger token
SecurityCookie attributesToken validation
Best forTraditional web appsAPIs, SPAs, microservices

Recommendation: Use sessions for server-rendered apps. Use JWT for APIs consumed by SPAs or mobile apps. For large-scale systems, use Redis-backed sessions for easy horizontal scaling.

Short Answer

Interview ready
Premium

A concise answer to help you respond confidently on this topic during an interview.

Finished reading?
Practice Problems