iobroker.poolcontrol 0.2.1 → 0.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -1,14 +1,18 @@
1
1
  # ioBroker.poolcontrol
2
2
 
3
- ![Test and Release](https://github.com/DasBo1975/iobroker.poolcontrol/actions/workflows/test-and-release.yml/badge.svg)
3
+ ![Test and Release](https://github.com/DasBo1975/ioBroker.poolcontrol/actions/workflows/test-and-release.yml/badge.svg)
4
4
  ![npm](https://img.shields.io/npm/v/iobroker.poolcontrol?color=blue)
5
5
  ![Downloads](https://img.shields.io/npm/dm/iobroker.poolcontrol)
6
6
  ![Installs](https://iobroker.live/badges/poolcontrol-installed.svg)
7
7
  ![Stable](https://iobroker.live/badges/poolcontrol-stable.svg)
8
8
  [![License](https://img.shields.io/github/license/DasBo1975/ioBroker.poolcontrol?cacheSeconds=3600)](https://github.com/DasBo1975/ioBroker.poolcontrol/blob/main/LICENSE)
9
9
 
10
+ ---
11
+
12
+ ## Beschreibung
13
+
10
14
  Der Adapter **ioBroker.poolcontrol** dient zur Steuerung und Überwachung von Poolanlagen.
11
- Er ermöglicht die Automatisierung von Pumpen, Temperatur- und Solarsteuerung sowie Verbrauchsauswertung.
15
+ Er ermöglicht die Automatisierung von Pumpen-, Temperatur- und Solarsteuerung sowie die Verbrauchsauswertung.
12
16
 
13
17
  ---
14
18
 
@@ -28,7 +32,7 @@ Er ermöglicht die Automatisierung von Pumpen, Temperatur- und Solarsteuerung so
28
32
  - **Solarsteuerung**
29
33
  - Ein-/Ausschaltgrenzen mit Hysterese
30
34
  - Kollektor-Warnung (mit automatischer Rücksetzung bei 10 % unter der Schwelle)
31
- - Optional Sprachausgabe bei Warnung
35
+ - Optionale Sprachausgabe bei Warnung
32
36
 
33
37
  - **Zeitsteuerung**
34
38
  - Bis zu 3 frei konfigurierbare Zeitfenster pro Woche
@@ -41,14 +45,15 @@ Er ermöglicht die Automatisierung von Pumpen, Temperatur- und Solarsteuerung so
41
45
  - Auswertung eines externen kWh-Zählers
42
46
  - Tages-, Wochen-, Monats- und Jahresverbrauch
43
47
  - Berechnung der Stromkosten anhand konfigurierbarem Preis
44
- **Hinweis:**
45
- Details zum Verhalten der Verbrauchs- und Kostenwerte (z. B. bei Neustarts oder beim Wechsel des Stromzählers) finden Sie in der Datei [help.md](./help.md).
48
+
49
+ **Hinweis:**
50
+ Details zum Verhalten der Verbrauchs- und Kostenwerte (z. B. bei Neustarts oder beim Wechsel des Stromzählers) finden Sie in der Datei [help.md](./help.md).
46
51
 
47
52
  - **Sprachausgaben**
48
53
  - Ausgabe über Alexa oder Telegram
49
54
  - Ansagen bei Pumpenstart/-stopp, Fehlern oder Temperaturschwellen
50
55
 
51
- - **Systemcheck (Diagnosebereich)**
56
+ - **SystemCheck (Diagnosebereich)**
52
57
  Ab Version **0.2.0** enthält der Adapter einen neuen Diagnosebereich **SystemCheck**.
53
58
  Er bietet interne Debug-Logs, mit denen bestimmte Teilbereiche (z. B. Pumpen-, Solar- oder Temperatursteuerung) gezielt überwacht werden können.
54
59
 
@@ -66,7 +71,7 @@ Er ermöglicht die Automatisierung von Pumpen, Temperatur- und Solarsteuerung so
66
71
 
67
72
  1. Adapter über ioBroker Admin installieren.
68
73
  2. Instanz anlegen.
69
- 3. Konfiguration im Admin-Tab vornehmen: Pumpenleistung, Sensoren, Solar, Sprachausgaben, etc.
74
+ 3. Konfiguration im Admin-Tab vornehmen: Pumpenleistung, Sensoren, Solar, Sprachausgaben usw.
70
75
 
71
76
  ---
72
77
 
@@ -88,81 +93,70 @@ Die Konfiguration erfolgt über Tabs im Admin-Interface:
88
93
  - Rückspülerinnerung (Intervall in Tagen, Erinnerung über State)
89
94
  - Wartung Kesseldruck (maximaler Druck, Warnung bei Überschreitung)
90
95
  - Weitere Komfortfunktionen nach Praxistests
96
+ - Kesseldruck-Wartung / Drucksensor-Warnung
97
+ - PV-Überschuss-Steuerung (für z.B. Pumpe oder Wärmepumpe)
98
+ - Zweite Pumpe (z.B. Wärmetauscher)
99
+ - Statistikbereich
100
+ - Eigene Widgets für VIS/VIS2
101
+ - Erweiterung Wärmepumpen-/Heizlogik
102
+ - Steuerung von Poolbeleuchtung
103
+ - Steuerung von Poolrobotern
104
+ - Steuerung von elektrischen Ventilen
105
+ - Steuerung von Gegenstromanlagen
91
106
 
92
107
  ---
93
108
 
94
109
  ## Hinweis
95
110
 
96
111
  Der Adapter befindet sich aktuell in der Entwicklung.
97
- Funktionen können sich ändern, bitte regelmäßig den Changelog beachten.
112
+ Funktionen können sich ändern bitte regelmäßig den Changelog beachten.
98
113
 
99
114
  ---
100
115
 
101
116
  ## Dokumentation
102
- - [Help.md (ausführliche Beschreibung und Hinweise)](./help.md)
117
+ - [help.md (ausführliche Beschreibung und Hinweise)](./help.md)
103
118
 
104
119
  ---
105
120
 
106
121
  ## Changelog
107
- Auszug, vollständige Liste siehe `io-package.json`:
108
-
109
- ### 0.2.0 (2025-10-06)
110
- - Neuer Diagnosebereich **SystemCheck** für interne Debug-Logs und Analysen.
111
- - Möglichkeit, einzelne Adapterbereiche (z. B. Pumpe, Solar, Temperatur) gezielt zu überwachen.
112
- - Fortlaufendes Textprotokoll mit manueller Löschfunktion.
113
- - Alle bisherigen Debug-Funktionen aus `zz_debuglogs` in `SystemCheck.debug_logs` integriert.
114
- - Vorbereitung für zukünftige Diagnose-Erweiterungen (Export, Systemprüfung, Plausibilitäts-Checks).
115
-
116
-
117
- ### 0.1.2
118
- - Verbesserung: Beim Adapterstart werden nun die letzten bekannten Temperaturwerte aller aktiven Sensoren (z. B. Oberfläche, Kollektor, Außentemperatur usw.) automatisch übernommen.
119
- - Dadurch werden auch Sensoren korrekt angezeigt, die ihren Messwert nur selten aktualisieren (z. B. Homematic oder stromsparende Funk-Sensoren).
120
- - Keine Änderung am Verhalten der restlichen Logik, reine Komfort- und Stabilitätsverbesserung.
122
+ ### **WORK IN PROGRESS**
121
123
 
122
- ### 0.1.1
123
- - Fehlerbehebung: Endlosschleife zwischen `pump_switch` und externer Steckdose (`deviceId`) behoben, die bei bestimmten Smart-Steckdosen (z. B. Shelly, Tasmota, FritzDECT) auftreten konnte.
124
- - Verbesserte Stabilität im `pumpHelper` durch interne Rückkopplungsprüfung.
125
- - Keine Änderungen an bestehenden Konfigurationen erforderlich.
124
+ ### 0.3.0 (12.10.2025)
125
+ **Neu:** Intelligentes Pumpen-Monitoring & Lernsystem
126
126
 
127
- ### 0.1.0
128
- - Sprachausgabe über **E-Mail** hinzugefügt (konfigurierbar: Instanz, Empfänger, Betreff).
129
- - Erweiterung der Instanz-Konfiguration im Tab „Sprachausgaben“.
130
- **Bugfixes**
131
- - Kleinere Korrekturen und Optimierungen in der Dokumentation (`help.md`).
132
- - Logging in `speechHelper` verbessert.
127
+ - Hinzugefügt: **Reelle Durchflussberechnung** auf Basis der tatsächlichen Leistungsaufnahme.
128
+ - Neuer Bereich **`pump.live`** zur Live-Überwachung von Leistung, Durchfluss und prozentualer Auslastung.
129
+ - Die **tägliche Umwälzberechnung** verwendet nun den realen Durchflusswert anstelle eines Fixwerts.
130
+ - Neuer Lernbereich **`pump.learning`**:
131
+ - Lernt automatisch die durchschnittlichen Leistungs- und Durchflusswerte.
132
+ - Bestimmt daraus einen dynamischen **Normalbereich (± 15 %)**.
133
+ - Berechnet prozentuale Abweichungen und erstellt **textbasierte Statusmeldungen**.
134
+ - Alle Lernwerte werden **persistent** gespeichert und bleiben auch nach Neustart erhalten.
135
+ - Vollständig **ereignisgesteuerte Logik** ohne zusätzliche Timer oder Polling-Zyklen.
133
136
 
134
- ### 0.0.10
135
-
136
- Statusübersicht
137
- Ab Version 0.0.10 gibt es einen eigenen Bereich `status.*` mit folgenden Datenpunkten:
138
-
139
- - **status.summary** → Textübersicht (Pumpe, Modus, Temperaturen, Laufzeit, Umwälzung)
140
- - **status.overview_json** → Übersicht als JSON (maschinenlesbar)
141
- - **status.last_summary_update** → Zeitpunkt der letzten Aktualisierung
142
- - **status.pump_last_start** → Letzter Pumpenstart (Zeitstempel)
143
- - **status.pump_last_stop** → Letztes Pumpenende (Zeitstempel)
144
- - **status.pump_was_on_today** → Boolean, ob die Pumpe heute lief
145
- - **status.pump_today_count** → Anzahl der Starts heute (Reset um Mitternacht)
146
- - **status.system_ok** → Boolean, ob das System fehlerfrei läuft
147
- - **status.system_warning** → Boolean, wenn eine Warnung aktiv ist
148
- - **status.system_warning_text** → Beschreibung der aktiven Warnung
149
- - **status.season_active** → Anzeige, ob die Poolsaison aktiv ist
150
-
151
- Diese Datenpunkte sind besonders für **VIS/vis2, Alexa- oder Telegram-Ausgaben** gedacht, da sie eine schnelle Übersicht über den aktuellen Poolstatus bieten.
137
+ > Mit dieser Version beginnt die lernfähige Phase des PoolControl-Adapters:
138
+ > Deine Pumpe weiß jetzt selbst, was für sie „normal“ ist.
152
139
 
140
+ ---
153
141
 
154
- ### 0.0.9
155
- - Laufzeit-, Umwälz-, Verbrauch-/Kosten- und Temperatur-Min/Max-States sind jetzt persistent
156
- (Werte bleiben nach Adapter-Neustart oder Stromausfall erhalten)
142
+ ### 0.2.2 (2025-10-08)
143
+ - Einführung einer **automatischen Rückspülerinnerung** (neuer Bereich im ControlHelper2)
144
+ - Erinnerung mit Intervall in Tagen und automatischer Rücksetzung nach erfolgter Rückspülung
145
+ - Log- und Sprachausgabe bei Fälligkeit oder Überfälligkeit
146
+ - Erweiterung des Control-Bereichs um zusätzliche States (backwash_reminder_active, interval_days, last_date, required)
147
+ - Anpassung der main.js und controlStates zur Integration
148
+ - Vorbereitung weiterer Wartungs- und Steuerungsfunktionen (Beleuchtung, Roboter, Ventile, Gegenstromanlage, Kesseldruck-Überwachung).
157
149
 
158
- ### 0.0.8
159
- - Hilfetab in der Instanzkonfiguration hinzugefügt (mit Link zur GitHub-Dokumentation)
150
+ ---
160
151
 
161
- ### 0.0.7
162
- - Help-Datei (`help.md`) und erste README-Version hinzugefügt
152
+ ### 0.2.0 (2025-10-06)
153
+ - Neuer Diagnosebereich **SystemCheck** für interne Debug-Logs und Analysen.
154
+ - Möglichkeit, einzelne Adapterbereiche (z. B. Pumpe, Solar, Temperatur) gezielt zu überwachen.
155
+ - Fortlaufendes Textprotokoll mit manueller Löschfunktion.
156
+ - Alle bisherigen Debug-Funktionen aus `zz_debuglogs` in `SystemCheck.debug_logs` integriert.
157
+ - Vorbereitung für zukünftige Diagnose-Erweiterungen (Export, Systemprüfung, Plausibilitäts-Checks).
163
158
 
164
- ### 0.0.1
165
- - initial release
159
+ *(ältere Versionen siehe [io-package.json](./io-package.json))*
166
160
 
167
161
  ---
168
162
 
@@ -174,7 +168,6 @@ Diese Datenpunkte sind besonders für **VIS/vis2, Alexa- oder Telegram-Ausgaben*
174
168
 
175
169
  ## Unterstützung der Adapterentwicklung
176
170
  Wenn Ihnen **ioBroker.poolcontrol** gefällt, denken Sie bitte über eine Spende nach:
177
-
178
171
  ➡️ [Unterstützen via PayPal](https://www.paypal.com/donate?business=dirk.bertin@t-online.de)
179
172
 
180
173
  ---
@@ -188,6 +181,6 @@ Der Nutzer ist für die **sichere Installation und den Betrieb seiner Hardware**
188
181
  ---
189
182
 
190
183
  ## License
191
- Copyright (c) 2025 DasBo1975 <dasbo1975@outlook.de>
184
+ Copyright (c) 2025 DasBo1975 <dasbo1975@outlook.de>
192
185
 
193
- MIT License
186
+ MIT License
package/io-package.json CHANGED
@@ -1,8 +1,32 @@
1
1
  {
2
2
  "common": {
3
3
  "name": "poolcontrol",
4
- "version": "0.2.1",
4
+ "version": "0.3.0",
5
5
  "news": {
6
+ "0.3.0": {
7
+ "en": "Added real pump flow calculation, live monitoring, and self-learning normal range system for pump analysis.",
8
+ "de": "Reelle Durchflussberechnung, Liveüberwachung und selbstlernendes Normalbereich-System zur Pumpenanalyse hinzugefügt.",
9
+ "ru": "Добавлен расчет реального расхода насоса, живой мониторинг и самообучающаяся система нормальных диапазонов для анализа насоса.",
10
+ "pt": "Adicionada cálculo de fluxo real da bomba, monitoramento ao vivo e sistema autoaprendente de faixa normal para análise da bomba.",
11
+ "nl": "Reële pompdebietberekening, livebewaking en zelflerend normaalbereiksysteem voor pompanalyse toegevoegd.",
12
+ "fr": "Ajout du calcul du débit réel de la pompe, de la surveillance en direct et d’un système de plage normale auto-apprenant pour l’analyse de la pompe.",
13
+ "it": "Aggiunto calcolo del flusso reale della pompa, monitoraggio live e sistema autoapprendente di intervallo normale per l'analisi della pompa.",
14
+ "es": "Se añadió el cálculo del caudal real de la bomba, la monitorización en vivo y un sistema de rango normal autoaprendente para el análisis de la bomba.",
15
+ "pl": "Dodano obliczanie rzeczywistego przepływu pompy, monitorowanie na żywo i samouczący się system normalnego zakresu do analizy pompy.",
16
+ "zh-cn": "添加了实际泵流量计算、实时监控以及用于泵分析的自学习正常范围系统。"
17
+ },
18
+ "0.2.2": {
19
+ "en": "Added automatic backwash reminder with speech and log notifications.",
20
+ "de": "Automatische Rückspülerinnerung mit Sprach- und Log-Benachrichtigung hinzugefügt.",
21
+ "ru": "Добавлено автоматическое напоминание о обратной промывке с голосовыми и журнальными уведомлениями.",
22
+ "pt": "Adicionado lembrete automático de retrolavagem com notificações de voz e registro.",
23
+ "nl": "Automatische terugspoelherinnering toegevoegd met spraak- en logmeldingen.",
24
+ "fr": "Ajout d’un rappel automatique de contre-lavage avec notifications vocales et journaux.",
25
+ "it": "Aggiunto promemoria automatico di controlavaggio con notifiche vocali e log.",
26
+ "es": "Recordatorio automático de contralavado añadido con notificaciones de voz y registro.",
27
+ "pl": "Dodano automatyczne przypomnienie o płukaniu wstecznym z powiadomieniami głosowymi i dziennikiem.",
28
+ "zh-cn": "添加了带语音和日志通知的自动反冲洗提醒。"
29
+ },
6
30
  "0.2.1": {
7
31
  "en": "Fixed the issue with invisible states for speech control and added proper internal variable handling.",
8
32
  "de": "Behebung des Problems mit unsichtbaren States für die Sprachsteuerung und hinzugefügte korrekte Handhabung interner Variablen.",
@@ -28,60 +52,8 @@
28
52
  "pl": "Nowy obszar diagnostyczny 'SystemCheck' dla wewnętrznych dzienników debugowania i przyszłych narzędzi analitycznych.",
29
53
  "uk": "Нова діагностична область 'SystemCheck' для внутрішніх журналів налагодження та майбутніх інструментів аналізу.",
30
54
  "zh-cn": "新的诊断区域“SystemCheck”,用于内部调试日志和未来的分析工具。"
31
- },
32
- "0.1.2": {
33
- "en": "Improved: The last known temperature values of all active sensors are now read at adapter start. Sensors that report rarely are now displayed correctly.",
34
- "de": "Verbesserung: Beim Adapterstart werden nun die letzten bekannten Temperaturwerte aller aktiven Sensoren übernommen. Sensoren, die nur selten Werte senden, werden jetzt korrekt angezeigt.",
35
- "ru": "Улучшение: При запуске адаптера теперь считываются последние известные значения температуры всех активных датчиков.",
36
- "pt": "Melhoria: Os últimos valores de temperatura conhecidos de todos os sensores ativos agora são lidos ao iniciar o adaptador.",
37
- "nl": "Verbetering: Bij het starten van de adapter worden nu de laatst bekende temperatuurwaarden van alle actieve sensoren opgehaald.",
38
- "fr": "Amélioration : les dernières valeurs de température connues de tous les capteurs actifs sont désormais lues au démarrage de l’adaptateur.",
39
- "it": "Miglioramento: all'avvio dell'adattatore vengono ora letti gli ultimi valori di temperatura noti di tutti i sensori attivi.",
40
- "es": "Mejora: ahora se leen al iniciar el adaptador los últimos valores de temperatura conocidos de todos los sensores activos.",
41
- "pl": "Ulepszenie: podczas uruchamiania adaptera odczytywane są ostatnie znane wartości temperatury wszystkich aktywnych czujników.",
42
- "uk": "Покращення: під час запуску адаптера тепер зчитуються останні відомі значення температури всіх активних датчиків.",
43
- "zh-cn": "改进:适配器启动时现在会读取所有活动传感器的最后已知温度值。"
44
- },
45
- "0.1.1": {
46
- "en": "Fixed endless loop between pump_switch and deviceId for some smart sockets",
47
- "de": "Endlosschleife zwischen pump_switch und Steckdose (deviceId) behoben",
48
- "ru": "Исправлен бесконечный цикл между pump_switch и deviceId для некоторых умных розеток",
49
- "pt": "Corrigido loop infinito entre pump_switch e deviceId em algumas tomadas inteligentes",
50
- "nl": "Eindeloze lus tussen pump_switch en deviceId voor sommige slimme stopcontacten opgelost",
51
- "fr": "Correction d'une boucle infinie entre pump_switch et deviceId pour certaines prises intelligentes",
52
- "it": "Corretto loop infinito tra pump_switch e deviceId per alcune prese intelligenti",
53
- "es": "Corregido bucle infinito entre pump_switch y deviceId en algunos enchufes inteligentes",
54
- "pl": "Naprawiono nieskończoną pętlę między pump_switch a deviceId dla niektórych inteligentnych gniazdek",
55
- "uk": "Виправлено нескінченний цикл між pump_switch і deviceId для деяких розумних розеток",
56
- "zh-cn": "修复了某些智能插座中 pump_switch 与 deviceId 之间的无限循环"
57
- },
58
- "0.1.0": {
59
- "en": "Added speech output via E-Mail (configurable: instance, recipient, subject)",
60
- "de": "Sprachausgabe per E-Mail hinzugefügt (konfigurierbar: Instanz, Empfänger, Betreff)",
61
- "ru": "Добавлен вывод речи по электронной почте (настраивается: экземпляр, получатель, тема)",
62
- "pt": "Adicionada saída de fala por e-mail (configurável: instância, destinatário, assunto)",
63
- "nl": "Spraakuitvoer via e-mail toegevoegd (configureerbaar: instantie, ontvanger, onderwerp)",
64
- "fr": "Ajout de la sortie vocale par e-mail (configurable : instance, destinataire, sujet)",
65
- "it": "Aggiunta uscita vocale via e-mail (configurabile: istanza, destinatario, oggetto)",
66
- "es": "Se agregó salida de voz por correo electrónico (configurable: instancia, destinatario, asunto)",
67
- "pl": "Dodano wyjście głosowe przez e-mail (konfigurowalne: instancja, odbiorca, temat)",
68
- "uk": "Додано озвучення електронною поштою (налаштовується: екземпляр, одержувач, тема)",
69
- "zh-cn": "新增通过电子邮件的语音输出(可配置:实例、收件人、主题)"
70
- },
71
- "0.0.10": {
72
- "en": "Added extended status overview with pump statistics, system flags and JSON summary",
73
- "de": "Erweiterte Statusübersicht mit Pumpenstatistiken, Systemanzeigen und JSON-Zusammenfassung hinzugefügt",
74
- "ru": "Добавлен расширенный обзор состояния с насосной статистикой, системными флагами и JSON-резюме",
75
- "pt": "Adicionada visão geral de status estendida com estatísticas da bomba, sinalizadores do sistema e resumo em JSON",
76
- "nl": "Uitgebreide statusoverzicht toegevoegd met pompstatistieken, systeemindicatoren en JSON-samenvatting",
77
- "fr": "Aperçu du statut étendu ajouté avec statistiques de la pompe, indicateurs système et résumé JSON",
78
- "it": "Aggiunta panoramica dello stato estesa con statistiche della pompa, indicatori di sistema e riepilogo JSON",
79
- "es": "Añadida vista general de estado extendida con estadísticas de la bomba, indicadores del sistema y resumen en JSON",
80
- "pl": "Dodano rozszerzony przegląd statusu ze statystykami pompy, flagami systemowymi i podsumowaniem JSON",
81
- "uk": "Додано розширений огляд статусу зі статистикою насоса, системними прапорцями та зведенням JSON",
82
- "zh-cn": "新增扩展状态概览,包括泵统计、系统标志和 JSON 摘要"
83
55
  }
84
- },
56
+ },
85
57
  "titleLang": {
86
58
  "en": "PoolControl",
87
59
  "de": "PoolControl",
@@ -159,5 +131,5 @@
159
131
  },
160
132
  "objects": [],
161
133
  "instanceObjects": []
162
- }
134
+ }
163
135
 
@@ -141,6 +141,7 @@ async function _startAutoPumping(missingLiter) {
141
141
 
142
142
  previousPumpMode = (await adapter.getStateAsync('pump.mode'))?.val || 'auto';
143
143
  await adapter.setStateAsync('pump.mode', { val: 'controlHelper', ack: true });
144
+ await adapter.setStateAsync('pump.active_helper', { val: 'controlHelper', ack: true });
144
145
  await adapter.setStateAsync('pump.reason', { val: 'nachpumpen', ack: true });
145
146
  await adapter.setStateAsync('pump.pump_switch', { val: true, ack: false });
146
147
 
@@ -157,6 +158,7 @@ async function _startAutoPumping(missingLiter) {
157
158
  clearInterval(interval);
158
159
  await adapter.setStateAsync('pump.pump_switch', { val: false, ack: false });
159
160
  await adapter.setStateAsync('pump.mode', { val: previousPumpMode, ack: true });
161
+ await adapter.setStateAsync('pump.active_helper', { val: '', ack: true });
160
162
  await adapter.setStateAsync('pump.reason', { val: '', ack: true });
161
163
  previousPumpMode = null;
162
164
 
@@ -199,6 +201,7 @@ async function handleStateChange(id, state) {
199
201
  previousPumpMode = (await adapter.getStateAsync('pump.mode'))?.val || 'auto';
200
202
  await adapter.setStateAsync('pump.mode', { val: 'controlHelper', ack: true });
201
203
  await adapter.setStateAsync('pump.reason', { val: 'wartung', ack: true });
204
+ await adapter.setStateAsync('pump.active_helper', { val: 'controlHelper', ack: true });
202
205
  await adapter.setStateAsync('pump.pump_switch', { val: false, ack: false });
203
206
  adapter.log.info('[controlHelper] Wartungsmodus aktiviert. Automatik pausiert.');
204
207
 
@@ -207,6 +210,7 @@ async function handleStateChange(id, state) {
207
210
  }
208
211
  } else {
209
212
  await adapter.setStateAsync('pump.mode', { val: previousPumpMode, ack: true });
213
+ await adapter.setStateAsync('pump.active_helper', { val: '', ack: true });
210
214
  await adapter.setStateAsync('pump.reason', { val: '', ack: true });
211
215
  previousPumpMode = null;
212
216
 
@@ -232,6 +236,7 @@ async function handleStateChange(id, state) {
232
236
  await adapter.setStateAsync('control.pump.backwash_active', { val: true, ack: true });
233
237
  await adapter.setStateAsync('control.pump.backwash_start', { val: false, ack: true });
234
238
  await adapter.setStateAsync('pump.mode', { val: 'controlHelper', ack: true });
239
+ await adapter.setStateAsync('pump.active_helper', { val: 'controlHelper', ack: true });
235
240
  await adapter.setStateAsync('pump.reason', { val: 'rückspülen', ack: true });
236
241
  await adapter.setStateAsync('pump.pump_switch', { val: true, ack: false });
237
242
 
@@ -250,6 +255,7 @@ async function handleStateChange(id, state) {
250
255
  try {
251
256
  await adapter.setStateAsync('pump.pump_switch', { val: false, ack: false });
252
257
  await adapter.setStateAsync('pump.mode', { val: prevMode, ack: true });
258
+ await adapter.setStateAsync('pump.active_helper', { val: '', ack: true });
253
259
  await adapter.setStateAsync('pump.reason', { val: '', ack: true });
254
260
  await adapter.setStateAsync('control.pump.backwash_active', { val: false, ack: true });
255
261
 
@@ -0,0 +1,195 @@
1
+ 'use strict';
2
+
3
+ /**
4
+ * controlHelper2
5
+ * ----------------------------------------------
6
+ * Rückspülerinnerungs-Logik (eigenständig)
7
+ * ----------------------------------------------
8
+ * - täglicher Check um 12:00 Uhr (lokale Host-Zeit)
9
+ * - prüft Intervall und letzte Rückspülung
10
+ * - erzeugt Erinnerungen (Log + speech.queue)
11
+ * - setzt Erinnerung automatisch zurück, wenn Rückspülung startet
12
+ * ----------------------------------------------
13
+ */
14
+
15
+ // NEU: Modulvariablen
16
+ let adapter;
17
+ let backwashReminderTimer = null;
18
+ let lastReminderDay = null; // verhindert doppelte tägliche Meldungen
19
+
20
+ // NEU: Initialisierung
21
+ /**
22
+ * Initialisiert den Rückspülerinnerungs-Helper
23
+ *
24
+ * @param {import('iobroker').Adapter} a – ioBroker-Adapterinstanz
25
+ */
26
+ function init(a) {
27
+ adapter = a;
28
+ adapter.log.info('[controlHelper2] Rückspülerinnerung initialisiert (täglicher Check um 12:00 Uhr).');
29
+
30
+ // Rückspülstart abonnieren, um Erinnerung zurückzusetzen
31
+ adapter.subscribeStates('control.pump.backwash_start');
32
+
33
+ // Täglichen Check planen
34
+ _scheduleBackwashReminder().catch(err =>
35
+ adapter.log.error(`[controlHelper2] Fehler bei _scheduleBackwashReminder(): ${err.message}`),
36
+ );
37
+ }
38
+
39
+ // NEU: Plant täglichen Timer um 12:00 Uhr lokale Zeit
40
+ async function _scheduleBackwashReminder() {
41
+ try {
42
+ if (backwashReminderTimer) {
43
+ clearTimeout(backwashReminderTimer);
44
+ }
45
+
46
+ const now = new Date();
47
+ const next = new Date();
48
+ next.setHours(12, 0, 0, 0); // 12:00 Uhr lokale Zeit
49
+
50
+ // Wenn 12:00 Uhr heute schon vorbei ist → morgen
51
+ if (next <= now) {
52
+ next.setDate(next.getDate() + 1);
53
+ }
54
+
55
+ const diffMs = next - now;
56
+ adapter.log.debug(`[controlHelper2] Nächster Rückspülerinnerungs-Check geplant für ${next.toLocaleString()}`);
57
+
58
+ backwashReminderTimer = setTimeout(async () => {
59
+ await _runBackwashReminderCheck();
60
+ await _scheduleBackwashReminder(); // neu planen
61
+ }, diffMs);
62
+ } catch (err) {
63
+ adapter.log.error(`[controlHelper2] Fehler bei _scheduleBackwashReminder(): ${err.message}`);
64
+ }
65
+ }
66
+
67
+ // NEU: Führt täglichen Erinnerungs-Check aus
68
+ async function _runBackwashReminderCheck() {
69
+ try {
70
+ adapter.log.debug('[controlHelper2] Starte Rückspülerinnerungs-Check ...');
71
+
72
+ const reminderActive = (await adapter.getStateAsync('control.pump.backwash_reminder_active'))?.val;
73
+ if (!reminderActive) {
74
+ adapter.log.debug('[controlHelper2] Rückspülerinnerung deaktiviert – Check übersprungen.');
75
+ return;
76
+ }
77
+
78
+ const intervalDays = Number((await adapter.getStateAsync('control.pump.backwash_interval_days'))?.val || 7);
79
+ const lastDateStr = (await adapter.getStateAsync('control.pump.backwash_last_date'))?.val || '';
80
+
81
+ const now = new Date();
82
+ const todayKey = now.toISOString().split('T')[0]; // yyyy-mm-dd
83
+
84
+ // Verhindert doppelte Erinnerungen am selben Tag
85
+ if (lastReminderDay === todayKey) {
86
+ adapter.log.debug('[controlHelper2] Erinnerung für heute bereits gesendet.');
87
+ return;
88
+ }
89
+
90
+ let daysSince = null;
91
+ if (lastDateStr) {
92
+ const lastDate = new Date(lastDateStr);
93
+ const diffMs = now - lastDate;
94
+ daysSince = Math.floor(diffMs / (1000 * 60 * 60 * 24));
95
+ }
96
+
97
+ if (daysSince === null) {
98
+ adapter.log.debug('[controlHelper2] Keine letzte Rückspülung bekannt – keine Erinnerung.');
99
+ return;
100
+ }
101
+
102
+ const notify = (await adapter.getStateAsync('control.pump.notifications_enabled'))?.val;
103
+ const speechEnabled = notify === true;
104
+
105
+ if (daysSince >= intervalDays) {
106
+ // Fällig oder überfällig
107
+ await adapter.setStateAsync('control.pump.backwash_required', { val: true, ack: true });
108
+ let text;
109
+
110
+ if (daysSince === intervalDays) {
111
+ text = 'Erinnerung: Rückspülung ist wieder fällig.';
112
+ } else {
113
+ const over = daysSince - intervalDays;
114
+ text = `Erinnerung: Rückspülung ist seit ${over} Tag${over === 1 ? '' : 'en'} überfällig.`;
115
+ }
116
+
117
+ adapter.log.info(`[controlHelper2] ${text}`);
118
+ if (speechEnabled) {
119
+ await _sendSpeech(text);
120
+ }
121
+
122
+ lastReminderDay = todayKey;
123
+ } else {
124
+ adapter.log.debug(`[controlHelper2] Rückspülung noch nicht fällig (${daysSince}/${intervalDays} Tage).`);
125
+ }
126
+ } catch (err) {
127
+ adapter.log.warn(`[controlHelper2] Fehler beim Erinnerungs-Check: ${err.message}`);
128
+ }
129
+ }
130
+
131
+ // NEU: Rücksetzung nach Rückspülstart
132
+ /**
133
+ * Reagiert auf State-Änderungen (z. B. Rückspülstart).
134
+ *
135
+ * @param {string} id – Objekt-ID des geänderten States
136
+ * @param {ioBroker.State} state – Neuer State-Wert
137
+ */
138
+ async function handleStateChange(id, state) {
139
+ try {
140
+ if (!state || state.ack) {
141
+ return;
142
+ }
143
+ if (!id.endsWith('control.pump.backwash_start') || !state.val) {
144
+ return;
145
+ }
146
+
147
+ adapter.log.debug('[controlHelper2] Rückspülstart erkannt – Erinnerung wird zurückgesetzt.');
148
+
149
+ await adapter.setStateAsync('control.pump.backwash_required', { val: false, ack: true });
150
+ await adapter.setStateAsync('control.pump.backwash_last_date', {
151
+ val: new Date().toISOString(),
152
+ ack: true,
153
+ });
154
+
155
+ const notify = (await adapter.getStateAsync('control.pump.notifications_enabled'))?.val;
156
+ if (notify) {
157
+ const text = 'Rückspülerinnerung wurde zurückgesetzt. Rückspülzyklus neu gestartet.';
158
+ adapter.log.info(`[controlHelper2] ${text}`);
159
+ await _sendSpeech(text);
160
+ }
161
+ } catch (err) {
162
+ adapter.log.warn(`[controlHelper2] Fehler bei handleStateChange(): ${err.message}`);
163
+ }
164
+ }
165
+
166
+ // NEU: Sprachausgabe
167
+ async function _sendSpeech(text) {
168
+ if (!text) {
169
+ return;
170
+ }
171
+ try {
172
+ await adapter.setStateAsync('speech.queue', { val: text, ack: false });
173
+ adapter.log.debug(`[controlHelper2] Nachricht an speech.queue: ${text}`);
174
+ } catch (err) {
175
+ adapter.log.warn(`[controlHelper2] Fehler beim Senden an speech.queue: ${err.message}`);
176
+ }
177
+ }
178
+
179
+ // NEU: Aufräumen
180
+ /**
181
+ * Stoppt den Rückspülerinnerungs-Timer und räumt Variablen auf.
182
+ *
183
+ * @returns {void}
184
+ */
185
+ function cleanup() {
186
+ if (backwashReminderTimer) {
187
+ clearTimeout(backwashReminderTimer);
188
+ backwashReminderTimer = null;
189
+ }
190
+ lastReminderDay = null;
191
+ adapter.log.debug('[controlHelper2] Cleanup ausgeführt.');
192
+ }
193
+
194
+ // NEU: Exporte
195
+ module.exports = { init, handleStateChange, cleanup };
@@ -33,8 +33,8 @@ const frostHelper = {
33
33
  async _checkFrost() {
34
34
  try {
35
35
  // --- NEU: Vorrangprüfung durch ControlHelper ---
36
- const pumpStatus = (await this.adapter.getStateAsync('pump.status'))?.val || '';
37
- if (pumpStatus.includes('controlHelper')) {
36
+ const activeHelper = (await this.adapter.getStateAsync('pump.active_helper'))?.val || '';
37
+ if (activeHelper === 'controlHelper') {
38
38
  this.adapter.log.debug('[frostHelper] Vorrang durch ControlHelper aktiv – Frostschutz pausiert.');
39
39
  return;
40
40
  }