Hallo Zusammen,
ich habe mich dazu entschlossen, meine mehr als 100 MQTT Geräte StepByStep von MQTT auf MQTT2 umzustellen.
Nun habe ich natürlich schon diverse Versuche unternommen, komme aber nicht zum Ziel, da die Doku(Wiki) aus meiner Sicht zuviel kreuz & quer verlinkt und für mich total unverständlich ist.
Topiclogik meiner Geräte:
shellies/<Typ>/<Stockwerk>/<Devicename>
z.B. shellies/light/1g/shelly1-ABCDEF123456
Broker:
Mosquitto
Den notwendigen MQTT2_CLIENT mit Autocreate habe ich angelegt.
define mqttIO MQTT2_CLIENT mqtt.mydomain.intranet:1883 MQTT2_CLIENT
attr mqttIO autocreate complex
attr mqttIO subscriptions shellies/#
Die Devices werden danach auch angelegt, allerdings komme ich mit der Template Funktion überhaupt nicht zurecht.
Angelegt wird ein:shellies/relay/0/command on
Anstatt (erwartet):shellies/light/1g/shelly1-ABCDEF123456/relay/0/command on
Muss hier an einem der MQTT2 Devices noch etwas konfuguriert werden, oder kommt hier die MQTT2_BRIDGE ins Spiel ?
Gruß,
JudgeDredd
Hi,
die Templates erwarten einen topic: shellies/<Devicename> damit wird der DEVNAME bei Dir nicht ermittelt und der Zweig fehlt komplett.
Was mich verwundert: Eigentlicht hätte er light ermitteln müssen https://regex101.com/r/8MlPOd/1
Du müsstest die Templates anpassen, eine Bridge brauchst Du dafür nicht.
ich würde an Deiner Stelle mit dem attr devicetopic arbeiten
Zitatdevicetopic value
replace $DEVICETOPIC in the topic part of readingList, setList and getList with value. if not set, $DEVICETOPIC will be replaced with the name of the device
Gruß Otto
Ergänzend, da auch schon fertig:
Also: die attrTemplate funktionieren am besten, wenn die "default"-Topic-Strukturen gegeben sind. Sind sie bei dir eben nicht, was bedeutet, dass Handarbeit angesagt ist (der Tipp mit $DEVICETOPIC ist gut!)... Dabei kannst du dir durchaus anzeigen lassen, was attrTemplate machen würde und diese Informationen dann eben für dich anpassen.
Eine "MQTT2_BRIDGE" kenne ich nicht, gemeint ist vielleicht "bridgeRegexp"? Eine solche könnte helfen, dass nicht alle Geräte in einem gemeinsamen Topf landen, zwingend ist das aber nicht, wenn du sowieso alles von Hand anlegen mußt.
Dann: "command" klingt nach Anweisung an das Gerät, nicht nach Info vom Gerät. Diesen Teil sollte man per ignoreRegexp komplett "ausknipsen".
Hoffe, das ist jetzt wenigstens ein klein wenig klarer?
(Zum Einstieg würde ich empfehlen, einen oder zwei Test-Shelly mit default-Topics mal per MQTT2_SERVER in FHEM einzubinden, dann wird das Prinzip evtl. klarer).
@Beta-User: Man könnte das Template ergänzen:
{ AttrVal("DEVICE","devicetopic",AttrVal("DEVICE","readingList","")) =~ m,shellies/([^/]*)/, ? $1 : undef }
Damit würde ein vorhandener devicetopic verwendet :)
Hmmm, grübel...
Das mit dem Rückgriff auf "devicetopic" ist eine Überlegung wert, allerdings müßte man dann die komplette innere Logik der Shelly-1-gen-Devices umkrempeln und auch diesen unseligen allgemeinen "announce"-Zweig stilllegen, da die Auswertung auf DEVNAME dann nicht mehr so einfach klappen würde.
Wik könnten bei Nichtvorhandensein von "devicetopic" den "online"-Topic auswerten und das ähnlich via "DEV_TPC" kodieren wie die 2.-Gen-Devices.
Ist aber eine Fleißaufgabe, über die ich mich ganz sicher nicht die kommende Zeit hermache... Aber für den TE wäre das (in Form von RAW-Defs) eine Lösung, wie man da relativ schnell zum Ziel kommen kann...
Zitat von: Otto123 am 16 Februar 2022, 15:07:18
die Templates erwarten einen topic: shellies/<Devicename> damit wird der DEVNAME bei Dir nicht ermittelt und der Zweig fehlt komplett.
Sollte es wirklich so sein, das die Mehrheit hier, keinerlei Struktur in ihrer Topic-Logik verwendet ? ???
Bin ich da echt ein Sonderfall ?
Zitat von: Otto123 am 16 Februar 2022, 15:07:18
ich würde an Deiner Stelle mit dem attr devicetopic arbeiten
Klingt gut, zumindest ausprobieren würde ich es mal, allerdings findet sich weder in der Ref noch im Wiki oder über Google ein vernünftiges Beispiel dafür.
Lediglich die von Dir zitierte Zeile ist alles dazu.
Wo finde ich denn eine ausführliche Doku ?
Zitat von: Beta-User am 16 Februar 2022, 15:13:24Eine "MQTT2_BRIDGE" kenne ich nicht, gemeint ist vielleicht "bridgeRegexp"?
Sorry, ich dachte damit an "MQTT_GENERIC_BRIDGE"
Zitat von: Beta-User am 16 Februar 2022, 15:13:24was bedeutet, dass Handarbeit angesagt ist
Ja, das habe ich befürchtet, aber bei mehr als 100 Geräten, ist das schon schade. Ich hatte mir von MQTT2 doch etwas mehr Komfort ggü. MQTT erhofft.
Zitat von: Beta-User am 16 Februar 2022, 15:13:24
Dann: "command" klingt nach Anweisung an das Gerät, nicht nach Info vom Gerät. Diesen Teil sollte man per ignoreRegexp komplett "ausknipsen".
Hoffe, das ist jetzt wenigstens ein klein wenig klarer?
Korrekt, beim Shelly steht im Topic .../command die Message zum ausführen (z.B. on/off)
Aber klarer wird es auf keinen Fall, leider eher das Gegenteil. Warum sollte man
ignoreRegexp verwenden ?
Wo wird dann von wem, was genau ignoriert ?
Gruß,
JudgeDredd
Zitat von: JudgeDredd am 16 Februar 2022, 16:24:35
Sollte es wirklich so sein, das die Mehrheit hier, keinerlei Struktur in ihrer Topic-Logik verwendet ? ???
Bin ich da echt ein Sonderfall ?
Naja zumindest ich mit meinen wenigen MQTT2-Devices (und keine Shelly, die hab ich [noch] mit dem Shelly-Modul eingebunden) lasse Topic "Standard"...
Ich mache die Name-Logic/Zugehörigkeit etc. in fhem.
Was machst du, wenn dein Shelly die Aufgabe oder den Ort wechselt? ;)
Gruß, Joachim
Zitat von: JudgeDredd am 16 Februar 2022, 16:24:35
Sollte es wirklich so sein, das die Mehrheit hier, keinerlei Struktur in ihrer Topic-Logik verwendet ? ???
Bin ich da echt ein Sonderfall ?
In der Regel gibt es bei "FHEM-only"-setups überhaupt keinen Grund, irgendwas anzupassen, und Shelly-User scheinen "konservativer" zu sein wie z.B. die, die Tasmota nutzen (da wird flexibler analysiert und du hättest die Probleme nicht).
Zitat
Klingt gut, zumindest ausprobieren würde ich es mal, allerdings findet sich weder in der Ref noch im Wiki oder über Google ein vernünftiges Beispiel dafür.
Lediglich die von Dir zitierte Zeile ist alles dazu.
Na ja, die die es nutzen, müssen es nicht groß dokumentieren. Es kommt z.B. bei zigbee2mqtt zum Einsatz, Quellcode wäre zu finden ab https://svn.fhem.de/trac/browser/trunk/fhem/FHEM/lib/AttrTemplate/mqtt2.template#L126 (https://svn.fhem.de/trac/browser/trunk/fhem/FHEM/lib/AttrTemplate/mqtt2.template#L126)
Zitat
Sorry, ich dachte damit an "MQTT_GENERIC_BRIDGE"
Das laß mal außen vor, wenn du es bisher nicht gebraucht hattest.
Zitat
Ja, das habe ich befürchtet, aber bei mehr als 100 Geräten, ist das schon schade. Ich hatte mir von MQTT2 doch etwas mehr Komfort ggü. MQTT erhofft.
Also mal ein Beispiel für "devicetopic" an einem "Einfach-Shelly":
Gezeigt hattest du:
shellies/light/1g/shelly1-ABCDEF123456/relay/0/command on
Das attrTemplate sieht prinzipiell so aus:
name:shelly1
filter:TYPE=MQTT2_DEVICE
desc:Base template for a lot of first generation shelly devices
par:DEVNAME;Shelly1 name in the topic;{ AttrVal("DEVICE","readingList","") =~ m,shellies/([^/]*)/, ? $1 : undef }
par:CALLSPEECHRECOGN;Set this to 0 to not set any speech recogn. related attributes;{ 1 }
order:A_10
attr DEVICE setList\
off:noArg shellies/DEVNAME/relay/0/command off\
on:noArg shellies/DEVNAME/relay/0/command on\
x_update:noArg shellies/DEVNAME/command update_fw\
x_mqttcom shellies/DEVNAME/command $EVTPART1
attr DEVICE readingList \
shellies/DEVNAME/relay/0:.* state\
shellies/DEVNAME/relay/0:.* relay0\
shellies/DEVNAME/input/0:.* input0\
shellies/DEVNAME/online:.* online\
shellies/DEVNAME/announce:.* { json2nameValue($EVENT) }\
shellies/announce:.* { $EVENT =~ m,..id...DEVNAME...mac.*, ? json2nameValue($EVENT) : return }
attr DEVICE devStateIcon {my $onl = ReadingsVal($name,"online","false") eq "false" ? "rot" : ReadingsVal($name,"new_fw","false") eq "true" ? "gelb" : "gruen"; my $light = ReadingsVal($name,"state","off"); my $show = '<a href="';$show .= $onl eq "gelb" ? "/fhem?cmd.dummy=set $name x_update&XHR=1\">" : "http://".ReadingsVal($name,"ip","none").' "target="_blank">'; $show .= FW_makeImage("10px-kreis-".$onl)."</a>"; "<div> $show <a href=\"/fhem?cmd.dummy=set $name toggle&XHR=1\">".FW_makeImage($light)."</a></div>" }
deletereading -q DEVICE (?!associatedWith|IODev).*
set DEVICE x_mqttcom announce
attr DEVICE model shelly1
setreading DEVICE attrTemplateVersion 20211030
option:{ CALLSPEECHRECOGN }
set DEVICE attrTemplate speechcontrol_type_switch
"DEVNAME" würde bei "normaler Topicstruktur" ermittelt als "shelly1-ABCDEF123456"
Wenn man das jetzt mit devicetopic notiert, kommt in etwa das hier raus:
attr testShelly devicetopic shellies/light/1g/shelly1-ABCDEF123456
attr testShelly setList\
off:noArg $DEVICETOPIC/relay/0/command off\
on:noArg $DEVICETOPIC/relay/0/command on\
x_update:noArg $DEVICETOPIC/command update_fw\
x_mqttcom $DEVICETOPIC/command $EVTPART1
attr testShelly readingList \
$DEVICETOPIC/relay/0:.* state\
$DEVICETOPIC/relay/0:.* relay0\
$DEVICETOPIC/input/0:.* input0\
$DEVICETOPIC/online:.* online\
$DEVICETOPIC/announce:.* { json2nameValue($EVENT) }\
shellies/announce:.* { $EVENT =~ m,..id...shelly1-ABCDEF123456...mac.*, ? json2nameValue($EVENT) : return }
attr testShelly devStateIcon {my $onl = ReadingsVal($name,"online","false") eq "false" ? "rot" : ReadingsVal($name,"new_fw","false") eq "true" ? "gelb" : "gruen"; my $light = ReadingsVal($name,"state","off"); my $show = '<a href="';$show .= $onl eq "gelb" ? "/fhem?cmd.dummy=set $name x_update&XHR=1\">" : "http://".ReadingsVal($name,"ip","none").' "target="_blank">'; $show .= FW_makeImage("10px-kreis-".$onl)."</a>"; "<div> $show <a href=\"/fhem?cmd.dummy=set $name toggle&XHR=1\">".FW_makeImage($light)."</a></div>" }
deletereading -q testShelly (?!associatedWith|IODev).*
set testShelly x_mqttcom announce
attr testShelly model shelly1
setreading testShelly attrTemplateVersion 20220216
set testShelly attrTemplate speechcontrol_type_switch
Edit: für einen anderen Shelly desselben Typs hast du also ggf. Anpassungsbedarf an drei Stellen: Name (klar, unvermeidbar), devicetopic und dem "announce" (könnte vermutlich auch per ignoreRegexp ignoriert werden, aber ich habe die Dinger nicht und kann/mag das nicht entscheiden...).
So dramatisch ist es also nicht, wenn das Prinzip mal klar ist (und du ein Gefühl dafür hast, welches attrTemplate ggf. die richtige Basis für weitere Ergänzungen wäre).
ZitatAber klarer wird es auf keinen Fall, leider eher das Gegenteil. Warum sollte man ignoreRegexp verwenden ?
Wo wird dann von wem, was genau ignoriert ?
Du abonnierst im MQTT2_CLIENT "shelly/#". Da sind auch die "Kommandozeilen" drin. Um die direkt wieder im MQTT2_CLIENT auszufiltern, gibt es ein Attribut, Beispiele (die auch diesen Fall umfassen sollten) sind im Wiki zu MQTT2_CLIENT zu finden.
Zitat von: Beta-User am 16 Februar 2022, 15:57:26
Das mit dem Rückgriff auf "devicetopic" ist eine Überlegung wert, allerdings müßte man dann die komplette innere Logik der Shelly-1-gen-Devices umkrempeln und auch diesen unseligen allgemeinen "announce"-Zweig stilllegen, da die Auswertung auf DEVNAME dann nicht mehr so einfach klappen würde.
ich meinte aber DEVNAME mit meinem Code. ich mache das bei valetudo so, um ein konfiguriertes Device erneut mit dem template bügeln zu können. Im Falle JudgeDredd bräuchte der "bloß" seinen devicetopic setzen und kann anschließend das Template anwenden. Kann aber sein ich sehe da jetzt was nicht.
Ich persönlich finde die zusätzliche Strukturierung der MQTT Topics so nützlich wie händische Vergabe von IPv6 Adressen :)
Hi Beta-User,
es liegt mit Sicherheit an mir, aber mit jedem Deiner Posts kommen bei mir mehr Fragzeichen.
Was genau ist denn nun zu tun ?
Soll ich in die Datei "mqtt2.template" manuell ein neues Template mit $DEVICETOPIC einbauen und dann das Attribut beim MQTT2_CLIENT
vor dem erzeugen setzen ?
Die Datei überschreibt es mir doch wieder bei jedem Update.
Zitat von: Beta-User am 16 Februar 2022, 16:43:04
Du abonnierst im MQTT2_CLIENT "shelly/#". Da sind auch die "Kommandozeilen" drin. Um die direkt wieder im MQTT2_CLIENT auszufiltern, gibt es ein Attribut, Beispiele (die auch diesen Fall umfassen sollten) sind im Wiki zu MQTT2_CLIENT zu finden.
Warum sollte man die "Kommandozeilen" denn rausfiltern wollen ? Die brauch ich doch um den Shelly zu schalten.
Gruß,
JudgeDredd
@Otto: Hmm, vielleicht könnte das klappen, dass er sich das so hintrickst (und dann gleich die regex so wählt, dass es mit seiner Topictruktur paßt). Wir können das m.E. so nicht verteilen, das wäre m.E. komplett verwirrend, wenn jemand tatsächlich devicetopic gesetzt hat.
Die Idee, das generell zu machen (aber in der Langform...), finde ich aber nach wie vor eine gute Idee, das würde das weiter verkürzen/standardisieren, da bei den Shelly ja alles bis auf diesen unnötigen (?) Topic mit der "Einheits-Vollstruktur" klarkommt....
Zitat von: Otto123 am 16 Februar 2022, 17:31:17
Ich persönlich finde die zusätzliche Strukturierung der MQTT Topics so nützlich wie händische Vergabe von IPv6 Adressen :)
...das sollte in die Sammlung von "Otto's griffigen Vergleichen" rein ;D .
@JudgeDredd:
Ich predige das "Hände weg von den defaults" (es sei denn, es wäre zwingend erforderlich) seit es attrTemplate gibt; scheinbar nützt das doch was...
Zitat von: JudgeDredd am 16 Februar 2022, 17:43:23
es liegt mit Sicherheit an mir, aber mit jedem Deiner Posts kommen bei mir mehr Fragzeichen.
Dann habe ich es vermutlich noch nicht gut erklärt.
Zitat
Was genau ist denn nun zu tun ?
Soll ich in die Datei "mqtt2.template" manuell ein neues Template mit $DEVICETOPIC einbauen und dann das Attribut beim MQTT2_CLIENT vor dem erzeugen setzen ?
Nein. Du arbeitest manuell, am besten mit einem externen Text-Editor und kopierst dann nur fertige Devices per "RAW-Import" in dein FHEM.
Die Vorlagen kannst du aus der Datei ziehen, falls mal was anderes dabei ist wie eben der gezeigte "einfache" Shelly. Der war als Beispiel gedacht, um den Weg aufzuzeigen, den man gehen muss, um aus einem attrTemplate ein fertiges Device zu bekommen.
Zitat
Warum sollte man die "Kommandozeilen" denn rausfiltern wollen ? Die brauch ich doch um den Shelly zu schalten.
Es geht nur darum, dass dir dein Mosquitto das nicht _weiter als bis zum ID-Device in FHEM hinein_ liefert. FHEM _muss_ diese Infos direkt verwerfen und darf daraus keine Reading-Werte ableiten. Anders gesagt: Diese Daten sind ausschließlich für den ESP bestimmt, FHEM braucht sie nicht, bekommt sie aber.
EDIT: Bitte nicht weiter diskutieren, sondern einfach machen, was unter https://wiki.fhem.de/wiki/MQTT2_CLIENT#ignoreRegexp zu finden ist (kannst gleich noch die tasmota-autodiscovery (
tasmota/
discovery) dazupacken, das ist dieselbe Kategorie "unnützes Zeug" (aus FHEM-Sicht)...)
Zitat von: Beta-User am 16 Februar 2022, 17:50:06Ich predige das "Hände weg von den defaults" (es sei denn, es wäre zwingend erforderlich) seit es attrTemplate gibt; scheinbar nützt das doch was...
ja schon klar, natürlich habe ich eine
neue Template Datei (so wie ich Deinen Post verstanden habe) angelegt und mit { AttrTemplate_Initialize() } eingelesen.
###########################################
# SHELLY
#
# shelly1 using original firmware.
name:MYshelly1
filter:TYPE=MQTT2_DEVICE
desc:Base template for a lot of first generation shelly devices
par:DEVNAME;Shelly1 name in the topic;{ AttrVal("DEVICE","readingList","") =~ m,shellies/([^/]*)/, ? $1 : undef }
par:CALLSPEECHRECOGN;Set this to 0 to not set any speech recogn. related attributes;{ 1 }
order:A_10
attr DEVICE setList\
off:noArg shellies/$DEVICETOPIC/DEVNAME/relay/0/command off\
on:noArg shellies/$DEVICETOPIC/DEVNAME/relay/0/command on\
x_update:noArg shellies/$DEVICETOPIC/DEVNAME/command update_fw\
x_mqttcom shellies/$DEVICETOPIC/DEVNAME/command $EVTPART1
attr DEVICE readingList \
shellies/$DEVICETOPIC/DEVNAME/relay/0:.* state\
shellies/$DEVICETOPIC/DEVNAME/relay/0:.* relay0\
shellies/$DEVICETOPIC/DEVNAME/input/0:.* input0\
shellies/$DEVICETOPIC/DEVNAME/online:.* online\
shellies/$DEVICETOPIC/DEVNAME/announce:.* { json2nameValue($EVENT) }\
shellies/announce:.* { $EVENT =~ m,..id...DEVNAME...mac.*, ? json2nameValue($EVENT) : return }
attr DEVICE devStateIcon {my $onl = ReadingsVal($name,"online","false") eq "false" ? "rot" : ReadingsVal($name,"new_fw","false") eq "true" ? "gelb" : "gruen"; my $light = ReadingsVal($name,"state","off"); my $show = '<a href="';$show .=
deletereading -q DEVICE (?!associatedWith|IODev).*
set DEVICE x_mqttcom announce
attr DEVICE model shelly1
setreading DEVICE attrTemplateVersion 20211030
option:{ CALLSPEECHRECOGN }
set DEVICE attrTemplate speechcontrol_type_switch
Das Attribut devtopic habe ich am Device auf "licht/1g" gesetzt.
Du kannst es Dir vermutlich denken, aber es funktioniert nicht.
Wahrscheinlich habe ich wieder was falsch verstanden. Bin ich wenigstens auf dem richtigen Weg ?
Zitat von: Beta-User am 16 Februar 2022, 17:50:06
Nein. Du arbeitest manuell, am besten mit einem externen Text-Editor und kopierst dann nur fertige Devices per "RAW-Import" in dein FHEM.
Verstehe ich wieder nicht. So habe ich das ja bisher mit dem klassischen MQTT gemacht.
Jetzt also doch wieder keine Templates und lieber alles wie bisher, oder ist das beides zu machen ?
Gruß,
JudgeDredd
...ok, überredet...
Falls du bereit bist, den Hauptteil der Arbeit für alle zu machen, liefere ich dir die Bausteine, mit denen du das zusammenpuzzeln kannst...?
Hi,
hatte auch das Probleme, das etliche Monate für die Umsetzung ins Land gegangen sind.
bei jeden versuch wurden die Fragezeichen mehr, so das ich es immer wieder in die Ecke geschmissen habe.....
Der Empfänger:
defmod HZ8 MQTT2_DEVICE HZ8
attr HZ8 alias M8 Heizung
attr HZ8 devStateStyle style="text-align:right;;;;"
attr HZ8 group Fernwärme
attr HZ8 readingList M/Haus8/Heizung/FV/measured-temp:.* FV\
M/Haus8/Heizung/FR/measured-temp:.* FR\
M/Haus8/Heizung/HV/measured-temp:.* HV\
M/Haus8/Heizung/HR/measured-temp:.* HR\
M/Haus8/Heizung/WV/measured-temp:.* WV\
M/Haus8/Heizung/WR/measured-temp:.* WR\
M/Haus8/Heizung/WW/measured-temp:.* WW\
M/Haus8/Heizung/WS/measured-temp:.* WS\
M/Haus8/Heizung/WZ/measured-temp:.* WZ
attr HZ8 room device-MQTT,heizung
attr HZ8 stateFormat [HZ8:FV] °C
setstate HZ8 72.2 °C
setstate HZ8 2022-02-16 19:10:30 FR 47.6
setstate HZ8 2022-02-16 19:10:18 FV 72.2
setstate HZ8 2022-02-16 19:10:18 HR 47.5
setstate HZ8 2022-02-16 19:10:19 HV 56.8
setstate HZ8 2022-02-16 08:08:08 IODev mqttClient
setstate HZ8 2022-02-16 19:10:25 WR 44.5
setstate HZ8 2022-02-16 19:10:17 WS 53.5
setstate HZ8 2022-02-16 19:10:21 WV 47.3
setstate HZ8 2022-02-16 19:10:14 WW 52.9
setstate HZ8 2022-02-16 19:10:17 WZ 50.5
und der Sender:
defmod no.DS18B20_046777911002 notify DS18B20_046777911002:.* \
set mqttClient publish -r M/Haus8/Heizung/FV/measured-temp [DS18B20_046777911002:measured-temp];;\
set mqttClient publish -r M/Haus8/Heizung/FV/fast-temp [DS18B20_046777911002:fast-temp];;\
set mqttClient publish -r M/Haus8/Heizung/FV/activity [DS18B20_046777911002:activity];;\
set mqttClient publish -r M/Haus8/Heizung/FV/alarm [DS18B20_046777911002:alarm];;
attr no.DS18B20_046777911002 alias Fernwärmevorlauf
attr no.DS18B20_046777911002 room Heizung
setstate no.DS18B20_046777911002 2022-02-16 19:16:04
setstate no.DS18B20_046777911002 2022-02-16 18:43:59 state active
setstate no.DS18B20_046777911002 2022-02-16 19:16:04 triggeredByDev DS18B20_046777911002
setstate no.DS18B20_046777911002 2022-02-16 19:16:04 triggeredByEvent fast-temp: 75.0
und damit habe ich dann alle devices auf MQTT2 umgesetzt....
gruss
Zitat von: eisman am 16 Februar 2022, 19:18:37
hatte auch das Probleme, das etliche Monate für die Umsetzung ins Land gegangen sind.
bei jeden versuch wurden die Fragezeichen mehr, so das ich es immer wieder in die Ecke geschmissen habe.....
...das ist aber doch ein Ersatzweg für die Verwendung von MQTT_GENERIC_BRIDGE und hat mit dem (im Threadtitel nur unzureichend widergegebenen) eigentlichen Anliegen des TE doch wenig zu tun, oder...?
So: einmal Bausteine für die Überarbeitung der attrTemplate; erst mal im Zusammenhang für ein Beispiel:
# shelly1 using original firmware.
name:shelly1
filter:TYPE=MQTT2_DEVICE
desc:Base template for a lot of first generation shelly devices
par:DEV_TPC;base topic to be used for devicetopic attribute;{ my $is = AttrVal('DEVICE','devicetopic',undef); return $is if $is; AttrVal('DEVICE','readingList,'') =~ m,(?:[^:]*:)?(shellies.*/[^/]*)/online, ? $1 : undef }
par:DEVNAME;Shelly1 name in the topic;{ par:DEV_TPC;Shelly name in the topic;{ AttrVal('DEVICE','devicetopic',undef) =~ m,shellies.*/(shelly[^/]+)?, ? $1 : AttrVal('DEVICE','readingList',') =~ m,shellies/([^/]+)/online, ? $1 : undef }
par:CALLSPEECHRECOGN;Set this to 0 to not set any speech recogn. related attributes;{ 1 }
order:A_10
attr DEVICE devicetopic DEV_TPC
attr DEVICE setList\
off:noArg $\DEVICETOPIC/relay/0/command off\
on:noArg $\DEVICETOPIC/relay/0/command on\
x_update:noArg $\DEVICETOPIC/command update_fw\
x_mqttcom $\DEVICETOPIC/command $EVTPART1
attr DEVICE readingList \
$\DEVICETOPIC/relay/0:.* state\
$\DEVICETOPIC/relay/0:.* relay0\
$\DEVICETOPIC/input/0:.* input0\
$\DEVICETOPIC/online:.* online\
$\DEVICETOPIC/announce:.* { json2nameValue($EVENT) }\
shellies/announce:.* { $EVENT =~ m,..id...DEVNAME...mac.*, ? json2nameValue($EVENT) : return }
attr DEVICE devStateIcon {my $onl = ReadingsVal($name,"online","false") eq "false" ? "rot" : ReadingsVal($name,"new_fw","false") eq "true" ? "gelb" : "gruen"; my $light = ReadingsVal($name,"state","off"); my $show = '<a href="';$show .= $onl eq "gelb" ? "/fhem?cmd.dummy=set $name x_update&XHR=1\">" : "http://".ReadingsVal($name,"ip","none").' "target="_blank">'; $show .= FW_makeImage("10px-kreis-".$onl)."</a>"; "<div> $show <a href=\"/fhem?cmd.dummy=set $name toggle&XHR=1\">".FW_makeImage($light)."</a></div>" }
deletereading -q DEVICE (?!associatedWith|IODev).*
set DEVICE x_mqttcom announce
attr DEVICE model shelly1
setreading DEVICE attrTemplateVersion 20220216
option:{ CALLSPEECHRECOGN }
set DEVICE attrTemplate speechcontrol_type_switch
Es wäre erst zu testen, ob das klappt (!!!). Möglichst mit "frischen" Shelly, existierenden Definitionen, und eben der Variante hier (wieder: Erstanwendung und Wiederholung).
Wenn ja:
Zu ändern in allen (!!) bestehenden Shelly-1.-Gen.- attrTemplates wäre:
- Ergänzen der Zeile für die Ermittlung des Parameters "DEV_TPC"
- Ergänzen der Zeile zum Setzen des neuen Attributs "devicetopic"
- Ändern der Sytax auf $\DEVICETOPIC in readingList, getList, setList
- update des "Zeitstempels" des attrTemplate
Am besten in der aktuellsten (eben nochmal im svn geändert) mqtt2.template direkt, Ergebnis dann gerne als Komplettdownload hier. Fragen? Gerne...
PS: Danke an Otto für den Schubs ;)
Hi Beta-User,
Zitat von: Beta-User am 16 Februar 2022, 19:05:42Falls du bereit bist, den Hauptteil der Arbeit für alle zu machen, liefere ich dir die Bausteine, mit denen du das zusammenpuzzeln kannst...?
Also gerne bin ich bereit im Rahmen meiner Möglichkeiten mitzuwirken. Auf keinen Fall möchte ich, das Andere für meine Sonderlocken die Arbeit machen.
Ich habe Dein Templatevorschlag mal ausprobiert.
3 kleine Syntaxfehler habe ich korrigiert.
Hochkomma hinter Readingsname bei AttrVal
'par:DEV_TPC;base topic to be used for devicetopic attribute;{ my $is = AttrVal('DEVICE','devicetopic',undef); return $is if $is; AttrVal('DEVICE','readingList','') =~ m,(?:[^:]*:)?(shellies.*/[^/]*)/online, ? $1 : undef }
Hochkomma beim default AttrVal-Wert
'Abschließende Klammen
}par:DEVNAME;Shelly1 name in the topic;{ par:DEV_TPC;Shelly name in the topic;{ AttrVal('DEVICE','devicetopic',undef) =~ m,shellies.*/(shelly[^/]+)?, ? $1 : AttrVal('DEVICE','readingList','') =~ m,shellies/([^/]+)/online, ? $1 : undef } }
Nach der Korrektur habe ich dann:
# shelly1 using original firmware.
name:shelly1_customTopic
filter:TYPE=MQTT2_DEVICE
desc:Base template for a lot of first generation shelly devices
par:DEV_TPC;base topic to be used for devicetopic attribute;{ my $is = AttrVal('DEVICE','devicetopic',undef); return $is if $is; AttrVal('DEVICE','readingList','') =~ m,(?:[^:]*:)?(shellies.*/[^/]*)/online, ? $1 : undef }
par:DEVNAME;Shelly1 name in the topic;{ par:DEV_TPC;Shelly name in the topic;{ AttrVal('DEVICE','devicetopic',undef) =~ m,shellies.*/(shelly[^/]+)?, ? $1 : AttrVal('DEVICE','readingList','') =~ m,shellies/([^/]+)/online, ? $1 : undef } }
par:CALLSPEECHRECOGN;Set this to 0 to not set any speech recogn. related attributes;{ 1 }
order:A_10
attr DEVICE devicetopic DEV_TPC
attr DEVICE setList\
off:noArg $\DEVICETOPIC/relay/0/command off\
on:noArg $\DEVICETOPIC/relay/0/command on\
x_update:noArg $\DEVICETOPIC/command update_fw\
x_mqttcom $\DEVICETOPIC/command $EVTPART1
attr DEVICE readingList \
$\DEVICETOPIC/relay/0:.* state\
$\DEVICETOPIC/relay/0:.* relay0\
$\DEVICETOPIC/input/0:.* input0\
$\DEVICETOPIC/online:.* online\
$\DEVICETOPIC/announce:.* { json2nameValue($EVENT) }\
shellies/announce:.* { $EVENT =~ m,..id...DEVNAME...mac.*, ? json2nameValue($EVENT) : return }
attr DEVICE devStateIcon {my $onl = ReadingsVal($name,"online","false") eq "false" ? "rot" : ReadingsVal($name,"new_fw","false") eq "true" ? "gelb" : "gruen"; my $light = ReadingsVal($name,"state","off"); my $show = '<a href="';$show .= $onl eq "gelb" ? "/fhem?cmd.dummy=set $name x_update&XHR=1\">" : "http://".ReadingsVal($name,"ip","none").' "target="_blank">'; $show .= FW_makeImage("10px-kreis-".$onl)."</a>"; "<div> $show <a href=\"/fhem?cmd.dummy=set $name toggle&XHR=1\">".FW_makeImage($light)."</a></div>" }
deletereading -q DEVICE (?!associatedWith|IODev).*
set DEVICE x_mqttcom announce
attr DEVICE model shelly1
setreading DEVICE attrTemplateVersion 20220216
option:{ CALLSPEECHRECOGN }
set DEVICE attrTemplate speechcontrol_type_switch
Wenn ich das Template anwende, bekomme ich aber noch immer den Fehler:
for param DEVNAME: Can't locate object method "in" via package "the" (perhaps you forgot to load "the"?)Hier komme ich aber gerade nicht weiter.
Sieht jemand den Fehler ?
Gruß,
JudgeDredd
Die hier sieht komisch aus:
par:DEVNAME;Shelly1 name in the topic;{ par:DEV_TPC;Shelly name in the topic;{ AttrVal('DEVICE','devicetopic',undef) =~ m,shellies.*/(shelly[^/]+)?, ? $1 : AttrVal('DEVICE','readingList','') =~ m,shellies/([^/]+)/online, ? $1 : undef } }
Vermutlich sollte es so gehen:
par:DEVNAME;Shelly1 name in the topic;{ AttrVal('DEVICE','devicetopic',undef) =~ m,shellies.*/(shelly[^/]+)?, ? $1 : AttrVal('DEVICE','readingList','') =~ m,shellies/([^/]+)/online, ? $1 : undef }
(War wohl etwas müde gestern)
Zitat von: Beta-User am 16 Februar 2022, 19:56:50
...das ist aber doch ein Ersatzweg für die Verwendung von MQTT_GENERIC_BRIDGE und hat mit dem (im Threadtitel nur unzureichend widergegebenen) eigentlichen Anliegen des TE doch wenig zu tun, oder...?
S
ist bei mir ohne MQTT_GENERIC_BRIDGE....
ja, hast recht, MQTT2_CLIENT => MQTT2_BRIDGE => MQTT2_DEVICE (Verständnisfrage) past nicht da zu....
danke für die INFO
Zitat von: eisman am 17 Februar 2022, 15:10:36
ist bei mir ohne MQTT_GENERIC_BRIDGE....
Das habe ich gesehen, und auch, dass deine Lösung einen kleinen "Pferdefuß" hat: gibt es keine Aktualisierungen bei anderen Devices, wird trotzdem von allen der jeweils letzte Wert versendet, gibt es keine Aktualisierung des "trigger-Readings", wird gar nichts mehr gepublisht...
Ist zwar OT, aber hier mal ein Beispiel für ein Device, das zum einen Informationen via MQTT (generisch) erhält, die Daten dann aber zum Teil direkt (bei triggerndem Empfang) über MQTT_GENERIC_BRIDGE weitersendet unter anderem Namen bzw. anderer Struktur (an einen anderen Server); verantwortlich dafür ist das Attribut "mqttGB1Publish":
define Raumfuehler_Wohnzimmer MQTT2_DEVICE A4C138CC86D1
attr Raumfuehler_Wohnzimmer alias Raumfühler
attr Raumfuehler_Wohnzimmer event-min-interval 300
attr Raumfuehler_Wohnzimmer event-on-change-reading batteryPercent,temperature:0.2,humidity:0.2,rssi:5,distance:5
attr Raumfuehler_Wohnzimmer genericDeviceType thermometer
attr Raumfuehler_Wohnzimmer group Heizung
attr Raumfuehler_Wohnzimmer icon temperature_humidity
attr Raumfuehler_Wohnzimmer jsonMap batt:batteryPercent tempc:temperature tempf:0 hum:humidity servicedatauuid:0 servicedata:0
attr Raumfuehler_Wohnzimmer model OpenMQTTGateway_BT_temp_hum_sensor
attr Raumfuehler_Wohnzimmer mqttGB1Publish temperature|humidity:topic={"$base/$device/$name"}
attr Raumfuehler_Wohnzimmer readingList home/O[^/]*M[^/]*G[^/]*/BTtoMQTT/A4C138CC86D1:.* { json2nameValue($EVENT,'',$JSONMAP) }
attr Raumfuehler_Wohnzimmer readingsWatcher 4000,0.000,temperature,humidity
attr Raumfuehler_Wohnzimmer rhasspyName raumfühler
attr Raumfuehler_Wohnzimmer room Wohnzimmer
attr Raumfuehler_Wohnzimmer stateFormat T: temperature°C, H: humidity%rH
Mit sowas kann man
- Displays füttern;
- externe Visualisierungen anbinden (HomeAssistant, z.B.);
- ein zentrales oder entferntes FHEM mit Infos versorgen (auch mit einer gewissen Toleranz gegen Verbindungsabbrüche, als Alternative z.B. zu FHEM2FHEM);
- ...
ok, ich habe die geänderte Zeile
par:DEVNAME... übernommen.
Allerdings hat nun der Devicename im Topic gefehlt.
Das habe ich im Template nochmal angepasst.
name:shelly1_customTopic
filter:TYPE=MQTT2_DEVICE
desc:Base template for a lot of first generation shelly devices
par:DEV_TPC;base topic to be used for devicetopic attribute;{ my $is = AttrVal('DEVICE','devicetopic',undef); return $is if $is; AttrVal('DEVICE','readingList','') =~ m,(?:[^:]*:)?(shellies.*/[^/]*)/online, ? $1 : undef }
par:DEVNAME;Shelly1 name in the topic;{ AttrVal('DEVICE','devicetopic',undef) =~ m,shellies.*/(shelly[^/]+)?, ? $1 : AttrVal('DEVICE','readingList','') =~ m,shellies/([^/]+)/online, ? $1 : undef }
par:CALLSPEECHRECOGN;Set this to 0 to not set any speech recogn. related attributes;{ 1 }
order:A_10
attr DEVICE devicetopic DEV_TPC
attr DEVICE setList\
off:noArg $\DEVICETOPIC/DEVNAME/relay/0/command off\
on:noArg $\DEVICETOPIC/DEVNAME/relay/0/command on\
x_update:noArg $\DEVICETOPIC/DEVNAME/command update_fw\
x_mqttcom $\DEVICETOPIC/DEVNAME/command $EVTPART1
attr DEVICE readingList \
$\DEVICETOPIC/DEVNAME/relay/0:.* state\
$\DEVICETOPIC/DEVNAME/relay/0:.* relay0\
$\DEVICETOPIC/DEVNAME/input/0:.* input0\
$\DEVICETOPIC/DEVNAME/online:.* online\
$\DEVICETOPIC/DEVNAME/announce:.* { json2nameValue($EVENT) }\
shellies/announce:.* { $EVENT =~ m,..id...DEVNAME...mac.*, ? json2nameValue($EVENT) : return }
attr DEVICE devStateIcon {my $onl = ReadingsVal($name,"online","false") eq "false" ? "rot" : ReadingsVal($name,"new_fw","false") eq "true" ? "gelb" : "gruen"; my $light = ReadingsVal($name,"state","off"); my $show = '<a href="';$show .=
deletereading -q DEVICE (?!associatedWith|IODev).*
set DEVICE x_mqttcom announce
attr DEVICE model shelly1
setreading DEVICE attrTemplateVersion 20220216
option:{ CALLSPEECHRECOGN }
set DEVICE attrTemplate speechcontrol_type_switch
Die Neuanlage funktioniert nun und der Shelly kann auch geschaltet werden.
Soweit sogut ... Jetzt kommt aber wieder mein Verständninsproblem.
Der Ablauf:
- Ich lege ein Device MQTT2_CLIENT an.
subscriptions shellies/licht/+/#
autocreate simple/complex - Nach ein paar Sekunden wird genau ein MQTT2_DEVICE angelegt.
Name: mqttIO_Licht
Im Attribut readingsList stehen nun sämtliche Shellies die das Topic matchen - Setzte ich das Attribut
devicetopic shellies/licht/1g - wende ich das Template an
Shelly1 name in the topic: shelly1-ABCDEF123456 - Nun kann ich den Shelly schalten.
Aber was nun ?
Das automatisch erzeugte Device
- heißt weiterhin
mqttIO_Licht- in readingsList stehen weiterhin alle gematchten Shellies drin.
- ein weiteres Dervice wird nicht automatisch erzeugt.
Ist das alles so korrekt wiedergegeben, oder sollte an irgendeiner Stelle etwas anderes passieren ?
Gruß,
JudgeDredd
Vielleicht nochmal ein bißchen Theorie:
- Ein MQTT2-IO gibt die Daten mit einer "CID" (ClientID) via "Dispatch" an das Modul MQTT2_DEVICE weiter. Das muss dann entscheiden, ob es
-- "jemanden kennt", der mit den Daten was anfangen kann. Das ist zu bejahen, wenn es (mindestens) eine MQTT2_DEVICE-Instanz gibt, deren readingList einen passenden Eintrag hat;
-- "autocreate" anwerfen soll (ein flag, wird am IO gesetzt), wenn das nicht der Fall ist;
-- wenn "autocreate" stattfinden soll: Welches Device bekommt die Daten? Das wird anhand der CID entschieden.
Daraus folgt:
- MQTT2_SERVER kennt den Sender und kann anhand von dessen ClientID die Daten passend verteilen;
- MQTT2_CLIENT kennt den Sender nicht (das liefert z.B. Mosquitto gar nicht mit) und versieht daher alle Pakete mit seiner eigenen CID => alles landet in ein und demselben Device...
Daraus folgt weiter:
- wenn du ein neues Device machst, nimmst du eine Kopie von deinem "Sammeldevice", machst alle Infos raus bis auf das, was attrTemplate braucht, entfernst insbesondere auch die CID aus der DEF und legst damit den "kleinen Klon" an => attrTemplate anwenden, alles ist gut...
ODER:
- du baust eine passende bridgeRegexp ;) . Das ermittelt "Pseudo-CID's", die dann im weiteren autocreate-Prozess verwendet werden.
Es gibt dafür ein Muster, das einen "normalen Shelly" direkt "vereinzeln" würde, zu finden im attrTemplate "MQTT2_CLIENT_general_bridge".
Da machst du einfach eine weitere Zeile rein, die deinen Fall umfasst. Mit den Infos aus der par:-Ermittlung zu DEVNAME sollte das hinzubekommen sein :P .
(Im Prinzip kannst du das frei gestalten, ich würde aber empfehlen, das so zu machen, dass die "Pseudo-CID" genau dem entspricht, was MQTT2_SERVER "sehen" würde, und das ist (hier und nur) das, was als DEVNAME ermittelt wird).
Zitat von: Beta-User am 17 Februar 2022, 15:58:35
ODER:
- du baust eine passende bridgeRegexp ;) . Das ermittelt "Pseudo-CID's", die dann im weiteren autocreate-Prozess verwendet werden.
Die bridgeRegexp als "Vereinzelner" Funktioniert. bei meinem Beispiel.
(shellies/licht/1g/shelly1-ABCDEF123456)
Problematisch wird es nur mit dynamischen Topics alles in einem Regex abzubilden.
z.B. (shellies/sensor/eg/temperatur/shelly1-ABCDEF123456)
Da muss ich mir erst nochmal Gedanken zu machen.
Danke mal bis hierhin für ein wenig Aufklärungsunterricht ;)
Gruß,
JudgeDredd
:)
Ist schon klar, dass es reichlich schwierig ist, das alles "auf einmal" zu überblicken, was es alles gibt und für was jeweils welches Attribut usw. gedacht ist und wie was ineinandergreift. Die meisten kennen auch nur das Ergebnis und haben wenig Ahnung davon, wie was zusammenhängt, von daher bin ich eigentlich ganz froh, wenn hin und wieder mal jemand "vorbeikommt", der etwas speziellere Anforderungen realisieren will (daher auch der OT-Exkurs zu MQTT_GENERIC_BRIDGE).
Kleines Helferlein noch:
https://regex101.com/r/LKnABh/1 (https://regex101.com/r/LKnABh/1)