Diese Datei beschreibt die HTTP-Schnittstellen der Anwendung.
Zusätzlich zur textuellen Referenz gibt es jetzt zwei API-Dokumentationsziele in der laufenden Anwendung:
/api-docs//openapi.yamlBeim lokalen Start mit php -S localhost:8000 sind die URLs:
http://localhost:8000/api-docs/http://localhost:8000/openapi.yamlDie OpenAPI-Datei ist handgeschrieben und dient als maschinenlesbare Quelle für die Swagger UI.
POST /api/v1/readings.phpNimmt genau einen Sensorwert für genau ein Fach entgegen.
Authorization: Bearer <token>Content-Type: application/json{
"machine_id": "automat-lobby",
"sensor_id": "fach-a1",
"distance_mm": 184,
"measured_at": "2026-04-15T19:20:00Z"
}
machine_id
config.jsonsensor_id
distance_mm
measured_at
POST.OPTIONS für Preflight-Requests mit 204 No Content.401.400.422.machine_id oder sensor_id nicht bekannt sind, antwortet die API mit 404.state.json aktualisiert.Status: 200 OK
{
"ok": true,
"machine_id": "automat-lobby",
"sensor_id": "fach-a1",
"slot_label": "A1",
"units_estimated": 4,
"fill_percent": 63,
"state": "ok"
}
Status: 401 Unauthorized
{
"ok": false,
"error": "Nicht autorisiert."
}
Status: 404 Not Found
{
"ok": false,
"error": "Unbekannter Automat oder Sensor."
}
Status: 422 Unprocessable Entity
{
"ok": false,
"error": "distance_mm muss numerisch sein."
}
Status: 405 Method Not Allowed
{
"ok": false,
"error": "Nur POST ist erlaubt."
}
Status: 400 Bad Request
{
"ok": false,
"error": "Ungültiger JSON-Body."
}
Status: 500 Internal Server Error
{
"ok": false,
"error": "Interner Fehler."
}
curlcurl -X POST http://localhost:8000/api/v1/readings.php \
-H 'Authorization: Bearer demo-esp32-token' \
-H 'Content-Type: application/json' \
-d '{
"machine_id": "automat-lobby",
"sensor_id": "fach-a1",
"distance_mm": 184
}'
Bei einer Apache-Unterordner-Installation unter https://example.com/monitor/ lautet derselbe Endpunkt:
POST https://example.com/monitor/api/v1/readings.php
GET /api/v1/status.phpLiefert den aktuellen Zustand der gesamten Anwendung.
GET.Status: 200 OK
Beispielstruktur:
{
"ok": true,
"generated_at": "2026-04-15T20:10:00+00:00",
"app": {
"name": "Getränkeautomat Monitor",
"dashboard_refresh_seconds": 15
},
"summary": {
"machine_count": 2,
"slot_count": 3,
"critical_count": 1
},
"machines": [
{
"id": "automat-lobby",
"name": "Lobby Automat",
"location": "Erdgeschoss",
"slots": []
}
],
"alerts": []
}
Bei einer Apache-Unterordner-Installation unter https://example.com/monitor/ lautet der Status-Endpunkt:
GET https://example.com/monitor/api/v1/status.php
machines[].slots[]machine_idmachine_namesensor_idslot_labelproduct_namefill_percentunits_estimatedmax_unitsdistance_mmstatemeasured_atupdated_atalert_below_unitsalerts[]idcreated_atpayload.eventpayload.machine_idpayload.machine_namepayload.sensor_idpayload.slot_labelpayload.product_namepayload.distance_mmpayload.units_estimatedpayload.max_unitspayload.fill_percentpayload.statepayload.previous_statepayload.measured_atdeliveries.webhooks[]deliveries.emails[]Status: 405 Method Not Allowed
{
"ok": false,
"error": "Nur GET ist erlaubt."
}
readings.php beantwortet OPTIONS mit 204 No Content und gibt folgende Header aus:
Access-Control-Allow-Methods: POST, OPTIONSAccess-Control-Allow-Headers: Authorization, Content-TypeFalls Sensor-Clients aus einem anderen Netzsegment oder über Browser-Tools senden, ist das hilfreich. Eine vollständige CORS-Konfiguration mit Access-Control-Allow-Origin ist aktuell noch nicht Teil der App.