Skip to content

API Reference

GreenThumb exposes two REST APIs, both built with FastAPI: the Pi API (runs on each Raspberry Pi node) and the Cloud API (runs in the cloud, behind the gateway).

Each API's Swagger UI (/docs) and OpenAPI schema (/openapi.json) are the authoritative reference for request and response bodies. This page is an index of the endpoints.


Pi API

Base URL: http://<pi-address>:8080 · Swagger: http://<pi-address>:8080/docs

Network access

The node's dashboard and API are meant for a trusted local network or the VPN. Never port-forward them.

State

Method Path Purpose
GET /state/ System state for the controller's Sense-Think-Act loop
POST /state/heartbeat Controller heartbeat; keeps safety mode from engaging
GET /state/safety Safety mode status and last heartbeat time

Actuators

Method Path Purpose
GET /actuator/ Every actuator with its capabilities, state and provenance
POST /actuator/{id}/command Command an actuator (refused with 409 when a safety bound blocks it)
POST /actuator/by-name/{name}/command Command an actuator by name
POST /actuator/{id}/release Drop the manual-override mark ("return to automatic")
PATCH /actuator/{id}/fail-safe Set whether the actuator keeps running through a safety-mode trip

Data

Method Path Purpose
GET /data Measurement history from the local database
GET /data/latest Latest measurement per active sensor component
POST /data/current_values Save the current sensor readings

Camera

Method Path Purpose
POST /camera/capture Capture a photo
GET /camera/stream Live MJPEG camera stream

Settings

Method Path Purpose
GET /settings Device settings
PATCH /settings/device-mode Change the device operating mode
GET / POST /settings/control-rules List or create control rules
PATCH /settings/control-rules/{id} Edit a control rule
GET /settings/growth-phases Growth phases
GET /settings/variables Variables
GET /settings/plant-species Plant species
GET /settings/components Components configured on the device, with calibration and liveness
POST /settings/components/{id}/calibration Calibrate a component
GET /settings/cultivation Active cultivation with its phase history
GET /settings/cultivation/template-sources Template sources available for a species
POST /settings/cultivation/begin Begin a cultivation
POST /settings/cultivation/end End the active cultivation
POST /settings/cultivation/advance-phase Advance to the next growth phase
POST /settings/sync Trigger a full cloud sync now
GET / PATCH /settings/runtime Per-device runtime settings (task intervals, heartbeat timeout)
POST /settings/reinit-drivers Re-run the driver bring-up from the local database

Meta and generic CRUD

Method Path Purpose
GET / Local dashboard, or API status when no dashboard is bundled
GET /version Build running on the device

Generic CRUD routes (GET /, GET /{id}, POST /, PUT /{id}, DELETE /{id}) exist for /device, /plant_species, /cultivation, /component_model, /device_component, /unit, /variable, /measurement and /component_capability.


Cloud API

The cloud API is not publicly reachable yet. For local development, run the cloud stack and open http://localhost:8000/docs.

Gateway routing

Path Service
/auth/** auth-service
/admin/**, /sync/**, / greenthumb-api

account-service is not routed by the gateway; only auth-service calls it.

Auth (/auth)

Method Path Purpose
POST /auth/login Returns {token} and sets the HttpOnly access_token cookie
POST /auth/logout Clears the access_token cookie
POST /auth/register Create a user account (admin only)
GET /auth/validate Internal, called by greenthumb-api: returns {id_user, role}

Admin (/admin)

Every /admin route needs a logged-in user: the access_token cookie, or Authorization: Bearer <jwt>. Routes marked admin also need the admin role.

Method Path Purpose
GET /admin/me Caller's user id and current role
GET /admin/version Cloud build, including the sync contract version
GET / POST /admin/devices List or create devices
GET / PATCH /admin/devices/{id} Read or edit a device
DELETE /admin/devices/{id} Delete a device (admin)
POST /admin/devices/{id}/token Generate a new device token; the old one stops working (admin)
POST /admin/devices/epoch/bump Make every device re-push its local data on the next sync (admin)
GET /admin/users, /admin/users/{id_user} List or read users (admin)
PATCH /admin/users/{id_user} Edit a user (admin)
GET /admin/alerts Fleet alerts (admin)
POST /admin/alerts/{id_system_alert}/resolve Resolve an alert (admin)
GET /admin/cultivations, /admin/cultivations/{id} List or read cultivations
PATCH /admin/cultivations/{id} Edit a cultivation
GET /admin/cultivation-phases, /admin/cultivation-phases/{id} Cultivation phases (read-only)
GET /admin/control-rule-logs Control-rule log (read-only)
GET /admin/actuator-logs/daily Daily actuator-log rollup
GET /admin/device-components/effects, /admin/device-components/{id_device_component}/effects Resolved actuator effects

Catalog CRUD (GET for any logged-in user; POST, PUT, DELETE admin): /admin/units, /admin/variables, /admin/plant-species, /admin/growth-phases, /admin/component-models, /admin/device-models, /admin/component-capabilities, /admin/species-rules, /admin/substances, /admin/substance-effects, /admin/component-model-effects, /admin/actuator-effects.

Owner-scoped CRUD (a user sees only their own rows; an admin sees all): /admin/properties, /admin/containers, /admin/device-components, /admin/control-rules, /admin/measurements, /admin/photos, /admin/actuator-logs, /admin/calibration-logs.

CRUD routes follow the pattern GET (list), GET /{id}, POST, PUT /{id}, DELETE /{id}.

Sync (/sync)

Called by the Pi. Every route needs Authorization: Bearer <device_token>; the token must match the device's device_token.

Method Path Purpose
GET /sync/devices/{id}/config Pull the shared catalog and the device configuration
POST /sync/devices/{id}/ping Liveness ping
POST /sync/devices/{id}/measurements Push measurements
POST /sync/devices/{id}/actuator-logs Push actuator logs
POST /sync/devices/{id}/calibration-logs Push calibration logs
POST /sync/devices/{id}/photos Push one photo (multipart); the API uploads it to R2
POST /sync/devices/{id}/photos/batch Push several photos; returns 207 with a per-photo result
POST /sync/devices/{id}/state Push device-owned state (cultivations, phases, control rules)

Error responses

Status Meaning
401 Missing or invalid user or device token
403 Role not allowed, or the row belongs to another owner
404 Not found
409 Sync contract mismatch (sync), or command refused by a safety bound (Pi)
422 Validation error
502 Upstream failure (auth-service, R2)
500 Unexpected error

Index generated from the routers on 2026-10-01; regenerate from /openapi.json.