10_MQTT2_DEVICE.pm: enahance the devicetopic attribute (Forum #126679)
git-svn-id: https://svn.fhem.de/fhem/trunk@25867 2b470e98-0d58-463d-a4d8-8e2adae1ed80
This commit is contained in:
@@ -73,7 +73,8 @@ MQTT2_DEVICE_Define($$)
|
|||||||
|
|
||||||
return "wrong syntax for $name: define <name> MQTT2_DEVICE [clientid]"
|
return "wrong syntax for $name: define <name> MQTT2_DEVICE [clientid]"
|
||||||
if(int(@a));
|
if(int(@a));
|
||||||
$hash->{DEVICETOPIC} = $name if(!AttrVal($name, "devicetopic", 0));
|
$hash->{".DT"} = ();
|
||||||
|
$hash->{".DT"}{DEVICETOPIC} = $name if(!AttrVal($name, "devicetopic", 0));
|
||||||
if($hash->{CID}) {
|
if($hash->{CID}) {
|
||||||
my $dpc = $modules{MQTT2_DEVICE}{defptr}{cid};
|
my $dpc = $modules{MQTT2_DEVICE}{defptr}{cid};
|
||||||
if(!$dpc->{$hash->{CID}}) {
|
if(!$dpc->{$hash->{CID}}) {
|
||||||
@@ -163,7 +164,7 @@ MQTT2_DEVICE_Parse($$)
|
|||||||
|
|
||||||
foreach my $re (keys %{$dp}) {
|
foreach my $re (keys %{$dp}) {
|
||||||
my $reAll = $re;
|
my $reAll = $re;
|
||||||
$reAll =~ s/\$DEVICETOPIC/\.\*/g;
|
$reAll =~ s/\$[a-z0-9_]+/\.\*/gi;
|
||||||
|
|
||||||
next if(!("$topic:$value" =~ m/^$reAll$/s ||
|
next if(!("$topic:$value" =~ m/^$reAll$/s ||
|
||||||
"$cid:$topic:$value" =~ m/^$reAll$/s));
|
"$cid:$topic:$value" =~ m/^$reAll$/s));
|
||||||
@@ -172,7 +173,7 @@ MQTT2_DEVICE_Parse($$)
|
|||||||
my $hash = $defs{$dev};
|
my $hash = $defs{$dev};
|
||||||
next if(!$hash);
|
next if(!$hash);
|
||||||
my $reRepl = $re;
|
my $reRepl = $re;
|
||||||
$reRepl =~ s/\$DEVICETOPIC/$hash->{DEVICETOPIC}/g;
|
map { $reRepl =~ s/\$$_/$hash->{".DT"}{$_}/g } keys %{$hash->{".DT"}};
|
||||||
next if(!("$topic:$value" =~ m/^$reRepl$/s ||
|
next if(!("$topic:$value" =~ m/^$reRepl$/s ||
|
||||||
"$cid:$topic:$value" =~ m/^$reRepl$/s));
|
"$cid:$topic:$value" =~ m/^$reRepl$/s));
|
||||||
next if(IsDisabled($dev));
|
next if(IsDisabled($dev));
|
||||||
@@ -180,9 +181,10 @@ MQTT2_DEVICE_Parse($$)
|
|||||||
Log3 $dev, 4, "MQTT2_DEVICE_Parse: $dev $topic => $code";
|
Log3 $dev, 4, "MQTT2_DEVICE_Parse: $dev $topic => $code";
|
||||||
|
|
||||||
if($code =~ m/^{.*}$/s) {
|
if($code =~ m/^{.*}$/s) {
|
||||||
$code = EvalSpecials($code, ("%TOPIC"=>$topic, "%EVENT"=>$value,
|
my %v = ("%TOPIC"=>$topic, "%EVENT"=>$value, "%NAME"=>$hash->{NAME},
|
||||||
"%DEVICETOPIC"=>$hash->{DEVICETOPIC}, "%NAME"=>$hash->{NAME},
|
"%CID"=>$cid, "%JSONMAP","\$defs{\"$dev\"}{JSONMAP}");
|
||||||
"%CID"=>$cid, "%JSONMAP","\$defs{\"$dev\"}{JSONMAP}"));
|
map { $v{"%$_"} = $hash->{".DT"}{$_} } keys %{$hash->{".DT"}};
|
||||||
|
$code = EvalSpecials($code, %v);
|
||||||
my $ret = AnalyzePerlCommand(undef, $code);
|
my $ret = AnalyzePerlCommand(undef, $code);
|
||||||
if($ret && ref $ret eq "HASH") {
|
if($ret && ref $ret eq "HASH") {
|
||||||
readingsBeginUpdate($hash);
|
readingsBeginUpdate($hash);
|
||||||
@@ -329,10 +331,10 @@ MQTT2_buildCmd($$$)
|
|||||||
|
|
||||||
shift @{$a};
|
shift @{$a};
|
||||||
if($cmd =~ m/^{.*}\s*$/) {
|
if($cmd =~ m/^{.*}\s*$/) {
|
||||||
$cmd = EvalSpecials($cmd,
|
my %v = ("%EVENT" => join(" ",@{$a}),
|
||||||
("%EVENT" => join(" ",@{$a}),
|
"%NAME" => $hash->{NAME});
|
||||||
"%NAME" => $hash->{NAME},
|
map { $v{"%$_"} = $hash->{".DT"}{$_} } keys %{$hash->{".DT"}};
|
||||||
"%DEVICETOPIC" => $hash->{DEVICETOPIC}));
|
$cmd = EvalSpecials($cmd,%v);
|
||||||
$cmd = AnalyzeCommandChain($hash->{CL}, $cmd);
|
$cmd = AnalyzeCommandChain($hash->{CL}, $cmd);
|
||||||
return if(!$cmd);
|
return if(!$cmd);
|
||||||
|
|
||||||
@@ -349,7 +351,7 @@ MQTT2_buildCmd($$$)
|
|||||||
$cmd .= " ".join(" ",@{$a}) if(@{$a});
|
$cmd .= " ".join(" ",@{$a}) if(@{$a});
|
||||||
}
|
}
|
||||||
$cmd =~ s/\$NAME/$hash->{NAME}/g;
|
$cmd =~ s/\$NAME/$hash->{NAME}/g;
|
||||||
$cmd =~ s/\$DEVICETOPIC/$hash->{DEVICETOPIC}/g;
|
map { $cmd =~ s/\$$_/$hash->{".DT"}{$_}/g } keys %{$hash->{".DT"}};
|
||||||
}
|
}
|
||||||
|
|
||||||
return $cmd;
|
return $cmd;
|
||||||
@@ -438,7 +440,19 @@ MQTT2_DEVICE_Attr($$)
|
|||||||
$attrName = "" if(!$attrName);
|
$attrName = "" if(!$attrName);
|
||||||
|
|
||||||
if($attrName eq "devicetopic") {
|
if($attrName eq "devicetopic") {
|
||||||
$hash->{DEVICETOPIC} = ($type eq "del" ? $hash->{NAME} : $param);
|
$hash->{".DT"} = ();
|
||||||
|
if($type eq "del") {
|
||||||
|
$hash->{".DT"}{DEVICETOPIC} = $hash->{NAME};
|
||||||
|
} elsif($param !~ m/=/) {
|
||||||
|
$hash->{".DT"}{DEVICETOPIC} = $param
|
||||||
|
} else {
|
||||||
|
my ($a, $h) = parseParams($param); #126679
|
||||||
|
foreach my $key (keys %{$h}) {
|
||||||
|
return "$key is not valid, must only contain a-zA-z0-9_"
|
||||||
|
if($key !~ m/[a-z0-9_]/);
|
||||||
|
}
|
||||||
|
$hash->{".DT"} = $h;
|
||||||
|
}
|
||||||
MQTT2_DEVICE_addReading($dev, AttrVal($dev, "readingList", ""));
|
MQTT2_DEVICE_addReading($dev, AttrVal($dev, "readingList", ""));
|
||||||
return undef;
|
return undef;
|
||||||
}
|
}
|
||||||
@@ -461,11 +475,10 @@ MQTT2_DEVICE_Attr($$)
|
|||||||
|
|
||||||
if($atype eq "reading") {
|
if($atype eq "reading") {
|
||||||
if($par2 =~ m/^{.*}\s*$/) {
|
if($par2 =~ m/^{.*}\s*$/) {
|
||||||
my $ret = perlSyntaxCheck($par2,
|
my %v = ("%TOPIC"=>1, "%EVENT"=>"0 1 2 3 4 5 6 7 8 9",
|
||||||
("%TOPIC"=>1, "%EVENT"=>"0 1 2 3 4 5 6 7 8 9",
|
"%NAME"=>$dev, "%CID"=>"clientId", "%JSONMAP"=>"");
|
||||||
"%NAME"=>$dev, "%CID"=>"clientId",
|
map { $v{"%$_"} = $hash->{".DT"}{$_} } keys %{$hash->{".DT"}};
|
||||||
"%DEVICETOPIC"=>$hash->{DEVICETOPIC},
|
my $ret = perlSyntaxCheck($par2, %v);
|
||||||
"%JSONMAP"=>""));
|
|
||||||
return $ret if($ret);
|
return $ret if($ret);
|
||||||
} else {
|
} else {
|
||||||
return "$dev: bad reading name $par2 ".
|
return "$dev: bad reading name $par2 ".
|
||||||
@@ -474,10 +487,9 @@ MQTT2_DEVICE_Attr($$)
|
|||||||
}
|
}
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
my $ret = perlSyntaxCheck($par2,
|
my %v = ("%NAME"=>$dev, "%EVENT"=>"0 1 2 3 4 5 6 7 8 9");
|
||||||
("%NAME"=>$dev,
|
map { $v{"%$_"} = $hash->{".DT"}{$_} } keys %{$hash->{".DT"}};
|
||||||
"%EVENT"=>"0 1 2 3 4 5 6 7 8 9",
|
my $ret = perlSyntaxCheck($par2, %v);
|
||||||
"%DEVICETOPIC"=>$dev));
|
|
||||||
return $ret if($ret);
|
return $ret if($ret);
|
||||||
|
|
||||||
}
|
}
|
||||||
@@ -603,8 +615,8 @@ MQTT2_DEVICE_addReading($$)
|
|||||||
{
|
{
|
||||||
my ($name, $param) = @_;
|
my ($name, $param) = @_;
|
||||||
MQTT2_DEVICE_delReading($name);
|
MQTT2_DEVICE_delReading($name);
|
||||||
|
my $hash = $defs{$name};
|
||||||
my $cid = $defs{$name}{CID};
|
my $cid = $defs{$name}{CID};
|
||||||
my $dt = $defs{$name}{DEVICETOPIC};
|
|
||||||
foreach my $line (split("\n", $param)) {
|
foreach my $line (split("\n", $param)) {
|
||||||
next if($line eq "");
|
next if($line eq "");
|
||||||
my ($re,$code) = split(" ", $line,2);
|
my ($re,$code) = split(" ", $line,2);
|
||||||
@@ -612,7 +624,7 @@ MQTT2_DEVICE_addReading($$)
|
|||||||
my $errMsg = CheckRegexp($re, "readingList attribute for $name");
|
my $errMsg = CheckRegexp($re, "readingList attribute for $name");
|
||||||
return $errMsg if($errMsg);
|
return $errMsg if($errMsg);
|
||||||
|
|
||||||
$re =~ s/\$DEVICETOPIC/$dt/g;
|
map { $re =~ s/\$$_/$hash->{".DT"}{$_}/g } keys %{$hash->{".DT"}};
|
||||||
if($cid && $re =~ m/^$cid:/) {
|
if($cid && $re =~ m/^$cid:/) {
|
||||||
if($re =~ m/^$cid:([^\\\?.*\[\](|)]+):\.\*$/) { # cid:topic:.*
|
if($re =~ m/^$cid:([^\\\?.*\[\](|)]+):\.\*$/) { # cid:topic:.*
|
||||||
$modules{MQTT2_DEVICE}{defptr}{"re:$cid:$1"}{$re}{"$name,$code"} = 1;
|
$modules{MQTT2_DEVICE}{defptr}{"re:$cid:$1"}{$re}{"$name,$code"} = 1;
|
||||||
@@ -652,8 +664,7 @@ MQTT2_DEVICE_Rename($$)
|
|||||||
my ($new, $old) = @_;
|
my ($new, $old) = @_;
|
||||||
MQTT2_DEVICE_delReading($old);
|
MQTT2_DEVICE_delReading($old);
|
||||||
MQTT2_DEVICE_addReading($new, AttrVal($new, "readingList", ""));
|
MQTT2_DEVICE_addReading($new, AttrVal($new, "readingList", ""));
|
||||||
$defs{$new}{DEVICETOPIC} = $new
|
$defs{$new}{".DT"}{DEVICETOPIC} = $new if(!AttrVal($new,"devicetopic",undef));
|
||||||
if($defs{$new}{DEVICETOPIC} eq $old && !AttrVal($new,"devicetopic",undef));
|
|
||||||
MQTT2_DEVICE_setBridgeRegexp();
|
MQTT2_DEVICE_setBridgeRegexp();
|
||||||
return undef;
|
return undef;
|
||||||
}
|
}
|
||||||
@@ -931,7 +942,7 @@ zigbee2mqtt_devStateIcon255($;$$)
|
|||||||
if set to 0, disables extending the readingList, when the IODev
|
if set to 0, disables extending the readingList, when the IODev
|
||||||
autocreate is also set. Default is 1, i.e. new topics will be
|
autocreate is also set. Default is 1, i.e. new topics will be
|
||||||
automatically added to the readingList.
|
automatically added to the readingList.
|
||||||
</li>
|
</li><br>
|
||||||
|
|
||||||
<a id="MQTT2_DEVICE-attr-bridgeRegexp"></a>
|
<a id="MQTT2_DEVICE-attr-bridgeRegexp"></a>
|
||||||
<li>bridgeRegexp <regexp> newClientId ...<br>
|
<li>bridgeRegexp <regexp> newClientId ...<br>
|
||||||
@@ -965,9 +976,20 @@ zigbee2mqtt_devStateIcon255($;$$)
|
|||||||
|
|
||||||
<a id="MQTT2_DEVICE-attr-devicetopic"></a>
|
<a id="MQTT2_DEVICE-attr-devicetopic"></a>
|
||||||
<li>devicetopic value<br>
|
<li>devicetopic value<br>
|
||||||
replace $DEVICETOPIC in the topic part of readingList, setList and
|
<ul>
|
||||||
getList with value. if not set, $DEVICETOPIC will be replaced with the
|
<li>if value does <b>not</b> contain an equal sign (=),
|
||||||
name of the device.
|
replace $DEVICETOPIC in the topic part of the readingList, setList and
|
||||||
|
getList attributes with value.</li>
|
||||||
|
<li>if the value <b>does</b> contain an equal sign (=), then it is
|
||||||
|
interpreted as
|
||||||
|
<ul><code>Var1=Var1Value Var2="Value with space" Var3=...</code></ul>
|
||||||
|
and $Var1,$Var2,$Var3 are replaced in the readingList, setList and
|
||||||
|
getList attributes with the corresponding value.<br>
|
||||||
|
Note: the name Var1,etc must only contain the letters A-Za-z0-9_.
|
||||||
|
If the attribute is not set, $DEVICETOPIC will be replaced with the
|
||||||
|
name of the device in the attributes mentioned above.
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
</li><br>
|
</li><br>
|
||||||
|
|
||||||
<a id="MQTT2_DEVICE-attr-devPos"></a>
|
<a id="MQTT2_DEVICE-attr-devPos"></a>
|
||||||
|
|||||||
Reference in New Issue
Block a user