# Budgets

> Exact-decimal spend budgets: reserve, settle, void.

Source: https://docs.getrunstate.com/api/budgets/

<!-- Generated by apps/docs/scripts/gen-api.mjs from packages/contracts/openapi.yaml. Do not edit. -->

All paths are relative to the API base URL (`https://api.getrunstate.com`) and require `Authorization: Bearer <api key>`. See [the API overview](https://docs.getrunstate.com/api/) for authentication, idempotency and the error envelope.

## GET /budgets

```http
GET /v1/spaces/{spaceId}/budgets
```

Read-only budget list.

- **Key permission:** `coordination_read`

**Path parameters**

| Name | Type | Notes |
| --- | --- | --- |
| `spaceId` | string (uuid) | required |

**Responses**

| Status | Meaning |
| --- | --- |
| `200` | Budgets |

```bash
curl -X GET "$RUNSTATE_BASE_URL/v1/spaces/$RUNSTATE_SPACE_ID/budgets" \
  -H "Authorization: Bearer $RUNSTATE_API_KEY"
```

## POST /budgets

```http
POST /v1/spaces/{spaceId}/budgets
```

Configure a spending budget in minor units.

- **Key permission:** `resource_config`
- **Idempotency-Key header:** required
- **TypeScript SDK:** `rs.budgets.ensure()`
- **Python SDK:** `rs.budgets.ensure()`

**Path parameters**

| Name | Type | Notes |
| --- | --- | --- |
| `spaceId` | string (uuid) | required |

**Request body** (JSON)

| Field | Type | Required | Notes |
| --- | --- | --- | --- |
| `name` | string | yes |  |
| `currency` | string | yes | length 3–3 |
| `scale` | integer | yes | 0–9 |
| `limitMinor` | string | yes | pattern `^\d+$` |

**Responses**

| Status | Meaning |
| --- | --- |
| `201` | Created budget |
| `409` | Error envelope `{"error":{"code","message","requestId"}}` |

```bash
curl -X POST "$RUNSTATE_BASE_URL/v1/spaces/$RUNSTATE_SPACE_ID/budgets" \
  -H "Authorization: Bearer $RUNSTATE_API_KEY" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{"name":"<name>","currency":"<currency>","scale":0,"limitMinor":"100"}'
```

## GET /budgets/{id}

```http
GET /v1/spaces/{spaceId}/budgets/{id}
```

Balances (limit/reserved/settled/available) and reservations.

- **Key permission:** `coordination_read`
- **TypeScript SDK:** `budget.status()`
- **Python SDK:** `budget.status()`

**Path parameters**

| Name | Type | Notes |
| --- | --- | --- |
| `spaceId` | string (uuid) | required |
| `id` | string (uuid) | required |

**Responses**

| Status | Meaning |
| --- | --- |
| `200` | Budget detail |
| `404` | Error envelope `{"error":{"code","message","requestId"}}` |

```bash
curl -X GET "$RUNSTATE_BASE_URL/v1/spaces/$RUNSTATE_SPACE_ID/budgets/<id>" \
  -H "Authorization: Bearer $RUNSTATE_API_KEY"
```

## POST /budgets/{id}/reserve

```http
POST /v1/spaces/{spaceId}/budgets/{id}/reserve
```

Reserve funds; INSUFFICIENT_BUDGET when unavailable.

- **Key permission:** `resource_config`
- **Idempotency-Key header:** required
- **TypeScript SDK:** `run.budget(name).reserve()`
- **Python SDK:** `run.budget(name).reserve()`

**Path parameters**

| Name | Type | Notes |
| --- | --- | --- |
| `spaceId` | string (uuid) | required |
| `id` | string (uuid) | required |

**Request body** (JSON)

| Field | Type | Required | Notes |
| --- | --- | --- | --- |
| `scopeId` | string (uuid) | yes |  |
| `holder` | string | yes |  |
| `amountMinor` | string | yes | pattern `^\d+$` |
| `settleBy` | string (date-time) | no |  |

**Responses**

| Status | Meaning |
| --- | --- |
| `201` | Active reservation |
| `409` | Error envelope `{"error":{"code","message","requestId"}}` |

```bash
curl -X POST "$RUNSTATE_BASE_URL/v1/spaces/$RUNSTATE_SPACE_ID/budgets/<id>/reserve" \
  -H "Authorization: Bearer $RUNSTATE_API_KEY" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{"scopeId":"<run id>","holder":"worker-1","amountMinor":"100"}'
```

## POST /budgets/{id}/settle

```http
POST /v1/spaces/{spaceId}/budgets/{id}/settle
```

Settle actual spend against a reservation; idempotent per work key.

- **Key permission:** `resource_config`
- **TypeScript SDK:** `reservation.settle()`
- **Python SDK:** `reservation.settle()`

**Path parameters**

| Name | Type | Notes |
| --- | --- | --- |
| `spaceId` | string (uuid) | required |
| `id` | string (uuid) | required |

**Request body** (JSON)

| Field | Type | Required | Notes |
| --- | --- | --- | --- |
| `reservationId` | string (uuid) | yes |  |
| `amountMinor` | string | yes | pattern `^\d+$` |
| `workKey` | string | yes | length 1–512 |

**Responses**

| Status | Meaning |
| --- | --- |
| `200` | Settlement entry; replay flag |
| `400` | Error envelope `{"error":{"code","message","requestId"}}` |
| `409` | Error envelope `{"error":{"code","message","requestId"}}` |

```bash
curl -X POST "$RUNSTATE_BASE_URL/v1/spaces/$RUNSTATE_SPACE_ID/budgets/<id>/settle" \
  -H "Authorization: Bearer $RUNSTATE_API_KEY" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{"reservationId":"<reservationId>","amountMinor":"100","workKey":"<workKey>"}'
```

## POST /budgets/{id}/void

```http
POST /v1/spaces/{spaceId}/budgets/{id}/void
```

Void the unspent remainder of a reservation; explicit only, never automatic.

- **Key permission:** `resource_config`
- **TypeScript SDK:** `reservation.void()`
- **Python SDK:** `reservation.void()`

**Path parameters**

| Name | Type | Notes |
| --- | --- | --- |
| `spaceId` | string (uuid) | required |
| `id` | string (uuid) | required |

**Request body** (JSON)

| Field | Type | Required | Notes |
| --- | --- | --- | --- |
| `reservationId` | string (uuid) | yes |  |
| `workKey` | string | yes | length 1–512 |

**Responses**

| Status | Meaning |
| --- | --- |
| `200` | Void entry; replay flag |
| `409` | Error envelope `{"error":{"code","message","requestId"}}` |

```bash
curl -X POST "$RUNSTATE_BASE_URL/v1/spaces/$RUNSTATE_SPACE_ID/budgets/<id>/void" \
  -H "Authorization: Bearer $RUNSTATE_API_KEY" \
  -H "Idempotency-Key: $(uuidgen)" \
  -H "Content-Type: application/json" \
  -d '{"reservationId":"<reservationId>","workKey":"<workKey>"}'
```
