# Cache Deception: How I discovered a vulnerability in Medium and helped them fix it

Medium cached profile pages whose usernames ended in a file extension, letting attackers retrieve victims' CSRF tokens and viewer info from cached responses.

- Payout: $100
- Severity: medium
- Program: Medium
- Credited: Yuval Shprinz
- Disclosed: 2019-02-06
- Write-up quality: 6/10
- Original: https://medium.freecodecamp.org/cache-deception-how-i-discovered-a-vulnerability-in-medium-and-helped-them-fix-it-31cec2a3938b
- Library page: https://bugbountylibrary.com/r/blog%3Amedium-freecodecamp-org-cache-deception-how-i-discovered-a-vulnerability-in-medium-and-helped-them-fix-it-31cec2a3938b
- Tags: domain:web impact:data-leak impact:integrity kind:bounty platform:blog sev:medium tech:android technique:recon technique:source-review vuln:cache-deception

**Target:** User profile pages / CDN cache
**Root cause:** CDN cached any root-level path that looked like a static file (e.g. /@yuval.png), but the profile page returned dynamic, sensitive content including CSRF tokens.
**Steps:**
1. Decompile Medium Android app and extract ~900 Retrofit API endpoints
2. Identify endpoints ending in user-controlled input; profile URL is https://medium.com/@<username>
3. Set username to `yuval.png` so profile URL becomes https://medium.com/@yuval.png
4. Visit the URL while logged in; CDN caches the dynamic profile response for 4 hours
5. Retrieve the cached response to read embedded CSRF token and viewer identity
6. Rotate username via script to generate fresh uncached URLs repeatedly
**How found:** Extracted all Retrofit API endpoints from the decompiled Android app, then looked for endpoints ending in user-controlled input because caching services commonly cache paths that look like files.
**Exploitation:** Attacker sets username ending in a file extension, lures a victim to the profile URL; the CDN caches the victim-specific response, which the attacker then fetches to steal CSRF tokens and viewer info.
**Insight:** Enumerate API endpoints from mobile app code and cross-reference with CDN caching rules: any endpoint whose path ends in user-controlled input resembling a file extension is a cache deception candidate.
