- docs/PLAYER-STATUS-HTTP.md vollstaendig neu strukturiert: q=, derived_state=, DELETE-Endpoint und Datei-Persistenz ergaenzt, Abgrenzung "keine dauerhafte Speicherung" entfernt - GET /api/v1 listet jetzt dieselben 5 Tools wie /api/v1/meta (player-status-ingest und screen-status-delete ergaenzt) Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
189 lines
7.3 KiB
Markdown
189 lines
7.3 KiB
Markdown
# Info-Board Neu - Erster HTTP-Statuspfad fuer den Player-Agent
|
||
|
||
## Ziel
|
||
|
||
Dieses Dokument beschreibt den ersten bewusst kleinen Statuspfad zwischen `player/agent` und `server/backend`.
|
||
|
||
Er ist fuer die aktuelle Entwicklungsstufe gedacht und noch kein finales Authentifizierungs- oder MQTT-Modell.
|
||
|
||
## V1-Dev-Entscheidung
|
||
|
||
- der Agent sendet zunaechst Statusdaten per HTTP an das Backend
|
||
- das Backend validiert und bestaetigt den Request und haelt den letzten bekannten Status pro Screen vor
|
||
- der Pfad dient als erste echte Backend-Agent-Integration vor Registration, Sync und MQTT
|
||
|
||
## Endpoints im Ueberblick
|
||
|
||
| Methode | Pfad | Beschreibung |
|
||
|----------|---------------------------------------|-------------------------------------|
|
||
| POST | /api/v1/player/status | Statusingest vom Player-Agent |
|
||
| GET | /api/v1/screens/status | JSON-Uebersicht aller Screens |
|
||
| GET | /api/v1/screens/{screenId}/status | JSON-Detail fuer einen Screen |
|
||
| DELETE | /api/v1/screens/{screenId}/status | Screen-Eintrag loeschen |
|
||
| GET | /status | HTML-Diagnoseseite (Uebersicht) |
|
||
| GET | /status/{screenId} | HTML-Diagnoseseite (Einzelscreen) |
|
||
|
||
## POST /api/v1/player/status
|
||
|
||
### Request-Felder
|
||
|
||
Pflichtfelder:
|
||
|
||
- `screen_id`
|
||
- `ts` (RFC3339-Zeitstempel)
|
||
- `status`: `starting`, `running`, `stopped`
|
||
- `heartbeat_every_seconds` (positive Ganzzahl)
|
||
|
||
Optionale Felder:
|
||
|
||
- `server_connectivity`: `unknown`, `online`, `degraded`, `offline`
|
||
- `server_url`
|
||
- `mqtt_broker`
|
||
- `started_at` (RFC3339-Zeitstempel)
|
||
- `last_heartbeat_at` (RFC3339-Zeitstempel)
|
||
|
||
### Beispiel
|
||
|
||
```json
|
||
{
|
||
"screen_id": "info01-dev",
|
||
"ts": "2026-03-22T16:00:00Z",
|
||
"status": "running",
|
||
"server_connectivity": "online",
|
||
"server_url": "http://127.0.0.1:8080",
|
||
"mqtt_broker": "tcp://127.0.0.1:1883",
|
||
"heartbeat_every_seconds": 30,
|
||
"started_at": "2026-03-22T15:59:30Z",
|
||
"last_heartbeat_at": "2026-03-22T16:00:00Z"
|
||
}
|
||
```
|
||
|
||
### Antwort
|
||
|
||
```json
|
||
{ "status": "accepted" }
|
||
```
|
||
|
||
Bei ungueltigen Requests wird der gemeinsame Fehlerumschlag verwendet.
|
||
|
||
## GET /api/v1/screens/status
|
||
|
||
Liefert eine Uebersicht aller bisher berichtenden Screens mit ihrem jeweils letzten bekannten Datensatz.
|
||
|
||
Die Antwort enthaelt:
|
||
|
||
- `summary` mit kompakten Counts fuer `total`, `online`, `degraded`, `offline`, `stale`
|
||
- `screens` sortiert nach Prioritaet: zuerst `offline`, dann `degraded`, dann `online`; innerhalb derselben Gruppe nach `screen_id`
|
||
|
||
Die `summary` beschreibt immer den gesamten bekannten Statusbestand, unabhaengig von aktiven Filtern.
|
||
Die `screens`-Liste wird durch die Query-Parameter eingeschraenkt.
|
||
|
||
### Query-Parameter
|
||
|
||
| Parameter | Erlaubte Werte | Fehlercode bei Verstoß |
|
||
|---------------------|-----------------------------------------|-------------------------------------|
|
||
| `q` | beliebig (Substring-Suche, case-insen.) | – |
|
||
| `derived_state` | `online`, `degraded`, `offline` | `invalid_derived_state` |
|
||
| `server_connectivity` | `online`, `degraded`, `offline`, `unknown` | `invalid_server_connectivity` |
|
||
| `stale` | `true`, `false` | `invalid_stale` |
|
||
| `updated_since` | RFC3339-Zeitstempel | `invalid_updated_since` |
|
||
| `limit` | positive Ganzzahl | `invalid_limit` |
|
||
|
||
`q` filtert nach Screen-ID-Substring (Gross-/Kleinschreibung wird ignoriert).
|
||
|
||
Dieselben Parameter koennen sowohl an `GET /api/v1/screens/status` als auch an `GET /status` uebergeben werden, damit Browser-Ansicht und JSON-Uebersicht dieselbe Diagnosesicht teilen.
|
||
|
||
## GET /api/v1/screens/{screenId}/status
|
||
|
||
Liefert den zuletzt akzeptierten Status fuer einen einzelnen Screen.
|
||
Wenn fuer den Screen noch kein Status vorliegt, liefert das Backend `404` mit dem gemeinsamen Fehlerumschlag.
|
||
|
||
Der Datensatz enthaelt neben den gespeicherten Feldern:
|
||
|
||
- `received_at` – serverseitiger Annahmezeitpunkt des letzten gueltigen Reports
|
||
- `stale` – ob der letzte Report bereits veraltet wirkt (mehr als zwei Heartbeat-Intervalle ohne neuen Report)
|
||
- `derived_state` – zusammengefasste Diagnoseeinschaetzung (s.u.)
|
||
|
||
## DELETE /api/v1/screens/{screenId}/status
|
||
|
||
Loescht den gespeicherten Statuseintrag fuer einen Screen endgueltig.
|
||
Wenn kein Eintrag vorhanden ist, liefert das Backend `404`.
|
||
|
||
### Antwort
|
||
|
||
```json
|
||
{ "status": "deleted" }
|
||
```
|
||
|
||
## GET /status
|
||
|
||
Serverseitig gerenderte HTML-Diagnoseseite fuer den Browser.
|
||
Nutzt dieselbe Statusuebersicht wie der JSON-Endpunkt.
|
||
|
||
- automatisches Refresh alle 15 Sekunden
|
||
- Shortcut-Links fuer Connectivity- und Freshness-Filter
|
||
- kleines Filterformular fuer dieselben Parameter wie beim JSON-Read-Pfad
|
||
- direkte JSON-Detail-Links pro Screen
|
||
|
||
Bei ungueltigen Query-Parametern liefert `/status` eine HTML-Fehlerseite (kein JSON), damit Browser-Aufrufe direkt lesbare Hinweise erhalten.
|
||
|
||
## GET /status/{screenId}
|
||
|
||
HTML-Detailseite fuer einen einzelnen Screen.
|
||
Zeigt denselben Datensatz wie `GET /api/v1/screens/{screenId}/status` (Derived State, Player-Status, Connectivity, Frische, Timestamps, Endpoints).
|
||
|
||
Bei unbekanntem Screen: 404 mit HTML-Fehlermeldung und Rueck-Link auf `/status`.
|
||
|
||
## Serverseitig abgeleitete Felder
|
||
|
||
### stale
|
||
|
||
Die Schwelle wird aus dem gemeldeten `heartbeat_every_seconds` abgeleitet: mehr als zwei Intervalle ohne neuen Report gelten als veraltet.
|
||
|
||
`stale` ist aktuell eine Diagnosehilfe fuer die Entwicklungsstufe und noch kein vollstaendiges Online-/Offline-Modell fuer Admin-Oberflaechen.
|
||
|
||
### derived_state
|
||
|
||
- `offline` bei `stale = true` oder `server_connectivity = offline`
|
||
- `degraded` bei `server_connectivity = degraded|unknown` oder wenn `status` nicht `running` ist
|
||
- `online` in den verbleibenden Faellen
|
||
|
||
## Persistenz
|
||
|
||
Der Status-Store kann dateibasiert betrieben werden.
|
||
|
||
Konfiguration ueber die Umgebungsvariable:
|
||
|
||
- `MORZ_INFOBOARD_STATUS_STORE_PATH` – Pfad zur JSON-Datei; leer lassen fuer reinen In-Memory-Betrieb
|
||
|
||
Beim Datei-Store gilt:
|
||
|
||
- beim Start wird die Datei eingelesen, falls sie vorhanden ist (fehlende Datei ist kein Fehler)
|
||
- bei jedem `Save` und `Delete` wird der Inhalt atomar in die Datei geschrieben (write + rename)
|
||
- nach einem Neustart des Backends bleibt der letzte bekannte Statusbestand erhalten
|
||
|
||
## Agentseitige Connectivity-Ableitung
|
||
|
||
Agent-seitig wird die Server-Erreichbarkeit lokal als `unknown`, `online`, `degraded` oder `offline` aus dem Erfolg der HTTP-Reports abgeleitet.
|
||
|
||
Fuer den transportierten Wert im erfolgreichen HTTP-Report gilt:
|
||
|
||
- wenn ein Report vom Backend akzeptiert wurde, wird dieser Report selbst als `server_connectivity = online` gespeichert
|
||
- anhaltende Ausfaelle werden primaer ueber lokale Agent-Zustaende und serverseitige `stale`-Ableitung sichtbar
|
||
|
||
## Abgrenzung
|
||
|
||
Noch nicht Teil dieser Stufe:
|
||
|
||
- Screen-Authentifizierung
|
||
- MQTT-Heartbeat oder MQTT-Status
|
||
- Admin-UI-Anzeige des letzten Status
|
||
- Retry-Queue oder lokale Zwischenspeicherung im Agent
|
||
|
||
## Folgeschritte
|
||
|
||
Auf diesem Pfad bauen spaeter auf:
|
||
|
||
- Screen-Identitaet und Authentifizierung
|
||
- Trennung zwischen HTTP-Snapshot und MQTT-Heartbeat
|
||
- Admin-Vorschau fuer Online-/Offline- und Degraded-Zustaende
|