Application Security In progress
Intermediate 17 min read Application Security
IDOR and Broken Access Control
The most common silent killer: horizontal and vertical access-control gaps, the Insecure Direct Object Reference subset, and how to test authorization like a two-account puzzle.
IDORbroken access controlauthorizationhorizontal privilege escalationvertical escalationobject reference
Introduction
What is this?
Broken access control means a user can reach a resource they were never meant to reach: someone else's record (horizontal), an admin function (vertical), or a list they shouldn't enumerate.
Motivation
Why do you need it?
- It is routinely the number-one-ranked web risk because the flaw lives in business logic, invisible to scanners.
- The blast radius is huge: IDOR across an API commonly exposes every customer record with a single sequence number.
- Learning to test as 'user A vs user B' is the single most transferable pentest skill.
Think about it
Mental model
Imagine
A shared filing room
Think of
Unlocked cabinets labeled by customer number
The labels are sequential, the handles are unlocked, and nobody checks who walks in.
Mechanics
How it works
- The app trusts the user-supplied object ID (invoice/1234, uid=42) and authenticates the session but never authorizes the object.
- Horizontal: user A reads user B's same-type object. Vertical: a normal user calls an admin endpoint directly.
- Scanners know nothing about your business objects, so discovery requires two accounts and manual inference.
- The fix is a middleware check on every object fetch: does THIS principal have rights over THIS resource?
A present-absent authorization path
Requestuser supplies object id
Authenticatesession is checked
Authorize? object-level permission check
Allow/Denyor silently 403
Logdenials to the audit trail
Real world
In production
- A SaaS added an object-access policy layer at the API gateway; invoice/1234 for user B now 403s before the handler runs.
- A fintech's admin endpoints moved behind a separate middleware that checks 'is_admin' on every route, not just the menu.
- A pentest found an IDOR in a PDF-export endpoint; the fix was a query scoping by the owner column instead of a raw id.
Guidelines
Best practices
- Authorize every object access with an explicit owner check; never scope queries by id alone.
- Use non-enumerable identifiers (UUIDs) AND enforce authorization — you need both layers.
- Centralize the authorization check (policy/permission service) so every route hits the same gate.
- Return the same 403/404 for both 'no such record' and 'no access' to stop enumeration signaling.
Watch out
Common mistakes
- Protecting the list page but forgetting the detail/export/download endpoints that show each single record.
- Relying on 'the UI hides the button' as authorization while the API remains unguarded.
- Authorizing at the controller for one path and skipping the identical logic in a bulk or admin endpoint.
- Assume-only: never running the two-account differential test that would have found the bug.
When things break
Debugging tips
- The two-account test: log in as A, capture the request/response; as B, replay and diff the result.
- Swap a sequence id for a UUID and check whether the handler still resolves it — predictors rarely work with UUIDs.
- Watch HTTP status codes: a 200 where a 403 belongs is the entire report in one number.
Security
Security considerations
- Differential testing must use accounts and data you own in a lab; crossing into other users' records is out of bounds.
- If you find an access-control gap in a real product, report through the ownership line — never demonstrate on live records.
- Treat the access-control audit as part of every release: it is the cheapest regression to skip and the most damaging to miss.
Interviews
Interview checkpoint
Practice
Hands-on lab
Find the IDOR with a Two-Account Differential
45 min · intermediate
Objectives
- Create two local accounts in DVWA/Juice Shop.
- Prove a horizontal IDOR using the differential method.
- Patch the example handler to scope by owner and re-test.
Find the IDOR with a Two-Account Differential
45 min · intermediate
0/5 steps
0%
sandbox · Linux sandbox
$
Try these commands
Test yourself
Quick quiz
0/2
1
IDOR is a specific flavor of...
2
User A reads user B's invoice by changing /invoice/5 to /invoice/6. This is...
Go deeper