Summary
Multiple JWT lifecycle flaws in FUXA allow deleted, disabled, or demoted users to retain privileged authenticated sessions after account changes.
The vulnerabilities affect both /api/refresh and /api/heartbeat token renewal flows when secureEnabled=true.
Under specific conditions, stale JWT claims continue to be trusted even after:
- the user account has been deleted
- the user role has been changed
- the user's
groups field has been cleared (groups=0)
This can allow previously issued refresh cookies or access tokens to continue minting new privileged JWTs.
Details
Affected Components
server/api/auth/index.js
server/api/jwt-helper.js
server/api/index.js
Root Causes
1. Stale JWT group fallback during refresh
POST /api/refresh uses:
userData?.groups || decoded.groups
This causes:
- deleted users (
userData == null) to fall back to stale JWT claims
- users with
groups = 0 to also fall back to stale JWT claims because 0 is falsy
As a result, previously issued admin refresh cookies may continue generating admin JWTs even after account changes.
2. Heartbeat endpoint re-signs stale claims
POST /api/heartbeat generates fresh JWTs using claims from the inbound token without validating current user state from the database.
This allows previously issued privileged access tokens to mint fresh privileged tokens after user demotion.
3. Refresh cookie lifetime extension
Successful refresh requests rotate the refresh cookie expiration window, allowing long-lived sessions to persist indefinitely if continuously refreshed.
Impact
An attacker with access to a previously issued refresh cookie or JWT may retain privileged access after:
- account deletion
- privilege removal
- user disablement
This weakens the effectiveness of incident-response actions intended to revoke compromised accounts or sessions.
Potential impact includes:
- persistent unauthorized administrative access
- access to user management APIs
- project manipulation
- creation of backdoor accounts
- modification of runtime configuration and scripts
Summary
Multiple JWT lifecycle flaws in FUXA allow deleted, disabled, or demoted users to retain privileged authenticated sessions after account changes.
The vulnerabilities affect both
/api/refreshand/api/heartbeattoken renewal flows whensecureEnabled=true.Under specific conditions, stale JWT claims continue to be trusted even after:
groupsfield has been cleared (groups=0)This can allow previously issued refresh cookies or access tokens to continue minting new privileged JWTs.
Details
Affected Components
server/api/auth/index.jsserver/api/jwt-helper.jsserver/api/index.jsRoot Causes
1. Stale JWT group fallback during refresh
POST /api/refreshuses:This causes:
userData == null) to fall back to stale JWT claimsgroups = 0to also fall back to stale JWT claims because0is falsyAs a result, previously issued admin refresh cookies may continue generating admin JWTs even after account changes.
2. Heartbeat endpoint re-signs stale claims
POST /api/heartbeatgenerates fresh JWTs using claims from the inbound token without validating current user state from the database.This allows previously issued privileged access tokens to mint fresh privileged tokens after user demotion.
3. Refresh cookie lifetime extension
Successful refresh requests rotate the refresh cookie expiration window, allowing long-lived sessions to persist indefinitely if continuously refreshed.
Impact
An attacker with access to a previously issued refresh cookie or JWT may retain privileged access after:
This weakens the effectiveness of incident-response actions intended to revoke compromised accounts or sessions.
Potential impact includes: