A scheduler's session cookie carries the presenter's identity and roster instead of a server-side record — when does signing that value suffice, and when must it be encrypted?
answer
- three positions, not two
- signed is readable, encrypted is not
- both replay until they expire
- authenticated encryption, not bare ciphertext
- carry a key identifier inside
basics
~20 sSigning stops alteration but not reading, so it suffices only when the contents are safe for the holder to see. Encrypt — with authenticated encryption, never bare ciphertext — when the roster or the roles are themselves worth hiding. Both replay until they expire.
solid answer
~50 sThere are three positions, not two. A **plain** value the caller can read and alter; a **signed** value the caller can read but cannot alter undetected, because a tag computed with a server-held key covers it; and an **authenticated-encrypted** value the caller can neither read nor alter. Signing answers integrity only, so choose it when everything inside is safe on the studio noticeboard. Encrypt when the contents themselves leak — a roster showing who is alone in the building overnight, role names that map your escalation path, internal record ids that disclose your scale. Plain encryption is not the third position: unauthenticated ciphertext can still be mangled, so the construction must authenticate. Both cookie-borne shapes share one cost: a copied value replays until the moment it expires, and you gave up the server-side record that would have let you withdraw it sooner.
code
json · 7 lines{
"kid": "2026-09",
"iat": 1789084800,
"sub": "a41c9",
"roles": ["presenter", "playout.edit"],
"slots": ["mon-2100", "thu-0300"]
}go deeper
Hold the one distinction: a tag over the contents stops them being altered, and it does not stop them being read. Anything you would not show the person holding the cookie must not travel in a signed one.
Explain all three positions and why encryption without authentication is not one of them, then name what belongs inside the payload: a key identifier, an issued-at value the server enforces, and as few claims as the design can survive on.
Own the operational consequence out loud. State the revocation lag as a number equal to the remaining lifetime, say what you would add if the business cannot accept it, and admit that adding it restores the lookup you removed.
Treat this as choosing where authority lives for the next several years. Cookie-borne state buys throughput and costs you the ability to intervene; decide which the service needs at its worst hour, not its busiest.
Once you decide the cookie will carry the scheduler's conclusion about the caller rather than a reference to a record, a second decision follows immediately, and most candidates only know half of it. ## The three positions | what the cookie holds | caller can read it | caller can alter it undetected | what a copied value leaks | |---|---|---|---| | plain claims | yes | **yes** | everything, and it is forgeable too | | signed claims | **yes** | no | everything it asserts | | authenticated-encrypted claims | no | no | nothing but its existence and size | The middle and right columns are the whole question. Interviewers ask it because "we sign the cookie" is said as though it settled both, and it settles one. ## What a signature proves, and to whom At issuance the scheduler serialises the claims and computes a tag over the bytes with a key only it holds — an HMAC with a symmetric key is the usual construction. At verification, the scheduler recomputes the tag over the bytes as received and compares. Two things follow, and keeping them apart is the point: - The **server** learns that these exact bytes are ones it produced and that nobody changed them in the caller's storage or on the way back. - The **caller** learns nothing new, but loses nothing either: the payload is still right there in front of them, usually in a reversible encoding chosen for URL safety rather than for secrecy. So a signature is an answer to forgery and not to disclosure. If the roster inside the value would be a problem printed on a noticeboard, signing has not helped. ## When the contents are themselves the secret A community station's cookie is a good example of contents that matter. It plausibly carries which presenter holds the desk, which roles they have, and which slots they may edit. Read off a machine in the studio that four people share across a shift, that tells a reader who is alone in the building at 03:00, which account is worth attacking, and — through an internal record id — roughly how many accounts exist. None of that is altered; all of it is disclosed. That is the case for authenticated encryption. One trap sits here: **encryption alone is not the third position**. A ciphertext without an authentication tag can often be modified in ways that change the plaintext predictably, so the construction must both hide and authenticate. Saying "encrypted, therefore tamper-proof" is the confusion this question is designed to surface. ## What you put inside the value 1. A **key identifier** (`kid`), so verification selects the one key that protected this value instead of trying every key you hold. Treat it strictly as a selector into your own keyring and nothing more — an arriving value must never be able to name a key you then go and fetch or construct. 2. An **issued-at** timestamp, because the server must be able to age the value out on its own terms; the cookie's own `Max-Age` and `Expires` attributes are enforced by the caller's browser, and a caller who keeps sending the value regardless is not violating anything. 3. The **smallest** set of claims that removes the lookup. Every extra field rides on every request to that path and enlarges whatever a copy discloses. ## What both cookie-borne shapes cost you - **Replay until expiry.** The value is a bearer credential. A copy taken off the shared machine is honoured exactly as the original, and because there is no server-side record, there is nothing to delete to stop it. - **Revocation lag equal to the remaining lifetime.** Removing a presenter's roster access does not reach a value already in a browser. You can only shorten the lifetime, or reintroduce server state — a version counter, a denylist — which is the very lookup the design existed to avoid. Be explicit about this number rather than claiming the value is "revoked". - **Staleness.** The roles inside were true at issuance and are quoted back to you long afterwards, so any change to them applies from the next issuance and not before. - **Every byte on every request**, which is the quiet reason these payloads should stay small. ## The honest summary Sign when integrity is the whole requirement and the contents are boring. Encrypt, with authentication, when the contents would embarrass you on a shared screen. And in both cases, say out loud how long a leaked value keeps working — because that sentence is the one a weak answer leaves out.
- Does encrypting the cookie mean a copied value can no longer be replayed?No. Replay needs no understanding of the contents — the holder presents the bytes and the scheduler decrypts them successfully, because it is the intended reader. Encryption removes disclosure, not bearer semantics. Only a shorter lifetime, or server state you can delete, shortens the window in which a copy works.
- The team wants to revoke one presenter's cookie-borne session immediately. What are the options?Shorten the lifetime so the wait is bounded, or reintroduce a server-side check — a per-account version counter compared against a value inside the payload, or a denylist of identifiers until they expire. Both are lookups, which is the cost the cookie-borne design was avoiding; choosing one is admitting that trade rather than working around it.
- Why does the payload need an issued-at value when the cookie already has an expiry attribute?Because `Max-Age` and `Expires` are instructions to the caller's browser, and the browser is the only party that acts on them. A caller who keeps presenting the value after the attribute lapses breaks nothing, so the server must carry its own timestamp inside the protected payload and enforce the age itself.
A postcard under a tamper-evident seal versus a sealed envelope. The seal proves nobody rewrote the message, and the postman still reads every word of it; only the envelope keeps the contents private, and it needs its own seal to prove nothing was swapped inside.
saying these in an interview costs you the question
- Signing the cookie hides what the value says
- Encryption stops the value being replayed by a copier
- Ciphertext cannot be tampered with, so no tag is needed
- A signed cookie can be revoked the moment a role changes
- Put the whole user profile in it while you are there