By NHI Mgmt Group Editorial TeamBased on Descope: “The Developer’s Guide to JWT Storage” (November 23, 2024)

TL;DR: JWTs are widely used for application authentication, but insecure browser storage can expose tokens to XSS, CSRF, and extension-based theft, according to Descope’s developer guide. The core issue is not token format but where the token lives, because storage choice directly changes the compromise path and revocation options.


At a glance

What this is: This guide compares common browser JWT storage patterns and shows that insecure storage expands token theft risk even when the JWT itself is well formed.

Why it matters: IAM and app security teams need to treat browser storage as part of the authentication design, because the wrong storage choice can turn a valid session token into a reusable bearer credential.


Context

JWT storage is not just an implementation detail. Once a token is issued, the browser becomes part of the authentication boundary, and the storage decision affects whether an attacker can steal, replay, or inspect the token through XSS, CSRF, or a malicious extension.

The guide separates creation, storage, and usage, which is the right way to think about the problem. For identity and access teams, that means browser token handling needs to be reviewed alongside session design, revocation behaviour, and cross-domain architecture rather than as a frontend convenience choice.


Key questions

Q: What breaks when JWTs are stored in local storage or session storage?

A: The main failure is script readability. Both storage methods are directly accessible to JavaScript, so an XSS event can expose active tokens quickly. Local storage also persists longer than session storage, which increases the time window for abuse if the token is stolen.

Q: When should teams prioritise HttpOnly cookies over local storage for JWTs?

A: Teams should prioritise HttpOnly cookies when reducing direct JavaScript access matters more than avoiding CSRF complexity. Cookies can narrow token theft paths, but only if the application also has anti-CSRF controls, proper domain scoping, and a server-side revocation model that matches the session design.

Q: What are the signs that browser JWT storage is failing in practice?

A: Warning signs include tokens surviving far longer than intended, refresh logic that hides stale sessions, repeated reliance on local storage for convenience, and authentication flows that cannot explain how revocation works. Those signals usually mean the team has not defined the token’s real exposure window.

Q: How should security teams handle JWT revocation after browser compromise?

A: Teams should assume the stolen token can be replayed until expiry unless revocation is enforced server side. That means revocation checks, short token lifetimes, and session invalidation paths must be designed before the browser storage decision is finalised.


Technical breakdown

How browser storage changes JWT exposure

JWTs are bearer tokens, so possession often matters more than the token format itself. If an attacker can read the token from local storage, session storage, or memory, they can replay it as the user until expiry or revocation. Cookies reduce direct JavaScript access when HttpOnly is set, but they introduce other trade-offs such as CSRF exposure and cross-domain complexity. The technical question is not which store is simplest to code against, but which store keeps the token outside the easiest theft path for the application’s threat model.

Practical implication: choose storage based on the dominant attack path, not developer convenience.

Why XSS, CSRF, and extensions matter differently by storage type

Local storage and session storage are readable by client-side scripts, which makes XSS the primary theft path. Cookies are harder for scripts to read when configured with HttpOnly, Secure, and SameSite, but they can still be replayed in unwanted requests if CSRF protections are weak. In-memory storage removes the obvious browser persistence target, yet it does not stop a sufficiently capable script from extracting the token at runtime. Browser extensions add another layer because they can access page context or storage depending on permissions and browser behaviour.

Practical implication: map each storage option to its most likely theft path and test that path explicitly.

How token lifecycle and revocation interact with browser storage

JWT storage cannot be evaluated separately from expiry, rotation, and revocation. A long-lived token in browser storage expands the window for replay after compromise, while short-lived tokens with refresh logic reduce exposure but increase implementation complexity. Cookie-based designs can support server-side invalidation more naturally than purely client-managed storage, but only if the server actually enforces revocation and session state. In other words, browser storage decides how easily the token can be stolen, while lifecycle controls decide how useful that stolen token remains.

Practical implication: align storage choice with token lifetime and revocation behaviour before shipping the flow.


Threat narrative

Attacker objective: The attacker wants a reusable bearer token that lets them act as the authenticated user without needing the user’s password.

  1. Entry occurs when an attacker exploits XSS, a malicious browser extension, or a compromised page context to reach the browser-held token.
  2. Credential access follows when the token is read from local storage, session storage, in-memory variables, or an accessible cookie context.
  3. Impact occurs when the stolen JWT is replayed to impersonate the user and access protected application data or actions.

Read our 52 NHI Breaches Analysis report for a comprehensive view of breaches impacting Non-Human Identities including AI Agents.


NHI Mgmt Group analysis

JWT storage is part of the authentication control plane, not a frontend preference. The moment a bearer token is placed in the browser, the application inherits the browser’s exposure model, including script access, extension access, and cross-site request behaviour. That means session design, token lifetime, and storage method must be governed together, not reviewed as separate layers. Practitioners should treat browser token placement as an IAM decision with direct compromise consequences.

HttpOnly cookies narrow one theft path but do not remove the governance problem. They reduce direct JavaScript access, yet they introduce CSRF handling, domain scoping, and server-side revocation questions that many teams underweight. The useful question is not whether cookies are safer in the abstract, but whether the rest of the session design is mature enough to support them. Teams need to validate the full authentication boundary, not just the storage primitive.

Long-lived browser tokens create identity blast radius that survives the original login event. If a token stays valid across refreshes, tabs, or sessions, the compromise window becomes much larger than the user’s active interaction window. That changes the governance burden from login security to token containment and invalidation discipline. Practitioners should narrow the exposure window wherever the use case allows.

Browser extension access is an overlooked trust boundary in JWT handling. Many storage discussions stop at XSS, but extensions can observe or manipulate session material in ways that bypass the assumptions behind simple storage choices. That is a reminder that browser-held credentials should be designed for the weakest execution context the user environment can plausibly present. Identity teams should account for the full browser runtime, not only application code.

From our research library:

What this signals

JWT storage decisions should be treated as control design decisions. The safe choice is not the same across every application. A single-page app with short sessions, a cross-domain BFF pattern, and a mobile companion app all shift the acceptable storage pattern, so practitioners need a storage policy rather than one default practice.

Browser-held bearer tokens expand the attack surface in ways that are easy to underestimate because the compromise path is often indirect. The practical signal to watch is whether your team can clearly explain who can read the token, how long it remains useful, and what actually invalidates it.


For practitioners

  • Review JWT storage against the dominant theft path Map whether XSS, CSRF, extension access, or cross-domain flow is the most realistic exposure route for your application, then choose storage around that route rather than defaulting to local storage.
  • Use HttpOnly, Secure, and SameSite together If cookies carry the token, require HttpOnly, Secure, and SameSite and pair them with anti-CSRF protections so the browser cannot silently turn authentication into request forgery.
  • Shorten token lifetime and rotate aggressively Reduce the time a stolen JWT remains useful by keeping browser tokens short-lived and tying renewal to explicit refresh handling and revocation checks.
  • Test browser extension and XSS exposure Verify whether a malicious script or extension can read or replay the token from the chosen storage pattern, including runtime access in single-page application flows.
  • Use a backend-for-frontend for cross-domain token handling When the frontend and APIs span domains, centralise browser interaction through a backend-for-frontend so the browser does not need to manage multiple token delivery paths directly.

Key takeaways

  • JWTs become a browser security problem when storage choices make tokens easy to steal and replay.
  • The article’s main lesson is that different storage options trade XSS exposure, CSRF exposure, and revocation control against each other.
  • Teams should align storage method, token lifetime, and invalidation behaviour before shipping authentication flows.

Standards & Framework Alignment

This section maps relevant standards and security frameworks to the operational risks and controls described in this guidance.

OWASP Non-Human Identity Top 10 and MITRE ATT&CK address the attack and risk surface, while NIST SP 800-53 Rev 5 and NIST CSF 2.0 set the governance and control requirements practitioners need to meet.

FrameworkControl / ReferenceRelevance
OWASP Non-Human Identity Top 10NHI-02 — Secret LeakageBrowser-held JWTs can be exposed to scripts, extensions, or theft paths that leak usable credentials.
NHI-07 — Long-Lived SecretsLong-lived JWTs in browser storage extend the replay window after compromise.
Recommendation — Reduce browser token leakage by moving JWTs away from script-readable storage where possible. Shorten JWT lifetime and pair storage with explicit renewal and revocation controls.
NIST SP 800-53 Rev 5IA-5 — Authenticator ManagementJWT expiry, rotation, and invalidation are authenticator lifecycle concerns.
Recommendation — Apply IA-5 discipline to token issuance, rotation, and invalidation timing.
NIST CSF 2.0PR.AA-05 — Access Permissions, Entitlements and AuthorizationsBrowser token handling governs who can present valid access to protected services.
Recommendation — Align browser token handling with entitlement scope and session revocation requirements.
MITRE ATT&CKTA0006 — Credential AccessThe article centres on theft of bearer tokens through browser-side access paths.
Recommendation — Map browser token theft scenarios to credential access and test exposure paths accordingly.

Key terms

  • Bearer Token: A bearer token is a credential that grants access to whoever possesses it, without requiring strong proof that the holder is the intended client. In NHI environments, that makes theft and replay the main risk, especially when tokens are long-lived, broadly scoped, or stored in local files.
  • HttpOnly Cookie: An HttpOnly cookie is a session cookie that JavaScript cannot read, which reduces the risk of theft through client-side script compromise. In BFF architectures, it is a common way to keep authentication material out of browser-accessible storage while still allowing the server to authorize requests.
  • Cross-Site Scripting (XSS): A web application flaw where untrusted input is rendered in a way that causes script to execute in a user’s browser. It usually appears when output encoding, templating, or input handling is inconsistent across code paths and frameworks.
  • Session Storage: Session storage is where an application keeps state tied to a user between requests. Secure session design keeps sensitive data out of the session, avoids client side exposure when possible, and uses encryption or server side persistence to reduce tampering, leakage, and session hijacking risk.

Deepen your knowledge

NHI governance, agentic AI identity, and machine identity lifecycle are core topics in our NHI Foundation Level course, the industry's only accredited NHI security programme. If you are responsible for identity security strategy or NHI governance in your organisation, it is worth exploring.
NHIMG Editorial Note
Published by the NHIMG editorial team on August 19, 2026.
Updated on October 6, 2026.
NHI Mgmt Group, the independent authority on Non-Human Identity, IAM, and Agentic AI security. nhimg.org