# Warehouses and fulfilment

Pick paid orders by SKU, keep stock in step with your system, and report each shipment. For warehouses, fulfilment centers, point of sale and ERP systems.

## What your app needs

| You want to | Scope | Where |
|---|---|---|
| See paid orders with SKU, choices, weight and quantity | `orders:read` | [`order.paid`](/events/order-paid), [`GET /orders`](/api/orders-list) |
| Get the recipient's name, phone and address | `customers:read` | Inside the order |
| Get the store's pickup address | `store:read` | [`GET /store`](/api/store-get) |
| Read products and find them by SKU | `products:read` | [`GET /products`](/api/products-list) |
| Read stock | `inventory:read` | [`GET /inventory`](/api/inventory-list) |
| Change stock | `inventory:write` | [`POST /products/{id}/inventory-adjustments`](/api/inventory-adjust) |
| Update the SKU, weight and size | `products:write` | [`PATCH /products/{id}/physical`](/api/products-physical-update) |
| Report the shipment, tracking number and label | `orders.shipment:write` | [`PATCH /orders/{id}/shipment`](/api/orders-shipment-update) |

## Pick an order

Listen for [`order.paid`](/events/order-paid). Each item tells you what to pick:

```json
{
  "product_id": "57",
  "name": "Cotton T-shirt",
  "kind": "physical",
  "quantity": 2,
  "unit_price": "79.00",
  "total": "158.00",
  "sku": "TS-100-M",
  "options": { "Size": "M" },
  "weight_grams": 250
}
```

`sku` is the code of the choice the customer picked, or of the product when it has no choices. An order can mix physical and digital items, so read `kind` and pick only what is physical. `customer_note` holds what the customer wrote at checkout, with `customers:read`.

## Keep stock in step

The store takes stock off by itself on each sale. Do not subtract a sale again.

To change stock, send the difference, with a reason the merchant sees in their log. Name the choice with `sku` or `options` when the product has choices:

```bash
curl -X POST "https://larm.sa/stores/$STORE_ID/v1/products/57/inventory-adjustments" \
  -H "Authorization: Bearer $ACCESS_TOKEN" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{"delta":40,"reason":"Received from supplier","sku":"TS-100-M"}'
```

To follow every change, subscribe to [`inventory.physical.updated`](/events/inventory-physical-updated). To start, read [`GET /inventory`](/api/inventory-list), or find what a code belongs to with `GET /inventory?sku=TS-100-M`.

Send one request per product. At 600 requests a minute, a full stock sync of a large store finishes within minutes.

## Report the shipment

Report the company, tracking number and stage as the parcel moves, and send `label_url` so the merchant can print the label from the order:

```bash
curl -X PATCH "https://larm.sa/stores/$STORE_ID/v1/orders/200123/shipment" \
  -H "Authorization: Bearer $ACCESS_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{"status":"shipped","carrier":"Fast Courier","tracking_number":"FC-20145","tracking_url":"https://track.example.com/FC-20145","label_url":"https://labels.example.com/FC-20145.pdf"}'
```

The stages, who owns a shipment and what the customer sees are all in [Delivery companies](/guides/delivery-companies).

## Not available

- **Stock per branch.** Each product or choice has one quantity.
- **A bulk stock call.** Send one request per product.
- **Returns.** A returned parcel is a shipment stage. The refund is the merchant's decision.
