Overview
Cookies are small pieces of data (up to about 4 KB each) that a server asks the browser to store with Set-Cookie and that the browser automatically sends back on matching requests. They carry session IDs, preferences, and tracking identifiers.
Because browsers send cookies automatically, their security attributes are critical. HttpOnly keeps JavaScript from reading them (protects against XSS theft), Secure sends them only over HTTPS, and SameSite controls whether they are sent on cross-site requests (protects against CSRF). Domain and Path limit where they are sent.
The bouncer stamps your hand when you enter. Every time you come back to the door, the stamp is checked automatically. You cannot easily copy it (HttpOnly), it is only honored at this club (Domain), and it washes off after tonight (expiry).
When to use it
- Storing session IDs for browser authentication.
- Remembering small preferences (language, theme).
- Keeping authentication tokens out of JavaScript's reach.
- Sharing login across subdomains of one site.
Where it shows up in interviews
Recognize it when: where to store credentials in a web app.
- Design login for a web banking app
- Protect a web app from XSS and CSRF
Recognize it when: sharing sessions across subdomains or sites.
- Design SSO across app.example.com and admin.example.com
Where it is used in real software
Chrome treats cookies without SameSite as Lax by default, which blocked a large class of CSRF attacks.
Safari and Firefox block third-party tracking cookies, and Chrome has been restricting them, changing ad tech and embedded login flows.
GDPR and ePrivacy rules require consent for non-essential cookies such as analytics and advertising.
Key terms
- HttpOnly
- Not readable by document.cookie; blocks theft via XSS.
- Secure
- Only sent over HTTPS.
- SameSite
- Strict (never cross-site), Lax (top-level navigations only), None (always, requires Secure).
- Domain / Path
- Which hosts and paths receive the cookie.
- Max-Age / Expires
- Lifetime; without it, a session cookie ends when the browser closes.
How it works, step by step
- 1Server sets the cookie
Set-Cookie: sid=abc; HttpOnly; Secure; SameSite=Lax; Path=/; Max-Age=1800.
- 2Browser stores it
Scoped to the domain and path.
- 3Browser sends it automatically
Cookie: sid=abc on matching requests, subject to SameSite rules.
- 4Server reads and validates
Looks up the session or verifies the signed value.
- 5Expire or clear
Max-Age=0 or a past Expires date deletes it.
SameSite behavior
Cookie set by bank.example; request initiated from evil.example
| Request from another site | Strict | Lax | None |
|---|---|---|---|
| Clicking a link to bank.example | Not sent | Sent | Sent |
| Form POST to bank.example | Not sent | Not sent | Sent |
| Image or fetch to bank.example | Not sent | Not sent | Sent |
| Same-site request | Sent | Sent | Sent |
NOWRequest from another site: Clicking a link to bank.example | Strict: Not sent | Lax: Sent | None: Sent
Lax blocks cross-site POST requests, which stops classic CSRF while keeping normal links working. Use None only when you truly need cross-site cookies (embedded widgets), and always with Secure.
Implementation
HTTP/1.1 204 No ContentSet-Cookie: sid=9f8c2a...; Path=/; HttpOnly; Secure; SameSite=Lax; Max-Age=1800Set-Cookie: lang=en; Path=/; Max-Age=31536000; SameSite=Lax # __Host- prefix: browser enforces Secure, Path=/, and no Domain (host-only)Set-Cookie: __Host-sid=9f8c2a...; Path=/; Secure; HttpOnly; SameSite=StrictComplexity and performance
And a per-domain count limit.
Keep cookies small; use a separate domain for static assets.
Trade-offs
HttpOnly cookies cannot be read by injected scripts but need CSRF protection; localStorage avoids CSRF but any XSS can steal the token.
Setting Domain=example.com shares the cookie with every subdomain, including less trusted ones.
Variants and related techniques
The value includes an HMAC so the server can detect tampering without a store.
__Host- and __Secure- enforce security attributes in the browser.
Common mistakes
- Session cookies without HttpOnly.
Fix: Always set HttpOnly for authentication cookies.
- SameSite=None without Secure.
Fix: Browsers reject it; None requires Secure.
- Storing sensitive data in cookie values.
Fix: Store an opaque ID and keep data server-side.
Interview questions
How do HttpOnly and SameSite protect a web app?
HttpOnly prevents JavaScript (including injected XSS scripts) from reading the cookie. SameSite prevents the browser from sending it on cross-site requests, which blocks most CSRF attacks.
Why serve static assets from a separate domain?
So large cookies for the main domain are not sent with every image and script request, reducing request size.
Practice problems
| Problem | Difficulty | What it trains |
|---|---|---|
| Write secure Set-Cookie headers for a session | Easy | Attributes. |
| Protect a legacy form-based app from CSRF | Medium | SameSite and CSRF tokens. |