Hallo zusammen,
ich frage mich ob, bzw. wie man es hinbekommen könnte folgendes DOIF zu vereinfachen:
([SensorArbeitszimmer:lueften] eq "nein" and [?Fenster_Arbeitszimmer] eq "open") (set Signal send 🪟 Lüften bringt jetzt nichts mehr, Fenster im Arbeitszimmer zu!)
DOELSEIF
([SensorSchlafzimmer:lueften] eq "nein" and [?Fenster_Schlafzimmer] eq "open") (set Signal send 🪟 Lüften bringt jetzt nichts mehr, Fenster im Schlafzimmer zu!)
.
.
Die Namen der Umweltsensoren beginnen immer mit "Sensor" und enden mit der Zimmerbezeichnung, die Namen der Fenstersensoren beginnen immer mit "Fenster_" und enden ebenfalls mit der Zimmerbezeichnung.
Was ich mir vorstellen könnte wäre,
die Abfrage des Fenstersensors in den Ausführungsteil zu verlegen und dort dann das $DEVICE vom Umweltsensor zu zerlegen (im Grunde muss nur der String Sensor entfernt werden) und mit diesem dann etwas ähnliches wie [Fenster_$DEVICESPLIT] eq "open" zu erzeugen.
Dies würde das riesige ungetüm auf eine Zeile reduzieren:
(["Sensor:^lueften:.nein") (IF [Fenster_$DEVICESPLIT] eq "open" (set Signal send 🪟 Lüften bringt jetzt nichts mehr, Fenster im $DEVICESPLIT zu!))
DOELSE
Leider habe ich keinen Plan wie ich das $DEVICE splitte und ob dies überhaupt in DOIF so möglich ist.
Für einen Wink mit dem Zaunpfahl wäre ich euch sehr dankbar.
Du kannst folgende Perlfunktion nutzen:
http://www.hidemail.de/blog/substr-perl.shtml
Hallo Damian,
leider bin ich bei Perl recht schnell raus :-(
würde so etwas funktionieren?
(((
{$raum=substr($DEVICE,0,6,"");;}, # erste 6 Zeichen mit löschen
IF [Fenster_$raum] eq "open") # prüfen ob das Fenster in dem entsprechendem Raum offen ist
(set Signal send 🪟 Lüften bringt jetzt nichts mehr, Fenster im $raum zu!))) # senden der Nachricht
oder eher so:
(((
{$raum=substr($DEVICE,0,6,"");; # erste 6 Zeichen mit löschen
if [Fenster_$raum] eq "open" # prüfen ob das Fenster in dem entsprechendem Raum offen ist
fhem_set (Signal send 🪟 Lüften bringt jetzt nichts mehr, Fenster im $raum zu!);;} # senden der Nachricht
))
z. B.
([SensorArbeitszimmer:lueften] eq "nein" and [?Fenster_Arbeitszimmer] eq "open") (set Signal send 🪟 Lüften bringt jetzt nichts mehr, Fenster im Arbeitszimmer zu, Fenster im Raum {(substr("$DEVICE",8))})
Hallo Damian,
ich möchte ja das Doif so weit wie möglich reduzieren, daher würde ich gerne in der if Abfrage innerhalb des Ausführungsteils das Device zusammenstzen aus dem String "Fenster_" und dem auf den Zimmernamen gekürzten String, also {(substr("$DEVICE",6))}.
Beispiel:
wenn am SensorKueche das Reading lueften auf "nein" wechselt, wird im Ausführungsteil abgefragt ob das Device Fenster_{(substr("$DEVICE",6))}, woraus in diesem Fall das Device Fenster_Kueche enstehen würde, "open" ist und dann die Medung an das Signal Device abschickt.
Dann musst du mit ReadingsVal arbeiten, in etwa:
if (ReadingsVal ("Fenster_$raum",state,"") eq "open") {fhem("set...")}
Hallo Damian,
leider bekomme ich es so nicht zum Laufen, es kommt die Fehlermeldung "Modification of a read-only value attempted at (eval 122710) line 1."
Internals:
DEF (["^Sensor:^lueftenMoeglich:.nein$"])
((
{( my $raum = substr( "$DEVICE",0,6,"" ));;}
(if (ReadingsVal ("Fenster_$raum",state,"") eq "open") {fhem("set Signal send 🪟 Lüften bringt jetzt nichts mehr, Fenster im $raum zu!")})
))
DOELSE
FUUID 5fffb2dc-f33f-357a-85c1-70c284d70ac2d537
MODEL FHEM
NAME di.Fenster_schliessen
NOTIFYDEV global,.*(^Sensor).*
NR 334
NTFY_ORDER 50-di.Fenster_schliessen
STATE cmd_1
TYPE DOIF
VERSION 25720 2022-02-20 21:38:26
Helper:
DBLOG:
cmd:
logdb:
TIME 1646660375.07581
VALUE 1
cmd_event:
logdb:
TIME 1646660375.07581
VALUE SensorArbeitszimmer
cmd_nr:
logdb:
TIME 1646660375.07581
VALUE 1
error:
logdb:
TIME 1646660375.07581
VALUE Modification of a read-only value attempted at (eval 122710) line 1.
mode:
logdb:
TIME 1646660017.89112
VALUE enabled
state:
logdb:
TIME 1646660375.07581
VALUE cmd_1
READINGS:
2022-03-07 14:39:35 Device SensorArbeitszimmer
2022-03-07 14:39:35 cmd 1
2022-03-07 14:39:35 cmd_event SensorArbeitszimmer
2022-03-07 14:39:35 cmd_nr 1
2022-03-07 14:39:35 error Modification of a read-only value attempted at (eval 122710) line 1.
2022-03-07 14:33:37 mode enabled
2022-03-07 14:39:35 state cmd_1
Regex:
accu:
collect:
cond:
:
0:
"^Sensor:^lueftenMoeglich:.nein$" ^Sensor:^lueftenMoeglich:.nein$
attr:
cmdState:
wait:
waitdel:
condition:
0 ::EventDoIf('^Sensor',$hash,'^lueftenMoeglich:.nein$',0)
do:
0:
0 ( {( my $raum = substr( "$DEVICE",0,6,"" ));;} (if (ReadingsVal ("Fenster_$raum",state,"") eq "open") {fhem("set Signal send 🪟 Lüften bringt jetzt nichts mehr, Fenster im $raum zu!")}) )
1:
0
helper:
NOTIFYDEV global,.*(^Sensor).*
event lueftenMoeglich: nein
globalinit 1
last_timer 0
sleeptimer -1
timerdev SensorArbeitszimmer
timerevent lueftenMoeglich: nein
triggerDev SensorArbeitszimmer
timerevents:
humidity: 22
brightness: 5897.0
lueftenMoeglich: nein
dewpoint: -1
timereventsState:
humidity: 22
brightness: 5897.0
lueftenMoeglich: nein
dewpoint: -1
triggerEvents:
humidity: 22
brightness: 5897.0
lueftenMoeglich: nein
dewpoint: -1
triggerEventsState:
humidity: 22
brightness: 5897.0
lueftenMoeglich: nein
dewpoint: -1
internals:
readings:
trigger:
uiState:
uiTable:
Attributes:
room 02_Fenster_Tueren
Warum setzt du so viele Klammern?
(["^Sensor:^lueftenMoeglich:.nein$"])
{ my $raum = substr( "$DEVICE",0,6,"" ));if (ReadingsVal ("Fenster_$raum",state,"") eq "open") {fhem("set Signal send Lüften bringt jetzt nichts mehr, Fenster im $raum zu!")}}
Die Klammern habe ich doppelt gemacht, da ich im Hinterkopf hatte dass bei mehreren Befehlen im Ausführungsteil doppelt geklammert werden muss zusätzlich kommt meine Perl-Unkenntniss dazu.
Leider bekomme ich auch mit deiner Variante den gleichen Fehler :
{ my $raum = substr( "SensorArbeitszimmer",0,6,"" );if (ReadingsVal ("Fenster_$raum","state","") eq "open") {fhem("set Signal send 🪟 Lüften bringt jetzt nichts mehr, Fenster im X zu!")}}: Modification of a read-only value attempted at (eval 312853) line 1.
Zitat von: Nighthawk am 07 März 2022, 16:31:22
Die Klammern habe ich doppelt gemacht, da ich im Hinterkopf hatte dass bei mehreren Befehlen im Ausführungsteil doppelt geklammert werden muss zusätzlich kommt meine Perl-Unkenntniss dazu.
Leider bekomme ich auch mit deiner Variante den gleichen Fehler :
{ my $raum = substr( "SensorArbeitszimmer",0,6,"" );if (ReadingsVal ("Fenster_$raum","state","") eq "open") {fhem("set Signal send 🪟 Lüften bringt jetzt nichts mehr, Fenster im X zu!")}}: Modification of a read-only value attempted at (eval 312853) line 1.
Dann ist es kein DOIF-spezifischer Fehler, irgendwo fehlen dir Schreibrechte.
Die substr Funktion wurde von mir falsch verwendet.
Hier die funktionierende Variante:
(["^Sensor:^lueftenMoeglich:.nein$"])
{ my $raum = substr( "$DEVICE",6 );if (ReadingsVal ("Fenster_$raum","state","") eq "open") {fhem("set Signal send 🪟 Lüften bringt jetzt nichts mehr, Fenster im $raum zu!")}}
Vielen Dank für deine Unterstützung und Geduld Damian!
Ohne Perl "Umwege" könnte man auch den Raum (room) abfragen, wenn gepflegt und passend.