[gelöst] Heizungs-Automatik, das geht doch bestimmt noch schöner, oder?!

Begonnen von Shojo, 07 Februar 2018, 23:04:16

Vorheriges Thema - Nächstes Thema

Shojo

Hi,

ich habe mir aktuell mit meiner Heizungsteuerung wie folgt beholfen.



Internals:
   DEF        ([".*.Sensor.(Fenster|Tuer)" eq "n/a"])
()
DOELSEIF((([06:00-22:00|AT] or [08:30-23:59|WE]) and [Bewohner] eq "home" ) or [HA.Dummy.Party] eq "IsParty")
(
IF ([BU.Sensor.Fenster] eq "closed")
(
    setex BU.Heizung_Clima desired-temp 21.0
)
ELSE
(
setex BU.Heizung_Clima desired-temp off
),

IF ([BZ.Sensor.Fenster] eq "closed")
(
setex BZ.Heizung_Clima desired-temp 21.0
)
ELSE
(
setex BZ.Heizung_Clima desired-temp off
),

IF ([GB.Sensor.Fenster] eq "closed")
(
setex GB.Heizung_Clima desired-temp 21.0
)
ELSE
(
setex GB.Heizung_Clima desired-temp off
),

IF ([WZ.Sensor.Tuer] eq "closed")
(
setex WZ.Heizung_Clima desired-temp 21.0
)
ELSE
(
setex WZ.Heizung_Clima desired-temp off
)
)
DOELSE
(
    IF ([BU.Sensor.Fenster] eq "closed")
(
    setex BU.Heizung_Clima desired-temp 17.0
)
ELSE
(
setex BU.Heizung_Clima desired-temp off
),

IF ([BZ.Sensor.Fenster] eq "closed")
(
setex BZ.Heizung_Clima desired-temp 17.0
)
ELSE
(
setex BZ.Heizung_Clima desired-temp off
),

IF ([GB.Sensor.Fenster] eq "closed")
(
setex GB.Heizung_Clima desired-temp 17.0
)
ELSE
(
setex GB.Heizung_Clima desired-temp off
),

IF ([WZ.Sensor.Tuer] eq "closed")
(
setex WZ.Heizung_Clima desired-temp 17.0
)
ELSE
(
setex WZ.Heizung_Clima desired-temp off
)
)
   NAME       Heizung.DOIF.Automatik
   NR         405
   NTFY_ORDER 50-Heizung.DOIF.Automatik
   STATE      cmd_2
   TYPE       DOIF
   READINGS:
     2018-02-08 06:42:18   Device          Bewohner
     2018-02-08 06:42:18   cmd             2
     2018-02-08 06:42:18   cmd_event       Bewohner
     2018-02-08 06:42:18   cmd_nr          2
     2018-02-08 06:42:18   e_Bewohner_STATE home
     2018-02-08 06:41:59   mode            enabled
     2018-02-08 06:42:18   state           cmd_2
     2018-02-08 06:41:59   timer_01_c02    09.02.2018 06:00:00|AT
     2018-02-08 06:41:59   timer_02_c02    08.02.2018 22:00:00|AT
     2018-02-08 06:41:59   timer_03_c02    08.02.2018 08:30:00|WE
     2018-02-08 06:41:59   timer_04_c02    08.02.2018 23:59:00|WE
   Regex:
     cond:
       :
         0:
           ".*.Sensor.(Fenster|Tuer)" .*.Sensor.(Fenster|Tuer)
         1:
   condition:
     0          EventDoIf('.*.Sensor.(Fenster|Tuer)',$hash,'',0)
     1          ((DOIF_time($hash,0,1,$wday,$hms,"AT") or DOIF_time($hash,2,3,$wday,$hms,"WE")) and InternalDoIf($hash,'Bewohner','STATE') eq "home" ) or InternalDoIf($hash,'HA.Dummy.Party','STATE') eq "IsParty"
   days:
     0          AT
     1          AT
     2          WE
     3          WE
   devices:
     1           Bewohner HA.Dummy.Party
     all         Bewohner HA.Dummy.Party
   do:
     0:
       0         
     1:
       0          IF ([BU.Sensor.Fenster] eq "closed") (      setex BU.Heizung_Clima desired-temp 21.0 ) ELSE ( setex BU.Heizung_Clima desired-temp off ), IF ([BZ.Sensor.Fenster] eq "closed") ( setex BZ.Heizung_Clima desired-temp 21.0 ) ELSE ( setex BZ.Heizung_Clima desired-temp off ), IF ([GB.Sensor.Fenster] eq "closed") ( setex GB.Heizung_Clima desired-temp 21.0 ) ELSE ( setex GB.Heizung_Clima desired-temp off ), IF ([WZ.Sensor.Tuer] eq "closed") ( setex WZ.Heizung_Clima desired-temp 21.0 ) ELSE ( setex WZ.Heizung_Clima desired-temp off )
     2:
       0               IF ([BU.Sensor.Fenster] eq "closed") (      setex BU.Heizung_Clima desired-temp 17.0 ) ELSE ( setex BU.Heizung_Clima desired-temp off ), IF ([BZ.Sensor.Fenster] eq "closed") ( setex BZ.Heizung_Clima desired-temp 17.0 ) ELSE ( setex BZ.Heizung_Clima desired-temp off ), IF ([GB.Sensor.Fenster] eq "closed") ( setex GB.Heizung_Clima desired-temp 17.0 ) ELSE ( setex GB.Heizung_Clima desired-temp off ), IF ([WZ.Sensor.Tuer] eq "closed") ( setex WZ.Heizung_Clima desired-temp 17.0 ) ELSE ( setex WZ.Heizung_Clima desired-temp off )
   helper:
     DOIF_Readings_events
     DOIF_eventas
     event      durTimerPresence_cr: 781,durTimerPresence: 13:01:29
     globalinit 1
     last_timer 4
     sleeptimer -1
     timerdev   Bewohner
     timerevent durTimerPresence_cr: 781,durTimerPresence: 13:01:29
     triggerDev Bewohner
     timerevents:
       durTimerPresence_cr: 781
       durTimerPresence: 13:01:29
     timereventsState:
       durTimerPresence_cr: 781
       durTimerPresence: 13:01:29
     triggerEvents:
       durTimerPresence_cr: 781
       durTimerPresence: 13:01:29
     triggerEventsState:
       durTimerPresence_cr: 781
       durTimerPresence: 13:01:29
   internals:
     1           Bewohner:STATE HA.Dummy.Party:STATE
     all         Bewohner:STATE HA.Dummy.Party:STATE
   interval:
     0          -1
     1          0
     2          -1
     3          2
   itimer:
   localtime:
     0          1518152400
     1          1518123600
     2          1518075000
     3          1518130740
   readings:
   realtime:
     0          06:00:00
     1          22:00:00
     2          08:30:00
     3          23:59:00
   time:
     0          06:00:00
     1          22:00:00
     2          08:30:00
     3          23:59:00
   timeCond:
     0          1
     1          1
     2          1
     3          1
   timer:
     0          0
     1          0
     2          0
     3          0
   timers:
     1           0  1  2  3
   trigger:
   triggertime:
     1518075000:
       localtime  1518075000
       hash:
     1518123600:
       localtime  1518123600
       hash:
     1518130740:
       localtime  1518130740
       hash:
     1518152400:
       localtime  1518152400
       hash:
   uiState:
   uiTable:
Attributes:
   do         always
   icon       helper_doif
   room       1.1_Wohnzimmer,1.2_Buero,1.6_Schlafzimmer,2.0_Heizung,9.2_DOIF


Mit gefällt aber  an der Lösung das"do always", das Triggern der Kontakten ([".*.Sensor.(Fenster|Tuer)" eq "n/a"])  und der viele Code nicht....
Gibt es da vielleicht eine "bessere" Schreibweise?

Bin für Tipps dankbar!

Hier noch das genutzte Alias:



Internals:
   ALIAS      setex
   DEF        setex .* AS set $EVTPART0:FILTER=$EVTPART1!=$EVTPART2 $EVTPART1 $EVTPART2
   NAME       c_setex
   NEWCMD     set $EVTPART0:FILTER=$EVTPART1!=$EVTPART2 $EVTPART1 $EVTPART2
   NR         128
   PARAM      .*
   STATE      defined
   TYPE       cmdalias
Attributes:
   room       9.1_CMDAlias

Gruß
Shojo
FHEM auf: Shuttle PC (x64) (Docker)
Bridge: SignalESP 433mHz, ConBee (deCONZ in Docker)
Rest: ESP8266, SONOFF, Sonos, Echo Dot, Xiaomi Vacuum (root), ESP RGBWW Wifi Led Controller, Node-RED, LEDMatrix, Pixel It

Per

Ohne mir deinen Code bis ins Letzte angeschaut zu haben (ich gehe davon aus, dass er sich wiederholt) folgende Anmerkungen:
1. dein DOIF-Teil ist ein Mix aus Status- und Event-Programmierung. Das sollte einen Fehler ergeben.
2. mittels Event- und Regex kannst du alle _clima setzen. Als Filter kannst du dann !=off eintragen.
3. wird bei dir nicht berücksichtigt, wenn außerhalb der Zeiten ein Fenster geöffnet oder geschlossen wird. Das solltest du in einem extra DOIF machen.
4. ebenso wie die Sensor-Kontrolle (1. Zweig)
5. dein Alias verstehe ich nicht (deshalb im Beispiel ohne)

Mein Beispiel (ohne Test!)
((([06:00-22:00|AT] or [08:30-23:59|WE]) and [Bewohner] eq "home" ) or [HA.Dummy.Party] eq "IsParty")
(setreading Heizung_Clima:FILTER=desired-temp!=off desired-temp 21.0)
DOELSE
(setreading Heizung_Clima:FILTER=desired-temp!=off desired-temp 17.0)
attr xxxx cmdState 21|17


Dazu der "Fensteröffner"
("^..\.(Fenster|Tuer)\.:closed")
([$DEVICE:"(..)\..*":"$1"].Heizung_Clima desired-temp [oberes_DOIF].0)
DOELSIF ("^..\.(Fenster|Tuer)\.:open")
([$DEVICE:"(..)\..*":"$1"].Heizung_Clima desired-temp off)
DOELSIF ("^..\.(Fenster|Tuer)\.:n/a")
() ##was auch immer


Besonders die Raum-Extraktion ([$DEVICE:"(..)\..*":"$1"].) ist jetzt von mir als Nicht-Perler geschrieben, @home könnte ich eine funktionierende Syntax nachschauen.
Könnte man auch in ein DOIF packen (wg. "Wer einschalten, soll auch ausschalten"), bräuchte dann allerdings weitere Merker.

Shojo

Das Alias macht nichts anderes als zu prüfen ob der wert geändert werden muss oder halt nicht, da er schon gegeben ist.
setex WZ.Heizung_Clima desired-temp 17.0
ergibt
set WZ.Heizung_Clima:Filter=desired-temp!=17.0 desired-temp 17.0

Obwohl ich das DOIF sehr mag, tue mich doch oft recht schwer damit  ;D

Und ein dickes Danke für die hilfreiche und kompetente Antwort!


FHEM auf: Shuttle PC (x64) (Docker)
Bridge: SignalESP 433mHz, ConBee (deCONZ in Docker)
Rest: ESP8266, SONOFF, Sonos, Echo Dot, Xiaomi Vacuum (root), ESP RGBWW Wifi Led Controller, Node-RED, LEDMatrix, Pixel It

Per

Zitat von: Shojo am 08 Februar 2018, 14:47:47
Das Alias macht nichts anderes als zu prüfen ob der wert geändert werden muss oder halt nicht, da er schon gegeben ist.
Sollte hier nicht benötigt werden, außer jemand verstellt manuell was. Ansonsten werden ja nur Änderungen weiter gegeben. Und nach interner Logic nur dann, wenn es auch Anlass dazu gab.

Shojo

Zitat von: Per am 08 Februar 2018, 12:09:42
Mein Beispiel (ohne Test!)
((([06:00-22:00|AT] or [08:30-23:59|WE]) and [Bewohner] eq "home" ) or [HA.Dummy.Party] eq "IsParty")
(setreading Heizung_Clima:FILTER=desired-temp!=off desired-temp 21.0)
DOELSE
(setreading Heizung_Clima:FILTER=desired-temp!=off desired-temp 17.0)
attr xxxx cmdState 21|17


Dazu der "Fensteröffner"
("^..\.(Fenster|Tuer)\.:closed")
([$DEVICE:"(..)\..*":"$1"].Heizung_Clima desired-temp [oberes_DOIF].0)
DOELSIF ("^..\.(Fenster|Tuer)\.:open")
([$DEVICE:"(..)\..*":"$1"].Heizung_Clima desired-temp off)
DOELSIF ("^..\.(Fenster|Tuer)\.:n/a")
() ##was auch immer


Besonders die Raum-Extraktion ([$DEVICE:"(..)\..*":"$1"].) ist jetzt von mir als Nicht-Perler geschrieben, @home könnte ich eine funktionierende Syntax nachschauen.
Könnte man auch in ein DOIF packen (wg. "Wer einschalten, soll auch ausschalten"), bräuchte dann allerdings weitere Merker.

Konnte es dank Dir jetzt so lösen:


((([06:00-22:00|AT] or [08:30-23:59|WE]) and [Bewohner] eq "home" ) or [HA.Dummy.Party] eq "IsParty")
(set (?!KZ)(?!SZ).*.Heizung_Clima:FILTER=desired-temp!=off desired-temp 21.0)
DOELSE
(set (?!KZ)(?!SZ).*.Heizung_Clima:FILTER=desired-temp!=off desired-temp 17.0)
attr xxxx cmdState 21|17

und

(["(?!KZ)(?!SZ).*.Sensor.(Fenster|Tuer):closed"])
(setex {("$DEVICE"=~/(..)\..*/;"$1.Heizung_Clima desired-temp")} [Heizung.DOIF.Automatik].0)
DOELSEIF (["(?!KZ)(?!SZ).*.Sensor.(Fenster|Tuer):open"])
(setex {("$DEVICE"=~/(..)\..*/;"$1.Heizung_Clima desired-temp")} off)
attr xxxx do always

Hier musste ich aber das do always wieder aktiveren da es ja sonst nicht reagiert wenn ein 2. Fester geöffnet wird.
Die Lösung gefällt mir nun :)
FHEM auf: Shuttle PC (x64) (Docker)
Bridge: SignalESP 433mHz, ConBee (deCONZ in Docker)
Rest: ESP8266, SONOFF, Sonos, Echo Dot, Xiaomi Vacuum (root), ESP RGBWW Wifi Led Controller, Node-RED, LEDMatrix, Pixel It

Per

Zitat von: Shojo am 08 Februar 2018, 19:48:47
Die Lösung gefällt mir nun :)
Schön.

Zitat von: Shojo am 08 Februar 2018, 19:48:47Hier musste ich aber das do always wieder aktiveren da es ja sonst nicht reagiert wenn ein 2. Fester geöffnet wird.
Na ein Bisschen Arbeit muss ich dir ja auch lassen ;).

Zitat von: Shojo am 08 Februar 2018, 19:48:47

(["(?!KZ)(?!SZ).*.Sensor.(Fenster|Tuer):closed"])
(setex {("$DEVICE"=~/(..)\..*/;"$1.Heizung_Clima desired-temp")} [Heizung.DOIF.Automatik].0)
DOELSEIF (["(?!KZ)(?!SZ).*.Sensor.(Fenster|Tuer):open"])
(setex {("$DEVICE"=~/(..)\..*/;"$1.Heizung_Clima desired-temp")} off)

Optisch noch schöner wäre:

(["(?!KZ)(?!SZ).*.Sensor.(Fenster|Tuer)"])
(setex {("$DEVICE"=~/(..)\..*/;"$1.Heizung_Clima")} desired-temp {"$EVENTS" ~= ".*closed.*"?"[Heizung.DOIF.Automatik].0":"off"})

(oder so ähnlich).