# $Id$ # 98_MSwitch.pm # # copyright ##################################################### # # 98_MSwitch.pm # # written by Byte09 # Maintained by Byte09 # # This file is part of FHEM. # # FHEM is free software: you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation, either version 2 of the License, or # (at your option) any later version. # # FHEM is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with FHEM. If not, see . ################################################################# # # MSwitchtoggle Suchmuster ab V3 [Befehl 1,Befehl 2,Befehl 3]:[1,2,3]:[reading] # [auszuführender Befehl]:[Inhalt reading]:[Name des readings] # ################################################################# # Todo's: #--------------------------------------------------------------- # # info sonderreadings # # reading '.info' wenn definiert -> infotext für device # reading '.change' wenn definiert -> angeforderte deviceänderung # reading '.change_inf' wenn definiert -> info für angeforderte deviceänderung # reading '.lock' sperrt das Interface (1 - alles / 2 alles bis auf trigger) # reading 'Sys_Extension' 'on' gibt Systemerweiterung frei # #--------------------------------------------------------------- # # info conffile - austausch eines/mehrerer devices # I Information zu Devicetausch # Q dummy1#zu schaltendes geraet#device # Q dummy2#zu schaltendes geraet2#device # ##--------------------------------------------------------------- # ################################################################# package main; use Time::Local; use strict; use warnings; use POSIX; use SetExtensions; use LWP::Simple; my $preconffile="https://raw.githubusercontent.com/Byte009/MSwitch_Addons/master/MSwitch_Preconf.conf"; my $autoupdate = 'off'; #off/on my $version = '3.02'; my $wizard = 'on'; # on/off my $importnotify = 'on'; # on/off my $importat = 'on'; # on/off my $vupdate = 'V2.00'; # versionsnummer der datenstruktur . änderung der nummer löst MSwitch_VUpdate aus . my $savecount = 50; # anzahl der zugriff im zeitraum zur auslösung des safemodes. kann durch attribut überschrieben werden . my $savemodetime = 10000000; # Zeit für Zugriffe im Safemode my $rename = "on"; # on/off rename in der FW_summary möglich my $standartstartdelay = 30; # zeitraum nach fhemstart , in dem alle aktionen geblockt werden. kann durch attribut überschrieben werden . #my $eventset = '0'; my $deletesavedcmds = 1800; # zeitraum nachdem gespeicherte devicecmds gelöscht werden ( beschleunugung des webinterfaces ) my $deletesavedcmdsstandart = "nosave"; # standartverhalten des attributes "MSwitch_DeleteCMDs" # standartlist ignorierter Devices . kann durch attribut überschrieben werden . my @doignore =qw(notify allowed at watchdog doif fhem2fhem telnet FileLog readingsGroup FHEMWEB autocreate eventtypes readingsproxy svg cul); my $startmode = "Notify";# Startmodus des Devices nach Define # degug my $ip = qx(hostname -I); chop ($ip); chop ($ip); my $debugging = "0"; $debugging = "0" if $ip ne "192.168.178.109"; sub MSwitch_Checkcond_time($$); sub MSwitch_Checkcond_state($$); sub MSwitch_Checkcond_day($$$$); sub MSwitch_Createtimer($); sub MSwitch_Execute_Timer($); sub MSwitch_LoadHelper($); sub MSwitch_debug2($$); sub MSwitch_ChangeCode($$); sub MSwitch_Add_Device($$); sub MSwitch_Del_Device($$); sub MSwitch_Debug($); sub MSwitch_Exec_Notif($$$$$); sub MSwitch_checkcondition($$$); sub MSwitch_Delete_Delay($$); sub MSwitch_Check_Event($$); sub MSwitch_makeAffected($); sub MSwitch_backup($); sub MSwitch_backup_this($); sub MSwitch_backup_all($); sub MSwitch_backup_done($); sub MSwitch_checktrigger(@); sub MSwitch_Cmd(@); sub MSwitch_toggle($$); sub MSwitch_Getconfig($); sub MSwitch_saveconf($$); sub MSwitch_replace_delay($$); sub MSwitch_repeat($); sub MSwitch_Createrandom($$$); sub MSwitch_Execute_randomtimer($); sub MSwitch_Clear_timer($); sub MSwitch_Createnumber($); sub MSwitch_Createnumber1($); sub MSwitch_Savemode($); sub MSwitch_set_dev($); sub MSwitch_EventBulk($$$$); sub MSwitch_priority; sub MSwitch_sort; sub MSwitch_dec($$); sub MSwitch_makefreecmd($$); sub MSwitch_clearlog($); sub MSwitch_LOG($$$); sub MSwitch_Getsupport($); sub MSwitch_confchange($$); sub MSwitch_setconfig($$); sub MSwitch_check_setmagic_i($$); sub MSwitch_Eventlog($$); sub MSwitch_Writesequenz($); sub MSwitch_del_singlelog($$); sub MSwitch_Checkcond_history($$); sub MSwitch_fhemwebconf($$$$); ############################## my %sets = ( "wizard" => "noArg", "on" => "noArg", "reset_device" => "noArg", "off" => "noArg", "reload_timer" => "noArg", "active" => "noArg", "inactive" => "noArg", "devices" => "noArg", "details" => "noArg", "del_trigger" => "noArg", "del_delays" => "noArg", "del_function_data" => "noArg", "trigger" => "noArg", "filter_trigger" => "noArg", "add_device" => "noArg", "del_device" => "noArg", "addevent" => "noArg", "backup_MSwitch" => "noArg", "import_config" => "noArg", "saveconfig" => "noArg", "savesys" => "noArg", "sort_device" => "noArg", "fakeevent" => "noArg", "exec_cmd_1" => "noArg", "exec_cmd_2" => "noArg", "del_repeats" => "noArg", "wait" => "noArg", "VUpdate" => "noArg", "Writesequenz" => "noArg", "confchange" => "noArg", "clearlog" => "noArg", "set_trigger" => "noArg", "reset_cmd_count" => "", "delcmds" => "", "deletesinglelog" => "noArg", "change_renamed" => "" ); my %gets = ( "active_timer" => "noArg", "restore_MSwitch_Data" => "noArg", "Eventlog" => "sequenzformated,timeline,clear", "restore_MSwitch_Data" => "noArg", "deletesinglelog" => "noArg", "config" => "noArg" ); #################### sub MSwitch_Initialize($) { my ($hash) = @_; $hash->{SetFn} = "MSwitch_Set"; $hash->{AsyncOutput} = "MSwitch_AsyncOutput"; $hash->{RenameFn} = "MSwitch_Rename"; $hash->{CopyFn} = "MSwitch_Copy"; $hash->{GetFn} = "MSwitch_Get"; $hash->{DefFn} = "MSwitch_Define"; $hash->{UndefFn} = "MSwitch_Undef"; $hash->{DeleteFn} = "MSwitch_Delete"; $hash->{ParseFn} = "MSwitch_Parse"; $hash->{AttrFn} = "MSwitch_Attr"; $hash->{NotifyFn} = "MSwitch_Notify"; $hash->{FW_detailFn} = "MSwitch_fhemwebFn"; $hash->{ShutdownFn} = "MSwitch_Shutdown"; $hash->{FW_deviceOverview} = 1; $hash->{FW_summaryFn} = "MSwitch_summary"; $hash->{NotifyOrderPrefix} = "45-"; $hash->{AttrList} = " disable:0,1" . " disabledForIntervals" . " MSwitch_Language:EN,DE" . " stateFormat:textField-long" . " MSwitch_Comments:0,1" . " MSwitch_Read_Log:0,1" . " MSwitch_Hidecmds" . " MSwitch_Help:0,1" . " MSwitch_Debug:0,1,2,3,4" . " MSwitch_Expert:0,1" . " MSwitch_Delete_Delays:0,1" . " MSwitch_Include_Devicecmds:0,1" . " MSwitch_generate_Events:0,1" . " MSwitch_Include_Webcmds:0,1" . " MSwitch_Include_MSwitchcmds:0,1" . " MSwitch_Activate_MSwitchcmds:0,1" . " MSwitch_Lock_Quickedit:0,1" . " MSwitch_Ignore_Types:textField-long " . " MSwitch_Reset_EVT_CMD1_COUNT" . " MSwitch_Reset_EVT_CMD2_COUNT" . " MSwitch_Trigger_Filter" . " MSwitch_Extensions:0,1" . " MSwitch_Inforoom" . " MSwitch_DeleteCMDs:manually,automatic,nosave" . " MSwitch_Mode:Full,Notify,Toggle,Dummy" . " MSwitch_Condition_Time:0,1" . " MSwitch_Selftrigger_always:0,1" . " MSwitch_RandomTime" . " MSwitch_RandomNumber" . " MSwitch_Safemode:0,1" . " MSwitch_Startdelay:0,10,20,30,60,90,120" . " MSwitch_Wait" . " MSwitch_Event_Id_Distributor:textField-long " . " MSwitch_Sequenz:textField-long " . " MSwitch_Sequenz_time" . " MSwitch_setList:textField-long " . " setList:textField-long " . " readingList:textField-long " . " MSwitch_Eventhistory:0,1,2,3,4,5,10,20,30,40,50,60,70,80,90,100,150,200" . " textField-long " . $readingFnAttributes; $hash->{FW_addDetailToSummary} = 0; } #################### sub MSwitch_Rename($) { # routine nicht in funktion my ( $new_name, $old_name ) = @_; my $hash_new = $defs{$new_name}; my $hashold = $defs{$new_name}{$old_name}; RemoveInternalTimer($hashold); Log3( $old_name, 5, "clear rename ! $old_name $new_name" ); my $inhalt = $hashold->{helper}{repeats}; foreach my $a ( sort keys %{$inhalt} ) { my $key = $hashold->{helper}{repeats}{$a}; RemoveInternalTimer($key); } delete( $hashold->{helper}{repeats} ); RemoveInternalTimer($hash_new); Log3( $old_name, 5, "clear rename ! $old_name $new_name" ); my $inhalt1 = $hash_new->{helper}{repeats}; foreach my $a ( sort keys %{$inhalt1} ) { my $key = $hash_new->{helper}{repeats}{$a}; RemoveInternalTimer($key); } delete( $hash_new->{helper}{repeats} ); delete( $modules{MSwitch}{defptr}{$old_name} ); $modules{MSwitch}{defptr}{$new_name} = $hash_new; return undef; } ##################################### sub MSwitch_Shutdown($) { my ($hash) = @_; my $Name = $hash->{NAME}; # speichern gesetzter delays my $delays = $hash->{helper}{delays}; my $x = 1; my $seq; foreach $seq ( keys %{$delays} ) { readingsSingleUpdate( $hash, "SaveDelay_$x", $seq, 1 ); $x++; } delete( $hash->{helper}{devicecmds1} ); delete( $hash->{helper}{last_devicecmd_save} ); return undef; } #################### sub MSwitch_Copy ($) { my ( $old_name, $new_name ) = @_; my $hash = $defs{$new_name}; my @areadings =qw(.Device_Affected .Device_Affected_Details .Device_Events .First_init .Trigger_Whitelist .Trigger_cmd_off .Trigger_cmd_on .Trigger_condition .Trigger_off .Trigger_on .Trigger_time .V_Check last_exec_cmd Trigger_device Trigger_log last_event state .sysconf Sys_Extension); #alle readings my $cs = "attr $new_name disable 1"; my $errors = AnalyzeCommandChain( undef, $cs ); if ( defined($errors) ) { MSwitch_LOG( $new_name, 1, "ERROR $cs" ); } foreach my $key (@areadings) { my $tmp = ReadingsVal( $old_name, $key, 'undef' ); fhem( "setreading " . $new_name . " " . $key . " " . $tmp ); } MSwitch_LoadHelper($hash); } #################### sub MSwitch_summary($) { my ( $wname, $name, $room ,$test1) = @_; my $hash = $defs{$name}; my $testroom = AttrVal( $name, 'MSwitch_Inforoom', 'undef' ); if (exists $hash->{helper}{mode} && $hash->{helper}{mode} eq "absorb") { return "Device ist im Konfigurationsmodus."; } my @areadings = ( keys %{$test1} ); if ( !grep /group/, @areadings ) { return; } if ( $testroom ne $room ) { return; } my $test = AttrVal( $name, 'comment', '0' ); my $info = AttrVal( $name, 'comment', 'No Info saved at ATTR omment' ); my $image = ReadingsVal( $name, 'state', 'undef' ); my $ret = ''; my $devtitle = ''; my $option = ''; my $html = ''; my $triggerc = 1; my $timer = 1; my $trigger = ReadingsVal( $name, 'Trigger_device', 'undef' ); my @devaff = split( / /, MSwitch_makeAffected($hash) ); $option .= ""; foreach (@devaff) { $devtitle .= $_ . ", "; $option .= ""; } chop($devtitle); chop($devtitle); my $affected = ""; # time my $optiontime; my $devtitletime = ''; my $triggertime = ReadingsVal( $name, 'Trigger_device', 'not defined' ); my $devtime = ReadingsVal( $name, '.Trigger_time', '' ); $devtime =~ s/\[//g; $devtime =~ s/\]/ /g; my @devtime = split( /~/, $devtime ); $optiontime .= ""; my $count = @devtime; $devtime[0] =~ s/on/on+cmd1: /g if defined $devtime[0]; $devtime[1] =~ s/off/off+cmd2: /g if defined $devtime[1]; $devtime[2] =~ s/ononly/only cmd1: /g if defined $devtime[2]; $devtime[3] =~ s/offonly/only cmd2: /g if defined $devtime[3]; if ( AttrVal( $name, 'MSwitch_Mode', 'Notify' ) ne "Notify" ) { $optiontime .="" if defined $devtime[0]; $optiontime .="" if defined $devtime[1]; } $optiontime .= "" if defined $devtime[2]; $optiontime .= "" if defined $devtime[3]; my $affectedtime = ''; if ( $count == 0 ) { $timer = 0; $affectedtime = ""; } else { chop($devtitletime); chop($devtitletime); $affectedtime = ""; } if ( $info eq 'No Info saved at ATTR omment' ) { $ret .= ""; } else { $ret .= ""; } $ret .= " "; if ( $trigger eq 'no_trigger' || $trigger eq 'undef' || $trigger eq '' ) { $triggerc = 0; if ( $triggerc != 0 || $timer != 0 ) { $ret .=""; } else { if ( AttrVal( $name, 'MSwitch_Mode', 'Notify' ) ne "Dummy" ) { $affectedtime = ""; $ret .="  Multiswitchmode (no trigger / no timer) "; } else { $affectedtime = ""; $affected = ""; $ret .= "  Dummymode "; } } } else { $ret .= ""; } $ret .= $affectedtime; $ret .= $affected; if ( ReadingsVal( $name, '.V_Check', 'not defined' ) ne $vupdate ) { $ret .= " Versionskonflikt !
(please help)
"; } else { if ( AttrVal( $name, 'disable', "0" ) eq '1' ) { $ret .= " State:
disabled
"; } else { $ret .= " State:
" . ReadingsVal( $name, 'state', '' ) . "
"; if ( AttrVal( $name, 'MSwitch_Mode', 'Notify' ) ne "Notify" ) { $ret .="
" . ReadingsTimestamp( $name, 'state', '' ) . "
"; } else { $ret .= "
" . ReadingsTimestamp( $name, 'state', '' ) . "
"; } } } $ret .= ""; $ret =~ s/#dp /:/g; return $ret; } ################################# sub MSwitch_check_init($) { my ($hash) = @_; my $Name = $hash->{NAME}; Log3( $Name, 5, "start checkinit !" );#LOG my $oldtrigger = ReadingsVal( $Name, 'Trigger_device', 'undef' ); if ( $oldtrigger ne 'undef') { $hash->{NOTIFYDEV} = $oldtrigger; readingsSingleUpdate( $hash, "Trigger_device", $oldtrigger, 0 ); } } #################### sub MSwitch_LoadHelper($) { my ($hash) = @_; my $Name = $hash->{NAME}; my $oldtrigger = ReadingsVal( $Name, 'Trigger_device', 'undef' ); my $devhash = undef; my $cdev = ''; my $ctrigg = ''; if ( $hash->{INIT} eq "def" ) { return; } if ( defined $hash->{DEF} ) { $devhash = $hash->{DEF}; my @dev = split( /#/, $devhash ); $devhash = $dev[0]; ( $cdev, $ctrigg ) = split( / /, $devhash ); if ( defined $ctrigg ) { $ctrigg =~ s/\.//g; } else { $ctrigg = ''; } if ( defined $devhash ) { $hash->{NOTIFYDEV} = $cdev; # stand auf global ... änderung auf ... if ( defined $cdev && $cdev ne '' ) { readingsSingleUpdate( $hash, "Trigger_device", $cdev, 0 ); } } else { $hash->{NOTIFYDEV} = 'no_trigger'; readingsSingleUpdate( $hash, "Trigger_device", 'no_trigger', 0 ); } } if (!defined $hash->{NOTIFYDEV}|| $hash->{NOTIFYDEV} eq 'undef'|| $hash->{NOTIFYDEV} eq '' ) { $hash->{NOTIFYDEV} = 'no_trigger'; } if ( $oldtrigger ne 'undef' ) { $hash->{NOTIFYDEV} = $oldtrigger; readingsSingleUpdate( $hash, "Trigger_device", $oldtrigger, 0 ); } ################# MSwitch_set_dev($hash); ################ if ( AttrVal( $Name, 'MSwitch_Activate_MSwitchcmds', "0" ) eq '1' ) { addToAttrList('MSwitchcmd'); } ################ erste initialisierung eines devices if ( ReadingsVal( $Name, '.V_Check', 'undef' ) ne $vupdate && $autoupdate eq "on" ) { MSwitch_VUpdate($hash); } ################ if ( ReadingsVal( $Name, '.First_init', 'undef' ) ne 'done' ) { $hash->{helper}{config} ="no_config"; readingsBeginUpdate($hash); readingsBulkUpdate( $hash, ".V_Check", $vupdate ); readingsBulkUpdate( $hash, "state", 'active' ); if ( defined $ctrigg && $ctrigg ne '' ) { readingsBulkUpdate( $hash, ".Device_Events", $ctrigg ); $hash->{DEF} = $cdev; } else { readingsBulkUpdate( $hash, ".Device_Events", 'no_trigger' ); } readingsBulkUpdate( $hash, ".Trigger_on", 'no_trigger' ); readingsBulkUpdate( $hash, ".Trigger_off", 'no_trigger' ); readingsBulkUpdate( $hash, ".Trigger_cmd_on", 'no_trigger' ); readingsBulkUpdate( $hash, ".Trigger_cmd_off", 'no_trigger' ); readingsBulkUpdate( $hash, "Trigger_log", 'off' ); readingsBulkUpdate( $hash, ".Device_Affected", 'no_device' ); readingsBulkUpdate( $hash, ".First_init", 'done' ); readingsBulkUpdate( $hash, ".V_Check", $vupdate ); readingsEndUpdate( $hash, 0 ); # setze ignoreliste $attr{$Name}{MSwitch_Ignore_Types} = join( " ", @doignore ); # setze attr inforoom my $testdev = ''; LOOP22: foreach my $testdevices ( keys %{ $modules{MSwitch}{defptr} } ) { if ( $Name eq $testdevices ) { next LOOP22; } $testdev = AttrVal( $testdevices, 'MSwitch_Inforoom', '' ); } if ( $testdev ne '' ) { $attr{$Name}{MSwitch_Inforoom} = $testdev,; } #setze alle attrs $attr{$Name}{MSwitch_Eventhistory} = '0'; $attr{$Name}{MSwitch_Safemode} = '1'; $attr{$Name}{MSwitch_Help} = '0'; $attr{$Name}{MSwitch_Debug} = '0'; $attr{$Name}{MSwitch_Expert} = '0'; $attr{$Name}{MSwitch_Delete_Delays} = '1'; $attr{$Name}{MSwitch_Include_Devicecmds} = '1'; $attr{$Name}{MSwitch_Include_Webcmds} = '0'; $attr{$Name}{MSwitch_Include_MSwitchcmds} = '0'; $attr{$Name}{MSwitch_Include_MSwitchcmds} = '0'; $attr{$Name}{MSwitch_Lock_Quickedit} = '1'; $attr{$Name}{MSwitch_Extensions} = '0'; $attr{$Name}{MSwitch_Mode} = $startmode; fhem("attr $Name room MSwitch_Devices") ; } # NEU; ZUVOR IN SET my $testnew = ReadingsVal( $Name, '.Trigger_on', 'undef' ); if ( $testnew eq 'undef' ) { readingsBeginUpdate($hash); readingsBulkUpdate( $hash, ".Device_Events", 'no_trigger' ); readingsBulkUpdate( $hash, ".Trigger_on", 'no_trigger' ); readingsBulkUpdate( $hash, ".Trigger_off", 'no_trigger' ); readingsBulkUpdate( $hash, "Trigger_log", 'on' ); readingsBulkUpdate( $hash, ".Device_Affected", 'no_device' ); readingsEndUpdate( $hash, 0 ); } MSwitch_Createtimer($hash); #Neustart aller timer #### savedelays einlesen my $counter = 1; while ( ReadingsVal( $Name, 'SaveDelay_' . $counter, 'undef' ) ne "undef" ) { my $del = ReadingsVal( $Name, 'SaveDelay_' . $counter, 'undef' ); my @msgarray = split( /#\[tr\]/, $del ); my $timecond = $msgarray[4]; if ( $timecond > time ) { $hash->{helper}{delays}{$del} = $timecond; InternalTimer( $timecond, "MSwitch_Restartcmd", $del ); } $counter++; } fhem("deletereading $Name SaveDelay_.*"); } #################### sub MSwitch_Define($$) { my $loglevel = 0; my ( $hash, $def ) = @_; my @a = split( "[ \t][ \t]*", $def ); my $name = $a[0]; my $devpointer = $name; my $devhash = ''; my $defstring = ''; foreach (@a) { next if $_ eq $a[0]; next if $_ eq $a[1]; $defstring = $defstring . $_ . " "; } $modules{MSwitch}{defptr}{$devpointer} = $hash; $hash->{Version_Modul} = $version; $hash->{Version_Datenstruktur} = $vupdate; $hash->{Version_autoupdate} = $autoupdate; $hash->{MODEL} = $startmode; $hash->{Support_Fhemforum} = "https://forum.fhem.de/index.php/topic,86199.0.html"; if ( $defstring ne "" and $defstring =~ m/(\(.+?\))/ ) { Log3( $name, 0, "ERROR MSwitch define over onelinemode deactivated" );#LOG return "This mode is deactivated"; # $hash->{INIT} = 'define'; # MSwitch_Define1( $hash, $defstring ); return; } else { $hash->{INIT} = 'fhem.save'; } if ( $init_done && !defined( $hash->{OLDDEF} ) ) { my $timecond = gettimeofday() + 5; InternalTimer( $timecond, "MSwitch_check_init", $hash ); } return; } #################### sub MSwitch_Get($$@) { my ( $hash, $name, $opt, @args ) = @_; my $ret; if ( ReadingsVal( $name, '.change', '' ) ne '' ) { return "Unknown argument, choose one of "; } return "\"get $name\" needs at least one argument" unless ( defined($opt) ); #################### if ( $opt eq 'restore_MSwitch_Data' && $args[0] eq "this_Device" ) { $ret = MSwitch_backup_this($hash); return $ret; } #################### my $KLAMMERFEHLER; my $CONDTRUE; my $CONDTRUE1; my $KLARZEITEN; my $READINGSTATE; my $NOREADING; my $INHALT; my $INCOMMINGSTRING; my $STATEMENTPERL; my $SYNTAXERROR; my $DELAYDELETE; my $NOTIMER; my $SYSTEMZEIT; my $SCHALTZEIT; if (AttrVal( $name, 'MSwitch_Language',AttrVal( 'global', 'language', 'EN' ) ) eq "DE") { $KLAMMERFEHLER ="Fehler in der Klammersetzung, die Anzahl öffnender und schliessender Klammern stimmt nicht überein."; $CONDTRUE="Bedingung ist Wahr und wird ausgeführt"; $CONDTRUE1="Bedingung ist nicht Wahr und wird nicht ausgeführt"; $KLARZEITEN="If Anweisung Perl Klarzeiten:"; $READINGSTATE="Status der geprüften Readings:"; $NOREADING="Reading nicht vorhanden !"; $INHALT="Inhalt:"; $INCOMMINGSTRING="eingehender String:"; $STATEMENTPERL="If Anweisung Perl:"; $SYNTAXERROR="Syntaxfehler:"; $DELAYDELETE="INFO: Alle anstehenden Timer wurden neu berechnet, alle Delays wurden gelöscht"; $NOTIMER="Timer werden nicht ausgeführt"; $SYSTEMZEIT="Systemzeit:"; $SCHALTZEIT="Schaltzeiten (at - kommandos)"; } else { $KLAMMERFEHLER ="Error in brace replacement, number of opening and closing parentheses does not match."; $CONDTRUE="Condition is true and is executed"; $CONDTRUE1="Condition is not true and will not be executed"; $KLARZEITEN="If statement Perl clears:"; $READINGSTATE="States of the checked readings:"; $NOREADING="Reading not available!"; $INHALT="content:"; $INCOMMINGSTRING="Incomming String:"; $STATEMENTPERL="If statement Perl:"; $SYNTAXERROR="Syntaxerror:"; $DELAYDELETE="INFO: All pending timers have been recalculated, all delays have been deleted"; $NOTIMER="Timers are not running"; $SYSTEMZEIT="system time:"; $SCHALTZEIT="Switching times (at - commands)"; } if ( $opt eq 'MSwitch_preconf' ) { MSwitch_setconfig( $hash, $args[0] ); return"MSwitch_preconfig for $name has loaded.\nPlease refresh device."; } #################### if ( $opt eq 'Eventlog' ) { $ret = MSwitch_Eventlog($hash,$args[0]); return $ret; } ######################## if ( $opt eq 'restore_MSwitch_Data' && $args[0] eq "all_Devices" ) { open( BACKUPDATEI, "{helper}{RESTORE_ANSWER} = $hash->{CL}; my $ret = MSwitch_backup_all($hash); return $ret; } #################### if ( $opt eq 'checkevent' ) { $ret = MSwitch_Check_Event( $hash, $args[0] ); return $ret; } #################### if ( $opt eq 'deletesinglelog' ) { $ret = MSwitch_delete_singlelog( $hash, $args[0] ); return $ret; } #################### if ( $opt eq 'config' ) { $ret = MSwitch_Getconfig($hash); return $ret; } #################### if ( $opt eq 'support_info' ) { $ret = MSwitch_Getsupport($hash); return $ret; } #################### if ( $opt eq 'sysextension' ) { $ret = MSwitch_Sysextension($hash); return $ret; } #################### if ( $opt eq 'checkcondition' ) { my ( $condstring, $eventstring ) = split( /\|/, $args[0] ); $condstring =~ s/#\[dp\]/:/g; $condstring =~ s/#\[pt\]/./g; $condstring =~ s/#\[ti\]/~/g; $condstring =~ s/#\[sp\]/ /g; $eventstring =~ s/#\[dp\]/:/g; $eventstring =~ s/#\[pt\]/./g; $eventstring =~ s/#\[ti\]/~/g; $eventstring =~ s/#\[sp\]/ /g; $condstring =~ s/\(DAYS\)/|/g; my $ret1 = MSwitch_checkcondition( $condstring, $name, $eventstring ); my $condstring1 = $hash->{helper}{conditioncheck}; my $errorstring = $hash->{helper}{conditionerror}; if ( !defined $errorstring ) { $errorstring = '' } $condstring1 =~ s//\>\;/g; $errorstring =~ s//\>\;/g; if ( $errorstring ne '' && $condstring1 ne 'Klammerfehler' ) { $ret1 ='
'.$SYNTAXERROR.'
'. $errorstring. '

'; } elsif ( $condstring1 eq 'Klammerfehler' ) { $ret1 ='
'.$SYNTAXERROR.'
'.$KLAMMERFEHLER.'

'; } else { if ( $ret1 eq 'true' ) { $ret1 = $CONDTRUE; } if ( $ret1 eq 'false' ) { $ret1 = $CONDTRUE1; } } $condstring =~ s/~/ /g; my $condmarker = $condstring1; my $x = 0; # exit while ( $condmarker =~ m/(.*)(\d{10})(.*)/ ) { $x++; # exit last if $x > 20; # exit my $timestamp = FmtDateTime($2); chop $timestamp; chop $timestamp; chop $timestamp; my ( $st1, $st2 ) = split( / /, $timestamp ); $condmarker = $1 . $st2 . $3; } $ret =$INCOMMINGSTRING."
$condstring

".$STATEMENTPERL."
$condstring1

"; $ret .= $KLARZEITEN."
$condmarker

" if $x > 0; $ret .= $ret1; my $condsplit = $condmarker; my $reads = '

'.$READINGSTATE.'
'; $x = 0; # exit while ( $condsplit =~ m/(if \()(.*)(\()(.*')(.*)',\s'(.*)',\s(.*)/ ) { $x++; # exit last if $x > 20; # exit $reads .= "ReadingVal: [$5:$6] - ".$INHALT." " . ReadingsVal( $5, $6, 'undef' ) . "
"; $reads .= "ReadingNum: [$5:$6:d] - ".$INHALT." ". ReadingsNum( $5, $6, 'undef' ); $reads .="
".$NOREADING."
" if ( ReadingsVal( $5, $6, 'undef' ) ) eq "undef"; $reads .= "
"; $condsplit = $1 . $2 . $3 . $4 . $7; } $ret .= $reads if $x > 0; ## anzeige funktionserkennung if ( defined $hash->{helper}{eventhistory}{DIFFERENCE} ) { $ret .= "
"; $ret .= $hash->{helper}{eventhistory}{DIFFERENCE}; $ret .= "
"; delete( $hash->{helper}{eventhistory}{DIFFERENCE} ); } if ( defined $hash->{helper}{eventhistory}{TENDENCY} ) { $ret .= "
"; $ret .= $hash->{helper}{eventhistory}{TENDENCY}; $ret .= "
"; delete( $hash->{helper}{eventhistory}{TENDENCY} ); } if ( defined $hash->{helper}{eventhistory}{AVERAGE} ) { $ret .= "
"; $ret .= $hash->{helper}{eventhistory}{AVERAGE}; $ret .= "
"; delete( $hash->{helper}{eventhistory}{AVERAGE} ); } if ( defined $hash->{helper}{eventhistory}{INCREASE} ) { $ret .= "
"; $ret .= $hash->{helper}{eventhistory}{INCREASE}; $ret .= "
"; delete( $hash->{helper}{eventhistory}{INCREASE} ); } my $err1; my $err2; if ( $errorstring ne '' ) { ( $err1, $err2 ) = split( /near /, $errorstring ); chop $err2; chop $err2; $err2 = substr( $err2, 1 ); $ret =~ s/$err2/$err2<\/span>/ig; } $hash->{helper}{conditioncheck} = ''; $hash->{helper}{conditionerror} = ''; return "" . $ret . "<\/span>"; } ################################################# if ( $opt eq 'active_timer' && $args[0] eq 'delete' ) { MSwitch_Clear_timer($hash); MSwitch_Createtimer($hash); MSwitch_Delete_Delay( $hash, 'all' ); $ret .="
".$DELAYDELETE."
"; return $ret; } ################################################# if ( $opt eq 'active_timer' && $args[0] eq 'show' ) { if ( defined $hash->{helper}{wrongtimespec} and $hash->{helper}{wrongtimespec} ne "" ) { $ret = $hash->{helper}{wrongtimespec}; $ret .= "
".$NOTIMER."
"; return $ret; } $ret .= "
".$SYSTEMZEIT." " . localtime() . "

"; $ret .= "
".$SCHALTZEIT."

"; #timer my $timehash = $hash->{helper}{timer}; foreach my $a ( sort keys %{$timehash} ) { my @string = split( /-/, $hash->{helper}{timer}{$a} ); my @string1 = split( /ID/, $string[1] ); my $number = $string1[0]; my $id = $string1[1]; my $time = FmtDateTime( $string[0] ); my @timers = split( /,/, $a ); if ( $number eq '1' ) { $ret .="
". $time. " switch MSwitch on + execute 'on' cmds
"; } if ( $number eq '2' ) { $ret .="
". $time. " switch MSwitch off + execute 'off' cmds
"; } if ( $number eq '3' ) { $ret .="
" . $time. " execute 'cmd1' commands only
"; } if ( $number eq '4' ) { $ret .="
". $time. " execute 'cmd2' commands only
"; } if ( $number eq '9' ) { $ret .="
". $time. " execute 'cmd1+cmd2' commands only
"; } if ( $number eq '10' ) { $ret .="
". $time. " execute 'cmd1+cmd2' commands with ID ". $id. " only
"; } if ( $number eq '5' ) { $ret .="
". $time. " neuberechnung aller Schaltzeiten
"; } if ( $number eq '6' ) { $ret .="
". $time. " execute 'cmd1' commands with ID ". $id. " only
"; } if ( $number eq '7' ) { $ret .="
". $time. " execute 'cmd2' commands from ID ". $id. " only
"; } } #delays $ret .= "
 
aktive Delays:

"; $timehash = $hash->{helper}{delays}; foreach my $a ( sort keys %{$timehash} ) { my $b = substr( $hash->{helper}{delays}{$a}, 0, 10 ); my $time = FmtDateTime($b); my @timers = split( /#\[tr\]/, $a ); $ret .= "
" . $time . " " . $timers[0] . "
"; } if ( $ret ne "
".$SCHALTZEIT."

aktive Delays:

") { return $ret; } return "Keine aktiven Delays/Ats gefunden <\/span>"; } my $extension = ''; if ( ReadingsVal( $name, 'Sys_Extension', '' ) eq 'on' ) { $extension = 'sysextension:noArg'; } if ( AttrVal( $name, 'MSwitch_Mode', 'Notify' ) eq "Dummy" ) { if (AttrVal( $name, "MSwitch_Selftrigger_always", 0 ) eq "1") { return "Unknown argument $opt, choose one of Eventlog:timeline,clear config:noArg support_info:noArg restore_MSwitch_Data:this_Device,all_Devices active_timer:show,delete"; } else { return "Unknown argument $opt, choose one of support_info:noArg restore_MSwitch_Data:this_Device,all_Devices"; } } if ( ReadingsVal( $name, '.lock', 'undef' ) ne "undef" ) { return "Unknown argument $opt, choose one of active_timer:show,delete config:noArg restore_MSwitch_Data:this_Device,all_Devices "; } else { return "Unknown argument $opt, choose one of Eventlog:sequenzformated,timeline,clear support_info:noArg config:noArg active_timer:show,delete restore_MSwitch_Data:this_Device,all_Devices $extension"; } } #################### sub MSwitch_AsyncOutput ($) { my ( $client_hash, $text ) = @_; return $text; } #################### sub MSwitch_Set($@) { my ( $hash, $name, $cmd, @args ) = @_; #MSwitch_LOG( $name, 6, "$name Set $cmd, @args " . __LINE__ ); my $dynlist =""; if ($cmd ne "?"){ MSwitch_LOG( $name, 6, "----------------------------------------" ); MSwitch_LOG( $name, 6, "AUSFUEHRUNG SET" ); MSwitch_LOG( $name, 6, "----------------------------------------" ); MSwitch_LOG( $name, 6, "eingehendr Befehl: Set $cmd, @args " ); } #lösche saveddevicecmd MSwitch_del_savedcmds($hash); return "" if ( IsDisabled($name) && ( $cmd eq 'on' || $cmd eq 'off' ) );# Return without any further action if the module is disabled my $execids = "0"; $hash->{eventsave} = 'unsaved'; my $ic = 'leer'; $ic = $hash->{IncommingHandle} if ( $hash->{IncommingHandle} ); my $showevents = AttrVal( $name, "MSwitch_generate_Events", 1 ); my $devicemode = AttrVal( $name, 'MSwitch_Mode', 'Notify' ); my $delaymode = AttrVal( $name, 'MSwitch_Delete_Delays', '0' ); ################################################################################### # verry special commands readingactivated ( my $special = ''; my $cs = ReadingsVal( $name, '.sysconf', 'undef' ); if ( $cs ne "undef" ) { $cs =~ s/#\[tr\]/[tr]/g; $cs =~ s/#\[wa\]/|/g; $cs =~ s/#\[sp\]/ /g; $cs =~ s/#\[nl\]/\n/g; $cs =~ s/#\[se\]/;/g; $cs =~ s/#\[dp\]/:/g; $cs =~ s/#\[st\]/'/g; $cs =~ s/#\[dst\]/\"/g; $cs =~ s/#\[tab\]/ /g; $cs =~ s/#\[ko\]/,/g; $cs =~ s/#.*\n//g; $cs =~ s/\n//g; $cs =~ s/\[tr\]/#[tr]/g; my $return = "no value"; if ($debugging eq "1") { MSwitch_LOG( "Debug", 0,"eval line" . __LINE__ ); } $return = eval($cs); if ($@) { MSwitch_LOG( $name, 1,"$name MSwitch_repeat: ERROR $cs: $@ " . __LINE__ ); } return if $return eq "exit"; } ########################## # mswitch dyn setlist my $mswitchsetlist = AttrVal( $name, 'MSwitch_setList', "undef" ); my @arraydynsetlist; my @arraydynreadinglist; my $dynsetlist ; if ($mswitchsetlist ne "undef") { my @dynsetlist = split( / /,$mswitchsetlist); foreach my $test (@dynsetlist) { if ( $test =~ m/(.*)\[(.*)\]:?(.*)/ ) { my @found_devices = devspec2array($2); if ($1 ne "") { my $reading = $1; chop ($reading); push @arraydynsetlist, $reading; $dynlist =join( ',', @found_devices ); $dynsetlist=$dynsetlist.$reading.":".$dynlist." "; } if ($3 ne "") { my $sets = $3; foreach my $test1 (@found_devices) { push @arraydynsetlist, $test1; $dynsetlist=$dynsetlist.$test1.":".$sets." "; } @arraydynreadinglist=@found_devices; } } else { $dynsetlist=$dynsetlist.$test; } } } ########################### # nur bei funktionen in setlist !!!! if ( AttrVal( $name, "MSwitch_Selftrigger_always", 0 ) eq "1" and $cmd ne "?" ) { # && defined $setlist{$cmd} my $atts = AttrVal( $name, 'setList', "" ); my @testarray = split( " ", $atts ); my %setlist; foreach (@testarray) { my ($arg1,$arg2) = split( ":", $_ ); if (!defined $arg2 or $arg2 eq "") {$arg2 = "noArg"} $setlist{$arg1} = $arg2; } MSwitch_Check_Event( $hash, "MSwitch_self:".$cmd.":".$args[0] ) if defined $setlist{$cmd}; } if ( AttrVal( $name, "MSwitch_Selftrigger_always", 0 ) eq "1" and $cmd ne "?" ) { # && defined $setlist{$cmd} my %setlist; foreach (@arraydynsetlist) { my ($arg1,$arg2) = split( ":", $_ ); if (!defined $arg2 or $arg2 eq "") {$arg2 = "noArg"} $setlist{$arg1} = $arg2; } MSwitch_Check_Event( $hash, "MSwitch_self:".$cmd.":".$args[0] ) if defined $setlist{$cmd}; } my %setlist; if ( !defined $args[0] ) { $args[0] = ''; } my $setList = AttrVal( $name, "setList", " " ); $setList =~ s/\n/ /g; if ( !exists( $sets{$cmd} ) ) { my @cList; # Overwrite %sets with setList my $atts = AttrVal( $name, 'setList', "" ); my @testarray = split( " ", $atts ); foreach (@testarray) { my ($arg1,$arg2) = split( ":", $_ ); if (!defined $arg2 or $arg2 eq "") {$arg2 = "noArg"} $setlist{$arg1} = $arg2; } ########################## foreach my $k ( sort keys %sets ) { my $opts = undef; $opts = $sets{$k}; $opts = $setlist{$k} if ( exists( $setlist{$k} ) ); if ( defined($opts) ) { push( @cList, $k . ':' . $opts ); } else { push( @cList, $k ); } } # end foreach if ( ReadingsVal( $name, '.change', '' ) ne '' ) { return "Unknown argument $cmd, choose one of " if ($name eq "test"); } # bearbeite setlist und readinglist ############################## if ( $cmd ne "?" ) { my @sl = split( " ", AttrVal( $name, "setList", "" ) ); my $re = qr/$cmd/; my @gefischt = grep( /$re/, @sl ); if ( @sl && grep /$re/, @sl ) { my @rl = split( " ", AttrVal( $name, "readingList", "" ) ); if ( @rl && grep /$re/, @rl ) { readingsSingleUpdate( $hash, $cmd, "@args", 1 ); } else { readingsSingleUpdate( $hash, "state", $cmd . " @args", 1 ); } return; } @gefischt = grep( /$re/, @arraydynsetlist ); if ( @arraydynsetlist && grep /$re/, @arraydynsetlist ) { my @rl = split( " ", AttrVal( $name, "readingList", "" ) ); if (( @rl && grep /$re/, @rl ) || ( @arraydynreadinglist && grep /$re/, @arraydynreadinglist )) { readingsSingleUpdate( $hash, $cmd, "@args", 1 ); } else { readingsSingleUpdate( $hash, "state", $cmd . " @args", 1 ); } return; } ############################## # dummy state setzen und exit if ( $devicemode eq "Dummy" ) { if ($cmd eq "on" || $cmd eq "off") { readingsSingleUpdate( $hash, "state", $cmd . " @args", 1 ); return; } else { if ( AttrVal( $name, 'useSetExtensions', "0" ) eq '1' ) { return SetExtensions($hash, $setList, $name, $cmd, @args); } else { return; } } } #AUFRUF DEBUGFUNKTIONEN if ( AttrVal( $name, 'MSwitch_Debug', "0" ) eq '4' ) { MSwitch_Debug($hash); } delete( $hash->{IncommingHandle} ); } ############################################ if (exists $hash->{helper}{config} && $hash->{helper}{config} eq "no_config") { return "Unknown argument $cmd, choose one of wizard:noArg" } if ( $devicemode eq "Notify" ) { return "Unknown argument $cmd, choose one of $dynsetlist reset_device:noArg active:noArg inactive:noArg del_function_data:noArg del_delays:noArg backup_MSwitch:all_devices fakeevent exec_cmd_1 exec_cmd_2 wait reload_timer:noArg del_repeats:noArg change_renamed reset_cmd_count:1,2,all $setList $special"; } elsif ( $devicemode eq "Toggle" ) { return "Unknown argument $cmd, choose one of $dynsetlist reset_device:noArg active:noArg del_function_data:noArg inactive:noArg on off del_delays:noArg backup_MSwitch:all_devices fakeevent wait reload_timer:noArg del_repeats:noArg change_renamed $setList $special"; } elsif ( $devicemode eq "Dummy" ) { if ( AttrVal( $name, 'useSetExtensions', "0" ) eq '1' ) { return SetExtensions($hash, $setList, $name, $cmd, @args); } else { if (AttrVal( $name, "MSwitch_Selftrigger_always", 0 ) eq "1") { return "Unknown argument $cmd, choose one of $dynsetlist del_repeats:noArg del_delays:noArg exec_cmd_1 exec_cmd_2 reset_device:noArg wait backup_MSwitch:all_devices $setList $special"; } else { return "Unknown argument $cmd, choose one of $dynsetlist reset_device:noArg backup_MSwitch:all_devices $setList $special"; } } } else { #full return "Unknown argument $cmd, choose one of $dynsetlist del_repeats:noArg reset_device:noArg active:noArg del_function_data:noArg inactive:noArg on off del_delays:noArg backup_MSwitch:all_devices fakeevent exec_cmd_1 exec_cmd_2 wait del_repeats:noArg reload_timer:noArg change_renamed reset_cmd_count:1,2,all $setList $special"; } } if ((( $cmd eq 'on' ) || ( $cmd eq 'off' ) )&& ( $args[0] ne '' )&& ( $ic ne 'fromnotify' )) { readingsSingleUpdate( $hash, "Parameter", $args[0], 1 ); if ( $cmd eq 'on' ) { $args[0] = "$name:on_with_Parameter:$args[0]"; } if ( $cmd eq 'off' ) { $args[0] = "$name:off_with_Parameter:$args[0]"; } } if ( AttrVal( $name, 'MSwitch_RandomNumber', '' ) ne '' ) { # randomnunner erzeugen wenn attr an MSwitch_Createnumber1($hash); } ############################# #absorb if ( $cmd eq 'wizard' ) { $hash->{helper}{mode} ='absorb'; $hash->{helper}{modesince} =time; } ############################## if ( $cmd eq 'reset_device' ) { if ($args[0] eq 'checked' ) { $hash->{helper}{config} ="no_config"; #readings my $testreading = $hash->{READINGS}; delete $hash->{DEF}; MSwitch_Delete_Delay( $hash, $name ); my $inhalt = $hash->{helper}{repeats}; foreach my $a ( sort keys %{$inhalt} ) { my $key = $hash->{helper}{repeats}{$a}; RemoveInternalTimer($key); } delete( $hash->{helper}{repeats} ); delete( $hash->{helper}{devicecmds1} ); delete( $hash->{helper}{last_devicecmd_save} ); delete( $hash->{helper}{eventhistory}); delete( $hash->{IncommingHandle} ); delete( $hash->{helper}{eventtoid} ); delete( $hash->{helper}{savemodeblock} ); delete( $hash->{helper}{sequenz}); delete( $hash->{helper}{history} ); delete( $hash->{helper}{eventlog} ); delete( $hash->{helper}{mode} ); delete( $hash->{helper}{reset} ); delete( $hash->{READINGS} ); # attribute my %keys; my $oldinforoom = AttrVal( $name, 'MSwitch_Inforoom', 'undef' ); my $oldroom =AttrVal( $name, 'MSwitch_Inforoom', 'undef' ); foreach my $attrdevice ( keys %{ $attr{$name} } )#geht { fhem("deleteattr $name $attrdevice "); } $hash->{Version_Modul} = $version; $hash->{Version_Datenstruktur} = $vupdate; $hash->{Version_autoupdate} = $autoupdate; $hash->{MODEL} = $startmode; $hash->{Support_Fhemforum} = "https://forum.fhem.de/index.php/topic,86199.0.html"; readingsBeginUpdate($hash); readingsBulkUpdate( $hash, ".Device_Events", "no_trigger", 1 ); readingsBulkUpdate( $hash, ".Trigger_cmd_off", "no_trigger", 1 ); readingsBulkUpdate( $hash, ".Trigger_cmd_on", "no_trigger", 1 ); readingsBulkUpdate( $hash, ".Trigger_off", "no_trigger", 1 ); readingsBulkUpdate( $hash, ".Trigger_on", "no_trigger", 1 ); readingsBulkUpdate( $hash, "Trigger_device", "no_trigger", 1 ); readingsBulkUpdate( $hash, "Trigger_log", "off", 1 ); readingsBulkUpdate( $hash, "state", "active", 1 ); readingsBulkUpdate( $hash, ".V_Check", $vupdate, 1 ); readingsBulkUpdate( $hash, ".First_init", 'done' ); readingsEndUpdate( $hash, 0 ); my $attrdefinelist = " disable:0,1" . " disabledForIntervals" . " stateFormat:textField-long" . " MSwitch_Comments:0,1" . " MSwitch_Read_Log:0,1" . " MSwitch_Hidecmds" . " MSwitch_Help:0,1" . " MSwitch_Debug:0,1,2,3,4" . " MSwitch_Expert:0,1" . " MSwitch_Delete_Delays:0,1" . " MSwitch_Include_Devicecmds:0,1" . " MSwitch_generate_Events:0,1" . " MSwitch_Include_Webcmds:0,1" . " MSwitch_Include_MSwitchcmds:0,1" . " MSwitch_Activate_MSwitchcmds:0,1" . " MSwitch_Lock_Quickedit:0,1" . " MSwitch_Ignore_Types:textField-long " . " MSwitch_Reset_EVT_CMD1_COUNT" . " MSwitch_Reset_EVT_CMD2_COUNT" . " MSwitch_Trigger_Filter" . " MSwitch_Extensions:0,1" . " MSwitch_Inforoom" . " MSwitch_DeleteCMDs:manually,automatic,nosave" . " MSwitch_Mode:Full,Notify,Toggle,Dummy" . " MSwitch_Condition_Time:0,1" . " MSwitch_Selftrigger_always:0,1" . " MSwitch_RandomTime" . " MSwitch_RandomNumber" . " MSwitch_Safemode:0,1" . " MSwitch_Startdelay:0,10,20,30,60,90,120" . " MSwitch_Wait" . " MSwitch_Event_Id_Distributor:textField-long " . " MSwitch_Sequenz:textField-long " . " MSwitch_Sequenz_time" . " MSwitch_setList:textField-long " . " setList:textField-long " . " readingList:textField-long " . " MSwitch_Eventhistory:0,1,2,3,4,5,10,20,30,40,50,60,70,80,90,100,150,200" . " textField-long " . $readingFnAttributes; setDevAttrList( $name, $attrdefinelist ); $hash->{NOTIFYDEV} = 'no_trigger'; $attr{$name}{MSwitch_Eventhistory} = '0'; $attr{$name}{MSwitch_Safemode} = '1'; $attr{$name}{MSwitch_Help} = '0'; $attr{$name}{MSwitch_Debug} = '0'; $attr{$name}{MSwitch_Expert} = '0'; $attr{$name}{MSwitch_Delete_Delays} = '1'; $attr{$name}{MSwitch_Include_Devicecmds} = '1'; $attr{$name}{MSwitch_Include_Webcmds} = '0'; $attr{$name}{MSwitch_Include_MSwitchcmds} = '0'; $attr{$name}{MSwitch_Lock_Quickedit} = '1'; $attr{$name}{MSwitch_Extensions} = '0'; $attr{$name}{room} = $oldroom if $oldroom ne "undef"; $attr{$name}{MSwitch_Mode} = $startmode; $attr{$name}{MSwitch_Ignore_Types} = join( " ", @doignore ); fhem("attr $name MSwitch_Inforoom $oldinforoom") if $oldinforoom ne "undef"; return; } my $client_hash = $hash->{CL}; $hash->{helper}{tmp}{reset}="on"; return; } ############################## if ( $cmd eq 'del_delays' ) { # löschen aller delays MSwitch_Delete_Delay( $hash, $name ); MSwitch_Createtimer($hash); return; } ############################## if ( $cmd eq 'del_repeats' ) { my $inhalt = $hash->{helper}{repeats}; foreach my $a ( sort keys %{$inhalt} ) { my $key = $hash->{helper}{repeats}{$a}; RemoveInternalTimer($key); } delete( $hash->{helper}{repeats} ); return; # MSwitch_Delete_Delay( $hash, $name ); } ############################## if ( $cmd eq 'inactive' ) { # setze device auf inaktiv readingsSingleUpdate( $hash, "state", 'inactive', 1 ); return; } ############################## if ( $cmd eq 'active' ) { # setze device auf aktiv readingsSingleUpdate( $hash, "state", 'active', 1 ); return; } ############################## if ( $cmd eq 'change_renamed' ) { my $changestring = $args[0] . "#" . $args[1]; MSwitch_confchange( $hash, $changestring ); return; } ################################## if ( $cmd eq 'reset_cmd_count' ) { if ( $args[0] eq "1" ) { readingsSingleUpdate( $hash, "EVT_CMD1_COUNT", 0, 1 ); } if ( $args[0] eq "2" ) { readingsSingleUpdate( $hash, "EVT_CMD2_COUNT", 0, 1 ); } if ( $args[0] eq "all" ) { readingsSingleUpdate( $hash, "EVT_CMD1_COUNT", 0, 1 ); readingsSingleUpdate( $hash, "EVT_CMD2_COUNT", 0, 1 ); } return; } ####################################### if ( $cmd eq 'reload_timer' ) { MSwitch_Clear_timer($hash); MSwitch_Createtimer($hash); return; } ####################################### if ( $cmd eq 'Writesequenz' ) { MSwitch_Writesequenz($hash); return; } ####################################### if ( $cmd eq 'VUpdate' ) { MSwitch_VUpdate($hash); return; } ####################################### if ( $cmd eq 'confchange' ) { MSwitch_confchange( $hash, $args[0] ); return; } ################################### if ( $cmd eq 'clearlog' ) { MSwitch_clearlog($hash); return; } ################################### if ( $cmd eq 'deletesinglelog' ) { my $ret = MSwitch_delete_singlelog( $hash, $args[0] ); return ; } ############################## if ( $cmd eq 'wait' ) { readingsSingleUpdate( $hash, "waiting", ( time + $args[0] ),$showevents ); return; } ############################### if ( $cmd eq 'sort_device' ) { readingsSingleUpdate( $hash, ".sortby", $args[0], 0 ); return; } if ( $cmd eq 'fakeevent' ) { # fakeevent abarbeiten MSwitch_Check_Event( $hash, $args[0] ); return; } ############################## if ( $cmd eq 'exec_cmd_1' ) { if ( $args[0] eq 'ID' ) { $execids = $args[1]; $args[0] = 'ID'; } if ( $args[0] eq "" ) { MSwitch_Exec_Notif( $hash, 'on', 'nocheck', '', 0 ); return; } if ( $args[0] ne 'ID' || $args[0] ne '' ) { if ( $args[1] !~ m/\d/ ) { Log3($name,1,"error at id call $args[1]: format must be exec_cmd_1 " ); return; } } # cmd1 abarbeiten MSwitch_Exec_Notif( $hash, 'on', 'nocheck', '', $execids ); return; } ############################## if ( $cmd eq 'exec_cmd_2' ) { if ( $args[0] eq 'ID' ) { $execids = $args[1]; $args[0] = 'ID'; } if ( $args[0] eq "" ) { MSwitch_Exec_Notif( $hash, 'off', 'nocheck', '', 0 ); return; } if ( $args[0] ne '' || $args[0] ne "ID" ) { if ( $args[1] !~ m/\d/ ) { Log3($name,1,"error at id call $args[1]: format must be exec_cmd_2 "); return; } } # cmd2 abarbeiten MSwitch_Exec_Notif( $hash, 'off', 'nocheck', '', $execids ); return; } ############################## if ( $cmd eq 'backup_MSwitch' ) { # backup erstellen MSwitch_backup($hash); return; } ############################## if ( $cmd eq 'saveconfig' ) { # configfile speichern $args[0] =~ s/\[s\]/ /g; MSwitch_saveconf( $hash, $args[0] ); return; } ############################## if ( $cmd eq 'savesys' ) { # sysfile speichern MSwitch_savesys( $hash, $args[0] ); return; } ############################## if ( $cmd eq "delcmds" ) { delete( $hash->{helper}{devicecmds1} ); delete( $hash->{helper}{last_devicecmd_save} ); return; } ############################## if ( $cmd eq "del_function_data" ) { delete( $hash->{helper}{eventhistory} ); fhem("deletereading $name DIFFERENCE"); fhem("deletereading $name TENDENCY"); fhem("deletereading $name AVERAGE"); return; } ############################## if ( $cmd eq "addevent" ) { delete( $hash->{helper}{config} ); # event manuell zufügen my $devName = ReadingsVal( $name, 'Trigger_device', '' ); $args[0] =~ s/\[sp\]/ /g; my @newevents = split( /,/, $args[0] ); if ( ReadingsVal( $name, 'Trigger_device', '' ) eq "all_events" ) { foreach (@newevents) { $hash->{helper}{events}{all_events}{$_} = "on"; } } else { foreach (@newevents) { $hash->{helper}{events}{$devName}{$_} = "on"; } } my $events = ''; my $eventhash = $hash->{helper}{events}{$devName}; foreach my $name ( keys %{$eventhash} ) { $events = $events . $name . '#[tr]'; } chop($events); chop($events); chop($events); chop($events); chop($events); readingsSingleUpdate( $hash, ".Device_Events", $events, 0 ); return; } ############################## if ( $cmd eq "add_device" ) { delete( $hash->{helper}{config} ); #add device MSwitch_Add_Device( $hash, $args[0] ); return; } ############################## if ( $cmd eq "del_device" ) { #del device MSwitch_Del_Device( $hash, $args[0] ); return; } ############################## if ( $cmd eq "del_trigger" ) { #lösche trigger MSwitch_Delete_Triggermemory($hash); return; } ############################## if ( $cmd eq "filter_trigger" ) { #filter to trigger MSwitch_Filter_Trigger($hash); return; } ############################## if ( $cmd eq "set_trigger" ) { delete( $hash->{helper}{config} ); delete( $hash->{helper}{wrongtimespeccond} ); chop( $args[1], $args[2], $args[3], $args[4], $args[5], $args[6] ); my $triggertime = 'on' . $args[1] . '~off' . $args[2] . '~ononly' . $args[3] . '~offonly' . $args[4] . '~onoffonly' . $args[5]; my $oldtrigger = ReadingsVal( $name, 'Trigger_device', '' ); readingsSingleUpdate( $hash, "Trigger_device", $args[0], '1' ); readingsSingleUpdate( $hash, ".Trigger_condition", $args[6], 0 ); if ( !defined $args[7] ) { readingsDelete( $hash, '.Trigger_Whitelist' ); } else { readingsSingleUpdate( $hash, ".Trigger_Whitelist", $args[7], 0 ); } my $testtrig = ReadingsVal( $name, 'Trigger_device', '' ); if ( $oldtrigger ne $args[0] ) { MSwitch_Delete_Triggermemory($hash); # lösche alle events } if ( $args[1] ne '' || $args[2] ne '' || $args[3] ne '' || $args[4] ne '' || $args[5] ne '' ) { readingsSingleUpdate( $hash, ".Trigger_time", $triggertime, 0 ); MSwitch_Createtimer($hash); } else { readingsSingleUpdate( $hash, ".Trigger_time", '', 0 ); MSwitch_Clear_timer($hash); } $hash->{helper}{events}{ $args[0] }{'no_trigger'} = "on"; if ( $args[0] ne 'no_trigger' ) { if ( $args[0] eq "all_events" ) { delete( $hash->{NOTIFYDEV} ); if ( ReadingsVal( $name, '.Trigger_Whitelist', '' ) ne '' ) { $hash->{NOTIFYDEV} = ReadingsVal( $name, '.Trigger_Whitelist', '' ); } } else { if ( $args[0] ne "MSwitch_Self" ) { $hash->{NOTIFYDEV} = $args[0]; my $devices = MSwitch_makeAffected($hash); $hash->{DEF} = $args[0] . ' # ' . $devices; } else { $hash->{NOTIFYDEV} = $name; my $devices = MSwitch_makeAffected($hash); $hash->{DEF} = $name . ' # ' . $devices; } } } else { $hash->{NOTIFYDEV} = 'no_trigger'; delete $hash->{DEF}; } return; } ############################## if ( $cmd eq "trigger" ) { delete( $hash->{helper}{config} ); # setze trigger events my $triggeron = ''; my $triggeroff = ''; my $triggercmdon = ''; my $triggercmdoff = ''; $args[0] =~ s/~/ /g; $args[1] =~ s/~/ /g; $args[2] =~ s/~/ /g; $args[3] =~ s/~/ /g; $args[4] =~ s/~/ /g; if ( !defined $args[1] ) { $args[1] = "" } if ( !defined $args[3] ) { $args[3] = "" } $triggeron = $args[0]; $triggeroff = $args[1]; if ( !defined $args[3] ) { $args[3] = "" } if ( !defined $args[4] ) { $args[4] = "" } $triggercmdon = $args[3]; $triggercmdoff = $args[4]; readingsBeginUpdate($hash); readingsBulkUpdate( $hash, ".Trigger_on", $triggeron ); readingsBulkUpdate( $hash, ".Trigger_off", $triggeroff ); if ( $args[2] eq 'nein' ) { readingsBulkUpdate( $hash, "Trigger_log", 'off' ); } if ( $args[2] eq 'ja' ) { readingsBulkUpdate( $hash, "Trigger_log", 'on' ); } readingsBulkUpdate( $hash, ".Trigger_cmd_on", $triggercmdon ); readingsBulkUpdate( $hash, ".Trigger_cmd_off", $triggercmdoff ); readingsEndUpdate( $hash, 0 ); return if $hash->{INIT} ne 'define'; my $definition = $hash->{DEF}; $definition =~ s/\n/#[nl]/g; $definition =~ m/(\(.+?\))(.*)/; my $part1 = $1; my $part2 = $2; my $device = ReadingsVal( $name, 'Trigger_device', '' ); my $newtrigger = "([" . $device . ":" . $args[3] . "])" . $part2; $newtrigger =~ s/#\[nl\]/\n/g; $hash->{DEF} = $newtrigger; fhem( "modify $name " . $newtrigger ); return; } ############################## if ( $cmd eq "devices" ) { delete( $hash->{helper}{config} ); # setze devices my $devices = $args[0]; if ( $devices eq 'null' ) { readingsSingleUpdate( $hash, ".Device_Affected", 'no_device', 0 ); return; } my @olddevices = split( /,/, ReadingsVal( $name, '.Device_Affected', 'no_device' ) ); my @devices = split( /,/, $args[0] ); my $addolddevice = ''; foreach (@devices) { my $testdev = $_; LOOP6: foreach my $olddev (@olddevices) { my $oldcmd = ''; my $oldname = ''; ( $oldname, $oldcmd ) = split( /-AbsCmd/, $olddev ); if ( !defined $oldcmd ) { $oldcmd = '' } if ( $oldcmd eq '1' ) { next LOOP6 } if ( $oldname eq $testdev ) { $addolddevice = $addolddevice . $olddev . ','; } } $_ = $_ . '-AbsCmd1'; } chop($addolddevice); $devices = join( ',', @devices ) . ',' . $addolddevice; my @sortdevices = split( /,/, $devices ); @sortdevices = sort @sortdevices; $devices = join( ',', @sortdevices ); readingsSingleUpdate( $hash, ".Device_Affected", $devices, 0 ); $devices = MSwitch_makeAffected($hash); if ( defined $hash->{DEF} ) { my $devhash = $hash->{DEF}; my @dev = split( /#/, $devhash ); $hash->{DEF} = $dev[0] . ' # ' . $devices; } else { $hash->{DEF} = ' # ' . $devices; } return; } ############################## if ( $cmd eq "details" ) { delete( $hash->{helper}{config} ); # setze devices details $args[0] = urlDecode( $args[0] ); $args[0] =~ s/#\[pr\]/%/g; #devicehasch my %devhash = split( /#\[DN\]/, $args[0] ); my @devices = split( /,/, ReadingsVal( $name, '.Device_Affected', '' ) ); my @inputcmds = split( /#\[ND\]/, $args[0] ); my $error = ''; my $key = ''; my $savedetails = ''; my $devicecmd = ''; LOOP10: foreach (@devices) { my @devicecmds = split( /#\[NF\]/, $devhash{$_} ); if ( $_ eq "FreeCmd-AbsCmd1" ) { $devicecmd = $devicecmds[2]; } $savedetails = $savedetails . $_ . '#[NF]'; $savedetails = $savedetails . $devicecmds[0] . '#[NF]'; $savedetails = $savedetails . $devicecmds[1] . '#[NF]'; $savedetails = $savedetails . $devicecmds[2] . '#[NF]'; $savedetails = $savedetails . $devicecmds[3] . '#[NF]'; $savedetails = $savedetails . $devicecmds[4] . '#[NF]'; $savedetails = $savedetails . $devicecmds[5] . '#[NF]'; $savedetails = $savedetails . $devicecmds[7] . '#[NF]'; $savedetails = $savedetails . $devicecmds[6] . '#[NF]'; if ( defined $devicecmds[8] ) { $savedetails = $savedetails . $devicecmds[8] . '#[NF]'; } else { $savedetails = $savedetails . '' . '#[NF]'; } if ( defined $devicecmds[9] ) { $savedetails = $savedetails . $devicecmds[9] . '#[NF]'; } else { $savedetails = $savedetails . '' . '#[NF]'; } if ( defined $devicecmds[10] ) { $savedetails = $savedetails . $devicecmds[10] . '#[NF]'; } else { $savedetails = $savedetails . '' . '#[NF]'; } if ( defined $devicecmds[11] ) { $savedetails = $savedetails . $devicecmds[11] . '#[NF]'; } else { $savedetails = $savedetails . '' . '#[NF]'; } # priority if ( defined $devicecmds[12] && $devicecmds[12] ne 'undefined' ) { $savedetails = $savedetails . $devicecmds[12] . '#[NF]'; } else { $savedetails = $savedetails . '1' . '#[NF]'; } # id if ( defined $devicecmds[13] && $devicecmds[13] ne 'undefined' ) { $savedetails = $savedetails . $devicecmds[13] . '#[NF]'; } else { $savedetails = $savedetails . '0' . '#[NF]'; } # comment if ( defined $devicecmds[14] && $devicecmds[14] ne 'undefined' ) { $savedetails = $savedetails . $devicecmds[14] . '#[NF]'; } else { $savedetails = $savedetails . '' . '#[NF]'; } # exit1 if ( defined $devicecmds[15] && $devicecmds[15] ne 'undefined' ) { $savedetails = $savedetails . $devicecmds[15] . '#[NF]'; } else { $savedetails = $savedetails . '0' . '#[NF]'; } # exit2 if ( defined $devicecmds[16] && $devicecmds[16] ne 'undefined' ) { $savedetails = $savedetails . $devicecmds[16] . '#[NF]'; } else { $savedetails = $savedetails . '0' . '#[NF]'; } # show if ( defined $devicecmds[17] && $devicecmds[17] ne 'undefined' ) { $savedetails = $savedetails . $devicecmds[17] . '#[NF]'; } else { $savedetails = $savedetails . '1' . '#[NF]'; } # show if ( defined $devicecmds[18] && $devicecmds[18] ne 'undefined' ) { $savedetails = $savedetails . $devicecmds[18] . '#[ND]'; } else { $savedetails = $savedetails . '0' . '#[ND]'; } # $counter++; } chop($savedetails); chop($savedetails); chop($savedetails); chop($savedetails); chop($savedetails); # ersetzung sonderzeichen etc mscode # auskommentierte wurden bereits dur jscript ersetzt $savedetails =~ s/\n/#[nl]/g; $savedetails =~ s/\t/ /g; $savedetails =~ s/ /#[sp]/g; $savedetails =~ s/\\/#[bs]/g; $savedetails =~ s/,/#[ko]/g; $savedetails =~ s/^#\[/#[eo]/g; $savedetails =~ s/^#\]/#[ec]/g; $savedetails =~ s/\|/#[wa]/g; $savedetails =~ s/\|/#[ti]/g; readingsSingleUpdate( $hash, ".Device_Affected_Details", $savedetails,0 ); return if $hash->{INIT} ne 'define'; my $definition = $hash->{DEF}; $definition =~ m/(\(.+?\))(.*)/; my $part1 = $1; my $part2 = $2; $devicecmd =~ s/#\[sp\]/ /g; $devicecmd =~ s/#\[nl\]/\\n/g; $devicecmd =~ s/#\[se\]/;/g; $devicecmd =~ s/#\[dp\]/:/g; $devicecmd =~ s/#\[st\]/\\'/g; $devicecmd =~ s/#\[dst\]/\"/g; $devicecmd =~ s/#\[tab\]/ /g; $devicecmd =~ s/#\[ko\]/,/g; $devicecmd =~ s/#\[wa\]/|/g; $devicecmd =~ s/#\[bs\]/\\\\/g; my $newdef = $part1 . " ($devicecmd)"; $hash->{DEF} = $newdef; fhem( "modify $name " . $newdef ); return; } ################################## my $update = ''; # unbedingt überarbeiten !!! my @testdetails =qw(_on _off _onarg _offarg _playback _record _timeon _timeoff _conditionon _conditionoff); my @testdetailsstandart =( 'no_action', 'no_action', '', '', 'nein', 'nein', 0, 0, '', '' ); ################################## #neu ausführung on/off if ( $cmd eq "off" || $cmd eq "on" ) { if ( $devicemode eq "Dummy" && AttrVal( $name, "MSwitch_Selftrigger_always", 0 ) eq "0" ) { readingsSingleUpdate( $hash, "state", $cmd, 1 ); return; } if ( $devicemode eq "Dummy" ) { if ($cmd eq "on" && ReadingsVal( $name, '.Trigger_cmd_on', 'no_trigger' ) eq "no_trigger") { readingsSingleUpdate( $hash, "state", $cmd, 1 ); return; } if ($cmd eq "off" && ReadingsVal( $name, '.Trigger_cmd_off', 'no_trigger' ) eq "no_trigger") { readingsSingleUpdate( $hash, "state", $cmd, 1 ); return; } } ################################################### ### neu if ( $delaymode eq '1' ) { MSwitch_Delete_Delay( $hash, $name ); } ############ if ( $ic ne 'fromnotify' && $ic ne 'fromtimer' ) { readingsSingleUpdate( $hash, "last_activation_by", 'manual',$showevents ); } delete( $hash->{IncommingHandle} ); # ausführen des off befehls my $zweig = 'nicht definiert'; $zweig = "cmd1" if $cmd eq "on"; $zweig = "cmd2" if $cmd eq "off"; my $exittest = ''; $exittest = "1" if $cmd eq "on"; $exittest = "2" if $cmd eq "off"; my $ekey = ''; my $out = '0'; MSwitch_Safemode($hash); MSwitch_LOG( $name, 6, "On/Off Kommando gefunden -> $cmd " . __LINE__ ); my @cmdpool; my %devicedetails = MSwitch_makeCmdHash($name); my @devices =split( /,/, ReadingsVal( $name, '.Device_Affected', '' ) ); # liste anpassen ( reihenfolge ) wenn expert = 1 @devices = MSwitch_priority( $hash, $execids, @devices ); my $expertmode = AttrVal( $name, 'MSwitch_Expert', "0" ); my $randomtime = AttrVal( $name, 'MSwitch_RandomTime', '' ); LOOP1: foreach my $device (@devices) { $out = '0'; if ( $expertmode eq '1' ) { $ekey = $device . "_exit" . $exittest; $out = $devicedetails{$ekey}; } MSwitch_LOG($name,6, "Angesprochener Befehlszweig: ". $zweig. " " . __LINE__ ); MSwitch_LOG($name,6, "Angesprochenes Device: ". $device . " " . __LINE__ ); # teste auf on kommando next LOOP1 if $device eq "no_device"; my @devicesplit = split( /-AbsCmd/, $device ); my $devicenamet = $devicesplit[0]; my $count = 0; foreach my $testset (@testdetails) { if ( !defined( $devicedetails{ $device . $testset } ) ) { my $key = ''; $key = $device . $testset; $devicedetails{$key} = $testdetailsstandart[$count]; } $count++; } # teste auf delayinhalt ########################################################### my $key = $device . "_" . $cmd; my $timerkey = $device . "_time" . $cmd; if ( $devicedetails{$timerkey} =~ m/{.*}/ ) { $devicedetails{$timerkey} = eval $devicedetails{$timerkey}; } if ( $devicedetails{$timerkey} =~ m/\[.*:.*\]/ ) { $devicedetails{$timerkey} = eval MSwitch_Checkcond_state( $devicedetails{$timerkey},$name ); } if ( $devicedetails{$timerkey} =~ m/[\d]{2}:[\d]{2}:[\d]{2}/ ) { my $hdel =( substr( $devicedetails{$timerkey}, 0, 2 ) ) * 3600; my $mdel =( substr( $devicedetails{$timerkey}, 3, 2 ) ) * 60; my $sdel =( substr( $devicedetails{$timerkey}, 6, 2 ) ) * 1; $devicedetails{$timerkey} = $hdel + $mdel + $sdel; } elsif( $devicedetails{$timerkey} =~ m/^\d*\.?\d*$/ ) { $devicedetails{$timerkey} = $devicedetails{$timerkey} ; } else { MSwitch_LOG($name,6, "ERROR im Timerformat: ". $devicedetails{$timerkey} . " " . __LINE__ ); $devicedetails{$timerkey} = 0; } MSwitch_LOG( $name,6, "Timerstatus (Befehlsverzögerung) -> ". $devicedetails{$timerkey}." " . __LINE__ ); # suche befehl if ( $devicedetails{$key} ne ""&& $devicedetails{$key} ne "no_action" ) #befehl gefunden { my $cs = ''; $cs ="set $devicenamet $devicedetails{$device.'_off'} $devicedetails{$device.'_offarg'}" if $cmd eq "off"; $cs ="set $devicenamet $devicedetails{$device.'_on'} $devicedetails{$device.'_onarg'}" if $cmd eq "on"; if ( $devicenamet eq 'FreeCmd' ) { $cs = "$devicedetails{$device.'_'.$cmd.'arg'}"; $cs = MSwitch_makefreecmd( $hash, $cs ); } MSwitch_LOG( $name, 6, "Befehl gefunden: -> " . $cs ." " . __LINE__ ); MSwitch_LOG( $name, 6,"Teste auf Verzögerung -> " . $devicedetails{$timerkey}." " . __LINE__ ); my $conditionkey = $device . "_condition" . $cmd; if ( $devicedetails{$timerkey} eq "0" || $devicedetails{$timerkey} eq "" ) { # $conditionkey = $device . "_conditionoff"; MSwitch_LOG( $name, 6,"Teste auf Schaltbedingung; ". $devicedetails{$conditionkey}. " " . __LINE__ ) if $devicedetails{$conditionkey} ne ''; MSwitch_LOG( $name, 6,"Schaltbedingung nicht vorhanden:" . $devicedetails{$conditionkey} . " " . __LINE__ ) if $devicedetails{$conditionkey} eq ''; my $execute = "true"; $execute = MSwitch_checkcondition( $devicedetails{$conditionkey},$name, $args[0] ) if $devicedetails{$conditionkey} ne ''; MSwitch_LOG( $name, 6,"Schaltbedingung Ergebniss: " . $execute . " " . __LINE__ ); if ( $execute eq 'true' ) { $cs =~ s/\$NAME/$hash->{helper}{eventfrom}/; $cs =~ s/\$SELF/$name/; MSwitch_LOG( $name, 6,"Befehl in Comand-Pool geschrieben ->" . $cs ." " . __LINE__); push @cmdpool, $cs . '|' . $device; $update = $device . ',' . $update; if ( $out eq '1' ) { MSwitch_LOG( $name, 6,"Abbruchbefehl erhalten von ". $device ." " . __LINE__); last LOOP1; } } } else { MSwitch_LOG( $name, 6,"Teste auf Schaltbedingungen -> keine vorhanden" ." " . __LINE__ ); if ($randomtime ne ''&& $devicedetails{$timerkey} eq '[random]' ) { MSwitch_LOG($name,6,"Zfallstimer gefunden -> ". $devicedetails{$timerkey} ." " . __LINE__); $devicedetails{$timerkey} = MSwitch_Execute_randomtimer($hash); # ersetzt $devicedetails{$timerkey} gegen randomtimer MSwitch_LOG($name,6,"Zufallstimer ersetzt durch: -> ". $devicedetails{$timerkey} ." " . __LINE__); } elsif ( $randomtime eq '' && $devicedetails{$timerkey} eq '[random]' ) { MSwitch_LOG($name, 6,"Zufallstimer gefunden aber Attribut nicht gesetzt -> 0" ." " . __LINE__); $devicedetails{$timerkey} = 0; } # ? my $execute = "true"; # conditiontest nur dann, wenn cond-test nicht nur nach verzögerung if ( $devicedetails{ $device . "_delayat" . $cmd } ne "delay2" && $devicedetails{ $device . "_delayat" . $cmd } ne "at02" ) { MSwitch_LOG($name,6,"Schaltbedingung für verzögerten Befehl gefunden -> ". $devicedetails{ $device . "_delayat" . $cmd } ." " . __LINE__); $execute = MSwitch_checkcondition( $devicedetails{$conditionkey}, $name, $args[0] ); MSwitch_LOG($name,6,"Prüfung für verzögerte Schaltbedingung-> ". $execute ." " . __LINE__); } MSwitch_LOG($name,6, "Verzögerung -> ". $devicedetails{$timerkey} ." " . __LINE__); if ( $execute eq 'true' ) { MSwitch_LOG( $name, 6,"Schaltbedingung erfüllt - Befehl mt at/delay wird ausgefuehrt -> ". $cs ." " . __LINE__ ); my $delaykey = $device . "_delayat" . $cmd; my $delayinhalt = $devicedetails{$delaykey}; my $delaykey1 = $device . "_delayat" . $cmd . "org"; my $teststateorg = $devicedetails{$delaykey1}; if ( $delayinhalt eq 'at0' || $delayinhalt eq 'at1' ) { MSwitch_LOG( $name, 6,"Verzögerung mit at erkannt -> ". $devicedetails{$timerkey} ." " . __LINE__ ); $devicedetails{$timerkey} = MSwitch_replace_delay( $hash, $teststateorg ); MSwitch_LOG( $name, 6,"Verzögerung ersetzt durch: -> ". $devicedetails{$timerkey} ." " . __LINE__ ); } if ( $delayinhalt eq 'at1' || $delayinhalt eq 'delay0' ) { MSwitch_LOG( $name, 6,"Verzögerung ohne zusatzprüfung erkannt -> ". $delayinhalt ); $conditionkey = 'nocheck'; MSwitch_LOG( $name, 6,"Bedingung ersetzt ersetzt -> ". $conditionkey ." " . __LINE__); } my $timecond = gettimeofday() + $devicedetails{$timerkey}; my $msg = $cs . "#[tr]" . $name . "#[tr]" . $conditionkey . "#[tr]#[tr]" . $timecond . "#[tr]" . $device; # variabelersetzung $msg =~ s/\$NAME/$hash->{helper}{eventfrom}/; $msg =~ s/\$SELF/$name/; $msg = MSwitch_check_setmagic_i( $hash, $msg ); $hash->{helper}{delays}{$msg} = $timecond; InternalTimer( $timecond, "MSwitch_Restartcmd", $msg ); MSwitch_LOG($name,5,"$name: verzoegerte befehl gesetzt -> ". $timecond . " : ". $msg); if ( $out eq '1' ) { MSwitch_LOG( $name, 6,"Abbruchbefehl erhalten von ". $device ." " . __LINE__); last LOOP1; } } } } } if ( $devicemode ne "Notify" ) { readingsSingleUpdate( $hash, "state", $cmd, 1 ); } else { # readingsSingleUpdate( $hash, "state", 'active', $showevents ); } my $anzahl = @cmdpool; MSwitch_LOG( $name, 6,"Anzahl der auszufuehrenden befehle -> " . $anzahl ." " . __LINE__); MSwitch_LOG( $name, 6, "Übergabe an Execute erfolgt" ." " . __LINE__) if $anzahl > 0; MSwitch_Cmd( $hash, @cmdpool ) if $anzahl > 0; return; } return; } ################################### sub MSwitch_Cmd(@) { my ( $hash, @cmdpool ) = @_; my $Name = $hash->{NAME}; my $lastdevice; my $showevents = AttrVal( $Name, "MSwitch_generate_Events", 1 ); my %devicedetails = MSwitch_makeCmdHash($Name); foreach my $cmds (@cmdpool) { MSwitch_LOG( $Name, 6, "Befehlsausführung -> " . $cmds ." " . __LINE__ ); my @cut = split( /\|/, $cmds ); $cmds = $cut[0]; #ersetze platzhakter vor ausführung my $device = $cut[1]; $lastdevice = $device; my $toggle = ''; if ( $cmds =~ m/set (.*)(MSwitchtoggle)(.*)/ ) { MSwitch_LOG( $Name, 6, "Togglemode erkannt -> " . $cmds ." " . __LINE__ ); $toggle = $cmds; $cmds = MSwitch_toggle( $hash, $cmds ); } if ( AttrVal( $Name, 'MSwitch_Expert', "0" ) eq '1' && $devicedetails{ $device . '_repeatcount' } ne '' ) { MSwitch_LOG($Name,6, "teste auf Befehlswiederholungen -> " . $devicedetails{ $device . '_repeatcount' } ." " . __LINE__); my $x = 0; while ( $devicedetails{ $device . '_repeatcount' } =~ m/\[(.*)\:(.*)\]/ ) { $x++; # exit last if $x > 20; # exitg my $setmagic = ReadingsVal( $1, $2, 0 ); $devicedetails{ $device . '_repeatcount' } = $setmagic; } MSwitch_LOG($Name,6,"Befehlswiederholungen nach SETMAGICersetzung -> " . $devicedetails{ $device . '_repeatcount' } ." " . __LINE__ ); } if ( AttrVal( $Name, 'MSwitch_Expert', "0" ) eq '1' && $devicedetails{ $device . '_repeattime' } ne '' ) { MSwitch_LOG($Name, 6,"Teste auf Wiederholungsintervall -> ". $devicedetails{ $device . '_repeattime' } ." " . __LINE__); my $x = 0; while ($devicedetails{ $device . '_repeattime' } =~ m/\[(.*)\:(.*)\]/ ) { $x++; # exit last if $x > 20; # exitg my $setmagic = ReadingsVal( $1, $2, 0 ); $devicedetails{ $device . '_repeattime' } = $setmagic; } MSwitch_LOG($Name,6,"Wiederholungsintervall nach SETMAGIcersetzung -> ". $devicedetails{ $device . '_repeattime' } ." " . __LINE__ ); } if ( AttrVal( $Name, 'MSwitch_Expert', "0" ) eq '1' && $devicedetails{ $device . '_repeatcount' } > 0 && $devicedetails{ $device . '_repeattime' } > 0 ) { my $i; for ( $i = 1 ;$i <= $devicedetails{ $device . '_repeatcount' };$i++ ) { my $msg = $cmds . "|" . $Name; if ( $toggle ne '' ) { $msg = $toggle . "|" . $Name; } my $timecond = gettimeofday() +( ( $i + 1 ) * $devicedetails{ $device . '_repeattime' } ); $msg = $msg . "|" . $timecond; $hash->{helper}{repeats}{$timecond} = "$msg"; MSwitch_LOG($Name,6,"gesetzte Wiederholung -> ". $timecond . " : ". $msg ." " . __LINE__); InternalTimer( $timecond, "MSwitch_repeat", $msg ); } } my $todec = $cmds; $cmds = MSwitch_dec( $hash, $todec ); MSwitch_LOG( $Name, 6, "Comand nach decodierung -> " . $cmds ." " . __LINE__); ############################ # debug2 mode , kein execute if ( AttrVal( $Name, 'MSwitch_Debug', "0" ) eq '2' ) { MSwitch_LOG( $Name, 6, "Comand ausgeführt -> " . $cmds ." " . __LINE__); } else { if ( $cmds =~ m/{.*}/ ) { MSwitch_LOG( $Name, 6,"Comand als Perlcode ausgeführt -> " . $cmds ." " . __LINE__ ); if ($debugging eq "1") { MSwitch_LOG( "Debug", 0,"eveal line" . __LINE__ ); } my $out = eval($cmds); if ($@) { MSwitch_LOG( $Name, 6,"MSwitch_Set: ERROR $cmds: $@ " . __LINE__ ); } } else { MSwitch_LOG( $Name, 6,"Comand als Fhemcode ausgeführt -> " . $cmds ); my $errors = AnalyzeCommandChain( undef, $cmds ); if ( defined($errors) and $errors ne "OK" ) { MSwitch_LOG( $Name, 6, "MSwitch_Set: ERROR $cmds: $errors " . __LINE__ ); } } } ############################# } my $showpool = join( ',', @cmdpool ); if ( length($showpool) > 100 ) { $showpool = substr( $showpool, 0, 100 ) . '....'; } readingsSingleUpdate( $hash, "last_exec_cmd", $showpool, $showevents ) if $showpool ne ''; if ( AttrVal( $Name, 'MSwitch_Expert', '0' ) eq "1" ) { readingsSingleUpdate( $hash, "last_cmd", $hash->{helper}{priorityids}{$lastdevice}, $showevents ); } } #################### sub MSwitch_toggle($$) { my @cmds; my $anzcmds; my @muster; my $anzmuster; my $reading ='state'; my ( $hash, $cmds ) = @_; my $Name = $hash->{NAME}; $cmds =~ m/(set) (.*)( )MSwitchtoggle (.*)/; my $newcomand = $1 . " " . $2 . " " ; my @togglepart = split( /:/, $4 ); if($togglepart[0]) { $togglepart[0] =~ s/\[//g; $togglepart[0] =~ s/\]//g; @cmds = split( /,/, $togglepart[0] ); $anzcmds = @cmds; } if($togglepart[1]) { $togglepart[1] =~ s/\[//g; $togglepart[1] =~ s/\]//g; @muster = split( /,/, $togglepart[1] ); $anzmuster = @cmds; } else{ @muster = @cmds; $anzmuster = $anzcmds; } if($togglepart[2]) { $togglepart[2] =~ s/\[//g; $togglepart[2] =~ s/\]//g; $reading = $togglepart[2]; } my $aktstate = ReadingsVal( $2, $reading, 'undef' ); my $foundmuster; for ( my $i = 0 ; $i < $anzmuster ; $i++ ) { if ($muster[$i] eq $aktstate) { $foundmuster=$i; last; } } my $nextpos=0; if (defined $cmds[$foundmuster+1]) { $nextpos=$foundmuster+1 } my $nextcmd=$cmds[$nextpos]; $newcomand=$newcomand.$nextcmd; MSwitch_LOG( $Name, 6, "########## Togglefunktion" ); MSwitch_LOG( $Name, 6, "Befehle: @cmds" ); MSwitch_LOG( $Name, 6, "Befehle anzahl: $anzcmds" ); MSwitch_LOG( $Name, 6, "Suchmuster: @muster" ); MSwitch_LOG( $Name, 6, "Suchmuster Anzahl: $anzmuster" ); MSwitch_LOG( $Name, 6, "betreffendes Reading: $reading" ); MSwitch_LOG( $Name, 6, "aktueller status des Readingd: $aktstate" ); MSwitch_LOG( $Name, 6, "Suchmuster an Position: $foundmuster" ); MSwitch_LOG( $Name, 6, "nächste Position: $nextpos" ); MSwitch_LOG( $Name, 6, "nächste Befehl: $nextcmd" ); MSwitch_LOG( $Name, 6, "Befehlszeile: $newcomand" ); MSwitch_LOG( $Name, 6, "########## Togglefunktion ende return: $newcomand" ); return $newcomand; } ###################################### sub MSwitch_toggleold($$) { my ( $hash, $cmds ) = @_; my $Name = $hash->{NAME}; $cmds =~ m/(set) (.*)( )MSwitchtoggle (.*)/; my @tcmd = split( /\//, $4 ); if ( !defined $tcmd[2] ) { $tcmd[2] = 'state' } if ( !defined $tcmd[3] ) { $tcmd[3] = $tcmd[0] } if ( !defined $tcmd[4] ) { $tcmd[4] = $tcmd[1] } my $cmd1 = $1 . " " . $2 . " " . $tcmd[0]; my $cmd2 = $1 . " " . $2 . " " . $tcmd[1]; my $chk1 = $tcmd[0]; my $chk2 = $tcmd[1]; my $testnew = ReadingsVal( $2, $tcmd[2], 'undef' ); if ( $testnew =~ m/$tcmd[3]/ ) { $cmds = $cmd2; } elsif ( $testnew =~ m/$tcmd[4]/ ) { $cmds = $cmd1; } else { $cmds = $cmd1; } Log3( $Name, 0, "nächste Befehl: $cmds" ); return $cmds; } ############################## sub MSwitch_Log_Event(@) { my ( $hash, $msg, $me ) = @_; my $Name = $hash->{NAME}; my $triggerdevice = ReadingsVal( $Name, 'Trigger_device', 'no_trigger' ); my $re = qr/$triggerdevice/; if ( $triggerdevice eq 'no_trigger' ) { delete( $hash->{helper}{writelog} ); return; } if ( $triggerdevice ne 'Logfile' && $triggerdevice ne 'all_events' && ( $hash->{helper}{writelog} !~ /$re/ ) ) { delete( $hash->{helper}{writelog} ); return; } MSwitch_Check_Event( $hash, $hash ); delete( $hash->{helper}{writelog} ); return; } ############################## sub MSwitch_Attr(@) { my ( $cmd, $name, $aName, $aVal ) = @_; my $hash = $defs{$name}; if ( $aName eq 'MSwitch_Debug' && ( $aVal == 2 || $aVal == 3 ) ) { readingsSingleUpdate( $hash, "Debug", 'Start_Debug', 1 ); } else { delete( $hash->{READINGS}{Debug} ); } if ( $aName eq 'MSwitch_Debug' && ( $aVal == 0 || $aVal == 1 || $aVal == 2 || $aVal == 3 ) ) { delete( $hash->{READINGS}{Bulkfrom} ); delete( $hash->{READINGS}{Device_Affected} ); delete( $hash->{READINGS}{Device_Affected_Details} ); delete( $hash->{READINGS}{Device_Events} ); #fhem("deletereading ".$name." Debug"); } if ( $aName eq 'MSwitch_RandomTime' && $aVal ne '' ) { if ( $aVal !~ m/([0-9]{2}:[0-9]{2}:[0-9]{2}-[0-9]{2}:[0-9]{2}:[0-9]{2})/ ) { return 'wrong syntax !
the syntax must be: HH:MM:SS-HH:MM:SS'; } else { $aVal =~ s/\://g; my @test = split( /-/, $aVal ); if ( $test[0] >= $test[1] ) { return 'fist ' . $test[0] . ' parameter must be lower than second parameter ' . $test[1]; } } return; } if ( $cmd eq "set" && $aName eq "MSwitch_Read_Log" ) { if ( defined($aVal) && $aVal eq "1" ) { $logInform{$name} = sub($$) { my ( $me, $msg ) = @_; return if ( defined( $hash->{helper}{writelog} ) ); $hash->{helper}{writelog} = $msg; MSwitch_Log_Event( $hash, $msg, $me ); } } else { delete( $hash->{helper}{writelog} ); delete $logInform{$name}; } } ################################## if ( $cmd eq 'set' && $aName eq 'MSwitch_Event_Id_Distributor' ) { delete( $hash->{helper}{eventtoid} ); return "Invalid Regex $aVal: $@" if $aVal eq ""; return "Invalid Regex $aVal: $@" if !$aVal; return "Invalid Regex $aVal: $@" if $aVal eq "1"; my @test = split( /\n/, $aVal ); foreach my $testdevices (@test) { if ( $testdevices !~ m/(.*:)?.*:.*=\>cmd(1|2)[\s]ID[\s](\d)(,\d){0,5}$/ ) { return "wrong syntax. The syntax must be: \n\n[DEVICE:]READING:STATE=>cmd<1|2> ID x[,y,z] \n\n[] = optional \n<1|2> = 1 or 2 \nseveral entries are separated by a line break"; } } foreach my $testdevices (@test) { my ( $key, $val ) = split( /=>/, $testdevices ); $hash->{helper}{eventtoid}{$key} = $val; } return; } if ( $cmd eq 'del' && $aName eq 'MSwitch_Event_Id_Distributor' ) { delete( $hash->{helper}{eventtoid} ); return; } ################################### if ( $cmd eq 'set' && $aName eq 'MSwitch_DeleteCMDs' ) { delete( $hash->{helper}{devicecmds1} ); delete( $hash->{helper}{last_devicecmd_save} ); } if ( $cmd eq 'set' && $aName eq 'MSwitch_Reset_EVT_CMD1_COUNT' ) { readingsSingleUpdate( $hash, "EVT_CMD1_COUNT", 0, 1 ); } if ( $cmd eq 'set' && $aName eq 'MSwitch_Reset_EVT_CMD2_COUNT' ) { readingsSingleUpdate( $hash, "EVT_CMD2_COUNT", 0, 1 ); } if ( $cmd eq 'set' && $aName eq 'disable' && $aVal == 1 ) { $hash->{NOTIFYDEV} = 'no_trigger'; MSwitch_Delete_Delay( $hash, 'all' ); MSwitch_Clear_timer($hash); } if ( $cmd eq 'set' && $aName eq 'disable' && $aVal == 0 ) { delete( $hash->{helper}{savemodeblock} ); delete( $hash->{READINGS}{Safemode} ); MSwitch_Createtimer($hash); if ( ReadingsVal( $name, 'Trigger_device', 'no_trigger' ) ne 'no_trigger' and ReadingsVal( $name, 'Trigger_device', 'no_trigger' ) ne "MSwitch_Self") { $hash->{NOTIFYDEV} = ReadingsVal( $name, 'Trigger_device', 'no_trigger' ); } if ( $init_done == 1 and ReadingsVal( $name, 'Trigger_device', 'no_trigger' ) eq "MSwitch_Self") { $hash->{NOTIFYDEV} = $name; } } if ( $aName eq 'MSwitch_Activate_MSwitchcmds' && $aVal == 1 ) { addToAttrList('MSwitchcmd'); } if ( $aName eq 'MSwitch_Debug' && $aVal eq '0' ) { unlink("./log/MSwitch_debug_$name.log"); } if ( defined $aVal && ($aName eq 'MSwitch_Debug' && ($aVal eq '2' || $aVal eq '3' ))) { MSwitch_clearlog($hash); } if ( $cmd eq 'set' && $aName eq 'MSwitch_Inforoom' ) { my $testarg = $aVal; foreach my $testdevices ( keys %{ $modules{MSwitch}{defptr} } ) { $attr{$testdevices}{MSwitch_Inforoom} = $testarg; } } if ( $aName eq 'MSwitch_Mode' && ( $aVal eq 'Full' || $aVal eq 'Toggle' ) ) { delete( $hash->{helper}{config} ); my $cs = "setstate $name ???"; my $errors = AnalyzeCommandChain( undef, $cs ); $hash->{MODEL} = 'Full' if $aVal eq 'Full'; $hash->{MODEL} = 'Toggle' if $aVal eq 'Toggle'; } ############################# if ( $aName eq 'MSwitch_Mode' && ( $aVal eq 'Dummy' ) ) { delete( $hash->{helper}{config} ); MSwitch_Delete_Delay( $hash, 'all' ); MSwitch_Clear_timer($hash); $hash->{NOTIFYDEV} = 'no_trigger'; $hash->{MODEL} = 'Dummy'; fhem("deleteattr $name MSwitch_Include_Webcmds"); fhem("deleteattr $name MSwitch_Include_MSwitchcmds"); fhem("deleteattr $name MSwitch_Include_Devicecmds"); fhem("deleteattr $name MSwitch_Safemode"); #fhem("deleteattr $name MSwitch_Expert"); fhem("deleteattr $name MSwitch_Extensions"); fhem("deleteattr $name MSwitch_Lock_Quickedit"); fhem("deleteattr $name MSwitch_Delete_Delays"); delete( $hash->{NOTIFYDEV} ); delete( $hash->{NTFY_ORDER} ); delete( $hash->{READINGS}{Trigger_device} ); delete( $hash->{IncommingHandle} ); delete( $hash->{READINGS}{EVENT} ); delete( $hash->{READINGS}{EVTFULL} ); delete( $hash->{READINGS}{EVTPART1} ); delete( $hash->{READINGS}{EVTPART2} ); delete( $hash->{READINGS}{EVTPART3} ); delete( $hash->{READINGS}{last_activation_by} ); delete( $hash->{READINGS}{last_event} ); delete( $hash->{READINGS}{last_exec_cmd} ); my $attrzerolist = " disable:0,1" . " MSwitch_Language:EN,DE" . " MSwitch_Debug:0,1" . " disabledForIntervals" . " MSwitch_Expert:0,1" . " stateFormat:textField-long" . " MSwitch_Eventhistory:0,10" . " MSwitch_Delete_Delays:0,1" . " MSwitch_Help:0,1" . " MSwitch_Ignore_Types:textField-long " . " MSwitch_Extensions:0,1" . " MSwitch_Inforoom" . " MSwitch_DeleteCMDs:manually,automatic,nosave" . " MSwitch_Mode:Full,Notify,Toggle,Dummy" . " MSwitch_Selftrigger_always:0,1" . " useSetExtensions:0,1" . " MSwitch_setList:textField-long " . " MSwitch_Event_Id_Distributor:textField-long " . " setList:textField-long " . " readingList:textField-long " . " textField-long "; setDevAttrList($name, $attrzerolist); } if ( $aName eq 'MSwitch_Mode' && $aVal eq 'Notify' ) { $hash->{MODEL} = 'Notify'; my $cs = "setstate $name active"; my $errors = AnalyzeCommandChain( undef, $cs ); if ( defined($errors) ) { MSwitch_LOG( $name, 1,"$name MSwitch_Notify: Fehler bei Befehlsausführung $errors -> Comand: $_ ". __LINE__ ); } } ############# if ( $cmd eq 'del' ) { my $testarg = $aName; my $errors; if ( $testarg eq 'MSwitch_Inforoom' ) { LOOP21: foreach my $testdevices ( keys %{ $modules{MSwitch}{defptr} } ) { if ( $testdevices eq $name ) { next LOOP21; } delete( $attr{$testdevices}{MSwitch_Inforoom} ); } } if ( $testarg eq 'disable' ) { MSwitch_Delete_Delay( $hash, "all" ); MSwitch_Clear_timer($hash); delete( $hash->{helper}{savemodeblock} ); delete( $hash->{READINGS}{Safemode} ); } if ( $testarg eq 'MSwitch_Reset_EVT_CMD1_COUNT' ) { delete( $hash->{READINGS}{EVT_CMD1_COUNT} ); } if ( $testarg eq 'MSwitch_Reset_EVT_CMD2_COUNT' ) { delete( $hash->{READINGS}{EVT_CMD2_COUNT} ); } if ( $testarg eq 'MSwitch_DeleteCMDs' ) { delete( $hash->{helper}{devicecmds1} ); delete( $hash->{helper}{last_devicecmd_save} ); } } return undef; } #################### sub MSwitch_Delete($$) { my ( $hash, $name ) = @_; RemoveInternalTimer($hash); return undef; } #################### sub MSwitch_Undef($$) { my ( $hash, $name ) = @_; RemoveInternalTimer($hash); delete( $modules{MSwitch}{defptr}{$name} ); return undef; } #################### sub MSwitch_Notify($$) { my $testtoggle = ''; my ( $own_hash, $dev_hash ) = @_; my $ownName = $own_hash->{NAME}; # own name / hash my $devName; $devName = $dev_hash->{NAME}; my $events = deviceEvents( $dev_hash, 1 ); ############################ if (exists $own_hash->{helper}{mode} and $own_hash->{helper}{mode} eq "absorb"){ if (time > $own_hash->{helper}{modesince}+600) # time bis wizardreset { delete( $own_hash->{helper}{mode} ); delete( $own_hash->{helper}{modesince} ); delete( $own_hash->{NOTIFYDEV} ); delete( $own_hash->{READINGS} ); readingsBeginUpdate($own_hash); readingsBulkUpdate( $own_hash, ".Device_Events", "no_trigger", 1 ); readingsBulkUpdate( $own_hash, ".Trigger_cmd_off", "no_trigger", 1 ); readingsBulkUpdate( $own_hash, ".Trigger_cmd_on", "no_trigger", 1 ); readingsBulkUpdate( $own_hash, ".Trigger_off", "no_trigger", 1 ); readingsBulkUpdate( $own_hash, ".Trigger_on", "no_trigger", 1 ); readingsBulkUpdate( $own_hash, "Trigger_device", "no_trigger", 1 ); readingsBulkUpdate( $own_hash, "Trigger_log", "off", 1 ); readingsBulkUpdate( $own_hash, "state", "active", 1 ); readingsBulkUpdate( $own_hash, ".V_Check", $vupdate, 1 ); readingsBulkUpdate( $own_hash, ".First_init", 'done' ); readingsEndUpdate( $own_hash, 0 ); return; } return if $devName eq $ownName; my @eventscopy = ( @{$events} ); foreach my $event ( @eventscopy ) { readingsSingleUpdate( $own_hash, "EVENTCONF", $devName.": ".$event, 1 ); } return; } ############################ if ( ReadingsVal( $ownName, '.First_init', 'undef' ) ne 'done' ) { # events blocken wenn datensatz unvollständig return; } # lösche saveddevicecmd # MSwitch_del_savedcmds($own_hash); if ( $own_hash->{helper}{testevent_device}&& $own_hash->{helper}{testevent_device} eq 'Logfile' ) { $devName = 'Logfile'; } my $trigevent = ''; #my $eventset = '0'; my $execids = "0"; my $foundcmd1 = 0; my $foundcmd2 = 0; my $showevents = AttrVal( $ownName, "MSwitch_generate_Events", 1 ); my $evhistory = AttrVal( $ownName, "MSwitch_Eventhistory", 10 ); my $resetcmd1 = AttrVal( $ownName, "MSwitch_Reset_EVT_CMD1_COUNT", 0 ); my $resetcmd2 = AttrVal( $ownName, "MSwitch_Reset_EVT_CMD2_COUNT", 0 ); if ( $resetcmd1 > 0 && ReadingsVal( $ownName, 'EVT_CMD1_COUNT', '0' ) >= $resetcmd1 ) { readingsSingleUpdate( $own_hash, "EVT_CMD1_COUNT", 0, $showevents ); } if ( $resetcmd2 > 0 && ReadingsVal( $ownName, 'EVT_CMD2_COUNT', '0' ) >= $resetcmd1 ) { readingsSingleUpdate( $own_hash, "EVT_CMD2_COUNT", 0, $showevents ); } # nur abfragen für eigenes Notify if ( $init_done && $devName eq "global" && grep( m/^MODIFIED $ownName$/, @{$events} ) ) { # reaktion auf eigenes notify start / define / modify my $timecond = gettimeofday() + 5; InternalTimer( $timecond, "MSwitch_LoadHelper", $own_hash ); } if ( $init_done && $devName eq "global" && grep( m/^DEFINED $ownName$/, @{$events} ) ) { # reaktion auf eigenes notify start / define / modify my $timecond = gettimeofday() + 5; InternalTimer( $timecond, "MSwitch_LoadHelper", $own_hash ); } if ( $devName eq "global"&& grep( m/^INITIALIZED|REREADCFG$/, @{$events} ) ) { # reaktion auf eigenes notify start / define / modify MSwitch_LoadHelper($own_hash); } # nur abfragen für eigenes Notify ENDE return ""if ( IsDisabled($ownName) ); # Return without any further action if the module is disabled my $devicemode = AttrVal( $ownName, 'MSwitch_Mode', 'Notify' ); my $devicefilter = AttrVal( $ownName, 'MSwitch_Trigger_Filter', 'undef' ); my $debugmode = AttrVal( $ownName, 'MSwitch_Debug', "0" ); my $startdelay = AttrVal( $ownName, 'MSwitch_Startdelay', $standartstartdelay ); my $attrrandomnumber = AttrVal( $ownName, 'MSwitch_RandomNumber', '' ); if ( AttrVal( $ownName, "MSwitch_Selftrigger_always", 0 ) ne "1") { return if ( ReadingsVal( $ownName, "Trigger_device", "no_trigger" ) eq 'no_trigger' ); return if ( !$own_hash->{NOTIFYDEV} && ReadingsVal( $ownName, 'Trigger_device', 'no_trigger' ) ne "all_events" ); } else { } # startverzöferung abwarten my $diff = int(time) - $fhem_started; if ( $diff < $startdelay ) { MSwitch_LOG( $ownName, 6, 'Anfrage fuer ' . $ownName . ' blockiert - Zeit seit start:' . $diff ); return; } # safemode testen MSwitch_Safemode($own_hash); MSwitch_LOG( $ownName, 6, "----------------------------------------" ); MSwitch_LOG( $ownName, 6, "$ownName: eingehendes Event von -> " . $devName ); MSwitch_LOG( $ownName, 6, "----------------------------------------" ); # versionscheck if ( ReadingsVal( $ownName, '.V_Check', $vupdate ) ne $vupdate ) { my $ver = ReadingsVal( $ownName, '.V_Check', '' ); MSwitch_LOG( $ownName, 4, $ownName . ' Versionskonflikt, aktion abgebrochen ! erwartet:' . $vupdate . ' vorhanden:' . $ver ); return; } if ( $attrrandomnumber ne '' ) { # create randomnumber wenn attr an MSwitch_Createnumber1($own_hash); } my $incommingdevice = ''; if ( defined( $own_hash->{helper}{testevent_device}) && $own_hash->{helper}{testevent_device} eq $ownName) { $incommingdevice = "MSwitch_Self"; $events = 'x'; } elsif ( defined( $own_hash->{helper}{testevent_device}) ) { # unklar $events = 'x'; $incommingdevice = ( $own_hash->{helper}{testevent_device} ); } else { $incommingdevice = $dev_hash->{NAME}; # aufrufendes device } ##### if ( ReadingsVal( $ownName, "waiting", '0' ) > time) { MSwitch_LOG( $ownName, 6, '$ownName: Aktion abgebrochen - wait gesetzt ->' . ReadingsVal( $ownName, "waiting", '0' ) ); # teste auf attr waiting verlesse wenn gesetzt return ""; } else { # reading löschen delete( $own_hash->{READINGS}{waiting} ); } MSwitch_LOG( $ownName, 6, "-------------waiting passiert-----------------" ); ##### if ( !$events && $own_hash->{helper}{testevent_device} ne 'Logfile' ) { return; } readingsSingleUpdate( $own_hash, "last_activation_by", 'event', $showevents ); my $triggerdevice = ReadingsVal( $ownName, 'Trigger_device', '' ); # Triggerdevice my @cmdarray; my @cmdarray1; # enthält auszuführende befehle nach conditiontest ########### ggf. löschen my $triggeron = ReadingsVal( $ownName, '.Trigger_on', '' ); my $triggeroff = ReadingsVal( $ownName, '.Trigger_off', '' ); my $triggercmdon = ReadingsVal( $ownName, '.Trigger_cmd_on', '' ); my $triggercmdoff = ReadingsVal( $ownName, '.Trigger_cmd_off', '' ); if ( $devicemode eq "Notify" ) { # passt triggerfelder an attr an $triggeron = 'no_trigger'; $triggeroff = 'no_trigger'; } if ( $devicemode eq "Toggle") { # passt triggerfelder an attr an $triggeroff = 'no_trigger'; $triggercmdon = 'no_trigger'; $triggercmdoff = 'no_trigger'; } my $set = "noset"; my $eventcopy = ""; # notify für eigenes device my $devcopyname = $devName; $own_hash->{helper}{eventfrom} = $devName; my @eventscopy; if ( defined( $own_hash->{helper}{testevent_event} ) ) { @eventscopy = "$own_hash->{helper}{testevent_event}"; } else { @eventscopy = ( @{$events} ) if $events ne "x"; } my $triggerlog = ReadingsVal( $ownName, 'Trigger_log', 'off' ); if ( $incommingdevice eq $triggerdevice || $triggerdevice eq "all_events" || $triggerdevice eq "MSwitch_Self" || $incommingdevice eq "MSwitch_Self" ) { # teste auf triggertreffer oder GLOBAL trigger my $activecount = 0; my $anzahl; #### SEQUENZE ###################################### my @sequenzall =split( /\//, AttrVal( $ownName, 'MSwitch_Sequenz', 'undef' ) ); my $sequenzarrayfull = AttrVal( $ownName, 'MSwitch_Sequenz', 'undef' ); $sequenzarrayfull =~ s/\// /g; my @sequenzarrayfull = split( / /, $sequenzarrayfull ); my @sequenzarray; my $sequenz; my $x = 0; my $sequenztime = AttrVal( $ownName, 'MSwitch_Sequenz_time', 5 ); foreach my $sequenz (@sequenzall) { $x++; if ( $sequenz ne "undef" ) { @sequenzarray = split( / /, $sequenz ); my $sequenzanzahl = @sequenzarray; my $deletezeit = time; my $seqhash = $own_hash->{helper}{sequenz}{$x}; foreach my $seq ( keys %{$seqhash} ) { if ( time > ( $seq + $sequenztime ) ) { delete( $own_hash->{helper}{sequenz}{$x}{$seq} ); } } } } ########################## EVENT: foreach my $event (@eventscopy) { MSwitch_LOG( $ownName, 6, "$ownName: event -> $event " ); if ( $event =~ m/^.*:.\{.*\}?/ ) { MSwitch_LOG( $ownName, 6, "$ownName: found jason -> $event " ); next EVENT; } if ( $event =~ m/(.*)(\{.*\})(.*)/ ) { my $p1 = $1; my $json = $2; my $p3 = $3; $json =~ s/:/[dp]/g; $json =~ s/\"/[dst]/g; $event = $p1 . $json . $p3; MSwitch_LOG( $ownName, 5,"$ownName: changedevent -> $event " ); #next EVENT; } $own_hash->{eventsave} = 'unsaved'; MSwitch_LOG( $ownName, 5, "$ownName: eingehendes Event -> " . $incommingdevice . " " . $event ); # durchlauf für jedes ankommende event $event = "" if ( !defined($event) ); $eventcopy = $event; $eventcopy =~ s/: /:/s; # BUG !!!!!!!!!!!!!!!!!!!!!!!! $event =~ s/: /:/s; # Teste auf einhaltung Triggercondition für ausführung zweig 1 und zweig 2 # kann ggf an den anfang der routine gesetzt werden ? test erforderlich my $triggercondition = ReadingsVal( $ownName, '.Trigger_condition', '' ); $triggercondition =~ s/#\[dp\]/:/g; $triggercondition =~ s/#\[pt\]/./g; $triggercondition =~ s/#\[ti\]/~/g; $triggercondition =~ s/#\[sp\]/ /g; if ( $triggercondition ne '' ) { MSwitch_LOG( $ownName, 5, "$ownName: teste die Triggercondition -> " . $triggercondition ); MSwitch_LOG( $ownName, 5, "$ownName: teste die eventcopy -> " . $eventcopy ); my $ret = MSwitch_checkcondition( $triggercondition, $ownName,$eventcopy ); MSwitch_LOG( $ownName, 5, "$ownName: ergebniss der Triggercondition -> " . $ret ); if ( $ret eq 'false' ) { MSwitch_LOG($ownName,6,"$ownName: ergebniss Triggercondition false-> abbruch"); MSwitch_LOG( $ownName, 6, "-----------------" ); next EVENT; } } # Triggerfilter if ( $devicefilter ne 'undef' && $devicefilter ne "" ) { my $eventcopy1 = $eventcopy; if ( $triggerdevice eq "all_events" ) { # fügt dem event den devicenamen hinzu , wenn global getriggert wird $eventcopy1 = "$devName:$eventcopy"; } my @filters =split( /,/, $devicefilter ); # beinhaltet filter durch komma getrennt MSwitch_LOG( $ownName, 5,"$ownName: Filtertest Event -> " . $eventcopy ); foreach my $filter (@filters) { if ( $filter eq "*" ) { $filter = ".*"; } MSwitch_LOG($ownName, 5,"$ownName: eingehendes Event teste Filter -> ". $filter); if ( $eventcopy1 =~ m/$filter/ ) { MSwitch_LOG( $ownName, 6,"Name: eingehendes Event durch MSwitch_Trigger_Filter ausgefiltert: ". $eventcopy1 ); next EVENT; } } } delete( $own_hash->{helper}{history} );# lösche historyberechnung verschieben auf nach abarbeitung conditions # sequenz my $x = 0; my $zeit = time; SEQ: foreach my $sequenz (@sequenzall) { $x++; if ( $sequenz ne "undef" ) { my $fulldev = "$devName:$eventcopy"; #MSwitch_LOG( $ownName, 0,"$_ -- $fulldev --- @sequenzarrayfull" ); foreach my $test(@sequenzarrayfull) { if ( $fulldev =~ /$test/ ) { $own_hash->{helper}{sequenz}{$x}{$zeit} = $fulldev; } } my $seqhash = $own_hash->{helper}{sequenz}{$x}; my $aktsequenz = ""; foreach my $seq ( sort keys %{$seqhash} ) { $aktsequenz .= $own_hash->{helper}{sequenz}{$x}{$seq} . " "; } if ( $aktsequenz =~ /$sequenz/ ) { delete( $own_hash->{helper}{sequenz}{$x} ); readingsSingleUpdate( $own_hash, "SEQUENCE", 'match', 1 ); readingsSingleUpdate( $own_hash, "SEQUENCE_Number", $x, 1 ); last SEQ; } else { if ( ReadingsVal( $ownName, "SEQUENCE", 'undef' ) eq "match" ) { readingsSingleUpdate( $own_hash, "SEQUENCE",'no_match', 1 ); } if ( ReadingsVal( $ownName, "SEQUENCE_Number", 'undef' ) ne "0" ) { readingsSingleUpdate( $own_hash, "SEQUENCE_Number", '0', 1 ); } } } } # Triggerlog/Eventlog if ( $triggerlog eq 'on' ) { my $zeit = time; if ($incommingdevice ne "MSwitch_Self") { if ( $triggerdevice eq "all_events" ) { $own_hash->{helper}{events}{'all_events'}{ $devName . ':' . $eventcopy } = "on"; } else { $own_hash->{helper}{events}{$devName}{$eventcopy} = "on"; } } else { $own_hash->{helper}{events}{MSwitch_Self}{$eventcopy} = "on"; } } if ( $evhistory > 0 ) { my $zeit = time; if ($incommingdevice ne "MSwitch_Self") { if ( $triggerdevice eq "all_events" ) { $own_hash->{helper}{eventlog}{$zeit}=$devName . ':' . $eventcopy ; } else { $own_hash->{helper}{eventlog}{$zeit}=$devName . ':' . $eventcopy; } } else { $own_hash->{helper}{eventlog}{$zeit}="MSitch_Self:". $eventcopy; } my $log = $own_hash->{helper}{eventlog}; my $x = 0; my $seq; foreach $seq ( sort{$b <=> $a} keys %{$log} ) { delete( $own_hash->{helper}{eventlog}{$seq} ) if $x > $evhistory; $x++; } } ################ alle events für weitere funktionen speichern ############################################################# #anzahl checken / ggf nicht mehr nötig #check checken / ggf nicht mehr nötig if ( $event ne '' ) { my $eventcopy1 = $eventcopy; if ( $triggerdevice eq "all_events" ) { # fügt dem event den devicenamen hinzu , wenn global getriggert wird $eventcopy1 = "$devName:$eventcopy"; } if ( AttrVal( $ownName, "MSwitch_Selftrigger_always", 0 ) eq "1" && $incommingdevice eq "MSwitch_Self") { $eventcopy1 = "MSwitch_Self:$eventcopy"; } MSwitch_LOG( $ownName, 5, "rufe eventbulk auf" ); MSwitch_EventBulk( $own_hash, $eventcopy1, '0','MSwitch_Notify' ); } # Teste auf einhaltung Triggercondition ENDE ############################################################################################################ my $eventcopy1 = $eventcopy; if ( $triggerdevice eq "all_events" ) { # fügt dem event den devicenamen hinzu , wenn global getriggert wird $eventcopy1 = "$devName:$eventcopy"; } if ( AttrVal( $ownName, "MSwitch_Selftrigger_always", 0 ) eq "1" && $incommingdevice eq "MSwitch_Self") { $eventcopy1 = "MSwitch_Self:$eventcopy"; $eventcopy = $eventcopy1; } my $direktswitch = 0; my @eventsplit = split( /\:/, $eventcopy ); my $eventstellen = @eventsplit; my $testvar = ''; my $check = 0; #test auf zweige cmd1/2 and switch MSwitch on/off if ( $triggeron ne 'no_trigger' ) { MSwitch_LOG( $ownName, 6,"$ownName: checktrigger trigger cmd1 -> " ); $testvar = MSwitch_checktrigger( $own_hash, $ownName, $eventstellen, $triggeron, $incommingdevice, 'on', $eventcopy, @eventsplit ); if ( $testvar ne 'undef' ) { MSwitch_LOG( $ownName, 6, "Teste auf bridge von 3609" ); my $chbridge = MSwitch_checkbridge( $own_hash, $ownName, $eventcopy1, ); next EVENT if $chbridge ne "no_bridge"; $set = $testvar; $check = 1; $foundcmd1 = 1; $trigevent = $eventcopy; } MSwitch_LOG( $ownName, 6,"$ownName: checktrigger ergebniss -> " . $testvar ); } if ( $triggeroff ne 'no_trigger' ) { MSwitch_LOG( $ownName, 6,"$ownName: checktrigger trigger cmd2 -> " ); $testvar = MSwitch_checktrigger( $own_hash, $ownName, $eventstellen, $triggeroff, $incommingdevice, 'off', $eventcopy, @eventsplit ); if ( $testvar ne 'undef' ) { MSwitch_LOG( $ownName, 6, "Teste auf bridge von 3631" ); my $chbridge = MSwitch_checkbridge( $own_hash, $ownName, $eventcopy1, ); next EVENT if $chbridge ne "no_bridge"; $set = $testvar; $check = 1; $foundcmd2 = 1; $trigevent = $eventcopy; } MSwitch_LOG( $ownName, 6,"$ownName: checktrigger ergebniss -> " . $testvar ); } #test auf zweige cmd1/2 and switch MSwitch on/off ENDE #test auf zweige cmd1/2 only #ergebnisse werden in @cmdarray geschrieben if ( $triggercmdoff ne 'no_trigger' ) { MSwitch_LOG( $ownName, 6,"$ownName: checktrigger trigger cmd4 -> " ); $testvar = MSwitch_checktrigger( $own_hash, $ownName, $eventstellen, $triggercmdoff, $incommingdevice, 'offonly', $eventcopy, @eventsplit ); if ( $testvar ne 'undef' ) { MSwitch_LOG( $ownName, 6, "Teste auf bridge von 3658" ); my $chbridge = MSwitch_checkbridge( $own_hash, $ownName, $eventcopy1, ); next EVENT if $chbridge ne "no_bridge"; push @cmdarray, $own_hash . ',off,check,' . $eventcopy1; $check = 1; $foundcmd2 = 1; } MSwitch_LOG( $ownName, 6, "$ownName: checktrigger ergebniss -> " . $testvar ); } if ( $triggercmdon ne 'no_trigger' ) { MSwitch_LOG( $ownName, 6, "$ownName: checktrigger trigger cmd-4 -> " ); $testvar = MSwitch_checktrigger( $own_hash, $ownName, $eventstellen, $triggercmdon, $incommingdevice, 'ononly', $eventcopy, @eventsplit ); MSwitch_LOG( $ownName, 6, "$ownName: checktrigger ergebniss -> " . $testvar ); if ( $testvar ne 'undef' ) { MSwitch_LOG( $ownName, 6, "Teste auf bridge von 3684" ); my $chbridge = MSwitch_checkbridge( $own_hash, $ownName,$eventcopy1, ); next EVENT if $chbridge ne "no_bridge"; push @cmdarray, $own_hash . ',on,check,' . $eventcopy1; $check = 1; $foundcmd1 = 1; } } # speichert 20 events ab zur weiterne funktion ( funktionen ) # ändern auf bedarfschaltung if ($check == '1' and defined( ( split( /:/, $eventcopy ) )[1] ) and ( ( split( /:/, $eventcopy ) )[1] =~ /^[-]?[0-9,.E]+$/ ) ) { my $evwert = ( split( /:/, $eventcopy ) )[1]; my $evreading = ( split( /:/, $eventcopy ) )[0]; my @eventfunction =split( / /, $own_hash->{helper}{eventhistory}{$evreading} );; unshift( @eventfunction, $evwert ); while ( @eventfunction > $evhistory ) { pop(@eventfunction); } my $neweventfunction = join( ' ', @eventfunction ); $own_hash->{helper}{eventhistory}{$evreading} = $neweventfunction; } ###################################### #test auf zweige cmd1/2 only ENDE $anzahl = @cmdarray; MSwitch_LOG( $ownName, 6, "$ownName: anzahl gefundener Befehle -> " . $anzahl ); MSwitch_LOG( $ownName, 6, "$ownName: inhalt gefundener Befehle -> @cmdarray" ); $own_hash->{IncommingHandle} = 'fromnotify' if AttrVal( $ownName, 'MSwitch_Mode', 'Notify' ) ne "Dummy"; $event =~ s/~/ /g; #? if ( $devicemode eq "Notify" and $activecount == 0 ) { # reading activity aktualisieren MSwitch_LOG( $ownName, 5,"setze state neu"); readingsSingleUpdate( $own_hash, "state",'active', $showevents ) if ReadingsVal( $ownName, 'state', '0' ) eq "active" ; $activecount = 1; } # abfrage und setzten von blocking # schalte blocking an , wenn anzahl grösser 0 und MSwitch_Wait gesetzt my $mswait = $attr{$ownName}{MSwitch_Wait}; if ( !defined $mswait ) { $mswait = '0'; } if ( $anzahl > 0 && $mswait > 0 ) { readingsSingleUpdate( $own_hash, "waiting", ( time + $mswait ),0 ); } # abfrage und setzten von blocking ENDE if ( $devicemode eq "Toggle"&& $set eq 'on' ) { # umschalten des devices nur im togglemode my $cmd = ''; my $statetest = ReadingsVal( $ownName, 'state', 'on' ); $cmd = "set $ownName off" if $statetest eq 'on'; $cmd = "set $ownName on" if $statetest eq 'off'; MSwitch_LOG( $ownName, 6, "$ownName: togglemode execute -> " . $cmd ); if ( $debugmode ne '2' ) { my $errors = AnalyzeCommandChain( undef, $cmd ); if ( defined($errors) ) { MSwitch_LOG( $ownName, 1,"$ownName MSwitch_Notify: Fehler bei Befehlsausführung $errors -> Comand: $_ " . __LINE__ ); } } return; } } #foundcmd1/2 if ( $foundcmd1 eq "1" && AttrVal( $ownName, "MSwitch_Reset_EVT_CMD1_COUNT", 'undef' ) ne 'undef' ) { my $inhalt = ReadingsVal( $ownName, 'EVT_CMD1_COUNT', '0' ); if ( $resetcmd1 == 0 ) { $inhalt++; readingsSingleUpdate( $own_hash, "EVT_CMD1_COUNT",$inhalt, $showevents ); } elsif ( $resetcmd1 > 0 && $inhalt < $resetcmd1 ) { $inhalt++; readingsSingleUpdate( $own_hash, "EVT_CMD1_COUNT", $inhalt, $showevents ); } } if ( $foundcmd2 eq "1" && AttrVal( $ownName, "MSwitch_Reset_EVT_CMD2_COUNT", 'undef' ) ne 'undef' ) { my $inhalt = ReadingsVal( $ownName, 'EVT_CMD2_COUNT', '0' ); if ( $resetcmd2 == 0 ) { $inhalt++; readingsSingleUpdate( $own_hash, "EVT_CMD2_COUNT", $inhalt, $showevents ); } elsif ( $resetcmd2 > 0 && $inhalt < $resetcmd2 ) { $inhalt++; readingsSingleUpdate( $own_hash, "EVT_CMD2_COUNT", $inhalt, $showevents ); } } #ausführen aller cmds in @cmdarray nach triggertest aber vor conditiontest #my @cmdarray1; #enthält auszuführende befehle nach conditiontest #schaltet zweig 3 und 4 # ACHTUNG if ( $anzahl && $anzahl != 0 ) { MSwitch_LOG( $ownName, 6, "$ownName: abarbeiten aller befehle aus eventprüfung " ); #aberabeite aller befehlssätze in cmdarray MSwitch_Safemode($own_hash); LOOP31: foreach (@cmdarray) { MSwitch_LOG( $ownName, 6, "$ownName: Befehl -> " . $_ ); if ( $_ eq 'undef' ) { next LOOP31; } my ( $ar1, $ar2, $ar3, $ar4 ) = split( /,/, $_ ); if ( !defined $ar2 ) { $ar2 = ''; } if ( $ar2 eq '' ) { next LOOP31; } my $returncmd = 'undef'; $returncmd = MSwitch_Exec_Notif( $own_hash, $ar2, $ar3, $ar4, $execids ); if ( defined $returncmd && $returncmd ne 'undef' ) { # datensatz nur in cmdarray1 übernehme wenn chop $returncmd; #CHANGE MSwitch_LOG( $ownName, 5, "$ownName: ergebniss execnotif datensatz to array -> ". $returncmd ); push( @cmdarray1, $returncmd ); } } my $befehlssatz = join( ',', @cmdarray1 ); foreach ( split( /,/, $befehlssatz ) ) { my $ecec = $_; if ( !$ecec =~ m/set (.*)(MSwitchtoggle)(.*)/ ) { if ( $attrrandomnumber ne '' ) { MSwitch_Createnumber($own_hash); } MSwitch_LOG( $ownName, 6,"$ownName: Befehlsausfuehrung -> " . $ecec ); if ( $debugmode ne '2' ) { my $errors = AnalyzeCommandChain( undef, $_ ); if ( defined($errors) ) { MSwitch_LOG( $ownName, 1,"$ownName MSwitch_Notify: Fehler bei Befehlsausführung $errors -> Comand: $_ " . __LINE__ ); } } if ( length($ecec) > 100 ) { $ecec = substr( $ecec, 0, 100 ) . '....'; } readingsSingleUpdate( $own_hash, "last_exec_cmd", $ecec, $showevents ) if $ecec ne ''; } else { # nothing } } } # ende loopeinzeleventtest # schreibe gruppe mit events my $selftrigger=""; my $events = ''; my $eventhash = $own_hash->{helper}{events}{$devName}; if ( AttrVal( $ownName, "MSwitch_Selftrigger_always", 0 ) eq "1" ) { $eventhash = $own_hash->{helper}{events}{MSwitch_Self}; foreach my $name ( keys %{$eventhash} ) { $events = $events .'MSwitch_Self:'. $name . '#[tr]'; } } if ( $triggerdevice eq "all_events" ) { $eventhash = $own_hash->{helper}{events}{all_events}; } else { $eventhash = $own_hash->{helper}{events}{$devName}; } foreach my $name ( keys %{$eventhash} ) { $events = $events . $name . '#[tr]'; } chop($events); chop($events); chop($events); chop($events); chop($events); if ( $events ne "" ) { readingsSingleUpdate( $own_hash, ".Device_Events", $events, 1 ); } # schreiben ende # schalte modul an/aus bei entsprechendem notify # teste auf condition return if $set eq 'noset'; # keine MSwitch on/off incl cmd1/2 gefunden ###################### # schaltet zweig 1 und 2 , wenn $set befehl enthält , es wird nur MSwitch geschaltet, Devices werden dann 'mitgerissen' my $cs; if ( $triggerdevice eq "all_events" ) { $cs = "set $ownName $set $devName:$trigevent"; } else { $cs = "set $ownName $set $trigevent"; } MSwitch_LOG( $ownName, 6, "$ownName MSwitch_Notif: Befehlsausfuehrung -> $cs " . __LINE__ ); # variabelersetzung $cs =~ s/\$NAME/$own_hash->{helper}{eventfrom}/; $cs =~ s/\$SELF/$ownName/; if ( $attrrandomnumber ne '' ) { MSwitch_Createnumber($own_hash); } MSwitch_LOG( $ownName, 6, "$ownName: Befehlsausführung -> " . $cs ); if ( $debugmode ne '2' ) { my $errors = AnalyzeCommandChain( undef, $cs ); } return; } } ######################### sub MSwitch_checkbridge($$$) { my ( $hash, $name, $event ) = @_; my $bridgemode = AttrVal( $name, 'MSwitch_Event_Id_Distributor', '0' ); my $expertmode = AttrVal( $name, 'MSwitch_Expert', '0' ); return "no_bridge" if $expertmode eq "0"; return "no_bridge" if $bridgemode eq "0"; MSwitch_LOG( $name, 6, "----------------------------------------" ); MSwitch_LOG( $name, 6, "TESTE AUF ID VERTEILUNG" ); MSwitch_LOG( $name, 6, "----------------------------------------" ); MSwitch_LOG( $name, 5, "expertmode $expertmode" ); MSwitch_LOG( $name, 5, "bridgemode $bridgemode " ); MSwitch_LOG( $name, 6, "EINGEHENDES EVENTT: $event" ); MSwitch_LOG( $name, 5, "checke keys" ); my $foundkey = "undef"; my $etikeys = $hash->{helper}{eventtoid}; foreach my $a ( sort keys %{$etikeys} ) { MSwitch_LOG( $name, 6, "PRUEFE GESPEICHERTEN KEY : $a" ); my $re = qr/$a/; $foundkey = $a if ( $event =~ /$re/ ); MSwitch_LOG( $name, 6, "FOUNDKEY : $foundkey " ); } MSwitch_LOG( $name, 6, "suche nach schluessel: $foundkey " ); if (!defined $hash->{helper}{eventtoid}{$foundkey}) { MSwitch_LOG( $name, 6, " " ); MSwitch_LOG( $name, 6, " " ); return "NOO BRIDGE FOUND !"; } MSwitch_LOG( $name, 6, "HELPER EVENT TO ID : " . $hash->{helper}{eventtoid}{$foundkey} ); my @bridge = split( / /, $hash->{helper}{eventtoid}{$foundkey} ); my $zweig; $zweig = "on" if $bridge[0] eq "cmd1"; $zweig = "off" if $bridge[0] eq "cmd2"; MSwitch_LOG( $name, 6, "distrubutorout: $bridge[2] " ); MSwitch_LOG( $name, 6, " " ); MSwitch_LOG( $name, 6, " " ); MSwitch_Exec_Notif( $hash, $zweig, 'nocheck', '', $bridge[2] ); return "undef"; } ############################ sub MSwitch_fhemwebconf($$$$) { my ( $FW_wname, $d, $room, $pageHash ) =@_; # pageHash is set for summaryFn. my $hash = $defs{$d}; my $Name = $hash->{NAME}; my @found_devices; delete( $hash->{NOTIFYDEV} ); readingsSingleUpdate( $hash, "EVENTCONF","start", 1 ); my $preconf = ''; $preconf = get( $preconffile ); $preconf =~ s/\n/#[NEWL]\\\n/g; $preconf =~ s/\r//g; $preconf =~ s/'/\\\'/g; # devicelist to objeckt my $devstring ; my $cmds; @found_devices = devspec2array("TYPE=.*"); for (@found_devices) { my $test = getAllSets($_); $cmds.="'".$test."',"; $devstring.="'".$_."',"; } chop $devstring; chop $cmds; $devstring = "[".$devstring."]"; $cmds = "[".$cmds."]"; my $fileend = "x".rand(1000); my $devicehash; my $at; my $atdef; my $athash; my $insert; my $comand; my $timespec; my $flag; my $trigtime; # suche at @found_devices = devspec2array("TYPE=at"); for (@found_devices) { $athash = $defs{$_}; $insert = $athash->{DEF}; $flag= substr($insert,0,1); if ($flag ne "+") { next if $athash->{PERIODIC} eq 'no'; next if $athash->{RELATIVE} eq 'yes'; } $at .="'".$_."',"; $trigtime .="'".$athash->{TRIGGERTIME}."',"; $atdef .="'".$insert."',"; $comand .="'".$athash->{COMMAND}."',"; $timespec .="'".$athash->{TIMESPEC}."',"; } chop $at; chop $atdef; chop $comand; chop $timespec; chop $trigtime; $at = "[".$at."]"; $atdef = "[".$atdef."]"; $comand = "[".$comand."]"; $timespec = "[".$timespec."]"; $trigtime = "[".$trigtime."]"; # suche notify my $nothash; my $notinsert; my $notify; my $notifydef; @found_devices = devspec2array("TYPE=notify"); for (@found_devices) { $nothash = $defs{$_}; $notinsert = $nothash->{DEF}; $notifydef .="'".$notinsert."',"; $notify .="'".$_."',"; } chop $notifydef; chop $notify; $notifydef = "[".$notifydef."]"; $notify= "[".$notify."]"; my $return="
Konfigurationsmodus:       


Hilfetext
 
Teil 1 (Auslöser des Devices)
 
 
 


 

 
@found_devices
import notify
import config
import preconf
"; my $j1 = " "; $return.="
 
".$j1; return $return; } ############################ sub MSwitch_fhemwebFn($$$$) { # my $loglevel = 5; my ( $FW_wname, $d, $room, $pageHash ) =@_; # pageHash is set for summaryFn. my $hash = $defs{$d}; my $Name = $hash->{NAME}; my $jsvarset = ''; my $j1 = ''; my $border = 0; my $ver = ReadingsVal( $Name, '.V_Check', '' ); my $expertmode = AttrVal( $Name, 'MSwitch_Expert', '0' ); my $noshow = 0; my @hidecmds = split (/,/,AttrVal( $Name, 'MSwitch_Hidecmds', 'undef' )) ; #"; $scripttriggers =$scripttriggers . "\"$_\": 1 ,"; if ( $_ eq 'no_trigger' ) { next LOOP12; } if ( $triggeron eq $_ ) { $optionon = $optionon . ""; $to = '1'; } else { $optionon = $optionon . ""; } if ( $triggercmdon eq $_ ) { $optioncmdon = $optioncmdon . ""; $toc = '1'; } else { $optioncmdon =$optioncmdon . ""; } #################### nur bei entsprechender regex my $test = $_; if ( $test =~ m/(.*)\((.*)\)(.*)/ ) { #nothing } else { if ( index( $_, '*', 0 ) == -1 ) { if ( ReadingsVal( $Name, 'Trigger_device', '' ) ne "all_events" ) { $optiongeneral = $optiongeneral . ""; } else { $optiongeneral = $optiongeneral . ""; } } } ##################### } chop($scripttriggers); if ( $to eq '1' ) { $optionon = "" . $optionon; } else { $optionon ="". $optionon; } if ( $toc eq '1' ) { $optioncmdon = "" . $optioncmdon; } else { $optioncmdon ="".$optioncmdon; } my $optioncmdoff = ''; my $optionoff = ''; $to = ''; $toc = ''; LOOP14: foreach (@eventsall) { if ( $_ eq 'no_trigger' ) { next LOOP14 } if ( $triggeroff eq $_ ) { $optionoff = $optionoff. ""; $to = '1'; } else { $optionoff = $optionoff . ""; } if ( $triggercmdoff eq $_ ) { $optioncmdoff = $optioncmdoff. ""; $toc = '1'; } else { $optioncmdoff = $optioncmdoff . ""; } } if ( $to eq '1' ) { $optionoff = "" . $optionoff; } else { $optionoff ="". $optionoff; } if ( $toc eq '1' ) { $optioncmdoff = "" . $optioncmdoff; } else { $optioncmdoff ="". $optioncmdoff; } $optionon =~ s/\[bs\]/|/g; $optionoff =~ s/\[bs\]/|/g; $optioncmdon =~ s/\[bs\]/|/g; $optioncmdoff =~ s/\[bs\]/|/g; #################### # mögliche affected devices und mögliche triggerdevices my $devicesets; my $deviceoption = ""; my $selected = ""; my $errors = ""; my $javaform = ""; # erhält javacode für übergabe devicedetail my $cs = ""; my %cmdsatz; # ablage desbefehlssatzes jedes devices my $globalon = 'off'; my $globalon1 = 'off'; if ( ReadingsVal( $Name, 'Trigger_device', 'no_trigger' ) eq 'no_trigger' ) { $triggerdevices =""; } else { $triggerdevices = ""; } if ( $expertmode eq '1' ) { if ( ReadingsVal( $Name, 'Trigger_device', 'no_trigger' ) eq 'all_events' ) { $triggerdevices .=""; $globalon = 'on'; } else { $triggerdevices .= ""; } } if ( AttrVal( $Name, 'MSwitch_Read_Log', "0" ) eq '1' ) { if ( ReadingsVal( $Name, 'Trigger_device', 'no_trigger' ) eq 'Logfile' ) { $triggerdevices .=""; #$globalon = 'on'; } else { $triggerdevices .= ""; } } if (ReadingsVal( $Name, 'Trigger_device', 'no_trigger' ) eq 'MSwitch_Self' ) { $triggerdevices .=""; } else { $triggerdevices .= ""; } my $affecteddevices = ReadingsVal( $Name, '.Device_Affected', 'no_device' ); # affected devices to hash my %usedevices; my @deftoarray = split( /,/, $affecteddevices ); my $anzahl = @deftoarray; my $anzahl1 = @deftoarray; my $anzahl3 = @deftoarray; my @testidsdev = split( /#\[ND\]/, ReadingsVal($Name, '.Device_Affected_Details', 'no_device' ) ); #PRIORITY # teste auf grössere PRIORITY als anzahl devices foreach (@testidsdev) { last if $_ eq "no_device"; MSwitch_LOG( $Name, 5, "dev @testidsdev" ); my @testid = split( /#\[NF\]/, $_ ); my $x = 0; MSwitch_LOG( $Name, 5, "devfelder @testid" ); my $id = $testid[13]; MSwitch_LOG( $Name, 5, "id $id" ); $anzahl = $id if $id > $anzahl; } my $reihenfolgehtml = ""; if ( $expertmode eq '1' ) { $reihenfolgehtml = ""; } ### display my $hidehtml = ""; $hidehtml = ""; ######################################### # SHOW # teste auf grössere PRIORITY als anzahl devices foreach (@testidsdev) { MSwitch_LOG( $Name, 5, "dev @testidsdev" ); my @testid = split( /#\[NF\]/, $_ ); my $x = 0; MSwitch_LOG( $Name, 5, "devfelder @testid" ); my $id = $testid[18]; if (defined $id) { MSwitch_LOG( $Name, 5, "id $id" ); $anzahl1 = $id if $id > $anzahl; } } ################################# my $showfolgehtml = ""; $showfolgehtml = ""; ###################################### #ID my $idfolgehtml = ""; if ( $expertmode eq '1' ) { $idfolgehtml = ""; } foreach (@deftoarray) { my ( $a, $b ) = split( /-/, $_ ); $usedevices{$a} = 'on'; } my $notype = AttrVal( $Name, 'MSwitch_Ignore_Types', "" ); if ( AttrVal( $Name, 'MSwitch_Mode', 'Notify' ) eq "Dummy" && AttrVal( $Name, "MSwitch_Selftrigger_always", 0 ) eq "0" ) { $notype = ".*"; } my @found_devices; my $setpattern = ""; my $setpattern1 = ""; ###### ersetzung ATTR oder READING if ( $notype =~ /(.*)\[(ATTR|READING):(.*):(.*)\](.*)/ ) { my $devname = $3; my $firstpart = $1; my $lastpart = $5; my $readname = $4; my $type = $2; $devname =~ s/\$SELF/$Name/; my $magic = ".*"; $magic = AttrVal( $devname, $readname, ".*" ) if $type eq "ATTR"; $magic = ReadingsVal( $devname, $readname, '.*' ) if $type eq "READING"; $notype = $firstpart . $magic . $lastpart; } if ( $notype =~ /(")(.*)(")/ ) { my $reg = $2; if ( $reg =~ /(.*?)(s)(!=|=)([a-zA-Z]{1,10})(:?)(.*)/ ) { $reg = $1 . $5 . $6; $setpattern1 = $4; $setpattern = "=~" if ( $3 eq "=" ); $setpattern = "!=" if ( $3 eq "!=" ); chop $reg if $6 eq ""; $reg =~ s/::/:/g; } @found_devices = devspec2array("$reg"); } else { $notype =~ s/ /|/g; @found_devices = devspec2array("TYPE!=$notype"); } if ( $setpattern eq "=~" ) { my @found_devices_new; my $re = qr/$setpattern1/; for my $name (@found_devices) { my $cs = "set $name ?"; my $errors = AnalyzeCommandChain( undef, $cs ); if ( $errors =~ /$re/ ) { push @found_devices_new, $name; } } @found_devices = @found_devices_new; } if ( $setpattern eq "!=" ) { my @found_devices_new; my $re = qr/$setpattern1/; for my $name (@found_devices) { my $cs = "set $name ?"; my $errors = AnalyzeCommandChain( undef, $cs ); if ( $errors !~ /$re/ ) { push @found_devices_new, $name; } } @found_devices = @found_devices_new; } if ( !grep { $_ eq $Name } @found_devices ) { MSwitch_LOG( $Name, 5, "grep Devicetest $Name nicht vorhanden -> wird ergänzt" ); push @found_devices, $Name; } my $includewebcmd = AttrVal( $Name, 'MSwitch_Include_Webcmds', "1" ); my $extensions = AttrVal( $Name, 'MSwitch_Extensions', "0" ); my $MSwitchIncludeMSwitchcmds = AttrVal( $Name, 'MSwitch_Include_MSwitchcmds', "1" ); my $MSwitchIncludeDevicecmds =AttrVal( $Name, 'MSwitch_Include_Devicecmds', "1" ); my $Triggerdevicetmp = ReadingsVal( $Name, 'Trigger_device', '' ); my $savecmds = AttrVal( $Name, 'MSwitch_DeleteCMDs', $deletesavedcmdsstandart ); LOOP9: for my $name ( sort @found_devices ) { my $selectedtrigger = ''; my $devicealias = AttrVal( $name, 'alias', "" ); my $devicewebcmd = AttrVal( $name, 'webCmd', "noArg" ); # webcmd des devices my $devicehash = $defs{$name}; #devicehash my $deviceTYPE = $devicehash->{TYPE}; # triggerfile erzeugen if ( $Triggerdevicetmp eq $name ) { $selectedtrigger = 'selected=\"selected\"'; if ( $name eq 'all_events' ) { $globalon = 'on' } } $triggerdevices .=""; # filter auf argumente on oder off ; if ( $name eq '' ) { next LOOP9; } # abfrage und auswertung befehlssatz if ( $MSwitchIncludeDevicecmds eq '1' and $hash->{INIT} ne "define" ) { if ( exists $hash->{helper}{devicecmds1}{$name} && $savecmds ne "nosave" ) { $cmdfrombase = "1"; $errors = $hash->{helper}{devicecmds1}{$name}; } else { $errors = getAllSets($name); if ( $savecmds ne "nosave" ) { $hash->{helper}{devicecmds1}{$name} = $errors; $hash->{helper}{last_devicecmd_save} = time; } } } else { $errors = ''; } if ( !defined $errors ) { $errors = ''; } $errors = '|' . $errors; $errors =~ s/\| //g; $errors =~ s/\|//g; if ( $includewebcmd eq '1' and $devicewebcmd ne "noArg" and $hash->{INIT} ne "define" ) { my $device = ''; my @webcmd = split( /:/, $devicewebcmd ); foreach (@webcmd) { $_ =~ tr/ /:/; my @parts = split( /:/, $_ ); if ( !defined $parts[1] || $parts[1] eq '' ) { $device .= $parts[0] . ':noArg '; } else { $device .= $parts[0] . ':' . $parts[1] . ' '; } } chop $device; $devicewebcmd = $device; $errors .= ' ' . $devicewebcmd; } if ( $MSwitchIncludeMSwitchcmds eq '1' and $hash->{INIT} ne "define" ) { my $usercmds = AttrVal( $name, 'MSwitchcmd', '' ); if ( $usercmds ne '' ) { $usercmds =~ tr/:/ /; $errors .= ' ' . $usercmds; } } if ( $extensions eq '1' ) { $errors .= ' ' . 'MSwitchtoggle'; } if ( $errors ne '' ) { $selected = ""; if ( exists $usedevices{$name} && $usedevices{$name} eq 'on' ) { $selected = "selected=\"selected\" "; } $deviceoption = $deviceoption . ""; # befehlssatz für device in scalar speichern $cmdsatz{$name} = $errors; } else { #nothing } } my $select = index( $affecteddevices, 'FreeCmd', 0 ); $selected = ""; if ( $select > -1 ) { $selected = "selected=\"selected\" " } $deviceoption = "" . $deviceoption; $select = index( $affecteddevices, 'MSwitch_Self', 0 ); $selected = ""; if ( $select > -1 ) { $selected = "selected=\"selected\" " } $deviceoption = "" . $deviceoption; #################### # #devices details # steuerdatei my $controlhtml; $controlhtml ="
MS-NAMESATZ MS-HELPpriority MS-IDSATZ
MS-COMMENTset
CMD 1     
MS-HELPonoff MS-SET1
MS-HELPcondition MS-COND1
MS-TEST-1MS-CONDCHECK1
MS-HELPexeccmd MS-EXEC1
MS-HELPdelay MS-DELAYset1
CMD 2     
MS-HELPonoff MS-SET2
MS-HELPcondition MS-COND2
MS-TEST-2MS-CONDCHECK2
MS-HELPexeccmd MS-EXEC2
MS-HELPdelay MS-DELAYset2
MS-HELPrepeats MS-REPEATset
 MS-ACTIONSATZ

"; $controlhtml = AttrVal( $Name, 'MSwitch_Develop_Affected', $controlhtml ) ; #### extrakt ersetzung my $extrakt = $controlhtml; $extrakt =~ s/\n/#/g; my $extrakthtml = $extrakt; # umstellen auf globales attribut !!!!!! if (AttrVal( $Name, 'MSwitch_Language',AttrVal( 'global', 'language', 'EN' ) ) eq "DE") { $extrakt =~m/start:textersetzung:ger(.*)end:textersetzung:ger/ ; $extrakt = $1; } else { $extrakt =~m/start:textersetzung:eng(.*)end:textersetzung:eng/ ; $extrakt = $1; } my @translate; if(defined $extrakt) { $extrakt =~ s/^.//; $extrakt =~ s/.$//; @translate = split(/#/,$extrakt); } $controlhtml =~m/MS-cellhigh=(.*);/ ; my $cellhight =$1."px"; my $cellhightexpert =$1."px"; my $cellhightdebug =$1."px"; $extrakthtml =~m/(.*)/ ; $controlhtml=$1; $controlhtml=~ s/#/\n/g; # detailsatz in scalar laden my %savedetails = MSwitch_makeCmdHash($Name); my $detailhtml = ""; my @affecteddevices = split( /,/, ReadingsVal( $Name, '.Device_Affected', 'no_device' ) ); ##################################### MSwitch_LOG( $Name, 5, "$Name: -> @affecteddevices" ); if ( $expertmode eq '1' && ReadingsVal( $Name, '.sortby', 'none' ) eq 'priority' ) { #sortieren my $typ = "_priority"; @affecteddevices = MSwitch_sort( $hash, $typ, @affecteddevices ); } if ( ReadingsVal( $Name, '.sortby', 'none' ) eq 'show' ) { #sortieren my $typ = "_showreihe"; @affecteddevices = MSwitch_sort( $hash, $typ, @affecteddevices ); } MSwitch_LOG( $Name, 5, "$Name: -> @affecteddevices" ); ######################################class='block wide' if ( AttrVal( $Name, 'MSwitch_Mode', 'Notify' ) eq "Dummy" && AttrVal( $Name, "MSwitch_Selftrigger_always", 0 ) eq "0" ) { $affecteddevices[0] = 'no_device'; } my $sortierung =""; my $modify=""; my $IDsatz=""; my $NAMEsatz=""; my $ACTIONsatz=""; my $SET1=""; my $SET2=""; my $COND1set1=""; my $COND1check1=""; my $COND2check2=""; my $COND1set2=""; my $EXECset1=""; my $EXECset2=""; my $DELAYset1=""; my $DELAYset2=""; my $REPEATset=""; my $COMMENTset=""; my $HELPpriority =""; my $HELPonoff =""; my $HELPcondition =""; my $HELPexit=""; my $HELPtimer=""; my $HELPrepeats=""; my $HELPexeccmd=""; my $HELPdelay=""; if ( AttrVal( $Name, 'MSwitch_Help', "0" ) eq '1' ) { $HELPpriority = ""; $HELPonoff = ""; $HELPcondition = ""; $HELPexit=""; $HELPtimer=""; $HELPrepeats=""; $HELPexeccmd=""; $HELPdelay=""; } if ( $affecteddevices[0] ne 'no_device' ) { ####################### sortierungsblock $sortierung =""; if ( $hash->{INIT} ne 'define' ) { $sortierung .= " device actions sortby: "; my $select = ReadingsVal( $Name, '.sortby', 'none' ); if ( $expertmode ne '1' && $select eq 'priority' ) { $select = 'none'; readingsSingleUpdate( $hash, ".sortby", $select, 0 ); } my $nonef = ""; my $priorityf = ""; my $showf = ""; $nonef = 'selected="selected"' if $select eq 'none'; $priorityf = 'selected="selected"' if $select eq 'priority'; $showf = 'selected="selected"' if $select eq 'show'; $sortierung .= ' $sortierung "; ########################## # $detailhtml .= $sortierung; ########################## my $alert; foreach (@affecteddevices) { $IDsatz=""; $ACTIONsatz=""; $COND1set1=""; $COND1set2=""; $EXECset1=""; $EXECset2=""; $COMMENTset=""; my $nopoint = $_; $nopoint =~ s/\./point/g; $alert = ''; my @devicesplit = split( /-AbsCmd/, $_ ); my $devicenamet = $devicesplit[0]; # prüfe auf nicht vorhandenes device if ( $devicenamet ne "FreeCmd" && $devicenamet ne "MSwitch_Self" && !defined $cmdsatz{$devicenamet} ) { $alert ='
Achtung: Dieses Device ist nicht vorhanden , bitte mit "set changed_renamed" korrigieren !
'; $cmdsatz{$devicenamet} = $savedetails{ $_ . '_on' } . " " . $savedetails{ $_ . '_off' }; } my $zusatz = ""; my $add = $devicenamet; if ( $devicenamet eq "MSwitch_Self" ) { $devicenamet = $Name; $zusatz = "MSwitch_Self -> "; $add = "MSwitch_Self"; } my $devicenumber = $devicesplit[1]; my @befehlssatz = ''; if ( $devicenamet eq "FreeCmd" ) { $cmdsatz{$devicenamet} = ''; } @befehlssatz = split( / /, $cmdsatz{$devicenamet} ); my $aktdevice = $_; ## optionen erzeugen my $option1html = ''; my $option2html = ''; my $selectedhtml = ""; if ( !defined( $savedetails{ $aktdevice . '_on' } ) ) { my $key = ''; $key = $aktdevice . "_on"; $savedetails{$key} = 'no_action'; } if ( !defined( $savedetails{ $aktdevice . '_off' } ) ) { my $key = ''; $key = $aktdevice . "_off"; $savedetails{$key} = 'no_action'; } if ( !defined( $savedetails{ $aktdevice . '_onarg' } ) ) { my $key = ''; $key = $aktdevice . "_onarg"; $savedetails{$key} = ''; } if ( !defined( $savedetails{ $aktdevice . '_offarg' } ) ) { my $key = ''; $key = $aktdevice . "_offarg"; $savedetails{$key} = ''; } if ( !defined( $savedetails{ $aktdevice . '_delayaton' } ) ) { my $key = ''; $key = $aktdevice . "_delayaton"; $savedetails{$key} = 'delay1'; } if ( !defined( $savedetails{ $aktdevice . '_delayatoff' } ) ) { my $key = ''; $key = $aktdevice . "_delayatoff"; $savedetails{$key} = 'delay1'; } if ( !defined( $savedetails{ $aktdevice . '_timeon' } ) ) { my $key = ''; $key = $aktdevice . "_timeon"; #$savedetails{$key} = '000000'; #change $savedetails{$key} = '00:00:00'; } if ( !defined( $savedetails{ $aktdevice . '_timeoff' } ) ) { my $key = ''; $key = $aktdevice . "_timeoff"; #$savedetails{$key} = '000000'; #change $savedetails{$key} = '00:00:00'; } if ( !defined( $savedetails{ $aktdevice . '_conditionon' } ) ) { my $key = ''; $key = $aktdevice . "_conditionon"; $savedetails{$key} = ''; } if ( !defined( $savedetails{ $aktdevice . '_conditionoff' } ) ) { my $key = ''; $key = $aktdevice . "_conditionoff"; $savedetails{$key} = ''; } foreach (@befehlssatz) #befehlssatz einfügen { my @aktcmdset = split( /:/, $_ ); # befehl von noarg etc. trennen $selectedhtml = ""; next if !defined $aktcmdset[0]; #changed 19.06 if ( $aktcmdset[0] eq $savedetails{ $aktdevice . '_on' } ) { $selectedhtml = "selected=\"selected\""; } $option1html = $option1html . ""; $selectedhtml = ""; if ( $aktcmdset[0] eq $savedetails{ $aktdevice . '_off' } ) { $selectedhtml = "selected=\"selected\""; } $option2html = $option2html . ""; } if ( '' eq $savedetails{ $aktdevice . '_delayaton' } ) { $savedetails{ $aktdevice . '_delayaton' } = 'delay1'; } if ( '' eq $savedetails{ $aktdevice . '_delayatoff' } ) { $savedetails{ $aktdevice . '_delayatoff' } = 'delay1'; } if ( '' eq $savedetails{ $aktdevice . '_timeoff' } ) { $savedetails{ $aktdevice . '_timeoff' } = '0'; } if ( '' eq $savedetails{ $aktdevice . '_timeon' } ) { $savedetails{ $aktdevice . '_timeon' } = '0'; } if ( !defined $savedetails{ $aktdevice . '_showreihe' } || '' eq $savedetails{ $aktdevice . '_showreihe' } ) { $savedetails{ $aktdevice . '_showreihe' } = '1'; } $savedetails{ $aktdevice . '_onarg' } =~ s/#\[ti\]/~/g; $savedetails{ $aktdevice . '_offarg' } =~ s/#\[ti\]/~/g; $savedetails{ $aktdevice . '_onarg' } =~ s/#\[wa\]/|/g; #neu $savedetails{ $aktdevice . '_offarg' } =~ s/#\[wa\]/|/g; #neu my $dalias = ''; if ( $devicenamet ne "FreeCmd" ) { $dalias = "(a: " . AttrVal( $devicenamet, 'alias', "no" ) . ")" if AttrVal( $devicenamet, 'alias', "no" ) ne "no"; } my $realname = ''; if ( AttrVal( $Name, 'MSwitch_Debug', "0" ) eq '4' ) { $realname = ""; } else { $realname = ""; } if ( $expertmode eq '1' ) { $NAMEsatz = "$zusatz $devicenamet $realname   $dalias $alert"; ###################### priority my $aktfolge = $reihenfolgehtml; my $newname = "reihe" . $nopoint; my $tochange =""; my $change =""; $aktfolge =~ s/reihe/$newname/g; $aktfolge =~ s/$tochange/$change/g; $IDsatz="priority: " . $aktfolge . " "; # ende # show # showfolgehtml $aktfolge = $showfolgehtml; $newname = "showreihe" . $nopoint; $tochange =""; $change =""; $aktfolge =~ s/showreihe/$newname/g; $aktfolge =~ s/$tochange/$change/g; $IDsatz.="displaysequence: " . $aktfolge . " " if ( $hash->{INIT} ne 'define' ); #### # ID $aktfolge = $idfolgehtml; $newname = "idreihe" . $nopoint; $tochange =""; $change =""; $aktfolge =~ s/idreihe/$newname/g; $aktfolge =~ s/$tochange/$change/g; $IDsatz.="ID: " . $aktfolge; $aktfolge = $hidehtml; $newname = "hidecmd" . $nopoint; $tochange =""; my $change =""; $aktfolge =~ s/showreihe/$newname/g; $aktfolge =~ s/$tochange/$change/g; $IDsatz.= "displaysequence: " . $aktfolge . " " if ( $hash->{INIT} ne 'define' ); $aktfolge = $hidehtml; $newname = "hidecmd" . $nopoint; $tochange ="