odoo_mqtt/docs/FEATURE_REQUEST_DYNAMIC_PARSER_REGISTRY.md
matthias.lotz 4de3401416 fix: odoo/ als normales Verzeichnis tracken + Bugfix db_name + Feature-Docs
- git rm --cached odoo: Gitlink-Eintrag entfernt, odoo/ wird jetzt korrekt versioniert
- odoo/src/odoo-dev.conf: db_name = odoo gesetzt (behebt 404 bei mehreren DBs)
- docs/FEATURE_REQUEST_DYNAMIC_PARSER_REGISTRY.md: Feature Request inkl. ADR
- docs/IMPLEMENTATION_PLAN_DYNAMIC_PARSER_REGISTRY.md: 3-Phasen-Implementierungsplan
- iot_bridge/README.md: Doku aktualisiert
2026-03-10 17:17:59 +01:00

6.2 KiB
Raw Blame History

Feature Request: Dynamic Parser Registry

Stand: 2026-03-10
Status: Architektur entschieden
Umsetzungs-Plan: docs/IMPLEMENTATION_PLAN_DYNAMIC_PARSER_REGISTRY.md


Motivation

Der parser_type ist derzeit an zwei Stellen hartcodiert:

  • IoT Bridge (core/device_manager.py): Es gibt einen einzigen globalen ShellyParser().
    Der parser_type-String aus der Konfiguration wird zwar transportiert, aber vollständig ignoriert.
  • Odoo (models/mqtt_device.py): Das Feld parser_type ist ein statisches fields.Selection
    mit fest eingetragenen Werten (shelly_pm, tasmota, generic).
    Es gibt keinen API-Call zur Bridge, um verfügbare Parser dynamisch zu ermitteln.

Das Ergebnis: Neue Parser können nicht hinzugefügt werden, ohne Code an mehreren Stellen
manuell anzupassen und die Odoo-Konfiguration bleibt inkonsistent mit dem, was die Bridge
tatsächlich unterstützt.


Ziele

1. Erweiterbare Parser-Registry in der IoT Bridge

Die Bridge soll eine Registry führen, die parser_type-Strings auf Parser-Klassen abbildet.
Neue Parser können registriert werden, ohne den DeviceManager oder andere Kern-Komponenten
zu ändern.

Aktueller Zustand:

self.parser = parser or ShellyParser()  # global, für alle Geräte

Ziel:

  • Pro-Gerät-Parser statt einem globalen Parser
  • Registry-lookup beim Anlegen eines Geräts: parser_type → ParserClass
  • Unbekannte parser_type-Strings erzeugen einen klar verständlichen Fehler (kein Silent-Fallback)

Die Registry soll außerdem einen API-Endpunkt (GET /parsers o. ä.) bereitstellen,
der die aktuell verfügbaren Parser-Typen auflistet.


2. Automatische Erkennung verfügbarer Parser in Odoo

Das parser_type-Feld in ows.mqtt.device soll nicht mehr hartcodiert sein.
Stattdessen ruft Odoo zur Laufzeit die Liste der verfügbaren Parser von der Bridge ab
(GET /parsers o. ä.) und befüllt die Auswahl dynamisch.

Mögliche Mechanismen:

  • fields.Selection mit dynamischer selection-Methode, die die Bridge befragt
  • Alternativer Ansatz: separates Modell ows.mqtt.parser.type mit Sync-Button / Cron

Welcher Mechanismus gewählt wird, ist Teil der Implementierungsplanung.


3. Parser-typ-abhängige Konfigurationsparameter in Odoo

Verschiedene Parser benötigen unterschiedliche Konfigurationsparameter.
Die aktuellen Felder (Leistungs-Schwellenwerte, Debounce-Zeiten usw.) sind spezifisch
für den Shelly-PM-Parser und ergeben für andere Gerätetypen keinen Sinn.

Ziel: Die Odoo-Oberfläche zeigt nur die Parameter an, die für den gewählten parser_type
relevant sind. Die Bridge kennt pro Parser-Typ das zugehörige Konfigurations-Schema
(JSON Schema o. ä.) und stellt dieses ebenfalls über die API bereit.

Damit kann Odoo:

  • Irrelevante Felder ausblenden (attrs/invisible in der View)
  • Validierung parser-spezifisch durchführen
  • Das korrekte Konfigurations-JSON für die Bridge generieren

Abgrenzung

  • Die konkrete Implementierung eines zweiten Parsers (z. B. Laser-Cutter On/Off) ist
    nicht Teil dieses Feature Requests. Sie setzt aber diese Architektur voraus.
  • Die Frage, welche Felder ein neuer Parser benötigt, wird im jeweiligen Parser-spezifischen
    Issue/Plan geklärt.

Architektur-Entscheidung (ADR)

Datum: 2026-03-10
Entscheidung: Bridge als Single Source of Truth, Odoo bleibt statisch

Kontext

IoT Bridge und Odoo-Modul sind fest gekoppelt sie werden gemeinsam deployed.
Ein neuer Parser erfordert immer eine Änderung an beiden Komponenten.

Entscheidung

Die Bridge ist die einzige Stelle, an der ein Parser definiert wird.
Das Odoo-Modul ist das statisch abgeleitete Ergebnis dieser Definition.

GET /parsers (JSON-Schema, definiert in der Bridge)
        │
        ▼
   Ableitung (bei jedem neuen Parser, manuell oder per Script)
        │
        ├──▶ Python-Felder im Odoo-Modell  (fields.Integer, fields.Float, …)
        ├──▶ XML-View mit invisible-Logik   (attrs invisible="parser_type != 'x'")
        └──▶ Selection-Eintrag              ('shelly_pm', 'Shelly PM Mini G3')

Schema-Format (Bridge → Ableitungsgrundlage)

Die Bridge liefert pro Parser-Typ ein maschinenlesbares Parameter-Schema:

{
  "shelly_pm": {
    "display_name": "Shelly PM Mini G3",
    "parameters": [
      {
        "key": "power_on_threshold_w",
        "odoo_field": "power_on_threshold_w",
        "type": "integer",
        "unit": "W",
        "label": "Einschalt-Schwelle",
        "default": 20,
        "required": true,
        "group": "session_detection",
        "help": "Ab welcher Leistung gilt das Gerät als eingeschaltet?"
      }
    ]
  }
}

Aus jedem Parameter-Eintrag lässt sich eindeutig ableiten:

Schema-Feld Odoo-Artefakt
odoo_field + type Feldname und Feldtyp im Python-Modell
label string= im Feldaufruf
help help= im Feldaufruf
default default= im Feldaufruf
required required=True (optional: nur pro Parser-Typ)
parser_types (Liste) invisible-Bedingung in der XML-View

Konsequenzen

Gewinn:

  • Kein EAV, kein Runtime-Rendering, kein Verbiegen des Odoo-Frameworks
  • Odoo bleibt wartbar und testbar wie bisher
  • Neue Parser = kleiner, mechanischer Änderungsaufwand in Odoo

Akzeptierter Kompromiss:

  • Ein neuer Parser erfordert ein neues Odoo-Modul-Deployment
  • Die GET /parsers-Antwort der Bridge und das Odoo-Modell können theoretisch
    aus dem Sync geraten wird durch Tests/CI abgesichert

Betroffene Komponenten (erster Überblick)

Komponente Datei(en) Art der Änderung
IoT Bridge Parser-Registry parsers/__init__.py, neu: parsers/registry.py Neu
IoT Bridge DeviceManager core/device_manager.py Umbau: pro-Gerät-Parser
IoT Bridge API api/models.py, api/server.py Erweiterung: GET /parsers
Odoo mqtt_device models/mqtt_device.py Umbau: dynamisches Selection-Feld
Odoo Views views/mqtt_device_views.xml Umbau: bedingte Sichtbarkeit
Odoo API-Client (neu oder bestehend) Neu: Fetch verfügbarer Parser