Categories
A category labels what a transaction was for. Categories are typed as income or expense. All routes require a bearer token and live under /api/v1.
Endpoints
Section titled “Endpoints”| Method | Path | Action |
|---|---|---|
GET | /api/v1/categories | List categories |
POST | /api/v1/categories | Create a category |
GET | /api/v1/categories/{id} | Show one category |
PUT | /api/v1/categories/{id} | Update a category |
DELETE | /api/v1/categories/{id} | Delete a category |
POST | /api/v1/categories/seed-defaults | Seed a default set of categories |
Listing supports a type query parameter (income or expense) to filter the result.
Fields
Section titled “Fields”| Field | Type | Required | Notes |
|---|---|---|---|
name | string | yes | Up to 255 characters. |
type | string | yes | income or expense. |
description | string | no | Free text. |
icon | string | no | Icon value. |
icon_type | string | no | Required with icon: icon, image, or emoji. |
client_id | string | no | Client-generated ID, {device_uuid}:{entity_uuid}. |
created_at | string | no | ISO 8601. |
Create
Section titled “Create”curl -X POST https://api.your-domain.example/api/v1/categories \ -H "Authorization: Bearer your-token-here" \ -H "Content-Type: application/json" \ -d '{ "name": "Groceries", "type": "expense" }'Seed defaults
Section titled “Seed defaults”To start from a common set instead of an empty list:
curl -X POST https://api.your-domain.example/api/v1/categories/seed-defaults \ -H "Authorization: Bearer your-token-here"Response shape
Section titled “Response shape”{ "success": true, "message": "Category created", "data": { "id": 4, "name": "Groceries", "type": "expense", "description": null, "icon": { "id": 8, "path": "cart.png", "type": "image" }, "client_generated_id": "device-uuid:entity-uuid", "last_synced_at": "2026-06-14T09:12:00.000000Z" }}