S3 Bucket to Source Code to Secrets to OAuth: A Five-Step Chain
Cybersecurity
One world-readable S3 bucket, a Webpack bundle with a sourcemap, a hardcoded API key, an OAuth client secret, an admin role. Five steps, one critical, and a lesson in why every public artifact is a foothold.
By Arjun Raghavan, Security & Systems Lead, BIPI · June 17, 2023 · 10 min read
The chain at a glance
- Find a misconfigured S3 bucket with directory listing
- Download production JavaScript bundle and its sourcemap
- Recover original source, find hardcoded API key
- Use the key to read an admin config that contains OAuth client_secret
- Use the client_secret to mint tokens for an admin service account
Step one, finding the bucket
Subdomain enumeration plus CNAME analysis reveals static assets hosted on S3. A direct request to the bucket root with ?list-type=2 returns the full object listing. The bucket was public for analytics offload and never locked down.
Step two, the sourcemap
Production builds often ship .js.map files alongside .js. They are not referenced in HTML, but they are listed in the bucket. Download every map, run them through a sourcemap reverse tool, and you have the original TypeScript source tree.
Step three, the secret in the source
Grep the recovered source for AKIA, sk_, AIza, ghp_, and the company's own key prefixes. In this case a third-party analytics admin API key was hardcoded in a debug feature flag that never shipped to production but never got removed from source.
Step four, the privilege escalation
The analytics API key let you read dashboard configs. One config blob contained the OAuth client_secret used by the dashboard to call the parent product's API on behalf of admins. Lateral movement via stored credential.
Step five, minting admin tokens
With the client_id and client_secret, run the client credentials grant. The token returned has the admin service account's scopes, which include reading every user and impersonating any of them. Full platform takeover.
Reporting strategy
Title by impact, not by S3. Something like, public bucket plus sourcemap plus stored OAuth secret leads to admin impersonation. Walk each step, but make the final impact the headline.
Severity argument
- Unauthenticated attacker, no prerequisite
- Full admin access to the platform
- Affects every user, every tenant
- Discoverable from public DNS in under an hour
Remediation, layered
- Lock down the S3 bucket, block public list and read
- Stop shipping sourcemaps to public assets
- Move all secrets to a managed secret store, scan source on every commit
- Rotate the analytics API key and OAuth client_secret immediately
- Tighten the admin service account's scopes
Every public artifact is a foothold. Sourcemaps, debug endpoints, old backups, stale buckets, they all become step one in someone's chain.
Hunting playbook
When you find a public bucket, do not stop at the bucket. List every object. Download every config, every backup, every map. Grep aggressively for secret patterns. The bucket itself is rarely the prize, what it leaks usually is.
Read more field notes, explore our services, or get in touch at info@bipi.in. Privacy Policy · Terms.