ich möchte gerne eine telegram benachrichtigung schicken sobald sich unser ofen ein oder ausschaltet.
ich lege also folgendes notify an, welches auch funktioniert:
define n_Heizung_Anforderung_Pelletsofen_Telegram notify Temperaturen:AnforderungPelletsofen:.* { my $status = ReadingsVal("Temperaturen","AnforderungPelletsofen","");; if ($status eq "EIN") { fhem("set TelegramBot message Pelletsofen gestartet!")};; if ($status eq "AUS") { fhem("set TelegramBot message Pelletsofen gestoppt!")} }
nun noch einige hintergrundinfos:
die heizungssteuerung (eine UVR1611) lese ich mit HTTPMOD aus und generiere damit meine readings (u.a. auch AnforderungPelletsofen, entweder "EIN" oder "AUS"), das pollingintervall zum auslesen ist 60 sekunden.
um das log nicht unnötig mit gleichen werten aufzufüllen ist mit
attr Temperaturen event-min-interval *:300
attr Temperaturen event-on-change-reading .*
das aktualisieren der readings nur bei änderung, spätestens aber nach 5 minuten (um die readings auch noch vernünftig plotten zu können) eingedämmt.
nun ists logischerweise auch so das das notify für die telegram message ebenfalls alle 5 minuten getriggert wird (weil ja ein event erzeugt wird).
hab ich irgendeine elegante möglichkeit das notify so abzuändern das es wirklich nur auf eine ÄNDERUNG des readings (von AUS auf EIN oder von EIN auf AUS) zu reagieren?
nimm den "min interval" raus und regle das im Plot.
mit dem Style der Linien bekommst Du den Plot auch so hin und hältst das Log sauberer.
weiterhin würde ich dir hierfür DOIF empfehlen. wird übersichtlicher.
oder nimm die gleiche Telegram Nachricht und schick das Reading mit. Ich such mal raus wie ich das zum testen hatte. werd ich nachher hier editieren.
Hallo fl_Indigo,
vielleicht reicht auch ein zusätzlicher Vergleich mit OldValue beim Status des Pelletofens (muß sich geändert haben, sonst keine Benachrichtigung).
Gruß, Beta-User
Zitat von: Beta-User am 05 April 2017, 10:20:14
Hallo fl_Indigo,
vielleicht reicht auch ein zusätzlicher Vergleich mit OldValue beim Status des Pelletofens (muß sich geändert haben, sonst keine Benachrichtigung).
Gruß, Beta-User
die variante hab ich auch schon im kopf, nur an der umsetzung in der praxis scheiterts: wie komme ich an den vorhergehenden wert? muss ich selber was zimmern und den wert in ein seperates reading packen oder gibts da irgendein internal OldValue? ich kann darüber nix (sinnvolles) finden. die abfrage wär nicht das problem, aber die datenbasis ;)
Damit hab ich mal experimentiert:
define ETA_Status notify ETA_Kessel_1_Status:Kessel_1_Status:.* set TelegramBot message Statusänderung Kessel. $EVENT
Damit bekam ich jede Statusänderung auf Telegram. $EVENT ist der Wert des Readings.
EventOnChange auf dieses Reading gesetzt OHNE min-interval
Zu OldValue kenne ich auch nur das, was in der commandref steht.
So wie ich das verstanden habe, handelt es sich um eine Abfragefunktion, der Aufruf sollte daher ähnlich wie bei ReadingsVal() funktionieren, nur dass eben nicht der aktuelle Wert des betreffenden Readings zurückkommt, sondern der alte. Damit sollte auch das Beibehalten des min-interval gehen.
OldValue bezieht sich, wie in der commandref beschrieben, auf ein device, nicht auf readings
wenn ich das oben in der kommandozeile eingebe bekomme ich den letzt state des devices zurück - also für diesen zweck kann man das nicht missbrauchen...
@Frank_Huber: min-interval möchte ich nicht ausschalten, die plots werden richtig unschön damit (die pumpendiagramme)
Zitat von: fl_Indigo am 05 April 2017, 10:58:31
@Frank_Huber: min-interval möchte ich nicht ausschalten, die plots werden richtig unschön damit (die pumpendiagramme)
probier mal die Linien-Typen durch. lines / steps / bars / ...
mit lines schauts bld aus, das ist richtig, mit steps und bars kriegst es aber hin. Hab ich in meinen Plots der Heizung auch drin.
Im Anhang ein Beispiel.
ich verwende tagesplots, keine 24h plots, das erschwert mir die thematik einfach...
aber bitte back to topic, hat noch irgendwer ideen wies sonst noch zu lösen wäre?
das event-min-interval kannst du ja auch auf bestimmte Readings filtern.
Zitatevent-min-interval
Dieses Attribut enthält eine durch Kommata getrennte Liste von "readings:minInterval" Paare. readings kann ein regexp sein. Ein Event wird nur dann generiert, falls seit dem letzten Auftreten des gleichen Events mindestens minInterval Sekunden vergangen sind. Falls event-on-change-reading auch spezifiziert ist, dann werden sie mit ODER kombiniert, d.h. wenn einer der beiden Bedingungen wahr ist.
oder ein DOIF ohne do always
define n_Heizung_Anforderung_Pelletsofen_Telegram DOIF
([Temperaturen:"AnforderungPelletsofen: EIN"]) (set TelegramBot message Pelletsofen gestartet!)
DOELSEIF
([Temperaturen:"AnforderungPelletsofen: AUS"]) (set TelegramBot message Pelletsofen gestoppt!)
Beispiel für ein Event das so aussieht:
Temperaturen AnforderungPelletsofen: EIN
ja schon, aber genau für diese EIN/AUS readings möchte ich ja (für meine plots) in bestimmten intervallen ein event haben, sonst reisst der plot ab... :p
so beisst sich die katze in den schwanz...
komme nochmal zurück auf OldValue...
Es sollte m.E. mit OldValue("<Device>:<Reading>") gehen, also z.B. OldValue("Temperaturen:AnforderungPelletsofen"). Das OldValue lebt aber nur innerhalb des notify, bezieht sich auf das auslösende Event (hier also die Änderung eines Readings, nicht eines Geräte-Status) und verschwindet danach im digitalen Nirvana.
Wäre vielleicht einen Test wert...
Zitat von: fl_Indigo am 05 April 2017, 11:44:42
ich verwende tagesplots, keine 24h plots, das erschwert mir die thematik einfach...
aber bitte back to topic, hat noch irgendwer ideen wies sonst noch zu lösen wäre?
das sollte nichts ändern. um 00:00 ist der Tagesplot identisch mit dem 24h plot.
Aber mach wie Du denkst. :)
Zitat von: Beta-User am 05 April 2017, 12:12:52
komme nochmal zurück auf OldValue...
Es sollte m.E. mit OldValue("<Device>:<Reading>") gehen, also z.B. OldValue("Temperaturen:AnforderungPelletsofen"). Das OldValue lebt aber nur innerhalb des notify, bezieht sich auf das auslösende Event (hier also die Änderung eines Readings, nicht eines Geräte-Status) und verschwindet danach im digitalen Nirvana.
Wäre vielleicht einen Test wert...
das haut so nicht hin
Unknown command OldValue("Temperaturen:AnforderungPelletsofen"), try help.
das notify schaut so aus:
define n_Heizung_Anforderung_Pelletsofen_Telegram notify Temperaturen:AnforderungPelletsofen:.* { my $status = ReadingsVal("Temperaturen","AnforderungPelletsofen","");; my $oldstatus = OldValue("Temperaturen:AnforderungPelletsofen");; if ($status eq "EIN" && $oldstatus ne "EIN") { fhem("set TelegramBot message Pelletsofen gestartet!")};; if ($status eq "AUS" && $oldstatus ne "AUS") { fhem("set TelegramBot message Pelletsofen gestoppt!")} }
die variante mit DOIF hab ich auch probiert, das löst ebenfalls alle 5 minuten eine meldung aus...
Die Funktion OldValue() gibt den Status der Definition $name zurück BEVOR der aktuelle Status aufgrund eines Events gesetzt wurde. Sollte die gewünschte Definition nicht existieren bzw. nicht gesetzt sein, wird "" (Leerstring) zurückgegeben.
define n_Heizung_Anforderung_Pelletsofen_Telegram notify Temperaturen:AnforderungPelletsofen:.* {
if ($EVTPART1 eq "EIN" && OldValue($NAME) ne "EIN") {
fhem("set TelegramBot message Pelletsofen gestartet!");
}
elsif ($EVTPART1 eq "AUS" && OldValue($NAME) ne "AUS") {
fhem("set TelegramBot message Pelletsofen gestoppt!");
}
}
Der Code ist für die DEF und NICHT für die fhem.cfg
@Cooltux:
Danke für die Klarstellung, wieder was gelernt!
(Im ersten if fehlt m.E. noch eine ")" nach $NAME))
Gruß, Beta-User
Zitat von: fl_Indigo am 05 April 2017, 12:54:26
die variante mit DOIF hab ich auch probiert, das löst ebenfalls alle 5 minuten eine meldung aus...
Ok, hast recht. Liegt an der Event-Auswertung - wenn du Readings Auswertest, dann funktioniert es aber.define n_Heizung_Anforderung_Pelletsofen_Telegram DOIF
([Temperaturen:AnforderungPelletsofen] eq "EIN") (set TelegramBot message Pelletsofen gestartet!)
DOELSEIF
([Temperaturen:AnforderungPelletsofen] eq "AUS") (set TelegramBot message Pelletsofen gestoppt!)
EDIT:
alles zurück! völliger blödsinn! ohne 'do always' funktioniert es, egal ob du Events oder Readings auswertest. Ich hatte nen Fehler in meinem testDOIF.
Es muss allerdings mehr als ein Zweig vorhanden sein. Also einen DOIF Zweig für AN und einen für AUS. Und nicht nur ein Zweig der auf AN und AUS triggert.
einen herzlichen dank an den profi, das notify tut jetzt was es soll! :)
danke für eure zeit!
muss mich nochmal korrigieren: das notify von cooltux funzt auch nicht, wieder alle 5min eine message :|
dafür funktioniert die zweite DOIF vom automatisierer jetzt wie sie soll! danke dafür!
das erste hätte aber auch funktionieren müssen... egal.
wenn das Notify von CoolTux nicht funzt - wäre es möglich, dass 'AnforderungPelletsofen' noch andere Zustände als 'AN' und 'AUS' hat?
Bei dem DOIF wäre das egal, da das nach einer triggerung durch 'AN' nur durch eine triggerung durch 'AUS' den Zustand wechselt.
nöp, das reading kann nur EIN oder AUS sein
egal, es funzt...
nö, nicht egal! so was juckt mich.
glaube jetzt hab ichs.
OldValue($NAME) ne "EIN"
$NAME dürfte in diesem Fall mit 'Temperaturen' gefüllt sein, du wolltest aber das OldValue von 'Temperaturen:AnforderungPelletsofen' haben.
ja, so stünde es ja auch in der commandref...
Auszug aus Commandref
[quote]
Value(<devicename>)
gibt den Status eines Gerätes zurück (entsprechend dem Ausdruck in Klammern, den Sie beim List-Befehl sehen).
OldValue(<devicename>)
OldTimestamp(<devicename>)
gibt den vorherigen Wert/Zeitstempel des Gerätes zurück.
Man müsste nun halt Mal schauen was genau in EVTPARTX oder EVENT genau drin steht. Also entweder Eventmonitor aufmachen und schauen oder eine Logausgaben beim Notify erzwingen
also im eventmonitor kommt nix sinnvolles, außer das das notify getriggert und erfolgreich ausgeführt wurde...
das notify hab ich jetzt mal mit verbose 5 attributiert...
im log steht das hier:
2017.04.05 19:22:17 5: Triggering n_Heizung_Anforderung_Pelletsofen_Telegram
2017.04.05 19:22:17 4: n_Heizung_Anforderung_Pelletsofen_Telegram exec { if ($EVTPART1 eq "EIN" && OldValue($NAME) ne "EIN") {fhem("set TelegramBot message Pelletsofen gestartet!");;} elsif ($EVTPART1 eq "AUS" && OldValue($NAME) ne "AUS") {fhem("set TelegramBot message Pelletsofen gestoppt!");; } }
aber nix von werten in den variablen, wie komm ich an die ran?
Im Eventmonitor stehen nur die Events. Da wird nichts mit Trigger Notify gezeigt. Wenn zum Beispiel ein Reading neu geschrieben wird kann ein Event ausgelöst werden.
Mach mal
Log 1, $EVENT;
Noch vor der ersten Bedingung
OK, ein log auf $EVENT liefert folgendes im log:
2017.04.05 20:34:25 5: Triggering n_Heizung_Anforderung_Pelletsofen_Telegram
2017.04.05 20:34:25 4: n_Heizung_Anforderung_Pelletsofen_Telegram exec { Log 1, $EVENT;; if ($EVTPART1 eq "EIN" && OldValue($NAME) ne "EIN") {fhem("set TelegramBot message Pelletsofen gestartet!");;} elsif ($EVTPART1 eq "AUS" && OldValue($NAME) ne "AUS") {fhem("set TelegramBot message Pelletsofen gestoppt!");; } }
2017.04.05 20:34:25 1: AnforderungPelletsofen: AUS
somit müsste die erste änderung auf $EVENTPART2 lauten anstatt PART1 um den richtigen wert zu vergleichen
ein log auf $NAME liefert folgendes:
2017.04.05 20:39:40 5: Triggering n_Heizung_Anforderung_Pelletsofen_Telegram
2017.04.05 20:39:40 4: n_Heizung_Anforderung_Pelletsofen_Telegram exec { Log 2, $NAME;; if ($EVTPART1 eq "EIN" && OldValue($NAME) ne "EIN") {fhem("set TelegramBot message Pelletsofen gestartet!");;} elsif ($EVTPART1 eq "AUS" && OldValue($NAME) ne "AUS") {fhem("set TelegramBot message Pelletsofen gestoppt!");; } }
2017.04.05 20:39:40 2: Temperaturen
und da liegt das eigentliche problem: das verhalten ist wie in der commandref beschrieben, OldValue geht nur aufs device, und nicht aufs reading...
$EVTPART1 war richtig, da wir mit 0 beginnen.
Und oldValue geht nicht auf das Device sondern auf STATE vom Device.
Wäre ja mal interessant wie der dann ist.
Log 1, 'oldValue ist ' . oldValue($DEVICE);
die syntax frisst mir die DEF nicht, --> "Global symbol "$DEVICE" requires explicit package name at (eval 412991) line 1."
Zitat von: fl_Indigo am 06 April 2017, 06:16:04
die syntax frisst mir die DEF nicht, --> "Global symbol "$DEVICE" requires explicit package name at (eval 412991) line 1."
Sorry mein Fehler. War gedanklich bei symbolischer Erklärung
Änder mal $DEVICE in $NAME so wie Du es ja weiter oben schon mal richtig gemacht hast.
ein log auf $NAME hatte ich bereits oben gepostet, da steht der devicename drin...
oder hab ichs jetzt falsch verstanden?
Ja hast Du.
Log 1, 'oldValue ist ' . oldValue($NAME);
errormeldung im log:
2017.04.06 18:38:32 1: ERROR evaluating my $NAME='Temperaturen';my $TYPE='HTTPMOD';my $SELF='n_Heizung_Anforderung_Pelletsofen_Telegram';my $EVENT='AnforderungPelletsofen: AUS';my $EVTPART1='AUS';my $EVTPART0='AnforderungPelletsofen:';{Log 1, 'oldValue ist ' . oldValue($NAME); if ($EVTPART1 eq "EIN" && OldValue($NAME) ne "EIN") {fhem("set TelegramBot message Pelletsofen gestartet!");} elsif ($EVTPART1 eq "AUS" && OldValue($NAME) ne "AUS") {fhem("set TelegramBot message Pelletsofen gestoppt!"); } }: Undefined subroutine &main::oldValue called at (eval 110886) line 1.
2017.04.06 18:38:32 3: n_Heizung_Anforderung_Pelletsofen_Telegram return value: Undefined subroutine &main::oldValue called at (eval 110886) line 1.
notify wird nicht ausgeführt...
Ich merke mir das Reading auf welches getriggert wurde in notify dadurch habe ich ein OldValue für das Reading zum Vergleich.
und wie stellst du das an? :)
Der Thread ist als "Gelöst" markiert. Irgendwie finde ich aber die Lösung nicht. Wie macht man denn nun ein notify, dass nur bei Änderung eines Readings feuert?
letztenendes: mit einem DOIF ;)
define DOIF_Telegram_Heizung_Anforderung_Pelletsofen DOIF ([Temperaturen:AnforderungPelletsofen] eq "EIN") (set TelegramBot message Pelletsofen gestartet!) DOELSEIF ([Temperaturen:AnforderungPelletsofen] eq "AUS") (set TelegramBot message Pelletsofen gestoppt!)