From dbefde7e8c824a29a5e39fff1250fe38fba9f9d8 Mon Sep 17 00:00:00 2001 From: damian-s <> Date: Sat, 30 Jan 2016 22:26:41 +0000 Subject: [PATCH] 98_DOIF.pm: $DEVICE $EVENT $EVENTS git-svn-id: https://svn.fhem.de/fhem/trunk/fhem@10671 2b470e98-0d58-463d-a4d8-8e2adae1ed80 --- FHEM/98_DOIF.pm | 735 +++++++++++++++++++++++++++++++++++++----------- 1 file changed, 578 insertions(+), 157 deletions(-) diff --git a/FHEM/98_DOIF.pm b/FHEM/98_DOIF.pm index 7aaac7e20..ff6c6f713 100644 --- a/FHEM/98_DOIF.pm +++ b/FHEM/98_DOIF.pm @@ -55,6 +55,7 @@ DOIF_delAll($) delete ($hash->{readings}); delete ($hash->{internals}); delete ($hash->{trigger}); + delete ($hash->{regexp}); delete ($defs{$hash->{NAME}}{READINGS}); } @@ -68,7 +69,7 @@ DOIF_Initialize($) $hash->{UndefFn} = "DOIF_Undef"; $hash->{AttrFn} = "DOIF_Attr"; $hash->{NotifyFn} = "DOIF_Notify"; - $hash->{AttrList} = "disable:0,1 loglevel:0,1,2,3,4,5,6 wait do:always,resetwait cmdState state initialize repeatsame repeatcmd waitsame waitdel cmdpause timerWithWait ".$readingFnAttributes; + $hash->{AttrList} = "disable:0,1 loglevel:0,1,2,3,4,5,6 wait do:always,resetwait cmdState state initialize repeatsame repeatcmd waitsame waitdel cmdpause timerWithWait notexist ".$readingFnAttributes; } @@ -109,21 +110,55 @@ GetBlockDoIf ($$) return ($cmd,"","",""); } } +sub +EventCheckDoif($$$$) +{ + my ($n,$dev,$eventa,$NotifyExp)=@_; + my $found=0; + my $s; + return 0 if ($dev ne $n); + return 0 if(!$eventa); + my $max = int(@{$eventa}); + my $ret = 0; + if ($NotifyExp eq "") { + return 1 ; + } + for (my $i = 0; $i < $max; $i++) { + $s = $eventa->[$i]; + $s = "" if(!defined($s)); + $found = ($s =~ m/$NotifyExp/); + if ($found) { + return 1; + } + } + return 0; +} sub EventDoIf($$$$) { - my ($n,$dev,$events,$NotifyExp)=@_; - return 0 if ($dev ne $n); - return 0 if(!$events); # Some previous notify deleted the array. - my $max = int(@{$events}); + my ($n,$hash,$NotifyExp,$check)=@_; + my $dev=$hash->{helper}{triggerDev}; + my $eventa=$hash->{helper}{triggerEvents}; + if ($check) { + return 0 if ($dev ne $n); + } else { + return 0 if ($n and $dev !~ /$n/); + } + return 0 if(!$eventa); + my $max = int(@{$eventa}); my $ret = 0; - return 1 if ($NotifyExp eq ""); + if ($NotifyExp eq "") { + return 1 ; + } for (my $i = 0; $i < $max; $i++) { - my $s = $events->[$i]; + my $s = $eventa->[$i]; $s = "" if(!defined($s)); my $found = ($s =~ m/$NotifyExp/); - return 1 if ($found); + if ($found) { + $hash->{helper}{event}=$s; + return 1; + } #if(!$found && AttrVal($n, "eventMap", undef)) { # my @res = ReplaceEventMap($n, [$n,$s], 0); # shift @res; @@ -134,18 +169,20 @@ EventDoIf($$$$) } sub -InternalDoIf($$$) -{ - my ($name,$internal,$regExp)=@_; +InternalDoIf($$$$) +{ + my ($name,$internal,$regExp,$default)=@_; my $r=""; my $element; - $r=$defs{$name}{$internal}; - if ($regExp) { - $element = ($r =~ /$regExp/) ? $1 : ""; - } else { - $element=$r; - } - return($element); + return ($default =~ /"(.*)"/) ? $1 : $default if (!defined $defs{$name}); + return ($default =~ /"(.*)"/) ? $1 : $default if (!defined $defs{$name}{$internal}); + $r=$defs{$name}{$internal}; + if ($regExp) { + $element = ($r =~ /$regExp/) ? $1 : ""; + } else { + $element=$r; + } + return($element); } sub @@ -157,11 +194,13 @@ ReadingSecDoIf($$) } sub -ReadingValDoIf($$$) +ReadingValDoIf($$$$) { - my ($name,$reading,$regExp)=@_; + my ($name,$reading,$regExp,$default)=@_; my $r; my $element; + return ($default =~ /"(.*)"/) ? $1 : $default if (!defined $defs{$name}); + return ($default =~ /"(.*)"/) ? $1 : $default if (!defined $defs{$name}{READINGS}{$reading}{VAL}); $r=$defs{$name}{READINGS}{$reading}{VAL}; $r="" if (!defined($r)); if ($regExp) { @@ -173,15 +212,21 @@ ReadingValDoIf($$$) } sub -EvalAllDoIf($) +EvalAllDoIf($$) { - my ($tailBlock)= @_; + my ($hash,$tailBlock)= @_; my $eval=""; my $beginning; my $err; my $cmd=""; my $ret=""; - + my $eventa=$hash->{helper}{triggerEvents}; + my $device=$hash->{helper}{triggerDev}; + my $event=$hash->{helper}{event}; + my $events=""; + if ($eventa) { + $events=join(",",@{$eventa}); + } while ($tailBlock ne "") { ($beginning,$eval,$err,$tailBlock)=GetBlockDoIf($tailBlock,'[\{\}]'); return ($eval,$err) if ($err); @@ -210,12 +255,14 @@ sub ReplaceReadingDoIf($) my $internal=""; my $notifyExp=""; if ($name) { - #return ($name,"unknown Device") if(!$defs{$name}); if ($reading) { if (substr($reading,0,1) eq "\?") { $notifyExp=substr($reading,1); - return("EventDoIf('$name',".'$hash->{helper}{triggerDev},'.'$hash->{helper}{triggerEvents},'."'$notifyExp')","",$name,undef,undef); - } + return("EventDoIf('$name',".'$hash,'."'$notifyExp',1)","",$name,undef,undef); + } elsif ($reading =~ /^"(.*)"$/g) { + $notifyExp=$1; + return("EventDoIf('$name',".'$hash,'."'$notifyExp',1)","",$name,undef,undef); + } $internal = substr($reading,1) if (substr($reading,0,1) eq "\&"); if ($format) { if ($format eq "d") { @@ -231,25 +278,27 @@ sub ReplaceReadingDoIf($) } } if ($internal) { - return("InternalDoIf('$name','$internal','$regExp')","",$name,undef,$internal); + return("InternalDoIf('$name','$internal','$regExp',".'AttrVal($hash->{NAME},'."'notexist',undef))","",$name,undef,$internal); } else { - return("ReadingValDoIf('$name','$reading','$regExp')","",$name,$reading,undef); + return("ReadingValDoIf('$name','$reading','$regExp',".'AttrVal($hash->{NAME},'."'notexist',undef))","",$name,$reading,undef); } } else { - return("InternalDoIf('$name','STATE','$regExp')","",$name,undef,'STATE'); + return("InternalDoIf('$name','STATE','$regExp',".'AttrVal($hash->{NAME},'."'notexist',undef))","",$name,undef,'STATE'); } } } -sub ReplaceReadingEvalDoIf($$) +sub ReplaceReadingEvalDoIf($$$) { - my ($element,$eval) = @_; + my ($hash,$element,$eval) = @_; my ($block,$err,$device,$reading,$internal)=ReplaceReadingDoIf($element); return ($block,$err) if ($err); if ($eval) { - return ($device,"device does not exist: $device") if(!$defs{$device}); - return ($block,"reading does not exist: $device:$reading") if (defined ($reading) and !defined($defs{$device}{READINGS}{$reading})); - return ($block,"internal does not exist: $device:$internal") if (defined ($internal) and !defined($defs{$device}{$internal})); + if (!AttrVal($hash->{NAME},'notexist',undef)) { + return ($device,"device does not exist: $device") if(!$defs{$device}); + return ($block,"reading does not exist: $device:$reading") if (defined ($reading) and !defined($defs{$device}{READINGS}{$reading})); + return ($block,"internal does not exist: $device:$internal") if (defined ($internal) and !defined($defs{$device}{$internal})); + } my $ret = eval $block; return($block." ",$@) if ($@); $block=$ret; @@ -267,7 +316,28 @@ sub AddItemDoIf($$) } return $items; } - + +sub AddRegexpTriggerDoIf($$$) +{ + my ($hash,$regexp,$condition)= @_; + my $max_regexp=keys %{$hash->{regexp}{$condition}}; + for (my $i=0; $i<$max_regexp;$i++) + { + if ($hash->{regexp}{$condition}{$i} eq $regexp) { + return; + } + } + $hash->{regexp}{$condition}{$max_regexp}=$regexp; + $max_regexp=keys %{$hash->{regexp}{all}}; + for (my $i=0; $i<$max_regexp;$i++) + { + if ($hash->{regexp}{all}{$i} eq $regexp) { + return; + } + } + $hash->{regexp}{all}{$max_regexp}=$regexp; +} + sub ReplaceAllReadingsDoIf($$$$) { my ($hash,$tailBlock,$condition,$eval)= @_; @@ -285,46 +355,66 @@ sub ReplaceAllReadingsDoIf($$$$) my $reading; my $internal; my $trigger=1; + my $nameExp; + my $notifyExp; + while ($tailBlock ne "") { $trigger=1; ($beginning,$block,$err,$tailBlock)=GetBlockDoIf($tailBlock,'[\[\]]'); return ($block,$err) if ($err); if ($block ne "") { - if (substr($block,0,1) eq "?") { - $block=substr($block,1); - $trigger=0; - } - # if ($block =~ /^[0-9]+$/) { - # $block="[".$block."]"; - # } elsif - if ($block =~ /^\??[a-z0-9._]*[a-z._]+[a-z0-9._]*($|:.+$)/i) { - ($block,$err,$device,$reading,$internal)=ReplaceReadingEvalDoIf($block,$eval); - return ($block,$err) if ($err); - if ($trigger) { + if ($block =~ /^\"(.*)\"$/){ + my $exp=$1; + if ($exp =~ /([^\:]*):(.*)/) { + $nameExp=$1; + $notifyExp=$2; + } else { + $nameExp=$exp; + } + #my ($nameExp,$notifyExp)=split (":",$1); + if ($condition >= 0) { + $nameExp="" if (!$nameExp); + $notifyExp="" if (!$notifyExp); + $block="EventDoIf('$nameExp',".'$hash,'."'$notifyExp',0)"; + AddRegexpTriggerDoIf($hash,$exp,$condition); + $event=1; + } + } else { + if (substr($block,0,1) eq "?") { + $block=substr($block,1); + $trigger=0; + } + $trigger=0 if (substr($block,0,1) eq "\$"); + if ($block =~ /^\$?[a-z0-9._]*[a-z._]+[a-z0-9._]*($|:.+$)/i) { + ($block,$err,$device,$reading,$internal)=ReplaceReadingEvalDoIf($hash,$block,$eval); + return ($block,$err) if ($err); if ($condition >= 0) { - $hash->{devices}{$condition} = AddItemDoIf($hash->{devices}{$condition},$device); - $hash->{devices}{all} = AddItemDoIf($hash->{devices}{all},$device); + if ($trigger) { + $hash->{devices}{$condition} = AddItemDoIf($hash->{devices}{$condition},$device); + $hash->{devices}{all} = AddItemDoIf($hash->{devices}{all},$device); + $event=1; + } $hash->{readings}{$condition} = AddItemDoIf($hash->{readings}{$condition},"$device:$reading") if (defined ($reading)); $hash->{internals}{$condition} = AddItemDoIf($hash->{internals}{$condition},"$device:$internal") if (defined ($internal)); $hash->{readings}{all} = AddItemDoIf($hash->{readings}{all},"$device:$reading") if (defined ($reading)); $hash->{internals}{all} = AddItemDoIf($hash->{internals}{all},"$device:$internal") if (defined ($internal)); $hash->{trigger}{all} = AddItemDoIf($hash->{trigger}{all},"$device") if (!defined ($internal) and !defined($reading)); - $event=1; + } elsif ($condition == -2) { $hash->{state}{device} = AddItemDoIf($hash->{state}{device},$device) if ($device ne $hash->{NAME}); } elsif ($condition == -3) { $hash->{itimer}{all} = AddItemDoIf($hash->{itimer}{all},$device); } + } elsif ($condition >= 0) { + ($timer,$err)=DOIF_CheckTimers($hash,$block,$condition,$trigger,\@timerarray); + return($timer,$err) if ($err); + if ($timer) { + $block=$timer; + $event=1 if ($trigger); + } + } else { + $block="[".$block."]"; } - } elsif ($condition >= 0) { - ($timer,$err)=DOIF_CheckTimers($hash,$block,$condition,$trigger,\@timerarray); - return($timer,$err) if ($err); - if ($timer) { - $block=$timer; - $event=1 if ($trigger); - } - } else { - $block="[".$block."]"; } } $cmd.=$beginning.$block; @@ -345,7 +435,13 @@ ParseCommandsDoIf($$$) my $last_error=""; my $ifcmd; my $ret; - + my $eventa=$hash->{helper}{triggerEvents}; + my $device=$hash->{helper}{triggerDev}; + my $event=$hash->{helper}{event}; + my $events=""; + if ($eventa) { + $events=join(",",@{$eventa}); + } while ($tailBlock ne "") { if ($tailBlock=~ /^\s*\{/) { # perl block ($beginning,$currentBlock,$err,$tailBlock)=GetBlockDoIf($tailBlock,'[\{\}]'); @@ -354,7 +450,7 @@ ParseCommandsDoIf($$$) ($currentBlock,$err)=ReplaceAllReadingsDoIf($hash,$currentBlock,-1,$eval); return ($currentBlock,$err) if ($err); if ($eval) { - ($currentBlock,$err)=EvalAllDoIf($currentBlock); + ($currentBlock,$err)=EvalAllDoIf($hash,$currentBlock); return ($currentBlock,$err) if ($err); } } @@ -390,7 +486,7 @@ ParseCommandsDoIf($$$) ($currentBlock,$err)=ReplaceAllReadingsDoIf($hash,$currentBlock,-1,$eval); return ($currentBlock,$err) if ($err); if ($eval) { - ($currentBlock,$err)=EvalAllDoIf($currentBlock); + ($currentBlock,$err)=EvalAllDoIf($hash, $currentBlock); return ($currentBlock,$err) if ($err); } } @@ -510,7 +606,7 @@ DOIF_time($$$$$$) ($days,$err)=ReplaceAllReadingsDoIf($hash,$days,-1,1); if ($err) { my $errmsg="error in days: $err"; - Log3 ($hash->{NAME},2 , "$hash->{NAME}: $errmsg"); + #Log3 ($hash->{NAME},2 , "$hash->{NAME}: $errmsg"); readingsSingleUpdate ($hash, "error", $errmsg,1); return 0; } @@ -542,7 +638,7 @@ DOIF_time_once($$$$) ($days,$err)=ReplaceAllReadingsDoIf($hash,$days,-1,1); if ($err) { my $errmsg="error in days: $err"; - Log3 ($hash->{NAME},2 , "$hash->{NAME}: $errmsg"); + #Log3 ($hash->{NAME},2 , "$hash->{NAME}: $errmsg"); readingsSingleUpdate ($hash, "error", $errmsg,1); return 0; } @@ -605,7 +701,7 @@ DOIF_SetState($$$$$) Log3 $pn,2 , "$pn: error in state: $err" if ($err); $state=$err; } else { - ($state,$err)=EvalAllDoIf($state); + ($state,$err)=EvalAllDoIf($hash, $state); if ($err) { Log3 $pn,2 , "$pn: error in state: $err" if ($err); $state=$err; @@ -641,26 +737,58 @@ DOIF_CheckCond($$) my ($sec,$min,$hour,$mday,$month,$year,$wday,$yday,$isdst) = localtime($seconds); my $hms = sprintf("%02d:%02d:%02d", $hour, $min, $sec); my $hm = sprintf("%02d:%02d", $hour, $min); - my $device; + my $dev; my $reading; my $internal; my $we=DOIF_we($wday); - + my $eventa=$hash->{helper}{triggerEvents}; + my $device=$hash->{helper}{triggerDev}; + my $event=$hash->{helper}{event}; + my $events=""; + if ($eventa) { + $events=join(",",@{$eventa}); + } $month++; $year+=1900; if (defined ($hash->{readings}{$condition})) { foreach my $devReading (split(/ /,$hash->{readings}{$condition})) { - ($device,$reading)=(split(":",$devReading)); - return (0,"reading does not exist: [$device:$reading]") if ($devReading and !defined($defs{$device}{READINGS}{$reading})); + $devReading=~ s/\$DEVICE/$hash->{helper}{triggerDev}/g if ($devReading); + if (!AttrVal($hash->{NAME},'notexist',undef)) { + ($dev,$reading)=(split(":",$devReading)); + return (-1,"device does not exist: [$dev:$reading]") if ($devReading and !defined ($defs{$dev})); + return (-1,"reading does not exist: [$dev:$reading]") if ($devReading and !defined($defs{$dev}{READINGS}{$reading}{VAL})); + } } } if (defined ($hash->{internals}{$condition})) { foreach my $devInternal (split(/ /,$hash->{internals}{$condition})) { - ($device,$internal)=(split(":",$devInternal)); - return (0,"internal does not exist: [$device:$internal]") if ($devInternal and !defined($defs{$device}{$internal})); + $devInternal=~ s/\$DEVICE/$hash->{helper}{triggerDev}/g if ($devInternal); + if (!AttrVal($hash->{NAME},'notexist',undef)) { + ($dev,$internal)=(split(":",$devInternal)); + return (-1,"device does not exist: [$dev:$internal]") if ($devInternal and !defined ($defs{$dev})); + return (-1,"internal does not exist: [$dev:$internal]") if ($devInternal and !defined($defs{$dev}{$internal})); + } } } - my $ret = eval $hash->{condition}{$condition}; + my $cmd=$hash->{condition}{$condition}; + if ($cmd) { + my $eventa=$hash->{helper}{triggerEvents}; + my $events=""; + if ($eventa) { + $events=join(",",@{$eventa}); + } + $cmd =~ s/\$DEVICE/$hash->{helper}{triggerDev}/g; + $cmd =~ s/\$EVENTS/$events/g; + $cmd =~ s/\$EVENT/$hash->{helper}{event}/g; + #my $idx = 0; + #my $evt; + #foreach my $part (split(" ", $hash->{helper}{event})) { + # $evt='\$EVTPART'.$idx; + # $cmd =~ s/$evt/$part/g; + # $idx++; + #} + } + my $ret = eval $cmd; if($@){ $err = "perl error in condition: $hash->{condition}{$condition}: $@"; $ret = 0; @@ -726,10 +854,28 @@ DOIF_cmd ($$$$) } if ($hash->{do}{$nr}{$subnr}) { $hash->{helper}{cur_cmd_nr}="cmd_".($nr+1)."_".($subnr+1); - ($cmd,$err)=ParseCommandsDoIf($hash,$hash->{do}{$nr}{$subnr},1); + $cmd=$hash->{do}{$nr}{$subnr}; + + my $eventa=$hash->{helper}{triggerEvents}; + my $events=""; + if ($eventa) { + $events=join(",",@{$eventa}); + } + $cmd =~ s/\$DEVICE/$hash->{helper}{triggerDev}/g; + $cmd =~ s/\$EVENTS/$events/g; + $cmd =~ s/\$EVENT/$hash->{helper}{event}/g; + #my $idx = 0; + #my $evt; + #foreach my $part (split(" ", $hash->{helper}{event})) { + # $evt='\$EVTPART'.$idx; + # $cmd =~ s/$evt/$part/g; + # $idx++; + #} + #readingsSingleUpdate ($hash, "Event",$hash->{helper}{event},0); + ($cmd,$err)=ParseCommandsDoIf($hash,$cmd,1); } DOIF_SetState ($hash,$nr,$subnr,$event,$err); - delete $hash->{helper}{cur_cmd_nr}; + delete $hash->{helper}{cur_cmd_nr}; if (defined $hash->{do}{$nr}{++$subnr}) { my $last_cond=ReadingsVal($pn,"cmd_nr",0)-1; if (DOIF_SetSleepTimer($hash,$last_cond,$nr,$subnr,$event,-1,undef)) { @@ -743,9 +889,60 @@ DOIF_cmd ($$$$) } } } + #delete $hash->{helper}{cur_cmd_nr}; return undef; } - +sub CheckRegexpDoIf($$$$) +{ + my ($hash,$name,$eventa,$condition)=@_; + my $cond=($condition == -1) ? "all" : $condition; + my $max_regexp=keys %{$hash->{regexp}{$cond}}; + my $c; + my $nameExp; + my $notifyExp; + + for (my $i=0; $i<$max_regexp;$i++) + { + if ($hash->{regexp}{$cond}{$i} =~ /([^\:]*):(.*)/) { + $nameExp=$1; + $notifyExp=$2; + } else { + $nameExp=$hash->{regexp}{$cond}{$i}; + } + $nameExp="" if (!$nameExp); + $notifyExp="" if (!$notifyExp); + if ($nameExp eq "" or $name =~ /$nameExp/) { + #my $eventa = $hash->{helper}{triggerEvents}; + my $events=""; + if ($eventa) { + $events=join(",",@{$eventa}); + } + if ($notifyExp eq "") { + if ($cond ne "all") { + $c=$cond+1; + readingsSingleUpdate ($hash, "machted_event_c".$c."_".($i+1),"$events",0); + } + return 1; + } + my $max = int(@{$eventa}); + my $s; + my $found; + for (my $j = 0; $j < $max; $j++) { + $s = $eventa->[$j]; + $s = "" if(!defined($s)); + $found = ($s =~ m/$notifyExp/); + if ($found) { + if ($cond ne "all") { + $c=$cond+1; + readingsSingleUpdate ($hash, "machted_event_c".$c."_".($i+1),$s,0); + } + return 1 + } + } + } + } + return 0; +} sub DOIF_Trigger ($$$) @@ -764,17 +961,22 @@ DOIF_Trigger ($$$) next if ($hash->{timers}{$i} !~ / $timerNr /); $event="timer_".($timerNr+1); } else { #event - next if (!defined ($hash->{devices}{$i})); - next if ($hash->{devices}{$i} !~ / $device /); + if (!CheckRegexpDoIf($hash, $device, $hash->{helper}{triggerEvents}, $i)) { + next if (!defined ($hash->{devices}{$i})); + next if ($hash->{devices}{$i} !~ / $device /); + } $event="$device"; } if (($ret,$err)=DOIF_CheckCond($hash,$i)) { if ($err) { - Log3 $hash->{Name},2,"$hash->{NAME}: $err"; + #Log3 $hash->{Name},2,"$hash->{NAME}: $err" if ($ret != -1); readingsSingleUpdate ($hash, "error", $err,1); return undef; } if ($ret) { + $hash->{helper}{timerevents}=$hash->{helper}{triggerEvents}; + $hash->{helper}{timerevent}=$hash->{helper}{event}; + $hash->{helper}{timerdev}=$hash->{helper}{triggerDev}; if (DOIF_SetSleepTimer($hash,$last_cond,$i,0,$device,$timerNr,undef)) { DOIF_cmd ($hash,$i,0,$event); return 1; @@ -788,6 +990,9 @@ DOIF_Trigger ($$$) } if ($doelse) { #DOELSE if (defined ($hash->{do}{$max_cond}{0}) or ($max_cond == 1 and !(AttrVal($pn,"do","") or AttrVal($pn,"repeatsame","")))) { #DOELSE + $hash->{helper}{timerevents}=$hash->{helper}{triggerEvents}; + $hash->{helper}{timerevent}=$hash->{helper}{event}; + $hash->{helper}{timerdev}=$hash->{helper}{triggerDev}; if (DOIF_SetSleepTimer($hash,$last_cond,$max_cond,0,$device,$timerNr,undef)) { DOIF_cmd ($hash,$max_cond,0,$event) ; return 1; @@ -797,6 +1002,7 @@ DOIF_Trigger ($$$) return undef; } + sub DOIF_Notify($$) { @@ -809,8 +1015,9 @@ DOIF_Notify($$) my $internal; my $ret; my $err; - - if ($dev->{NAME} eq "global" and ((EventDoIf("global","global",deviceEvents($dev, AttrVal("global", "addStateEvent", 0)),"INITIALIZED")) or EventDoIf("global","global",deviceEvents($dev, AttrVal("global", "addStateEvent", 0)),"REREADCFG"))) + my $eventa; + $eventa = deviceEvents($dev, AttrVal($dev->{NAME}, "addStateEvent", 0)); + if ($dev->{NAME} eq "global" and (EventCheckDoif($dev->{NAME},"global",$eventa,"INITIALIZED") or EventCheckDoif($dev->{NAME},"global",$eventa,"REREADCFG"))) { $hash->{helper}{globalinit}=1; if ($hash->{helper}{last_timer} > 0){ @@ -829,16 +1036,15 @@ DOIF_Notify($$) } } } - - return "" if (!$hash->{devices}{all} and !$hash->{state}{device}); - return "" if (!$hash->{helper}{globalinit}); return "" if (ReadingsVal($pn,"mode","") eq "disabled"); - - if (($hash->{devices}{all}) and $hash->{devices}{all} =~ / $dev->{NAME} /) { + return "" if (!$hash->{helper}{globalinit}); + return "" if (defined $hash->{helper}{cur_cmd_nr}); + return "" if (!$hash->{devices}{all} and !$hash->{state}{device} and !$hash->{regexp}{all}); + + if ((($hash->{devices}{all}) and $hash->{devices}{all} =~ / $dev->{NAME} /) or CheckRegexpDoIf($hash,$dev->{NAME},$eventa,-1)){ readingsSingleUpdate ($hash, "Device",$dev->{NAME},0); #my $events = deviceEvents($dev, AttrVal($dev->{NAME}, "addStateEvent", 0)); #readingsSingleUpdate ($hash, "Event","@{$events}",0); - if ($hash->{readings}{all}) { foreach my $item (split(/ /,$hash->{readings}{all})) { ($device,$reading)=(split(":",$item)); @@ -852,22 +1058,20 @@ DOIF_Notify($$) readingsSingleUpdate ($hash, "e_".$dev->{NAME}."_".$internal,$defs{$device}{$internal},0) if ($item and $device eq $dev->{NAME} and defined ($defs{$device}{$internal})); } } - #my ($seconds, $microseconds) = gettimeofday(); - #if ($hash->{helper}{last_event_time}) { - # return undef if (($seconds-$hash->{helper}{last_event_time}) < AttrVal($pn,"eventpause",0)); - #} - #$hash->{helper}{last_event_time}=$seconds; if ($hash->{trigger}{all}) { foreach my $item (split(/ /,$hash->{trigger}{all})) { - my $events = deviceEvents($dev, AttrVal($dev->{NAME}, "addStateEvent", 0)); - $hash->{helper}{triggerEvents}=$events; - $hash->{helper}{triggerDev}=$dev->{NAME}; - readingsSingleUpdate ($hash, "e_".$dev->{NAME}."_events","@{$events}",0); + readingsSingleUpdate ($hash, "e_".$dev->{NAME}."_events",join(",",@{$eventa}),0); } } + $hash->{helper}{triggerEvents}=$eventa; + $hash->{helper}{triggerDev}=$dev->{NAME}; + $hash->{helper}{event}=join(",",@{$eventa}); $ret=DOIF_Trigger($hash,$dev->{NAME},-1); } if (($hash->{state}{device}) and $hash->{state}{device} =~ / $dev->{NAME} / and !$ret) { + $hash->{helper}{triggerEvents}=$eventa; + $hash->{helper}{triggerDev}=$dev->{NAME}; + $hash->{helper}{event}=join(",",@{$eventa}); DOIF_SetState($hash,"",0,"",""); } return undef; @@ -881,9 +1085,15 @@ DOIF_TimerTrigger ($) my $hash=${$timer}->{hash}; my $pn = $hash->{NAME}; my $ret; + my @triggerEvents; # if (!AttrVal($hash->{NAME},"disable","")) { if (ReadingsVal($pn,"mode","") ne "disabled") { $hash->{timer}{$nr}=1; + my $timer_nr=$nr+1; + @triggerEvents=("timer_$timer_nr"); + $hash->{helper}{triggerEvents}=\@triggerEvents; + $hash->{helper}{triggerDev}=""; + $hash->{helper}{event}="timer_$timer_nr"; $ret=DOIF_Trigger ($hash,"",$nr); $hash->{timer}{$nr}=0; } @@ -960,9 +1170,9 @@ DOIF_DetTime($) } sub -DOIF_CalcTime($) +DOIF_CalcTime($$) { - my ($block)= @_; + my ($hash,$block)= @_; my $tailBlock; my $beginning; my $err; @@ -990,7 +1200,7 @@ DOIF_CalcTime($) if ($block =~ /^\[/) { ($beginning,$block,$err,$tailBlock)=GetBlockDoIf($block,'[\[\]]'); return ($block,$err) if ($err); - ($block,$err,$device,$reading,$internal)=ReplaceReadingEvalDoIf($block,1); + ($block,$err,$device,$reading,$internal)=ReplaceReadingEvalDoIf($hash,$block,1); return ($block,$err) if ($err); } ($err,$rel,$block)=DOIF_DetTime($block); @@ -1003,7 +1213,7 @@ DOIF_CalcTime($) return ($block,$err) if ($err); if ($block ne "") { if ($block =~ /^\??[a-z0-9._]*[a-z._]+[a-z0-9._]*($|:.+$)/i) { - ($block,$err,$device,$reading,$internal)=ReplaceReadingEvalDoIf($block,1); + ($block,$err,$device,$reading,$internal)=ReplaceReadingEvalDoIf($hash,$block,1); return ($block,$err) if ($err); } ($err,$rel,$block)=DOIF_DetTime($block); @@ -1039,7 +1249,7 @@ DOIF_SetTimer($$) my $cond=$hash->{timeCond}{$nr}; my $next_time; - my ($second,$err, $rel)=DOIF_CalcTime($timeStr); + my ($second,$err, $rel)=DOIF_CalcTime($hash,$timeStr); if ($err) { readingsSingleUpdate ($hash,"timer_".($nr+1)."_c".($cond+1),"error: ".$err,0); @@ -1086,9 +1296,6 @@ DOIF_SetSleepTimer($$$$$$$) { my ($hash,$last_cond,$nr,$subnr,$device,$timerNr,$repeatcmd)=@_; my $pn = $hash->{NAME}; - if (defined $hash->{helper}{cur_cmd_nr}) { - return 0; - } my $sleeptimer=$hash->{helper}{sleeptimer}; my @waitdel=split(/:/,AttrVal($pn,"waitdel","")); my @waitdelsubnr=split(/,/,defined $waitdel[$sleeptimer] ? $waitdel[$sleeptimer] : ""); @@ -1177,6 +1384,9 @@ DOIF_SleepTrigger ($) $hash->{helper}{sleeptimer}=-1; $hash->{helper}{sleepsubtimer}=-1; my $pn = $hash->{NAME}; + $hash->{helper}{triggerEvents}=$hash->{helper}{timerevents}; + $hash->{helper}{event}=$hash->{helper}{timerevent}; + $hash->{helper}{triggerDev}=$hash->{helper}{timerdev}; readingsSingleUpdate ($hash, "wait_timer", "no timer",1); # if (!AttrVal($hash->{NAME},"disable","")) { if (ReadingsVal($pn,"mode","") ne "disabled") { @@ -1426,7 +1636,7 @@ The commands are always processed from left to right. There is only one command + definition of the status display with use of any readings or statuses


-Many examples with english identifiers - see german section. +Many examples with english identifiers - see german section.
=end html @@ -1435,10 +1645,10 @@ Many examples with english identifiers - see german section.

DOIF

=end html_DE =cut \ No newline at end of file