After the login, the session cookie is the visitor's key: whoever sends it is logged in as them. In the Set-Cookie header the server can add flags that tell the browser how to guard the cookie. HttpOnly: the page's JavaScript can't read it, so a script slipped into the page can't steal it. SameSite=Lax: the browser leaves it out of a form that another site posts to your API. Secure: it travels only over HTTPS. Expires: how long the browser keeps it. Without an expiry, the cookie is gone when the browser closes.
In server/app.js the session middleware is taken out, so req.session is undefined. At the start, /api/me and the login answer 500 with TypeError: Cannot read properties of undefined. You write the middleware back, now with the cookie's flags.
Any cookie can get these flags. Here is a theme cookie, on another route, that the browser keeps for one hour:
res.cookie("theme", "dark", {
httpOnly: true,
sameSite: "lax",
maxAge: 60 * 60 * 1000,
});
maxAge counts milliseconds. express-session reads the same flags from its cookie option. secure should be on only in production: the development site is plain http://localhost, where the browser would drop a Secure cookie. The session's secret signs the cookie, so nobody can make up a session id. A secret written in the code is known to everyone who reads the code, so in production it comes from the environment: process.env.SESSION_SECRET.
After the login, your server must send:
development (no NODE_ENV, no SESSION_SECRET):
POST /api/login → 200 Set-Cookie: connect.sid=<session id>; Path=/; Expires=<in 7 days>; HttpOnly; SameSite=Lax
production (NODE_ENV=production, SESSION_SECRET=x7Kq9vR2mW4pL8sN):
POST /api/login → 200 Set-Cookie: connect.sid=<session id>; Path=/; Expires=<in 7 days>; HttpOnly; Secure; SameSite=Lax
GET /api/me, same session id signed with "dev-secret-123" → 401 {"error": "Not logged in"}
On the page, Ana logs in and is still logged in after a reload, and the page's JavaScript can read no cookies at all.
Your task: in server/app.js, below app.use(express.json());, write the session middleware with one option per line: the secret from SESSION_SECRET (or "dev-secret-123"), resave and saveUninitialized set to false, and a cookie object with httpOnly, sameSite: "lax", secure in production and a maxAge of one week.
Assignment
Follow the Coding Tutorial to give the session cookie its flags and take the session secret from the environment.
Hintsecure is true or false: compare process.env.NODE_ENV with "production". A week in milliseconds is days × hours × minutes × seconds × 1000.
Free plan: 30 tutor messages. PRO is unlimited.
