← Back to list

API5:2019 — Broken Function Level Auth II

Hello all, today we will be looking into OWASP API Security Top 10’s another vulnerability, i.e. Broken Function Level Authorization.

Shivam Bathla in Pentester Academy Blog · 2020-07-29 02:29 · 0 claps · 8.5 min read
#rest-api #api-security #web-application-security #owasp-api-security-top-10 #broken-function-auth
Open on Medium ↗
Wiki topics: LIT · Literature & Writing 🔒 · Cybersecurity

API5:2019 — Broken Function Level Auth II

Hello all, today we will be looking into OWASP API Security Top 10’s another vulnerability, i.e. Broken Function Level Authorization.

The Issue:

“The API relies on the client to use user-level or admin-level APIs as appropriate. Attackers figure out the ‘hidden’ admin API methods and invoke them directly.”

Reference: https://apisecurity.io/encyclopedia/content/owasp/api5-broken-function-level-authorization.htm

Lab Scenario

We have set up the below scenario in our Attack-Defense labs for our students to practice. The screenshots have been taken from our online lab environment.

Lab: Broken Function Level Auth II

This lab environment consists of a Banking WebApp hosted on the target server. The webapp allows its user to update their password and Email ID after a successful login. The issue is that the authorization system in place is not properly implemented. The Banking API just validates the token and allows the user to reset the password of the account corresponding to the provided Email ID. Therefore, anyone having a valid token could update the password for any other user if the Email ID of the other user is known.

Note: The authorization system relies on a scope parameter in the issued token. If the token issued to a user has the scope of “account-write”, then they get write access on the account, else, for token having the scope of “account-read”, the user gets read-only access to the account.

Challenge Statement

Objective: Leverage the vulnerability to hijack admin’s account and retrieve the Golden Ticket!

Solution

Step 1: Check the IP address of the machine.

Command: ifconfig

Determining the IP address of the host machine

Determining the IP address of the host machine

The IP address of the machine is “192.248.164.2”

Therefore, the Banking WebApp is running on “192.248.164.3”, at port 5000.

Step 2: Viewing the Banking WebApp.

Open the following URL in firefox.

URL: http://192.248.164.3:5000

Viewing the Banking WebApp

Viewing the Banking WebApp

Step 3: Configuring the browser to use BurpSuite proxy and making BurpSuite intercept all the requests made to the API.

Launch BurpSuite.

Select Web Application Analysis > burpsuite

Launching BurpSuite

Launching BurpSuite

The following window will appear:

Launching BurpSuite (contd.)

Launching BurpSuite (contd.)

Click Next.

Finally, click Start Burp in the following window:

Launching BurpSuite (contd.)

Launching BurpSuite (contd.)

The following window will appear after BurpSuite has started:

Launching BurpSuite (contd.)

Launching BurpSuite (contd.)

Configure the browser to use the Burp proxy listener as its HTTP Proxy server.

Open the browser preference settings and search for network proxy settings.

Changing browser settings to proxy all HTTP requests through BurpSuite

Changing browser settings to proxy all HTTP requests through BurpSuite

Select Manual Proxy Configuration and set the HTTP Proxy address to localhost and the port to 8080.

Changing browser settings to proxy all http requests through BurpSuite (contd.)

Changing browser settings to proxy all http requests through BurpSuite (contd.)

Click OK.

Everything required to intercept the requests has been setup.

Step 4: Interacting with the Banking API using the WebApp.

Login into the webapp using the provided credentials:

Username: elliot Password: elliotalderson

Note: Make sure that intercept is on in BurpSuite.

Login using the provided credentials

Login using the provided credentials

Notice the corresponding requests in BurpSuite.

Forward the OPTIONS request to the /login endpoint

Forward the OPTIONS request to the /login endpoint

Forward the above request.

Forward the login request

Forward the login request

Forward the above request and view the changes reflected in the web app.

Login was successful!!

Login was successful!!

Click on the Check Balance button.

Checking the account balance

Checking the account balance

Forward above request.

The balance of the user after the above request was forwarded

The balance of the user after the above request was forwarded

Click on Get Golden Ticket button.

Request to retrieve the Golden Ticket

Request to retrieve the Golden Ticket

Forward the above request.

Request to retrieve the Golden Ticket (contd). Notice the JWT token sent in the above request

Request to retrieve the Golden Ticket (contd). Notice the JWT token sent in the above request

Notice that a JWT Token is sent in the request.

JWT Token: eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJEdW1teSBCYW5rIiwiYWNjdCI6MTMzNywic2NvcGUiOiJhY2NvdW50LXJlYWQiLCJleHAiOjE1NzU4ODcwODgsImlhdCI6MTU3NTg4NjQ4OH0.iMbfch1vv3DvNiWBmpBWace-YosFJba6la-X5hJFfzno6eWSggOC8AMryRlF8AtrAS7ykMgcsLjsRuX22MqovbrbUMjnkVQ8Ron_sJu2JyHKRh62H7uSXt54s-cx6lAFLGlvUxjfhTqo2cSaNXBsSqcRhi4oiiseHRFX5b342nD9pXL-9RaRv7JxJkIgdgUzEtCOnq4U5-cAOzEHKoksBh2EiLzV08J2bS8HZ3YL9gaZZCqWl9y-JDYHWffNv8ljz57nr1KSlpb7xN5bLKhyKQpMJ85Csf2R3ePybE-fcVquXyLVr4myz2_dOiNR0Jpwr47nW2aGNFTi32A6YxQYmw

Visit https://jwt.io and decode the above obtained token:

Decoding the above obtained JWT token

Decoding the above obtained JWT token

Notice that the token has a scope claim and it is set to the value “account-read”.

Forward the above request and view the changes reflected on the web page.

The Golden Ticket couldn’t be retrieved due to insufficient balance

The Golden Ticket couldn’t be retrieved due to insufficient balance

As mentioned in the challenge description:

“The authorization system used relies on a scope parameter in the issued token. If the token issued to a user has the scope of “account-write”, then they get write access on the account, else, for scope of “account-read”, the user gets read-only access to the account.”

And the token obtained above has scope set to “account-read”.

This means that the above user (“Elliot Alderson”) also has read-only access to the account. Therefore, he can only read his account balance.

Step 5: Resetting password for Elliot.

Updating the password for “elliot”

Updating the password for “elliot”

Set the password to 123.

Setting the password to “123”

Setting the password to “123”

Forward the above OPTIONS request to update the password

Forward the above OPTIONS request to update the password

Forward the above request.

Forward the above POST request to update the password

Forward the above POST request to update the password

Forward the above request.

The password was updated successfully!!

The password was updated successfully!!

Notice that the password got successfully updated.

Step 6: Updating the password for the admin user.

As it is mentioned in the challenge description that the Banking API just validates the token and allows the user to reset the password of the account corresponding to the provided Email ID. Therefore, anyone having a valid token could update the password for any other user if the Email ID of the other user is known.

Since the Email ID of the admin user is also known, it is possible to reset the password for the admin user.

Resetting the password for Elliot again:

Login again as “elliot”

Login again as “elliot”

Check the corresponding request in BurpSuite.

Forward the above login request

Forward the above login request

Forward the above request.

Forward the above login request (contd.)

Forward the above login request (contd.)

Check the changes reflected on the web page.

Login was successful!!

Login was successful!!

Click on the Update Profile button.

Updating the password for “elliot”

Updating the password for “elliot”

Set the new password as 1234.

Setting the password to “1234“

Setting the password to “1234“

Check the corresponding request in BurpSuite:

Forward the above OPTIONS request to update the password

Forward the above OPTIONS request to update the password

Forward the above request.

Send the above POST request to repeater and turn off the intercept mode

Send the above POST request to repeater and turn off the intercept mode

Send the above request to Repeater and turn off the intercept mode:

The password was updated successfully!!

The password was updated successfully!!

Notice on the web page a pop-up gets displayed acknowledging that the password has been updated successfully.

Navigate to the Repeater window and send a request again after editing the data sent:

Navigate to the repeater window

Navigate to the repeater window

Set the Email ID of “admin” user in the email field.

Replace the email id with that of “admin” user

Replace the email id with that of “admin” user

Send the modified request.

Send the modified request

Send the modified request

Notice the response. It reflects that the password has been successfully updated.

Login to the web app again using the updated credentials of admin user:

Login as admin

Login as admin

Login was successful

Login was successful

Click on Check Balance button.

Note: Run the Burp Proxy in intercept mode for this request to get the JWT token passed in the request.

Request to check the balance. Notice the JWT token passed in the above request

Request to check the balance. Notice the JWT token passed in the above request

Notice that a JWT Token is passed in this request.

JWT Token: eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJEdW1teSBCYW5rIiwiYWNjdCI6OTk5OSwic2NvcGUiOiJhY2NvdW50LXdyaXRlIiwiZXhwIjoxNTc2MDAzMDY2LCJpYXQiOjE1NzYwMDI0NjZ9.T2MSHu5510CYrhs2-efQhsSRcBVPkUE-Fwi9qkxjEJDlWYZUzwqSwHHMVNSFrUGbQHOYwzwusrXU_jv1hCz5Lq0frLlCAf5q-oqvrIp7Ke_xIBEawu6FLXQGLOk1w297KSpKGGiJJq-qbS8068GaccK4oL5HFefDdEDh35V4NOUPvpePGfS6b0vkLdO2iX4h_ErCbcfB1dAe52syKNGRqYwRwh3koj_1ih3JrReF4pABU2IoYWmx7wNnXBbiUxBlUmU1d0OMRWyEzM6tIB1NV_L_EWAVZLyFvNciEdCwYLRLv9K8l2cHg3NdowkxvkItAtFANtQVbqjneP8O-ZhIRg

Decoding this token using https://jwt.io:

Decoding the above obtained JWT token

Decoding the above obtained JWT token

Notice that this token has a scope of “account-write”.

Forward the above intercepted request and notice the change reflected on the web page.

The balance for admin user is $6000

The balance for admin user is $6000

Click on Golden Ticket button:

The Golden Ticket couldn’t be retrieved due to insufficient balance

The Golden Ticket couldn’t be retrieved due to insufficient balance

The Golden Ticket is not returned since the balance is not greater than $5000000.

Step 7: Increasing the balance for Elliot’s account and retrieving the Golden Ticket.

In the challenge description, it is mentioned that the /balance endpoint supports a POST request as well. That request is used to modify the account balance.

Send a POST request to the /balance endpoint and modify the balance of admin’s account and set it to a value greater than 5000000:

Command: curl -X POST -H “Content-Type: application/json” http://192.248.164.3:8081/balance -d ‘{“acct”: 9999, “balance”: 100000000, “token”: “eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJEdW1teSBCYW5rIiwiYWNjdCI6OTk5OSwic2NvcGUiOiJhY2NvdW50LXdyaXRlIiwiZXhwIjoxNTc2MDAzMDY2LCJpYXQiOjE1NzYwMDI0NjZ9.T2MSHu5510CYrhs2-efQhsSRcBVPkUE-Fwi9qkxjEJDlWYZUzwqSwHHMVNSFrUGbQHOYwzwusrXU_jv1hCz5Lq0frLlCAf5q-oqvrIp7Ke_xIBEawu6FLXQGLOk1w297KSpKGGiJJq-qbS8068GaccK4oL5HFefDdEDh35V4NOUPvpePGfS6b0vkLdO2iX4h_ErCbcfB1dAe52syKNGRqYwRwh3koj_1ih3JrReF4pABU2IoYWmx7wNnXBbiUxBlUmU1d0OMRWyEzM6tIB1NV_L_EWAVZLyFvNciEdCwYLRLv9K8l2cHg3NdowkxvkItAtFANtQVbqjneP8O-ZhIRg”}’

Modifying the account balance of the admin user

Modifying the account balance of the admin user

Notice the account balance now:

The account balance was updated successfully!

The account balance was updated successfully!

Note: Turn off the intercept mode in Burp Proxy for all further requests.

The balance was updated successfully.

Since the balance is now greater than $5000000, the Golden Ticket could be retrieved.

Awesome! We have got the Golden Ticket :)

Awesome! We have got the Golden Ticket :)

Golden Ticket: This_Is_The_Golden_Ticket_2a2461a19d93085b8ac26bc3593bf4d0

It was great! But tell me how to avoid the issue in the first place?

The issue was that the email id corresponding to the account whose password had to be changed was passed in the request and the backend didn’t validate the email id.

Therefore, the issue could be fixed using the following countermeasures:

  1. Check if the email id supplied in the request belongs to the logged-in user.
  2. Do not pass the email id in the request. Rely on the account number JWT token and use it to update the user’s profile.

Stay Safe and Happy Hacking!

References:

  1. API5:2019 — Broken Function Level Authorization
  2. OWASP API Security
  3. JWT debugger

메타데이터
post_id
46e8728dc705
slug
api5-2019-broken-function-level-auth-ii-46e8728dc705
url
https://medium.com/pentester-academy-blog/api5-2019-broken-function-level-auth-ii-46e8728dc705
canonical_url
https://medium.com/pentester-academy-blog/api5-2019-broken-function-level-auth-ii-46e8728dc705
author_url
https://medium.com/@shivam_bathla
status
ok
fetched_at
2026-08-12 06:39:12