F-2025-0001·authentication

JWT cookie set without security flags (token theft and CSRF risk)

Fixedpentesttypescriptbackend
TL;DR

The session JWT was set in a cookie without HttpOnly, Secure, or SameSite attributes, leaving the token readable by client-side JavaScript and vulnerable to CSRF and theft via XSS.

Severity
HIGH
Impact
HIGH
Likelihood
HIGH
Method
MManual review
CAT.
Complexity
LOW
Exploitability
HIGH
02Section · Description

Description

The application issued a session JWT and stored it in a cookie using cookies().set("jwt", jwt) without specifying any security attributes. Because the cookie lacked HttpOnly, Secure, SameSite, Path, and expiration controls:

  • HttpOnly missing: The token was trivially accessible to any JavaScript executing in the origin. A single XSS or compromised third-party script equals full session theft.
  • Secure missing: If the site is ever served over HTTP (misconfiguration or staging), the cookie could be intercepted.
  • SameSite missing: Cross-site requests could carry the JWT, enabling CSRF state-changing actions.
typescript
// src/actions/auth.ts (excerpt)
const jwt = await thirdwebAuth.generateJWT({ payload: verifiedPayload.payload });
const cookieStore = await cookies();
cookieStore.set("jwt", jwt); // <-- no httpOnly/secure/sameSite/maxAge/path
03Section · Impact

Impact

  • Account takeover: an attacker with the JWT can call protected APIs and act as the user.
  • Privilege escalation: if tokens encode roles or claims, the attacker may reach privileged functionality.
  • Data exfiltration and financial loss: any actions available to the stolen session (viewing or moving funds, changing settings) become possible.
04Section · Recommendation

Recommendation

Set the cookie with secure attributes (server-side only):

typescript
cookies().set({
name: "jwt",
value: jwt,
httpOnly: true,
secure: process.env.NODE_ENV === "production",
sameSite: "lax",
path: "/",
maxAge: 60 * 60 * 24 * 7,
});

Use matching attributes on logout/delete. Issue short-lived JWTs (exp) and pair them with refresh tokens stored with stricter storage and rotation (refresh token HttpOnly, refresh endpoint protected).

Ipal Network: Confirmed. Zealynx: Fixed.

Status
Fixed
F-2025-0001