- Implement build script (build_docs.py) with AST parser to auto-generate HTML docs from docstrings - Add comprehensive Google-style docstrings to all controllers and models - Create static/description/index.html for Odoo Apps UI with module overview - Generate api_reference.html (20.5 KB) from source code, linked from Odoo UI - Add DOCUMENTATION_STRATEGY.md with comparison of 5 documentation approaches - Create API.md with complete REST API documentation Device Status Monitoring: - Implement device_status_monitor.py with health checks and offline detection - Add /status endpoint for device health overview - Automatic offline detection after message_timeout_s Config Push Architecture: - Add POST /config endpoint to IoT Bridge for dynamic device management - Auto-push device config from Odoo on create/write/unlink - Implement device_manager.py for runtime device updates E2E Tests: - All 6 E2E tests passing (Create, Update, Push, Delete, Restart, Status Monitor) - Test coverage for device lifecycle and config synchronization Documentation is auto-generated via: ./build_docs.sh View in Odoo: Settings → Apps → Open Workshop MQTT → API Reference
4.3 KiB
4.3 KiB
Implementation Plan: Device Online/Offline Status
Overview
Wir leiten den Device Online/Offline Status von MQTT Message Activity (last_seen) ab. Die Bridge überwacht die Aktivität und informiert Odoo via Events. Odoo aktualisiert die bestehenden Status-Felder und zeigt sie in der UI an.
Wichtig: Die benötigten Felder existieren bereits in mqtt.device:
state(selection: offline/idle/active)last_message_time(datetime)
Implementierung: Event-basierte Status-Updates
Bridge
- Track last_seen per device on every MQTT message.
- Add a background monitor that marks devices Offline after timeout.
- Emit status events to Odoo:
- event_type: device_online, device_offline
- payload: device_id, last_seen_at, reason
- Add optional MQTT LWT handling if available from devices.
- Persist last_seen state in /data to survive restart.
Odoo
- Bestehende Felder nutzen (mqtt.device):
state(offline/idle/active)last_message_time(datetime)
- Event Controller erweitern (/ows/iot/event):
- Event-Type
device_onlineverarbeiten: state → 'idle', last_message_time aktualisieren - Event-Type
device_offlineverarbeiten: state → 'offline'
- Event-Type
- Views aktualisieren:
- Status-Anzeige mit Farb-Kodierung (grün=idle/active, grau=offline)
- Last_message_time in List und Form View
- Filter in List View: Online (idle/active), Offline
Data Model
Bestehende Felder (keine Änderungen nötig):
state: selection [offline, idle, active] - Current device statuslast_message_time: datetime - Timestamp of last MQTT message
Configuration
- BRIDGE_DEVICE_TIMEOUT_S (default 30)
- BRIDGE_STATUS_CHECK_INTERVAL_S (default 5)
Implementation Steps
Phase 1: Bridge - Status Monitoring
- mqtt_client.py: Track last_seen timestamp pro device bei jedem MQTT Message
- Status Monitor Thread:
- Background Task, läuft alle BRIDGE_STATUS_CHECK_INTERVAL_S (default: 5s)
- Prüft jedes device: if (now - last_seen) > BRIDGE_DEVICE_TIMEOUT_S → Offline
- State Transitions:
- first_message → device_online event
- timeout → device_offline event
- Persistenz: last_seen state in /data/device_status.json speichern (Restart-Recovery)
- Event Emission: device_online/device_offline via odoo_client.send_event()
Phase 2: Odoo - Event Processing
- iot_api.py (Event Controller):
- Erweitere
_process_event()für event_type='device_online':device.write({'state': 'idle', 'last_message_time': event_data['timestamp']}) - Erweitere für event_type='device_offline':
device.write({'state': 'offline'})
- Erweitere
- Views aktualisieren:
- mqtt_device_views.xml: Status-Badge mit Farbe (idle/active=success, offline=secondary)
- List View: last_message_time column hinzufügen
- Filter: "Online" (state in ['idle','active']), "Offline" (state='offline')
Phase 3: Testing
- Unit Tests (Bridge):
- Test timeout detection logic
- Test state persistence (save/load)
- Test event emission
- Integration Tests:
- iot_bridge/tests/tools/shelly_simulator.py erweitern:
scenario_online_test(): Kontinuierliches Sendenscenario_offline_test(): Stop-Senden für X Sekunden
- Odoo Test: Prüfe state-Updates nach Online/Offline Events
- iot_bridge/tests/tools/shelly_simulator.py erweitern:
- Test Cases:
- Device wird Online: state='idle', last_message_time gesetzt
- Device timeout: state='offline' nach TIMEOUT_S
- Bridge restart: last_seen State recovered
Phase 4: Documentation
- README.md: Status Monitoring section
- API.md: device_online/device_offline event schema
- config.example.yaml: BRIDGE_DEVICE_TIMEOUT_S, BRIDGE_STATUS_CHECK_INTERVAL_S
Acceptance Tests
- ✅ Start shelly_simulator: status wird 'idle' within 1 message
- ✅ Stop simulator: status wird 'offline' nach TIMEOUT_S (default: 30s)
- ✅ Restart bridge: last_seen state wird recovered, status korrekt innerhalb 1 timeout window
- ✅ Multiple devices: Status-Updates unabhängig voneinander
Rollback Plan
- Config Flag:
BRIDGE_STATUS_MONITORING_ENABLED=falsedeaktiviert Status Monitor - Odoo: Ignoriere device_online/device_offline events (graceful degradation)
Notes
- Event-basiert: Near real-time Status ohne Polling overhead
- Bestehende Felder: Keine DB-Migration nötig
- Backward Compatible: Alte Events funktionieren weiterhin