# Recompute after a change

> Refresh a category's stored summary after a change, so the app's shop page agrees at once, and read the fresh summary in the same call.

Markdown twin of https://panlytics.net/developers/guides/recompute-after-a-change (last updated 2026-10-25). Every page of the Panlytics developer docs is listed at https://panlytics.net/developers/llms.txt, and all of them are in one file at https://panlytics.net/developers/llms-full.txt. The site guide is https://panlytics.net/llms.txt.

## You rarely need it

Every figure the API answers with is worked out when you read it, from the category's newest report, its settings, its suppliers and its exceptions as they stand at that moment. A change made through the API or in the app shows on the next read of the reorder points (the level that triggers a new order), the order list or the stop-stocking list, with no recompute.

What a recompute refreshes is the category's stored summary: the sales, the sales you missed and the waste that the app's shop page shows. Call it after a change when a person is about to look at the shop page and should see the new summary at once:

- after you changed a category's settings with `PATCH /v1/categories/{id}`;
- after you changed a supplier's delivery days or the categories it delivers.

A new report needs no recompute. The upload works the category out as part of filing it.

## Recompute and read the summary

The call answers with the fresh summary, so one call does both:

```bash title="curl"
curl -X POST https://panlytics.net/api/v1/categories/40/recompute \
  -H "Authorization: Bearer $PANLYTICS_KEY"
```
```python title="Python"
import os
import requests

answer = requests.post(
    "https://panlytics.net/api/v1/categories/40/recompute",
    headers={"Authorization": f"Bearer {os.environ['PANLYTICS_KEY']}"},
    timeout=60,
)
answer.raise_for_status()
print(answer.json())
```
```typescript title="TypeScript"
const answer = await fetch("https://panlytics.net/api/v1/categories/40/recompute", {
  method: "POST",
  headers: { Authorization: `Bearer ${process.env.PANLYTICS_KEY}` },
});
if (!answer.ok) throw new Error(`Panlytics answered ${answer.status}`);
console.log(await answer.json());
```

```json title="200"
{
  "categoryId": 40,
  "reportId": 311,
  "salesEur": 48210.5,
  "missedSalesEur": 1310.2,
  "wasteEur": 420.75,
  "computedAt": "2026-10-25T09:31:00.000Z"
}
```

It needs **See the figures** in that category. A category with no report answers `409 report.none`.

## What it does not do

- It does not change any setting, and it does not change any figure the other endpoints answer with.
- It does not place an order. Panlytics tells you what to order; ordering stays with you.
- It needs no `Idempotency-Key`: running it twice gives the same summary.
