Learning on Web Dev Open is free for all.

Backend Engineering > Who is asking, and what may they doAuthorisation is the part that breaks
Phase 05Who is asking, and what may they do265 of 434

Authorisation is the part that breaks

Knowing who someone is turns out to be the easy half. Broken access control is the most common serious web vulnerability, and it looks like ordinary code.

Concept14 minAI adversary

The bug looks like this: GET /api/invoices/:id loads the invoice by id and returns it, and the developer, thinking about it at all, remembered that the route is behind a login check. It is. Every logged-in user in the world can now read every invoice by counting. This is broken object-level authorisation, it tops the OWASP list year after year, and it is invisible in code review because the handler looks like all the others.

The structural fix is to make ownership part of the query rather than a check after it. Fetch where id matches and tenant matches the caller, so a wrong id returns nothing rather than someone else's row. Applied consistently this removes a whole bug class, because forgetting the clause returns no data rather than the wrong data.

Do the same on writes and on fields. A user updating their own profile should not be able to set role: admin because your handler spread the request body into the update. Allow-list the fields you accept for each role; never deny-list, because the next field someone adds will not be on the list.

You should now be able to

  • Distinguish authentication from authorisation in code
  • Spot a missing ownership check
  • Place authorisation where it cannot be forgotten
Ask the community

Loading…