Einfache Angabe von Reading-Values in notify Commands

Begonnen von Markus Bloch, 18 Juni 2015, 23:01:02

Vorheriges Thema - Nächstes Thema

Markus Bloch

Hallo zusammen,

in dem Post http://forum.fhem.de/index.php/topic,27218.msg304040.html#msg304040 hatte ich einen Vorschlag zur einfachen Verwendung von Reading-Values in notify Commands gemacht. Generell würde ich es ja toll finden eine solche Möglichkeit systemweit zu schaffen. Allerdings gibt es im DOIF Modul ja bereits eine ähnliche Syntax (mit doppelten Klammern). Daher wär mein Vorschlag dies nur für notify Commands zu machen, da man sich so die ganzen Perl-Kontstrukte mit ReadingsVal spart.

Im notify-Modul wär das mit einem Einzeiler erledigt.

Die Frage hier in die Runde: Macht das Sinn?

Danke und viele Grüße

Markus
Developer für Module: YAMAHA_AVR, YAMAHA_BD, FB_CALLMONITOR, FB_CALLLIST, PRESENCE, Pushsafer, LGTV_IP12, version

aktives Mitglied des FHEM e.V. (Technik)

justme1968

ich glaube so etwas wäre recht praktisch.

eventuell ist aber [device:reading] nicht ohne probleme rückwärts kompatibel ist. vielleicht ist [[device:reading]] besser.

das könnte man in EvalSpecials einbauen, dann wäre es ziemlich notify spezifisch
oder in commandSet, dann könnte man es bei jedem fhem set verfügbar und könnte auch mit FILTER= verwendet werden
oder in AnalyzeCommand dann, wäre es im prinzip überall möglich. eventuell beisst es sich dann aber mit doif.

ich wäre mindestens für variante 2. dann kann man über devspec z.b. alle devices suchen die ein reading haben das genau einem reading eines bestimmten devices entspricht (oder nicht entspricht).

das ersetzen an sich könnte so aussehen:$cmd =~ s/\[\[([^\]]*):([^\]]*)\]\]/${\(ReadingsVal($1,$2,"\[$1:$2\]"))}/g;

gruss
  andre
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

rudolfkoenig

[name:reading] waere eine Idee, wenn es vom DOIF nicht besetzt waere.
[[name:reading]] ist mAn deswegen nicht optimal, weil Anfaenger, die DOIF Schnipsel sehen, verwirrt, und in ausgelagerten Funktionen nicht  klappt. DOIF implementiert mit [] auch Zeitpruefungen, damit will ich nicht anfangen.

Mein Vorschlag: ReadingsVal(.*), ReadingsNum(.*), ReadingsTimestamp(.*), InternalVal(.*), OldValue(.*), AttrVal(.*), Value() wird in FHEM-Befehlen und im Shellskripten ersetzt.

$value{x}, % und @ wird nur noch bei aktivierten Attribut (compatibility < 5.6) ersetzt.

justme1968

das hätte theoretisch den vorteil das es sehr einfach von einem fhem zu einem perl notify umgebaut werden könnte. praktisch aber nicht weil es mit den strings und der interpolation nicht hin haut. eventuell verwirrt das einsteiger auch?

irgendwie ist es auch nicht elegant so viel schreiben zu müssen :)

ist die [device:reading] variante wirklich problematisch wenn sie auf set beschränkt ist und genau so funktioniert wie in doif?

die anderen funktionen zur verfügung zu haben wäre aber tatsächlich nicht schlecht.

ich weiß. das klingt alles sehr unentschieden und wenig hilfreich...


das compatibility attribut  finde ich gut. auch wenn es vermutlich mehr als einen aufschrei geben wird. vielleicht wäre in einem ersten schritt nur eine log und motd meldung besser?
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

Markus Bloch

Hallo zusammen,

ich würde es ebenfalls begrüßen ein [device:reading] zu unterstützen, als auch die genannten Vorschläge mit den Funktionsnamen von Rudi.

Soweit ich der commandref zu DOIF entnehme, ist es nicht möglich in den Kommandos ein solches Konstrukt [device:reading] zu verwenden. Diese Syntax beschränkt sich offenbar nur auf die Expressions und sind nicht für auszuführenden Kommandos anwendbar.

Viele Grüße

Markus
Developer für Module: YAMAHA_AVR, YAMAHA_BD, FB_CALLMONITOR, FB_CALLLIST, PRESENCE, Pushsafer, LGTV_IP12, version

aktives Mitglied des FHEM e.V. (Technik)

Damian

Zitat von: Markus Bloch am 19 Juni 2015, 08:57:37
Hallo zusammen,

ich würde es ebenfalls begrüßen ein [device:reading] zu unterstützen, als auch die genannten Vorschläge mit den Funktionsnamen von Rudi.

Soweit ich der commandref zu DOIF entnehme, ist es nicht möglich in den Kommandos ein solches Konstrukt [device:reading] zu verwenden. Diese Syntax beschränkt sich offenbar nur auf die Expressions und sind nicht für auszuführenden Kommandos anwendbar.

Viele Grüße

Markus

Die Syntax [<device>:<reading>] wird hauptsächlich in den Bedingungen von DOIF benutzt. Allerdings kann man sie bei DOIF auch im ausführenden Teil benutzen (sowohl bei FHEM-Befehlen, wie auch in Kombination mit geschweiften Klammern) z. B.

...(set <device> [<device>:<reading>])

...({fhem("set <device>  [<device<:<reading>]"})

Auch so etwas ist möglich:

... (set <device> {([<device1>:<reading1>]+[<device2>:<reading2>])})


allerdings wird nicht alles in eckigen Klammern ersetzt. Es ist eine Plausibilität eingebaut, es wird geprüft, ob die Angaben in eckigen Klammern tatsächlich ein Device bzw. Reading darstellen können.

Gruß

Damian
Programmierte FHEM-Module: DOIF-FHEM, DOIF-Perl, DOIF-uiTable, THRESHOLD, FHEM-Befehl: IF

justme1968

das wäre glaube ich mit der oben vorgeschlagenen ausdruck zum ersetzen kompatibel. und wenn es das device und das reading nicht gibt bleibt der [...] ausdruck auch unverändert stehen. den [^\]] teil der regex könnte man noch etwas schärfer auf die in reading erlaubten werte einschränken. aber ich glaube das gibt im ergebnis keinen unterschied.

ich habe gestern etwas mit dieser variante in commandSet gespielt und vor allem die möglichkeit das auch in :FILTER= zu verwenden ist wirklich praktisch.

gruß
  andre
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

rudolfkoenig

andre/Damian: bin etwas verloren: soll ich die Ersetzung jetzt mit [] oder mit [[]] einbauen?

Damian

#8
Zitat von: rudolfkoenig am 21 Juni 2015, 09:54:05
andre/Damian: bin etwas verloren: soll ich die Ersetzung jetzt mit [] oder mit [[]] einbauen?


Ich denke beides wird für Probleme in Verbindung mit DOIF sorgen.

[[]] wird in der Bedingung von DOIF bereits für indirekte Zeitangaben genutzt. Das dürfte für Verwirrung sorgen.

[<device>:<Reading>] funktioniert bei DOIF nur mit konkreten Angaben, also ohne regexp. [<Device>:*] führt z. Zt. bei DOIF zu einer Fehlermeldung "reading does not exist: <Device>:*"

Da müsste ich also Anpassungen in DOIF vornehmen. In der Bedingung von DOIF wird [<Device>:*] prinzipiell nicht gehen, da es in Perl übersetzt wird und dort muss es ein eindeutiger Bezeichner sein (if (a* eq "") {} macht in Perl und anderen höheren Programmiersprachen wenig Sinn).

Gruß

Damian


Programmierte FHEM-Module: DOIF-FHEM, DOIF-Perl, DOIF-uiTable, THRESHOLD, FHEM-Befehl: IF

justme1968

ich hatte es gar nicht so verstanden das es auch darum geht im device oder reading namen sogar eine regex zu erlauben. es geht ja darum ein bestimmtes reading aus einem bestimmten device zu verwenden. und beides sollte genau angegeben sein.

wegen dem [[..]] konflikt mit doif würde ich doch die einfachen klammern verwenden. diese verwendung wäre dann auch identisch mit DOIF (bis auf die fehlermeldung).

der vorschlag von oben das mit$cmd =~ s/\[([^\]]*):([^\]]*)\]/${\(ReadingsVal($1,$2,"\[$1:$2\]"))}/g; zu lösen erlaubt auch gar keine regex. wenn es das reading im device gibt wird es verwendet, wenn nicht bleibt der [device:reading] ausdruck unverändert stehen. man könnte auch direkt eine 'no such reading...' meldung einsetzen.

gruss
  andre
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

Damian

Zitat von: justme1968 am 21 Juni 2015, 11:13:32
ich hatte es gar nicht so verstanden das es auch darum geht im device oder reading namen sogar eine regex zu erlauben. es geht ja darum ein bestimmtes reading aus einem bestimmten device zu verwenden. und beides sollte genau angegeben sein.

wegen dem [[..]] konflikt mit doif würde ich doch die einfachen klammern verwenden. diese verwendung wäre dann auch identisch mit DOIF (bis auf die fehlermeldung).

der vorschlag von oben das mit$cmd =~ s/\[([^\]]*):([^\]]*)\]/${\(ReadingsVal($1,$2,"\[$1:$2\]"))}/g; zu lösen erlaubt auch gar keine regex. wenn es das reading im device gibt wird es verwendet, wenn nicht bleibt der [device:reading] ausdruck unverändert stehen. man könnte auch direkt eine 'no such reading...' meldung einsetzen.

gruss
  andre
Ich ging von Rudis Vorschlag aus:

ZitatMein Vorschlag: ReadingsVal(.*), ReadingsNum(.*), ReadingsTimestamp(.*), InternalVal(.*), OldValue(.*), AttrVal(.*), Value() wird in FHEM-Befehlen und im Shellskripten ersetzt.

Gruß

Damian
Programmierte FHEM-Module: DOIF-FHEM, DOIF-Perl, DOIF-uiTable, THRESHOLD, FHEM-Befehl: IF

Markus Bloch

Ich würde ebenfalls [device:Reading] nehmen. Da es ja analog zu DOIF ist, wäre das Verhalten für den User transparent. Wenn er so etwas in einem set-Befehl innerhalb von DOIF verwendet, ersetzt DOIF den Ausdruck, außerhalb von DOIF würde es dann AnalyzeCommand() machen.

Ich würde generell anregen, diese Funktionalität dann aus DOIF zu entfernen, da sie ja dann allgemeingültig in FHEM wäre. Dann gebe es keine Probleme

Gruß Markus
Developer für Module: YAMAHA_AVR, YAMAHA_BD, FB_CALLMONITOR, FB_CALLLIST, PRESENCE, Pushsafer, LGTV_IP12, version

aktives Mitglied des FHEM e.V. (Technik)

Damian

Zitat von: Markus Bloch am 21 Juni 2015, 11:18:03
Ich würde ebenfalls [device:Reading] nehmen. Da es ja analog zu DOIF ist, wäre das Verhalten für den User transparent. Wenn er so etwas in einem set-Befehl innerhalb von DOIF verwendet, ersetzt DOIF den Ausdruck, außerhalb von DOIF würde es dann AnalyzeCommand() machen.

Ich würde generell anregen, diese Funktionalität dann aus DOIF zu entfernen, da sie ja dann allgemeingültig in FHEM wäre. Dann gebe es keine Probleme

Gruß Markus

Im Gegensatz zu

$cmd =~ s/\[([^\]]*):([^\]]*)\]/${\(ReadingsVal($1,$2,"\[$1:$2\]"))}/g;

wird in DOIF nach Klammern geparst und auf fehlende Klammern hingewiesen. Auf diese Eigenschaft würde ich ungern verzichten, da bei DOIF viel mit Klammernhierarchie gearbeitet wird.

Gruß

Damian
Programmierte FHEM-Module: DOIF-FHEM, DOIF-Perl, DOIF-uiTable, THRESHOLD, FHEM-Befehl: IF

rudolfkoenig

Damian: wuerde ein auf das set Befehl beschraenktes umwandeln von [geraet:readingname] DOIF stoeren?
Ich vermute nicht.

@Markus: [] generisch in AnalyseCommand zu ersetzen ist problematisch: DOIF erwartet vermutlich "String", set aber String.

Ich bin weiterhin bei meinem ReadingsVal Vorschlag (evtl. zusaetzlich): andre, was meinst du mit "praktisch aber nicht weil es mit den strings und der interpolation nicht hin haut" ? Alternativ koennte man im set alles, was mit {} geschrieben ist, als Perl auswerten, damit waere Readingsval als
set bla cmd {ReadingsVal("bla", "reading")}
zu schreiben.

Damian

Zitat von: rudolfkoenig am 21 Juni 2015, 12:43:18
Damian: wuerde ein auf das set Befehl beschraenktes umwandeln von [geraet:readingname] DOIF stoeren?
Ich vermute nicht.

Na ja, es würde nie bei set ankommen bzw. set bla [<Device>.*:...] würde zu Fehlermeldung führen, weil regexp im Devicenamen bei DOIF, z. Zt. nicht erlaubt ist.


Gruß

Damian
Programmierte FHEM-Module: DOIF-FHEM, DOIF-Perl, DOIF-uiTable, THRESHOLD, FHEM-Befehl: IF

Markus Bloch

Zitat von: Damian am 21 Juni 2015, 13:23:49
Na ja, es würde nie bei set ankommen bzw. set bla [<Device>.*:...] würde zu Fehlermeldung führen, weil regexp im Devicenamen bei DOIF, z. Zt. nicht erlaubt ist.

Wenn DOIF das schon vorher umsetzt ist das doch kein Problem.

eine Regexp Unterstützung würde ich hier momentan raus lassen. [device:reading] müssen tatsächlich existierende Bezeichnungen sein (keine regexp).

Gruß
Markus
Developer für Module: YAMAHA_AVR, YAMAHA_BD, FB_CALLMONITOR, FB_CALLLIST, PRESENCE, Pushsafer, LGTV_IP12, version

aktives Mitglied des FHEM e.V. (Technik)

justme1968

die auf set beschränkte variante sollte keine auswirkungen auf doif haben. die sind ja komplett unabhängig voneinander.

das einzige das hier eventuell probleme machen könnte wäre ein set das aus einem doif aufgerufen wird. aber ich denke falls hier ein [] ausdruck vorkommt würde der schon vom doif auf die gleiche weise ersetzt und garnicht erst beim set ankommen. sollte also auch gehen.

das mit der inerpolation bezog sich auf das umschreiben von der fhem version in die perl version. ist aber nicht schlimm bzw. jemand der das tut muss ja sowieso wissen was er tut.

das mit dem {} direkt innerhalb eines fhem kommandos gefällt mir besser als ReadingsVal & co. auf fhem ebene einzuabuen.

wenn man die [device:reading] variante einbaut und zusätzlich das {...} dann hätte man glaube ich das beste aus beiden vorschlägen. zum einen eine wirklich kurze variante wenn es nur um ein reading geht und eine die mehr kann.

@Damian: ich glaube immer noch nicht das es um regex innerhalb von device oder reading namen geht. das .* aus rudis erstem vorschlag war nur 'faulheit' alles auszuschreiben.
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

rudolfkoenig

Ich habe im set [name:reading] eingebaut, und auch {} fuer Eval. Damit kann man Unsinn wie
Zitatset heating temperature {[heating:temperature]+1}
schreiben. Da mir das beliebige Auswerten solcher Ausdruecke gewagt vorkam, ist das nur mit
Zitatattr global featurelevel 5.7
freigeschaltet, default ist 5.6. Ich haette aber lieber eine bessere Alternative, oder irgendwer kann mir zusichern, dass in set ein {}, was nicht ausgewertet wird, nie sinnvoll ist.

Apropos featurelevel: folgendes ist nur bis featurelevel 5.6 aktiviert:
- das Fuellen der $value Hash beim Perl-Befehlen in AnalyzeCommand
- @/% Ersetzung fuer Notify
- lastinclude

justme1968

sehr schön. genau die anwendung das set relativ zu einem bestehenden readings wert zu machen ist ist mir auch noch gekommen.


noch ein paar anmerkungen/vorschläge:

wäre es nicht besser den aufruf von ReplaceSetMagic gleich am anfang von CommandSet vor dem split zu machen statt erst später von DoSet aus? das würde pro device dann ein join und ein split in ReplaceSetMagic sparen.

deine variante erlaubt keine leeren readings. ist es tatsächlich so das es diese nicht gibt?

wenn es das reding nicht gibt verschwinden trotzdem die [] um den ausdruck. sollte man die nicht besser beibehalten?

wäre es für die {..} auswertung nicht besser klammerebenen zu zählen? sonst sollte man dokumentieren das innerhalb des ausdrucks keine geschweiften klammern vor kommen dürfen.

für das eval von {..} wäre im fehlerfall eine meldung im log gut. besonders wenn die klammern nicht gematched werden. für die auswertung von des [] vielleicht auch?

das ganze per default abzuschalten ist zwar sicher, aber auch schade. vor allem da beides abgeschaltet ist.
was das zusichern angeht: mir fällt keine anwendung ein bei der das bis jetzt verwendet worden wäre. aber das heisst nichts :)
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

rudolfkoenig

Das ist aber sehr hoeflich gewesen.

- ReplaceSetMagic vorne: wuerde mAn zu haeufig fuer "set X ?" aufgerufen. Set sollte sonst nicht soo haeufig aufgerufen werden.
- []/{} wird im "Fehlerfall" jetzt wieder hinzugefuegt.
- wie zaehlt man Klammern?
- habe Logging im Fehlerfall eingebaut.

justme1968

ich hab doch keinen grund unhöflich zu sein :)


zum klammern zählen schaue ich mir für readingsGroup gerade drei varianten an:

- es geht per regex und rekursion und/oder backtracking.
  das wäre am kürzesten zum hinschreiben aber das ist mir zu undurchsichtig :(

- es geht natürlich ganz altmodisch per schleife über alle zeichen und selber zählen.

- es gibt das Text::Balanced modul das ich mir gerade für readingsGroup anschaue.
  das gibt es ab perl 5.8 und es scheint mir am einfachsten.
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

Reinerlein

Hallo zusammen,

jetzt muss ich doch noch mal mitsprechen.
Ich habe im Sonos-Modul einige Set-Anweisungen, die einen textuellen Perl-Hash (also einen String, der zu einem Hash evaluiert werden kann) annehmen, der dann vom Modul interpretiert und verarbeitet wird...

Nun versucht der Set also den {}-Ausdruck zu verarbeiten und gibt was genau weiter?
Wenn es nicht gelingt (ist ein gültiger Perl-Hash ein "nicht-gelingen"?) wird der komplette String an den entsprechenden Setter des Moduls weitergereicht?

Sorry für diese Fragen, ich kann mir das gerade nicht im Quelltext anschauen...
Danke schon mal.

Grüße
Reinerlein

justme1968

das wird im feature level 5.7 vermutlich tatsächlich schief gehen.

vorschlag: den wert in ReplaceSetMagic nur dann zuweisen wenn ref auf das eval ergebnis einen leeren string liefert.
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

rudolfkoenig

ZitatIch habe im Sonos-Modul einige Set-Anweisungen, die einen textuellen Perl-Hash (also einen String, der zu einem Hash evaluiert werden kann) annehmen, der dann vom Modul interpretiert und verarbeitet wird...

Kannst du das bitte mit einem Beispiel demonstrieren?

Reinerlein

Hallo,

das wäre aber ja blöd :(
Und wie sähe es aus, wenn das Modul einen Marker setzen könnte, ob diese Auswertung gemacht werden soll oder nicht?
Dann könnte man das zumindest mal im Modul entscheiden.

Oder könnte man eine Erweiterung der bereits jetzt vorhandenen Steuerung für die Fhemweb-Widgets machen, und dort angeben, ob eine Perl-Auswertung vorher zulässig ist, oder nicht?
Dann könnte man es sogar für jede set-Anweisung getrennt festlegen, was überhaupt das beste wäre, da es in meinem Modul ja nur ein paar Anweisungen beträfe. Dann könnte der Anwender für alle anderen Setter dieses neue Feature immer noch nutzen (was sicherlich praktisch wäre)...

Grüße
Reinerlein

justme1968

der ref vorschlag sollte das eigentlich alles abdecken ohne so viele manuelle eingriffe
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

Reinerlein

Hi Rudi,

es geht hier eigentlich nur um die Alarmverarbeitung (die anderen von mir gedachten Setter verwenden eckige Klammern) Dort gibt es die Möglichkeit einen Alarm anzulegen oder zu verändern. Dabei werden die möglichen Parameter als Hash mitgegeben (so wie bei der ReadingsGroup sowas als Attribut abgelegt werden kann):

set Sonos_Wohnzimmer Alarm Update 17 { Shuffle => 1 }

oder

set Sonos_Wohnzimmer Alarm Update 17 { Shuffle => 1, Enabled => 1, Volume => 10 }


Und das würde mit der Ref-Prüfung klappen? Ich dachte, der würde hier bei eval eine Referenz auf einen Hash zurückgeben, womit ref doch true liefern würde, oder?

Grüße
Reinerlein

justme1968

die idee ist das egal ergebnis nur dann in das set einzusetzen wenn es ein string ist. wenn beim eval ein hash raus kommt dann wird das ergebnis verworfen und der klammer inhalt ohne eval unverändert durchgereicht.
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

rudolfkoenig

Mit featurelevel 5.7 hagelt es z.Zt. an Fehler wie
Useless use of a constant ("Shuffle") in void context

Nach einem Umbau, der den eval immer mit {} ausfuehrt, scheint es mit der ref($x) eq "HASH" Pruefung zu funktionieren.
Wuesste ich gerne, wonach perl entscheidet, ob das Ergebnis ein String (return aus dem Codeblock) oder ein HASH sein soll.
Ich fuehle mich weiterhin sehr unwohl mit {}, und bin nicht sicher, dass es bleibt.

Ein Modul oder set Argument abhaengige Evaluirung finde ich falsch, entweder funktioniert es ueberall, oder nirgends.

UliM

Zitat von: rudolfkoenig am 19 Juni 2015, 07:40:03
$value{x}, % und @ wird nur noch bei aktivierten Attribut (compatibility < 5.6) ersetzt.
Oha. Das sollte eine Ankündigung im Forum wert sein - vielleicht hab ich die verpasst.

Hab mit dem hier Diskutierten nicht getestet, frage mich aber, ob man für notify nicht ohne Klammer auskäme:
device:regexp als Bedingung für notify gibt's schon lang.
device:reading:regexp könnte neu sein, also bei 2x ':' in der Bedingung wird ein reading erwartet. Für set ginge das natürlich nicht, Ber zumindest ich persönlich hab seltenst den Bedarf, mit Reading-Werten zu rechnen.
(Falls diese Idee total off ist, bitte eher ignorieren als mit hämischen Kommentaren versehen :)

Gruß,
Uli
RPi4/Raspbian, CUL V3 (ca. 30 HomeMatic-devices), LAN (HarmonyHub, alexa etc.).  Fördermitglied des FHEM e.V.

rudolfkoenig

Es zaehlt mein Beitrag #17 vom 22 Juni 2015, 20:32: die erwaehnten Punkte werden bis featurelevel 5.6 inklusive unterstuetzt.

Das mit device:reading:regexp habe ich nicht kapiert.

Damian

#31
Zitat von: rudolfkoenig am 23 Juni 2015, 19:37:37
Mit featurelevel 5.7 hagelt es z.Zt. an Fehler wie
Useless use of a constant ("Shuffle") in void context

Nach einem Umbau, der den eval immer mit {} ausfuehrt, scheint es mit der ref($x) eq "HASH" Pruefung zu funktionieren.
Wuesste ich gerne, wonach perl entscheidet, ob das Ergebnis ein String (return aus dem Codeblock) oder ein HASH sein soll.
Ich fuehle mich weiterhin sehr unwohl mit {}, und bin nicht sicher, dass es bleibt.

Ein Modul oder set Argument abhaengige Evaluirung finde ich falsch, entweder funktioniert es ueberall, oder nirgends.

Ich habe {} zu erst in DOIF für alle FHEM-Befehle als eval eingebaut, das ging nicht lange gut. Daher habe ich es auf  {(...)} innerhalb eines beliebigen Ausdrucks eingeschränkt. Damit gibt es bei über 7000 definierten DOIF-Modulen keine Kompatibilitätsprobleme zum bisherigen FHEM. Es ist zwar nicht so elegant mit den doppelten Klammern, aber eben ohne Nebenwirkungen.

Gruß

Damian
Programmierte FHEM-Module: DOIF-FHEM, DOIF-Perl, DOIF-uiTable, THRESHOLD, FHEM-Befehl: IF

rudolfkoenig

Da kommen die ersten Beschwerden wg. {}.
Ich habe eine Weile lang gegruebelt, diesen Artikel wieder durchgelesen, und Damians Loesung {(...)} implementiert.

rudolfkoenig

Gerade aufgefallen: mit {()} (aka ReplaceSetMagic) kann man allowedCommands in bestimmten ausgefallenen Faellen umgehen. Irgendeine elegante Idee, wie wir das verhindern koennen?

Btw. $hash->{CL} wird jetzt auch in set bzw. setreading gesetzt, und ReplaceSetMagic verwendet AnalyzePerlCommand, statt einen direkten eval. Ist aufgefallen, weil {($min)} nicht funktioniert hat.


justme1968

für {} hatten wir eingebaut das es nur geht wenn perl in den allowedCommands steht. entweder verwenden wir das gleiche schlüsselwort oder wir überlegen uns ein neues. ich wäre dafür bei perl zu bleiben.
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

rudolfkoenig

Das ist klar, allerdings habe ich an der Stelle kein Zugriff auf das Attribut. $cl zeigt nicht auf die FHEMWEB-Instanz (Server), sondern auf die konkrete Verbindung, und das hat keine Attribute :/

justme1968

achso...

drei ideen:

- ReplaceSetMagic wird nicht in DoSet und CommandSetReading aufgerufen sondern zentral in AnalyzeCommandChain bzw. AnalyzeCommand. da ist $allowed direkt vorhanden. dann würde das {()} auch an anderen stellen wie z.b. get funktionieren. ich weiss nicht ob es unerwünschte nebeneffekte hätte. das ist aber glaube ich die sauberste variante da nirgends auf irgendwelche attribute von unbekannten devices zugegriffen werden muss.

- $allowed wird von AnalyzeCommand als zusätzlicher parameter an alle cmds durchgereicht.

- AnalyzeCommand steckt $allowed in $cl->{'.allowed'}. ich glaube das ist die zweit beste lösung. kein zusätzlicher parameter wie bei 2., keine potentiellen nebeneffekte wie bei 1 aber auch kein {()} in kommandos ausser set und setreading.

- hier standen noch ein paar ideen wie fhemweb $allowed oder die server instanz in den hash für die konkrete verbindung stecken kann. aber 1. oder 3. oben sind sowieso besser.
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

rudolfkoenig

Danke, ich habe Vorschlag #3 uebernommen, ich befuerchte #1 kollidiert mit DOIF.
Habe allowedCommands jetzt auch fuer telnet eingefuehrt.

Dabei entdeckt, dass devspec2array AnalyzePerlCommand aufruft, und damit lustige Sachen, wie
Zitatset {exit}
moeglich sind. Damit allowedCommands greift, rufe ich aus fhem.pl devspec2array ab sofort mit $cl auf, es gibt aber noch 26 weitere Module, die devspec2array aufrufen. Daher die Frage: koennten wir dieses Feature in devspec2array bitte abschaffen? Nutzt das jemand?

BioS

Hi zusammen,

in der neuen Funktion ReplaceSetMagic in Featurelevel 5.7 werden die Argumente in einen string ge-joined und zum Schluss wieder per split(" ",...) zu einem Array geteilt.

Ist es Absicht, dass der split() Aufruf whitespaces (und auch newlines etc.) mit entfernt?

Ich habe aktuell das Problem, dass ein paar User meines Moduls 70_Jabber.pm sich per "set msg ... text\n text2 \n text3" schicken lassen und das nun seit neuestem zu einem one-liner wird.

Könnte man in der Funktion ReplaceSetMagic  split(/ /, $a, $nsplit) anstatt split(" "...) benutzen?
Damit lässt er eventuell vorhandene whitespaces so wie am Anfang auch drin.

Grüße
Heiko
FHEM auf Debian in ESXi5 VM
Homematic mit HMLAN
Raspi mit Pilight für Relais der Heizung

rudolfkoenig

Habe den Vorschlag uebernommen. Weiterhin wird der alte Parametersatz zurueckgeliefert (d.h. kein split durchgefuehrt), falls keine Ersetzung stattgefunden ist.

viegener

@Rudi et al: Sorry wenn ich das hier nochmal hochhole, aber ich war gerade auf der Suche nach einer Funktion um elegant auf dem Server für das Tablet UI auch Ersetzungen (Readings etc) durchzuführen (siehe hier --> http://forum.fhem.de/index.php/topic,43110.0.html). Dazu würde ich einfach gerne ReplaceSetMagic verwenden, um nicht das Rad neu erfinden zu müssen.

Gibt es Gründe ReplaceSetMagic nicht in eigenen Modulen einzusetzen?

Generische Anschlussfrage, wäre es nicht hilfreich eine Art von Library der für Modulentwickler zur Verfügung stehenden Funktionen zu machen, um eine Art API-Beschreibung für Modulentwickler zu haben, oder habe ich das nur nicht gefunden.

Johannes
Kein Support über PM - Anfragen gerne im Forum - Damit auch andere profitieren und helfen können

betateilchen

Zitat von: viegener am 08 Februar 2016, 22:42:26
eine Art von Library der für Modulentwickler zur Verfügung stehenden Funktionen zu machen

Die Library nennt sich fhem.pl und wer noch mehr braucht, findet weitere nützliche Funktionen in der 99_Utils.pm :)
-----------------------
Formuliere die Aufgabe möglichst einfach und
setze die Lösung richtig um - dann wird es auch funktionieren.
-----------------------
Lesen gefährdet die Unwissenheit!

viegener

Zitat von: betateilchen am 08 Februar 2016, 22:53:18
Die Library nennt sich fhem.pl und wer noch mehr braucht, findet weitere nützliche Funktionen in der 99_Utils.pm :)
Das finde ich jetzt weder witzig noch hilfreich, aber vielleicht fehlt mir ja der entsprechende Tiefgang
Kein Support über PM - Anfragen gerne im Forum - Damit auch andere profitieren und helfen können

rudolfkoenig

@Johannes: Ich bin in deinem Fall bei ReplaceSetMagic unsicher: du willst damit ein mit PHP vergleichbares Konzept umsetzen. Ob ReplaceSetMagic dem gewachsen ist, weiss ich nicht. Falls du ReplaceSetMagic deswegen staendig anpassen muesstest, dann waere es falsch, sie zu verwenden. Wenn sie dir passt, so wie sie ist: nur zu.

Falls du Lust hast, die zur Verfuegung stehenden Funktionen zu dokumentieren: nur zu. Ich werde mir keine neue Baustelle aufmachen, ich habe einfach zu viele offen. Ich beantworte aber gerne Fragen, soweit ich es kann.

betateilchen

Zitat von: viegener am 09 Februar 2016, 01:18:04
Das finde ich jetzt weder witzig

Das war von mir auch in keinster Weise witzig gemeint, sondern mein voller Ernst.

Wo sonst - ausser in der fhem.pl - willst Du fhem-spezifische Funktionen finden, die man als Entwickler in eigenen Modulen verwenden kann?
-----------------------
Formuliere die Aufgabe möglichst einfach und
setze die Lösung richtig um - dann wird es auch funktionieren.
-----------------------
Lesen gefährdet die Unwissenheit!

viegener

@betateilchen: ich erkläre es gerne: Es geht nicht darum die Funktion zu finden, sondern zu wissen, welche Funktion in API und Semantik stabil bleibt. Ich gehe davon aus, dass in fhem.pl offizell nutzbare Funktionen sind, die auch im API einigermassen stabil bleiben, da sie in anderen Modulen verwendet werden und auch interne Hilfsfunktionen, die einfach zur Modularisierung verwendet werden und sich auch mal ohen Ankündigung ändern. Da Rudi die Funktionen grundsätzlich relativ sprechend benennt, ist manchmal nicht klar, was offiziell ist und was "intern" ist.

@Rudi: Anpassen will ich ReplaceSetMagic gar nicht, ich bin nur ein fauler Programmierer und bin über deshalb auf die Funktion gestolpert. Die macht eigentlich viel mehr als ich momentan brauche aber Stand heute keine Erweiterung und Ja eigentlich implementiere ich Teile von PHP nach   ;)

Und klar, mir ging es auch nicht darum Dich aufzufordern, sondern nach Interesse bei anderen zu fragen. Deine Hilfe wäre im wesentlichen da wichtig zu klären ob etwas zum "offiziellen" Modul API gehört.
Kein Support über PM - Anfragen gerne im Forum - Damit auch andere profitieren und helfen können

viegener

OK, Ich habe mal angefangen: http://www.fhemwiki.de/wiki/DevelopmentModuleAPI

Kommentare, Erweiterungen, Feedback wie immer willkommen,
Johannes
Kein Support über PM - Anfragen gerne im Forum - Damit auch andere profitieren und helfen können

betateilchen

Zitat von: viegener am 10 Februar 2016, 00:32:15
OK, Ich habe mal angefangen:

Deine Bemühungen in allen Ehren, aber ich halte das Vorhaben nach wie vor für sinnlos.

Einer der größten Vorteile von fhem ist es doch gerade, dass eben nichts so in Stein gemeißelt ist, wie es für ein echtes API erforderlich wäre.
Wenn ich eine bestimmte Funktionalität brauche und die Vermutung habe, dass es dazu etwas in der fhem.pl geben könnte, werde ich immer in die fhem.pl schauen, denn dort ist der aktuelle Stand. Was im Wiki steht, kann einen Tag später veraltet sein und es gibt eine große Anzahl von Wiki Beiträgen, die definitiv veraltet sind und von niemandem mehr gepflegt werden. Und "Unsinn", der irgendwann mal ins Wiki geschrieben wurde, zieht sich oft noch über Monate (Jahre) als gefährliches Halbwissen durchs Forum - immer mit der Rechtfertigung "aber es steht doch so im Wiki". Das ist einer der Hauptgründe, warum ich beispielsweise für meine Module keine Wiki-Beiträge schreibe und auch nie begeistert bin, wenn es jemand anderes tut.

-----------------------
Formuliere die Aufgabe möglichst einfach und
setze die Lösung richtig um - dann wird es auch funktionieren.
-----------------------
Lesen gefährdet die Unwissenheit!

rudolfkoenig

Die Frage reduziert sich fuer mich auf: "was ist besser: potentiell veraltete Doku oder gar kein Doku".

betateilchen hat zwar grundsaetzlich Recht, allerdings gibt es auch FHEM Modul-Entwickler, die nicht in der Lage sind, alle Aspekte von (gewachsenen) Perl Code zu verstehen oder nicht gewillt sind, die dafuer noetige Zeit zu investieren. Fuer diese Leute ist potentiell veraltetete Doku besser, fuer die anderen (wie betateilchen oder mich) kein Doku.

Mein Vorschlag: ins Wiki-Artikel gehoert vorne ein Hinweis, dass im Zweifel der perl-Code zu konsultieren ist, und wer Probleme feststellt, der moege sie melden. Und generell ist die Bemuehung, die Sachen zu dokumentieren, lobenswert.

viegener

@ph1959de: Da warst Du schneller als ich, so stelle ich mir wiki for  ;D

@Rudi: Macht Sinn das Hinzuzufügen und die Intention ist für mich auch nicht das Konsultieren von Code zu ersetzen sondern das Lesen zu vereinfachen

Vielleicht noch wichtiger: Einen Hinweis zu geben, was verwendet werden kann (weniger Codeduplizierung, mehr Einheitlichkeit und schnellerer Einstieg für Entwickler). Mir hätte es geholfen, obwohl ich gefühlt seit Äonen Code anderer Leute lese und auch in Programmiersprachen die heute mit Recht nicht mehr so gebräuchlich sind  ;)

Also schonmal Dank an alle die beitragen...
Kein Support über PM - Anfragen gerne im Forum - Damit auch andere profitieren und helfen können

Loredo

Wäre es denkbar ReplaceSetMagic() dahingehend zu erweitern, dass auch INTERNALs und Attribute damit abgefragt werden können?


Anbei ein Patch als Vorschlag.




Gruß
Julian
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

rudolfkoenig

1. Doku fehlt :)
2. da es mehr als 10 Zeilen betrifft: ich baue die Aenderung erst ein, falls sonst noch jemand Interesse bekundet.

viegener

Ich würde auch Interesse bekunden, da ich ReplaceSetMagic intensiv sowohl für TelegramBot verwende als auch im Servermodul für das Tablet UI (FTUISRV). Man kann sich zwar heute behelfen durch den Wechsel auf die perl-Ebene, das erzeugt aber häufig Klammerorgien und schwer lesbare Konstrukte.

Ich fände es gut, wenn es zumindest auch etwas Einheitlichkeit bringen würde, damit die Syntax mit IF identisch wäre?

Kein Support über PM - Anfragen gerne im Forum - Damit auch andere profitieren und helfen können

rudolfkoenig

ZitatIch fände es gut, wenn es zumindest auch etwas Einheitlichkeit bringen würde, damit die Syntax mit IF identisch wäre?
Kanns bitte jemand bestaetigen, dass id/di/ad/da kompatibel zu IF ist?

Loredo

Das konnte ich aus der DOIF CommandRef leider auch nicht in Erfahrung bringen. Mir war so als wenn es da früher einmal ähnliche Optionen gab (mir ist was in Erinnerung mit "&" am Ende, um ein Internal statt ein Reading abzufragen), aber diese Information konnte ich nirgends finden.


Einen Patch für die set-Befehl Doku liefere ich dann gerne nach ;-)
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

justme1968

das verhalten von list sollte man auch im hinterkopf behalten.

list verendet i: r: und a: vor dem reading/attribut/internal namen. ohne angabe werden alle drei in dieser reihenfolge durchsucht, mit angabe jeweils nur das angegebene.

wenn die anderen kommandos den selektor an den namen anhängen sollte man list vielleicht auch umstellen/erweitern.
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

Loredo

Ich habe mich etwas im DOIF Quellcode umgesehen; die einzige Übereinstimmung ist offenbar das bisherige :d für die Extraktion der 1. Dezimalzahl aus einem Reading.
Für INTERNALs wird am Beginn(!) des Readingnamen ein & erwartet, Attribute lassen sich gar nicht abfragen und für beides gibt es keine Dezimalzahl Extraktion.


Es gibt hier also keine Konsistenz/Kompatibilität zum list Befehl in DOIF.
Ich denke es macht hier Sinn, dass ReplaceSetMagic() weitestgehend zum list Befehl kompatibel ist und die Art der Quelle als Präfix führt und die zusätzliche Beschränkung auf die erste Zahl wie bisher als Suffix. Allerdings sehe ich es eher als kritisch an, wenn das aktuelle Verhalten dahingehend ersetzt wird, dass bei keiner Angabe alle 3 Quellen nacheinander durchgegangen werden. Ich würde r: zwar explizit einbauen, das weglassen von selbigem sollte aber auch aus Performancegründen ebenfalls nur nach einem Reading suchen wie bisher auch.
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

viegener

Zitat von: Loredo am 04 April 2017, 07:55:34
Ich habe mich etwas im DOIF Quellcode umgesehen; die einzige Übereinstimmung ist offenbar das bisherige :d für die Extraktion der 1. Dezimalzahl aus einem Reading.
Für INTERNALs wird am Beginn(!) des Readingnamen ein & erwartet, Attribute lassen sich gar nicht abfragen und für beides gibt es keine Dezimalzahl Extraktion.


Es gibt hier also keine Konsistenz/Kompatibilität zum list Befehl in DOIF.

ich frage mich,ob es nicht ein guter Ansatz wäre mehr Konsistenz zu erreichen, und list, set, IF und DOIF, etc zu versuchen die gleiche Syntax zu verpassen. Zweiheitlichkeit oder gar Dreiheitlichkeit anstatt Einheitlichkeit ist für mich nicht wirklich eine Lösung im Sinne der Benutzer (und zwar erfahrene und unerfahrene Benutzer gleichermassen)

Kein Support über PM - Anfragen gerne im Forum - Damit auch andere profitieren und helfen können

Loredo

#58
Ich habe den Patch nun angepasst.

Man kann r:, a:, i: als Präfix sowohl beim Device Namen als auch beim Readingnamen verwenden. Um mit DOIF kompatibel zu sein, kann man auch & statt i: verwenden.

Der bisherige Suffix :d wird so auch von DOIF unterstützt und verwendet.
Ich habe den Suffix noch dahingehend erweitert, dass man auch :i oder :r oder :r[0-9]+ verwenden kann, um die Zahl gleichzeitig noch in einen Integer zu wandeln oder runden zu lassen.

ReadingsNum() ist dahingehend optimiert, dass nun tatsächlich nur der erste Zahlenwert eines Strings zurückgegeben wird (so wie zumindest zuvor in der englischen Doku beschrieben; die deutsche Doku wich davon ab, war aber präziser was das alte Verhalten angeht einfach alles wegzuschmeißen, was keiner Zahl entspricht). Dies stimmt jetzt mit dem Verhalten von DOIF überein, was vorher nicht der Fall war.

AttrNum() und InternalNum() sind als neue Funktionen hinzugekommen.
Alle 3 *Num() Funktionen haben einen 4. optionalen Parameter erhalten, um darüber ebenfalls den Wert als Integer bzw. gerundeten Wert zurückgeben zu lassen.

Ich habe alles auf deutsch und englisch dokumentiert und die Patches ebenfalls angefügt.
Dabei habe ich auch fehlende Doku zu ReadingsAge() hinzugefügt, die Formatierung angeglichen und die Beispiele korrigiert.
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

rudolfkoenig

Ich bin erschlagen vom Patch, sowohl vom vorne/mitten/hinten Platzierbarkeit der Optionen, wie von den verschiedenen Rundungsparameter (:i, :d, :r0). Dass man & _und_ i: verwenden kann, finde ich verwirrend. Ich habe die Befuerchtung, dass ich das so nicht supporten kann.

Ich habe jetzt eine kleinere Version eingecheckt, die genauso wie der devspec Filter arbeitet, also mit optionalen a:, r: oder i:, liefert aber den erstbesten zureck, falls kein Praefix spezifiziert ist. Immerhin ist damit die urspruengliche Forderung auch erfuellt.

Danke fuer die Doku fuer ReadingsTimestamp und ReadingsAge, habs uebernommen.

Loredo

Sehr enttäuschend  :'(


Mir ist nicht klar, nach welchen Kriterien ich dir einen guten Patch zukommen lassen soll. Bei AnalyzeDevice() war er dir offensichtlich zu wartbar ("optimierungsbedürftig"), hier ist er dir zu kompakt (und dabei habe ich mich nur am vorher existierenden Code orientiert, was auch nicht einfach war).


Sei es drum, ich schreibe dir auf Basis deines Patches gerne nochmals einen neuen, da es mir wichtig ist die Mehrfunktionen drin zu haben.


Die Änderungen in ReadingsNum() sind IMHO auf jeden Fall sinnvoll, die neuen Funktionen InternalsNum() und AttrNum() sind eine logische und konsequente Ergänzung, die bisher gefehlt hat.
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

DeeSPe

Zitat von: rudolfkoenig am 04 April 2017, 16:51:16
Ich bin erschlagen vom Patch, sowohl vom vorne/mitten/hinten Platzierbarkeit der Optionen, wie von den verschiedenen Rundungsparameter (:i, :d, :r0). Dass man & _und_ i: verwenden kann, finde ich verwirrend. Ich habe die Befuerchtung, dass ich das so nicht supporten kann.

Ich habe jetzt eine kleinere Version eingecheckt, die genauso wie der devspec Filter arbeitet, also mit optionalen a:, r: oder i:, liefert aber den erstbesten zureck, falls kein Praefix spezifiziert ist. Immerhin ist damit die urspruengliche Forderung auch erfuellt.

Danke fuer die Doku fuer ReadingsTimestamp und ReadingsAge, habs uebernommen.

Ich denke in der deutschen commandref hat sich ein Fehler eingeschlichen. Zeile 1791:
      <li>ReadingsTimestamp(&lt;devicename&gt;)<br>
Sollte aber wie im Englischen sein:
      <li>ReadingsTimestamp(&lt;devicename&gt;,&lt;reading&gt;,&lt;defaultvalue&gt;)<br>

Gruß
Dan
MAINTAINER: 22_HOMEMODE, 98_Hyperion, 98_FileLogConvert, 98_serviced

Als kleine Unterstützung für meine Programmierungen könnt ihr mir gerne einen Kaffee spendieren: https://buymeacoff.ee/DeeSPe

rudolfkoenig

@DeeSPe: danke, habs geaendert.

@Loredo: Mein Problem ist nicht, dass es "zu kompakt" ist, sondern dass ich die Vielfalt von & und i: bzw. :r, :i, :d nicht gut finde.
Ich muss die Notwendigkeit von einem Patch erkennen, bevor ich es einbaue, und dann kann ich notfalls, falls es mir nicht gefaellt, auch selbst implementieren. Hier habe ich das Gefuehl, dass wir schleichend eine zweite Programmiersprache wie DOIF einfuehren, und ich will irgendwo die Grenze ziehen.

Ich lasse mich aber ueberstimmen.

Loredo

#63
Ich hoffe, dass beiliegender Patch verständlicher ist.

Es ist keine neue Programmiersprache oder ein zweites DOIF, es soll lediglich die Kompatibilität da sein auch &INTERNAL verwenden zu können.
Außerdem sollte sich das Extraktionsergebnis von DOIF und ReplaceSetMagic() nicht unterscheiden, was bei der Verwendung von :d derzeit ganz klar der Fall ist.

Ich habe ReplaceSetMagic() in den msg-Befehl eingebaut und darüber werden Nachrichten verschickt. Ich hätte gerne, dass man in Nachrichten in einfacher Weise auf alle Daten eines Devices zugreifen kann. Dabei wollte ich das Rad nicht neu erfinden und nicht ReplaceSetMagic() kopieren sondern es direkt erweitern. Das ist für Benutzer nicht logisch, warum sie bei dem einen Befehl etwas verwenden können und bei dem anderen nicht.

DOIF hat neben :d noch :sec (entspricht im Grunde ReadingsAge()), welches ich auch eingebaut habe. Außerdem erschien es mir sinnvoll die Palette wie folgt zu komplettieren:

       
  • :t für den Zeitstempel (analog zu ReadingsTimestamp())
  • :i um den Zahlenwert als Integer zurück zu erhalten
  • :r um den Zahlenwert auf die 1. Kommastelle zu runden
  • :rX um den Zahlenwert auf die X. Kommastelle zu runden
Ich halte das alles für sinnvolle und überschaubare Ergänzungen. Die von mir oben schon verfasste CommandRef erklärt das genauso einfach wie die bisherigen Optionen auch beschrieben sind.

Anschließend wäre es konsequent, wenn die Funktion ReadingsNum() die Integer-/Rundungsfunktion ebenfalls bekäme (diese Funktion wird in ReplaceSetMagic() ja nun nicht mehr verwendet).
Zu guter letzt erscheint es mir auch logisch die Lücke der Funktionen durch AttrNum() und InternalNum() zu schließen.

Über etwas Unterstützung dabei würde ich mich freuen.



Gruß
Julian
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

justme1968

das ReadingsNum nur die erste zahl aus dem reading holt statt alles was nicht \d ist zu entfernen finde ich gut. das aktuelle verhalten liefert bei manchen readings unerwartete ergebnisse.

die anderen flags finde ich nützlich. wenn sie tatsächlich einheitlich (ReplaceSetMagic, list, FILTER,...) verwendet werden würde ich sie auch in readingsGroup einbauen. vor allem das runden würde einige valueFormat attribute sparen. auch die i:,r: und a: präfixe wären einfacher als die + und ? variante die es dort aktuell gibt.

AttrNum() und InternalNum() wären tatsächlich konsequent. vor allem das das handling von attributen/readings/internals zwischen modulen nicht konsistent ist und man in die verlegnheit kommen kann alle drei zu verwenden.
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

rudolfkoenig

Na dann. Ich habe:
- die ReplaceSetMagic Syntax mit den Suffixen :t, :sec, :r und :r\d erweitert
- getestet, und die neuen Suffixe dokumentiert
- ReadingsNum umgestellt auf Zahl-Extrahieren, und einen optionalen vierten Parameter round eingefuehrt.
- AttrNum und InternalNum eingefuehrt, und alles getestet und dokumentiert.

Was ich nicht uebernomen habe:
- a:, r:, i: wahlweise vor oder nach dem Geraetenamen: es ist weiterhin nur davor zulaessig. Selbs so gibt es Probleme, wenn man ein Geraet a, r oder i nennt, und ein Suffix spezifiziert.
- optional & (es bleibt bei i:)
- :r\d+ habe ich auf :r\d eingeschraenkt.

ZitatÜber etwas Unterstützung dabei würde ich mich freuen.
Ich habe jetzt mit diesem Thema mehrere Stunden verbracht, fuer mich ist das mehr als "etwas". Da ich die Verantwortung fuer fhem.pl habe, muss ich das, was ich uebernehme, verstehen und vertreten koennen.

Loredo

#66

Vielen Dank, Rudi. Ich verstehe deinen Aufwand durchaus. Es ist nur auch von meiner Seite aus anstrengend, denn ich habe ebenfalls mehrere Stunden damit zugebracht und mir Mühe gegeben es bestmöglich vorzubereiten. Deine erste Reaktion erschien mir deshalb etwas zu schnell; daher nochmals VIELEN Dank, dass du dir die Zeit dafür genommen hast. Das weiß ich zu schätzen und damit sehe ich auch meinen eigenen Aufwand wieder als wertgeschätzt.

Also offenbarer Beschluss: Wir leben mit den Inkonsistenzen zu DOIF und damit, dass es zwar ähnlich aussieht, aber Texte nicht miteinander per Copy&Paste austauschbar sind.
Vielmehr liegt der Ball dann bei DOIF die nun allgemein definierte Notation zu unterstützen, um interoperabel zu sein/werden.



---
EDIT:

Was mir auffällt: Wir haben jetzt ein ganz anders Verhalten als zuvor bei :d, da es intern durch :r0 ersetzt wird. Das ist aber nicht das, was erreicht werden soll mit :d.
:d soll die unveränderte Zahl so extrahieren, wie sie im Reading steht. Diese Option gibt es jetzt nicht mehr und außerdem ist es ein anderes Verhalten als :d bei DOIF.

Nur auf explizites Verlangen des Users soll mittels :r auf die erste Stelle gerundet werden (da es in FHEM anderswo auch der Standard ist Zahlen auf die 1. Stelle zu runden) oder optional auf die X. Stelle bei :rX. Du hast jetzt :i weg gelassen, was explizit zur Unterscheidung zwischen :d (also dem Originalwert) und :i (also dem Integerwert des Originalwertes) gedacht war. Grundsätzlich wollte ich für :i auch explizit int() statt rand() verwenden, denn wer eine genaue Rundung will, kann explizit :r0 verwenden.

Kannst du dieses Verhalten bitte noch anpassen? Aktuell ist es leider weder Fisch noch Fleisch.

Ich hatte mir da also schon sehr viele Gedanken gemacht und nichts dem Zufall überlassen. Ich hätte es bevorzugt, wenn du hier ggf. nochmals nachgefragt hättest, um es besser zu verstehen.
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

rudolfkoenig


Loredo

#68
Danke!

Mir ist gerade noch aufgefallen, dass die neuen *Num() Funktionen gar keinen Wert nicht zurückgeben, wenn keine Zahl gefunden werden konnte. Stattdessen wird "" zurückgegeben bzw. wenn $round gesetzt ist 0.0.
Das erwartete Verhalten ist, dass der komplette Text zurückgegeben wird, wenn keine Zahl gefunden wird.

Außerdem muss der Default-Wert derzeit eine Zahl sein und kann keinen Text beinhalten, da round() daraus dann 0.0 macht.


Patch Vorschlag:


sub
InternalNum($$$;$)
{
  my ($d,$n,$default,$r) = @_;
  my $val = InternalVal($d,$n,$default);
  return $val !~ /(-?\d(\.\d)?)/ ? $val :
    !defined($r) ? $1 :
    $r eq "i" ? int($1) :
    round($1,$r);
}



       
  • Steigt möglichst früh aus
  • Berücksichtigt den Default Wert
  • Kann mit Text umgehen
  • Kann zusätzlich wie in ReplaceSetMagic auch die Nummer nur kürzen statt runden
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

rudolfkoenig

Das ist aber jetzt nicht neu, beim ReadingsNum war es doch genauso.

ZitatDas erwartete Verhalten ist, dass der komplette Text zurückgegeben wird, wenn keine Zahl gefunden wird.
Das mag bei ReplaceSetMagic so sein, bei ReadingsNum & co hat das niemand je versprochen.
Bin nichtmal sicher, ob das sinnvoll ist, und bei ReadingsNum waere es nicht kompatibel.

ZitatAußerdem muss der Default-Wert derzeit eine Zahl sein und kann keinen Text beinhalten, da round() daraus dann 0.0 macht.
Hier apelliere ich an dem Verstand des Benutzers.

Loredo

Mein gestriger Patch hatte das alles berücksichtigt. Ich finde hier braucht es keine Rückwärtskompatibilität.
Ich kann *Num() so nicht flexibel einsetzen. Wozu wird darin intern *Val() angewendet, wenn es dann nicht die selbe Rückgabe liefern kann?
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

justme1968

wie wäre es eplaceSetMagic auf auf stateFormat anzuwenden?

das würde einige sprintf zum runden einsparen.

für userReadings wäre es auch nützlich.

in beiden fällen wäre es gut mit $name:<reading> auch das aktuelle device verwenden zu können.
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

rudolfkoenig

Zitatwie wäre es eplaceSetMagic auf auf stateFormat anzuwenden?
Habe es mit etwas Bauchschmerzen eingebaut: eigentlich muesste die alte Ersetzung durch replaceMagic abgeloest werden, andererseits will ich kompatibel bleiben.

Loredo

Ich würde noch vorschlagen, dass der Regex von ReplaceSetMagic() übereinstimmend mit dem für die Readingnamen aus CommandSetstate() ist.
Außerdem sollte er wohl case sensitive sein, da rsmVal() es auch ist.





Index: fhem.pl
===================================================================
--- fhem.pl (revision 13929)
+++ fhem.pl (working copy)
@@ -1682,8 +1682,8 @@
     return $val;
   }

-  $a =~ s/(\[([ari]:)?([a-z0-9._]+):([a-z0-9._-]+)(:(t|sec|i|d|r|r\d))?\])/
-         rsmVal($1,$2,$3,$4,$5)/egi;
+  $a =~ s/(\[([ari]:)?([A-Za-z\d_\.]+):([A-Za-z\d_\.\-\/]+)(:(t|sec|i|d|r|r\d))?\])/
+         rsmVal($1,$2,$3,$4,$5)/eg;

   $evalSpecials->{'%DEV'} = $hash->{NAME};
   $a =~ s/{\((.*?)\)}/AnalyzePerlCommand($hash->{CL},$1,1)/egs;
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

rudolfkoenig

Soweit ich es sehe: setstate erlaubt zusaetzlich /, das habe ich uebernommen, die Pruefung ist jetzt wie gefordert, auch case-sensitive.
Define erlaubt (noch) Doppelpunkt im Namen, das wuerde ich gerne abschaffen. Was sagt ihr dazu: per featurelevel oder rabiat/direkt?

Loredo

Zitat von: rudolfkoenig am 08 April 2017, 15:22:50
Define erlaubt (noch) Doppelpunkt im Namen, das wuerde ich gerne abschaffen. Was sagt ihr dazu: per featurelevel oder rabiat/direkt?


Das dachte ich auch erst, aber eine Zeile darunter wird der Doppelpunkt gesondert als Warnung während des Starts behandelt, um nur keine neuen Devices mehr anlegen zu lassen.
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

betateilchen

Zitat von: rudolfkoenig am 08 April 2017, 15:22:50
Define erlaubt (noch) Doppelpunkt im Namen, das wuerde ich gerne abschaffen. Was sagt ihr dazu: per featurelevel oder rabiat/direkt?

Bitte rabiat, aber mit vorheriger Ankündigung eines Stichtags mit entsprechender Vorlaufzeit (4 Wochen?). Es könnte Module geben, die darauf angepaßt werden müssen.
-----------------------
Formuliere die Aufgabe möglichst einfach und
setze die Lösung richtig um - dann wird es auch funktionieren.
-----------------------
Lesen gefährdet die Unwissenheit!

Ellert

#77
Wenn es bei der Erweiterung von "set magic" auch um die Vereinheitlichung der Syntax geht und daum, Fragen entgegen zu wirken, die aus der unterschiedlichen Verhaltensweise der Set-Befehle (im notify oder DOIF) entstehen, dann möchte ich anmerken, dass im DOIF auch folgendes funktioniert:

[<Device>:<Reading>|<Internal>:d|"<Regex>":<Output>]

Beispiele aus der Commandref ( https://fhem.de/commandref_DE.html#DOIF_Filtern_nach_Zahlen ):


[mydevice:myreading:d]
entspricht:
[mydevice:myreading:"(-?\d+(\.\d+)?)"]
entspricht:
[mydevice:myreading:"(-?\d+(\.\d+)?)":$1]
entspricht:
[mydevice:myreading:"(-?\d+(\.\d+)?)":"$1"]
entspricht:
[mydevice:myreading:"(-?\d+(\.\d+)?)":sprintf("%s":$1)]

[mydevice:myreading:"(\d\d):(\d\d):(\d\d)":"hours: $1, minutes $2, seconds: $3"]


im "Output" ist Perl-Code erlaubt, also z.B.

[mydevice:myreading:"(-?\d+(\.\d+)?)":$1 ? $1 : 0]

Es wäre sicherlich benutzerfreundlich, wenn das in jedem set, setreading, ... funktionieren würde.

Edit:
Das [mydevice:myreading:"(-?\d+(\.\d+)?)":$1 ? $1 : 0] funktioniert bei $1 gleich undef nicht.

rudolfkoenig

ZitatDas dachte ich auch erst, aber eine Zeile darunter wird der Doppelpunkt gesondert als Warnung während des Starts behandelt, um nur keine neuen Devices mehr anlegen zu lassen.
Danke fuer den Hinweis, habs uebersehen. Diese Meldung gibt es inzwischen seit 15 Monaten, das reicht -> Habe : fuer define entfernt.

@Ellert: ich verstehe nicht, was "<Regex":<Output> machen soll (filtern will ich ja nicht, nur setzen). Kannst du bitte ein Beispiel mit set machen?

Ellert

Zitat von: rudolfkoenig am 08 April 2017, 19:52:42
Danke fuer den Hinweis, habs uebersehen. Diese Meldung gibt es inzwischen seit 15 Monaten, das reicht -> Habe : fuer define entfernt.

@Ellert: ich verstehe nicht, was "<Regex":<Output> machen soll (filtern will ich ja nicht, nur setzen). Kannst du bitte ein Beispiel mit set machen?

Ein Dummy du hat den Wert Es ist 17:00 Uhr.
set du1 [du:state:"(\d\d:\d\d)":$1]
setzt du1 auf den Wert 17:00.

Ein Dummy du hat den Wert 5 Eier kosten je Stück 13 Cent.
set du1 Summe [du:state:"(\d+).*(\d+)":$1*$2] Cent
setzt du1 auf den Wert Summe 65 Cent.

Regexp ist ein Ausdruck, der auf den Readingwert matched.
Output ist ein Perl-Ausdruck der die Variablen weiterverarbeitet.

rudolfkoenig

Danke, verstanden. Und danke, nein, das ist mir erstmal zu viel.

Loredo

Mir ist gerade aufgefallen, dass ich im Logfile hin und wieder solche Meldungen bekomme:



2017.04.09 14:00:54.147 1: PERL WARNING: Use of uninitialized value $d in hash element at fhem.pl line 3963.



Beiliegender Patch prüft, ob $d und $n an die *Val() Funktionen übergeben worden sind.
Bei AttrVal() war das für $d sogar schon (ansatzweise) der Fall.
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

rudolfkoenig

Ich haette gerne auch die Meinung anderer dazu.
Mein Ziel ist nicht FHEM Warnungsfrei zu machen, nur damit der Benutzer oder Modulautor jeden Unsinn als Parameter uebergeben kann.

justme1968

fhem sollte alles abfangen das zu fehlverhalten oder
abstürzen führen kann.
es sollte meldungen ausgeben für alles das ein endanwender verkonfigurieren kann.

perl warnungen die ein modulentwickler durch falschen aufruf von dokumentierten routinen verursacht sollten nicht angefangen werden wenn es performance einbußen zur folge haben kann. ob man es in anderen fällen abfängt ist geschmacksache. es gehört auf jeden fall im aufrufenden modul repariert.

die routinen hier sind auch für endanwender. auch wenn sie nicht gelesen werden sollte es hier prüfung und sprechende meldungen geben. dann kann man zumindest sagen: schau ins log.
hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968

rudolfkoenig

Zitatauch wenn sie nicht gelesen werden sollte es hier prüfung und sprechende meldungen geben. dann kann man zumindest sagen: schau ins log.
Aber wenn es wie vorgeschlagen geprueft wird, dann gibt es keine Warnung im Log.
Und wenn ich nichts mache, dann gibt es eine Warnung. Ich finde es mit Warnung besser.

Loredo

Dann bitte konsequenterweise auch die vorhandene Prüfung aus AttrVal() entfernen.
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

Loredo

#86
Hallo Rudi,

mit Bezug auf diesen Post würde ich ReplaceSetMagic() gerne noch darum erweitern, dass die Ausgabe auch mit Dezimaltrennzeichen erfolgen kann.
Einen Patch dazu habe ich angehängt, vielleicht schaust du ihn dir ja einmal an. Damit ist es möglich, hinter :r, :i oder :d noch ein m (für mark) zu hängen, optional gefolgt von einer Zahl für die gewünschte Sprache Formatierung.



Gruß
Julian
Hat meine Arbeit dir geholfen? ⟹ https://paypal.me/pools/c/8gDLrIWrG9

Maintainer:
FHEM-Docker Image, https://github.com/fhem, Astro(Co-Maintainer), ENIGMA2, GEOFANCY, GUEST, HP1000, Installer, LaMetric2, MSG, msgConfig, npmjs, PET, PHTV, Pushover, RESIDENTS, ROOMMATE, search, THINKINGCLEANER

rudolfkoenig

Siehe meine Frage bzw. Kommentar dazu im verlinkten Thema.

rudolfkoenig

 
ZitatDann bitte konsequenterweise auch die vorhandene Prüfung aus AttrVal() entfernen.
Jawohl!
Habs gemacht. :)

Thorsten Pferdekaemper

Hi,
könnte sich das hier mal jemand anschauen:
https://forum.fhem.de/index.php?topic=70390
Es scheint Warnungen dieser Form zu hageln...

[Mon Apr 10 21:57:25 2017] fhem.pl: Use of uninitialized value $s in pattern match (m//) at fhem.pl line 1677.

...wenn man das ":d" am Ende weglässt. D.h. so etwas hier erzeugt diese Warnung:

[PoolController:Pool_Aussen_Num]

Aber das hier ist ok:

[PoolController:Pool_Aussen_Num:d]

Das soll doch nicht so sein, oder?
Gruß,
   Thorsten
FUIP

rudolfkoenig


justme1968

hue, tradfri, alexa-fhem, homebridge-fhem, LightScene, readingsGroup, ...

https://github.com/sponsors/justme-1968