They happen when the application grants direct access to a resource based on the user’s request, without validation.

By changing Id’s can you see something meant for another user??, this is the core of IDOR

Finally, IDORs can affect resources other than database objects. Another type of IDOR happens when applications reference a system file directly. For example, this request allows users to access a file they’ve uploaded: https:// example.com/uploads?file=user1234-01.jpeg. Since the value of the file parameter is user1234–01.jpeg, we can easily deduce that user-uploaded files follow the naming convention of USER_ID-FILE_NUMBER.FILE_EXTENSION. Therefore, another user’s uploaded files might be named user1233–01.jpeg

IDORs happen when an application fails at two things. First, it fails to implement access control based on user identity. Second, it fails to randomize object IDs and instead keeps references to data objects, like a file or a database entry, predictable

Applications can prevent IDORs in two ways. First, the application can check the user’s identity and permissions before granting access to a resource. For example, the application can check if the user’s session cookies correspond to the user_id whose messages the user is requesting. Second, the website can use a unique, unpredictable key or a hashed identifier to reference each user’s resources. Hashing refers to the one-way process that transforms a value into another string.

Let’s hunt for some IDORs! The best way to discover IDORs is through a source code review that checks if all direct object references are protected by access control. But if you cannot access the application’s source code, here’s a simple and effective way to test for IDORs.

Step 1: Create Two Accounts First, create two different accounts on the target website. If users can have different permissions on the site, create two accounts for each permission level. For example, create two admin accounts, two regular user accounts, two group member accounts, and two non-group-member accounts. This will help you test for access control issues among similar user accounts, as well as across users with different privileges.

Step 2: Discover Features Next, try to discover as many application features as possible. Use the highestprivileged account you own and go through the application, looking for application features to test. Pay special attention to functionalities that return user information or modify user data. Note them for future reference. Here are some features that might have IDORs on example.com: This endpoint lets you read user messages: https://example.com/messages?user_id=1236 This one lets you read user files: https://example.com/uploads?file=user1236-01.jpeg

Step 3: Capture Requests Browse through each application feature you mapped in the preceding step and capture all the requests going from your web client to the server. Inspect each request carefully and find the parameters that contain numbers, usernames, or IDs. Remember that you can trigger IDORs from different locations within a request, like URL parameters, form fields, filepaths, headers, and cookies. To make testing more efficient, use two browsers, and log into a different account in each. Then manipulate the requests coming from one browser to see if the change is immediately reflected on the other account. For example, let’s say you create two accounts, 1235 and 1236. Log into 1235 in Firefox and 1236 in Chrome.

Step 4: Change the IDs Finally, switch the IDs in the sensitive requests and check if the information returned also changes. See if you can access the victim account’s information by using the attacker account. And check if you can modify the second user’s account from the first.

Bypassing IDOR Protection IDORs aren’t always as simple as switching out a numeric ID. As applications become more functionally complex, the way they reference resources also often becomes more complex. Modern web applications have also begun implementing more protection against IDORs, and many now use more complex ID formats. This means that simple, numeric IDORs are becoming rarer. How do we bypass these obstacles and find IDORs anyway? IDORs can manifest in applications in different ways. Here are a few places to pay attention to, beyond your plain old numeric IDs. Encoded IDs and Hashed IDs First, don’t ignore encoded and hashed IDs. When faced with a seemingly random string, always suspect that it is encoded and try to decode it. You should also learn to recognize the most common encoding schemes, like base64, URL encoding, and base64url. For example, take a look at the IDs of this endpoint: https://example.com/messages?user_id=MTIzNQhttps://example.com/messages?user_id=MTIzNg These user_ids are just the base64url-encoded version of a user’s ID. MTIzNQ is the base64url-encoded string of 1235, and MTIzNg is the encoded version of 1236.

Leaked IDs It might also be possible that the application leaks IDs via another API endpoint or other public pages of the application, like the profile page of a user. I once found an API endpoint that allowed users to retrieve detailed direct messages through a hashed conversation_id value. The request looks like this: GET /messages?conversation_id=O1SUR7GJ43HS93VAR8xxxx This seems safe at first glance, since the conversation_id is a long, random, alphanumeric sequence. But I later found that anyone could request a list of conversation_ids for each user, just by using their public user ID! The following request would return a list of conversation_ids belonging to that user: GET /messages?user_id=1236 Since the user_id is publicly available on each user’s profile page, I could read any user’s messages by first obtaining their user_id on their profile page, retrieving a list of conversation_ids belonging to that user, and finally loading the messages via their conversation_ids.

Offer the Application an ID, Even If It Doesn’t Ask for One In modern web applications, you’ll commonly encounter scenarios in which the application uses cookies instead of IDs to identify the resources a user can access. For example, when you send the following GET request to an endpoint, the application will deduce your identity based on your session cookie, and then send you the messages associated with that user: GET /api_v1/messages Host: example.com Cookies: session=YOUR_SESSION_COOKIE Since you don’t know another user’s session cookies, you cannot use those session cookies to read their messages. This might make it seem like the application is safe from IDORs. But some applications will implement an alternative way of retrieving resources, using object IDs. They sometimes do this for the convenience of the developers, for backward compatibility, or just because developers forgot to remove a test feature.

Keep an Eye Out for Blind IDORs Still, sometimes endpoints susceptible to IDOR don’t respond with the leaked information directly. They might lead the application to leak information elsewhere, instead: in export files, email, and maybe even in text alerts. For example, imagine that this endpoint on example.com allows users to email themselves a copy of a receipt: POST /get_receipt (POST request body) receipt_id=3001 This request will send a copy of receipt 3001 to the registered email of the current user. Now, what if you were to request a receipt that belongs to another user, receipt 2983? POST /get_receipt (POST request body) receipt_id=2983 While the HTTP response does not change, you may get a copy of receipt 2983 in your email inbox!

Change the Request Method If one HTTP request method doesn’t work, you can try plenty of others instead: GET, POST, PUT, DELETE, PATCH, and so on. Applications often enable multiple request methods on the same endpoint but fail to implement the same access control for each method. For example, if this GET request is not vulnerable to IDOR and doesn’t return another user’s resources GET example.com/uploads/user1236-01.jpeg you can try to use the DELETE method to delete the resource instead. The DELETE method removes the resource from the target URL: DELETE example.com/uploads/user1236-01.jpeg

Change the Requested File Type Switching the file type of the requested file sometimes leads the server to process the authorization differently. Applications might be flexible about how the user can identify information: they could allow users to either use IDs to reference a file or use the filename directly. But applications often fail to implement the same access controls for each method of reference. For example, applications commonly store information in the JSON file type. Try adding the .json extension to the end of the request URL and see what happens. If this request is blocked by the server GET /get_receipt?receipt_id=2983 then try this one instead: GET /get_receipt?receipt_id=2983.json

Escalating the Attack The impact of an IDOR depends on the affected function, so to maximize the severity of your bugs, you should always look for IDORs in critical functionalities first. Both read-based IDORs (which leak information but do not alter the database) and write-based IDORs (which can alter the database in an unauthorized way) can be of high impact.