# Grotti HTTP-API (`/api/v1`) Stand für Android/App-Clients und Integrationen. Nutzer-Anleitungen bleiben unter `docs/Anleitung-*.md`. ## Auth | Weg | Header / Cookie | CSRF | | --- | --- | --- | | Session | Cookie nach `POST /auth/login` | `X-CSRF-Token` bei mutierenden API-Calls | | Bearer | `Authorization: Bearer grt_…` | nicht nötig | **Token ausstellen** - Eingeloggt: `POST /tokens` `{name, role?}` → Klartext einmalig in `token` - Ohne Session (App): `POST /auth/token` `{username, password, device_name?, role?}` → `201` mit `token` + `user` (Rate-Limit wie Login) Öffentlich ohne Login: `/auth/status`, `/auth/login`, `/auth/token`, `/auth/setup`, `/version`. Rollen: `operator` ≤ `admin`. Admin-only u. a. Benutzer, Backup, volle Einstellungen, Drucker anlegen. **Medien mit Query-Token** (nur GET): `?token=grt_…` für Kamera, Live-Vorschau, Datei-Vorschau (`/dateien//vorschau`), Projekt-Assets. ## Fehler ```json {"error": "Text", "code": "kurzcode"} ``` HTTP-Status: 400/401/403/404/409/429/503. Bild-Endpunkte liefern bei fehlendem Bild ebenfalls dieses JSON (nicht nur leeren 404). ## Pagination Listen akzeptieren `limit` / `offset` wo sinnvoll. Antwort bleibt ein **JSON-Array**; Gesamtzahl im Header `X-Total-Count`. Ohne `limit` liefern `/dateien` und `/spulen` die volle Liste (Web-UI). ## Bestätigung Mutierende Druckaktionen brauchen oft `"confirm": true`: - `POST /senden`, `POST /druck-queue`, `POST /ablauf` - `POST /projekte//einreihen`, `POST /auftraege//einreihen` - `POST /drucker//abraeumen` - `steuern` mit `emergency_stop`, `clear_error`, `exclude_object` ## Server-Info `GET /version` → `{name, version, api: 1, features: [...]}`. ## SSE Live `GET /stream` (Session-Cookie oder Bearer). Events: | Event | Bedeutung | | --- | --- | | `ping` | Keepalive (~15 s), Payload `{}` | | `drucker` | Live-Zustand der Drucker geändert | | `queue` | Druckwarteschlange geändert | | `senden` | Sende-Auftrag geändert | | `ereignis` | Neues Ereignis / Aktivität | | `aufgaben` | Offene Aufgaben (Platte …) | Ohne Stream: Client pollt `/drucker?live=1`, `/jetzt`, `/druck-queue`. ## Push an Geräte Grotti sendet **kein** FCM. Empfohlen: **ntfy** (Topic unter Einstellungen). Die App kann denselben Topic abonnieren; Secrets (ntfy-Token) bleiben serverseitig. ## Wichtige Ressourcen | Bereich | Pfade | | --- | --- | | Drucker | `GET /drucker?live=1`, `POST /drucker//pause\|fortsetzen\|abbrechen` (Alias `resume`/`cancel`), `…/steuern`, `…/abraeumen` | | Dateien | `GET /dateien?family=&material=&project_id=&host=&q=&limit=&offset=`, Upload multipart, `…/vorschau`, `…/pfad` | | Senden / Queue | `POST /senden`, `GET /senden-zuletzt?host=&file_id=`, `GET\|POST /druck-queue?host=&status=`, `POST /ablauf` | | Projekte | `GET\|POST /projekte`, `GET /projekte/`, `…/laeufe`, `POST …/einreihen`, Assets | | Aufträge | `GET\|POST /auftraege`, Positionen, `…/einreihen` | | Material | `GET /spulen?aktiv=1`, Akte, Einlegen | | Protokoll | `GET /laeufe`, `GET /laeufe/`, `GET /statistik?project_id=` | | Kamera | `GET /kamera?host=`, `…/stream` | Pfadnamen sind überwiegend **deutsch**. Aktionen: deutsch + englische Alias für Pause/Resume/Cancel. ## MCP `python -m grotti.mcp_server` nutzt dieselbe REST-API (Teilmenge). Siehe `docs/internal/MCP.md`.