e1d570992e
Drei zusammengehörige Teile in einem Repository: - homeassistant/ Das fertige, im Einsatz befindliche Home-Assistant-Panel (panel_custom Custom Element + pyscript-Backend). Echte Fahrzeug- und Personendaten (fahrzeugprofil.json, fahrten.jsonl, tankvorgaenge.jsonl, Tankbelege) bleiben per .gitignore außen vor; die anonymisierte Vorlage fahrzeugprofil.example.json ist mit dabei. - design-system/ Eigenständige React-Komponentenbibliothek (@audi-dash/ui), die die visuelle Sprache des Panels nachbildet - ohne Audi-Markenzeichen und ohne die lizenzierte Hausschrift. Dient als Grundlage für Claude Design. War bis hierher ein eigenes Repository und ist in dieses eingeschmolzen worden. - companion-app/ Datenschicht der neuen App DataMetric360 (iOS/Android via Capacitor, zusätzlich als Iframe im HA-Dashboard). Noch ohne Oberfläche: REST- und WebSocket-Zugriff auf Home Assistant plus Warteschlange für Änderungen ohne Netz. Ersetzt das eingespritzte hass-Objekt, das nur innerhalb des HA-Frontends existiert. Dazu die Projektdokumentation: SPECIFICATION.md (Ist-Stand des Panels), COMPANION_APP_ARCHITECTURE.md (Architekturentscheidungen der neuen App), AUDIT_2026-08-10.md, DESIGN_BRIEF_DATAMETRIC360.md und der ursprüngliche Bauauftrag. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
76 lines
3.2 KiB
Python
76 lines
3.2 KiB
Python
"""Verbindung zwischen Frontend und Backend.
|
|
|
|
Lesen: das Frontend liest hass.states["pyscript.audi_dashboard_profil"] usw.
|
|
direkt - kein Service-Aufruf mit Rückgabewert. Die Frontend-Dokumentation von
|
|
Home Assistant zu response-fähigen Services beschreibt das Verhalten aus
|
|
Sicht des Browsers nicht abschließend (Community-Diskussionen deuten auf
|
|
Einschränkungen hin); Zustände lesen ist dagegen ein seit Jahren stabiler,
|
|
einfacher Weg. Veröffentlicht wird periodisch UND sofort nach jeder
|
|
Schreibaktion (siehe frontend_veroeffentlichung.py, dort auch der Hinweis zur
|
|
Größengrenze von Zustands-Attributen).
|
|
|
|
Schreiben: einzig audi_dashboard_profil_schreiben() als generischer Weg für
|
|
das gesamte Profil - das Frontend hält Profil, Fahrzeugdaten und
|
|
Einstellungen ohnehin als einen zusammenhängenden Stand im Speicher (wie
|
|
schon im Prototyp) und schickt ihn nach jeder Änderung komplett zurück,
|
|
statt für jedes einzelne Feld einen eigenen Service zu brauchen.
|
|
"""
|
|
|
|
import json
|
|
|
|
import einstellungen
|
|
import frontend_veroeffentlichung
|
|
import profil
|
|
|
|
|
|
@time_trigger("startup")
|
|
def beim_start():
|
|
profil.ordner_sicherstellen()
|
|
frontend_veroeffentlichung.alles_veroeffentlichen()
|
|
|
|
|
|
@time_trigger("period(now, 20 seconds)")
|
|
def periodisch_aktualisieren():
|
|
frontend_veroeffentlichung.fahrzeugstatus_veroeffentlichen()
|
|
|
|
|
|
@time_trigger("period(now, 60 seconds)")
|
|
def periodisch_daten_aktualisieren():
|
|
# seltener als der Fahrzeugstatus - Profil/Fahrten/Tankvorgänge ändern
|
|
# sich normalerweise nur durch Aktionen, die ohnehin sofort selbst
|
|
# veröffentlichen (siehe unten); das hier ist nur das Sicherheitsnetz
|
|
# für Änderungen direkt im Dateisystem (§6.2, dritter Bearbeitungsweg).
|
|
frontend_veroeffentlichung.profil_veroeffentlichen()
|
|
frontend_veroeffentlichung.fahrten_veroeffentlichen()
|
|
frontend_veroeffentlichung.tankvorgaenge_veroeffentlichen()
|
|
|
|
|
|
@service
|
|
def audi_dashboard_jetzt_aktualisieren():
|
|
"""Gegenstück zum "Ziehen zum Aktualisieren" auf der Übersicht: stößt den
|
|
von der Integration bereitgestellten Refresh-Knopf an (siehe
|
|
einstellungen.REFRESH_BUTTON) statt auf den nächsten periodischen Takt zu
|
|
warten, und veröffentlicht den Status danach sofort neu. Ohne
|
|
eingetragenen Knopf (leerer Platzhalter) nur die direkte Neu-
|
|
veröffentlichung - besser als gar nichts, auch wenn dann kein echter neuer
|
|
Abruf beim Fahrzeug passiert. Aufruf als
|
|
pyscript.audi_dashboard_jetzt_aktualisieren."""
|
|
if einstellungen.REFRESH_BUTTON:
|
|
button.press(entity_id=einstellungen.REFRESH_BUTTON)
|
|
task.sleep(3)
|
|
frontend_veroeffentlichung.fahrzeugstatus_veroeffentlichen()
|
|
log.info("audi_dashboard: manuelle Aktualisierung (Ziehen zum Aktualisieren) ausgelöst")
|
|
|
|
|
|
@service
|
|
def audi_dashboard_profil_schreiben(profil_json=None):
|
|
"""Überschreibt das komplette Fahrzeugprofil. Aufruf als
|
|
pyscript.audi_dashboard_profil_schreiben."""
|
|
if not profil_json:
|
|
log.warning("audi_dashboard: profil_schreiben ohne profil_json aufgerufen")
|
|
return
|
|
p = json.loads(profil_json) if isinstance(profil_json, str) else profil_json
|
|
profil.profil_schreiben(p)
|
|
frontend_veroeffentlichung.profil_veroeffentlichen()
|
|
log.info("audi_dashboard: Profil aktualisiert")
|