Seite 1 von 1

Schaltsteckdose P110 in Rule einbinden

Verfasst: 22. Nov 2022 17:49
von manes
Hi,
ich habe mir die Schaltsteckdose Tapo P110 von tp-link zugelegt. Ich möchte gerne auf Änderungen reagieren, wenn das Teil eine Stromaufnahme mißt und wenn nicht. Also habe ich eine Regel geschrieben, die eigentlich auf den Wechsel von 0 Watt auf Verbrauch und eine Regel, die andersherum reagiert von Leistungsaufnahme auf 0 Watt. Leider klappt es nicht. Das ist der Wert, den ich über die Code Tools zurück bekomme.
P110.PNG
Was muß man da abfragen? ich habe 0 als numerisch, 0 als text 0W 0 W eingetragen. Es gibt keine Reaktion der Regel. Was müßte ich anders machen?
Die Regel sieht so z.B. aus.

Code: Alles auswählen

configuration: {}
triggers:
  - id: "1"
    configuration:
      itemName: P110SmartPlug_Power
      state: Any
      previousState: '"0"'
    type: core.ItemStateChangeTrigger
conditions: []
actions:
  - inputs: {}
    id: "2"
    configuration:
      type: application/javascript
      script: >-
        var cMessage = "" 
        val telegramAction =   getActions("telegram","telegram:telegramBot:XXXXXXXXXXX")
            cMessage = "Stromverbrauch"
        telegramAction.sendTelegram(cMessage)
    type: script.ScriptAction

Re: Schaltsteckdose P110 in Rule einbinden

Verfasst: 22. Nov 2022 21:14
von udo1toni
Das wird so nicht funktionieren. Erstelle stattdessen eine Rule, welche auf changed reagiert und füge bei but only if eine Bedingung Wert > 0 ein
Das sollte dann so aussehen:

Code: Alles auswählen

configuration: {}
triggers:
  - id: "1"
    configuration:
      itemName: P110SmartPlug_Power
    type: core.ItemStateChangeTrigger
conditions: []
  - id: "2"
    configuration:
      itemName: P110SmartPlug_Power
      operator: ">"
      state: "0"
    type: core.ItemStateCondition
actions:
  - inputs: {}
    id: "2"
    configuration:
      type: application/javascript
      script: >-
        var cMessage = "" 
        val telegramAction =   getActions("telegram","telegram:telegramBot:XXXXXXXXXXX")
            cMessage = "Stromverbrauch"
        telegramAction.sendTelegram(cMessage)
    type: script.ScriptAction
Allerdings wird die Rule natürlich bei jedem Wert über 0 getriggert, wenn sich der Wert ändert. Das heißt, telegram bekommt was zu tun und Du brauchst gute Nerven :)

Wie ist das Item P110SmartPlug_Power exakt definiert?

Re: Schaltsteckdose P110 in Rule einbinden

Verfasst: 23. Nov 2022 07:14
von manes
sowas ähnliches hatte ich auch schon gedacht, aber Du hast es schon erwähnt, dann knallt Telegramm ohne Ende und das wäre ein absolutes no go. Was meinst Du mit genau definiert? Ich wüßte jetzt nicht, welche Info Du genau benötigst.

Re: Schaltsteckdose P110 in Rule einbinden

Verfasst: 23. Nov 2022 12:22
von udo1toni
Handelt es sich um ein Number Item? Oder handelt es sich um ein Number:Energy Item? Es gibt verschiedene Möglichkeiten, die Leistung als Zahl zu erfassen. Es könnte sich sogar um ein String Item handeln (was einen vielen Möglichkeiten beraubt, aber auch das habe ich schon mehrfach gesehen...)

Ich sehe auch gerade, das mir gestern ein anderer Fehler durchgerutscht ist. Die Rulenotation ist die einer DSL Rule, nicht JavaScript. Entsprechend muss es

Code: Alles auswählen

      type: application/vnd.openhab.dsl.rule
heißen
manes hat geschrieben: 23. Nov 2022 07:14 Du hast es schon erwähnt, dann knallt Telegramm ohne Ende und das wäre ein absolutes no go.
Die Frage ist, wie sinnvoll ist eine einmalige Messwertanzeige im Einschaltmoment? Oder anders ausgedrückt: Was möchtest Du tatsächlich angezeigt bekommen?

Re: Schaltsteckdose P110 in Rule einbinden

Verfasst: 23. Nov 2022 13:09
von manes
Ah, jetzt verstehe ich. Typ Number:Power steht drin. Ich habe es angelegt, direkt als ich es dem Thing zugeordnet habe. Und der Grund warum es so über Telegeram laufen soll ist ganz einfach: Das Teil ist an einem Kühlschrank dran, der etwas wild kühlt. Ich möchte nur eine genauere Info bekommen, wann und wie oft der Kühlschrank anspringt um dann etwas anderes zu kontrollieren.

Re: Schaltsteckdose P110 in Rule einbinden

Verfasst: 23. Nov 2022 13:44
von peter-pan
Hier noch meine 2 Cent.

Ich hab's nicht so mit den Rules per UI, aber vielleicht einen kleinen Tipp. Um das UoM(Einheit) zu eliminieren, kannst du das Item "parsen".

Ein Beispiel hierzu, das du so in dein Scratch-Pad kopieren kasnnst:

Code: Alles auswählen

="mit displayState: " +items.P110SmartPlug_Power.displayState + "  / und nur state: " +items.P110SmartPlug_Power.state + "  / und mit Eliminierung der UoM: " + Number.parseFloat(items.P110SmartPlug_Power.state)
Vielleicht kannst du damit was anfangen.

Re: Schaltsteckdose P110 in Rule einbinden

Verfasst: 23. Nov 2022 14:27
von udo1toni
manes hat geschrieben: 23. Nov 2022 13:09 Ah, jetzt verstehe ich. Typ Number:Power steht drin. Ich habe es angelegt, direkt als ich es dem Thing zugeordnet habe. Und der Grund warum es so über Telegeram laufen soll ist ganz einfach: Das Teil ist an einem Kühlschrank dran, der etwas wild kühlt. Ich möchte nur eine genauere Info bekommen, wann und wie oft der Kühlschrank anspringt um dann etwas anderes zu kontrollieren.
Also geht es eigentlich nicht um den wert selbst. Das ist gut :) Wobei... Wenn man den Kühlschrank öffnet, geht ja meist eine Funzel an (oder bei neueren Modellen ein besserer Baustrahler, da LED-Technik) ;)

Mein Vorschlag dazu: Nutze ein Proxy Item für die Meldung. Das Item legst Du einfach an, ohne eine Verknüpfung zu einem Channel vorzunehmen. Lege es als Switch Item an. In den Rules unten habe ich KuehlschrankAktiv als Item verwendet.
Eine Rule kümmert sich um die Werterfassung bzw. Auswertung:

Code: Alles auswählen

configuration: {}
triggers:
  - id: "1"
    configuration:
      itemName: P110SmartPlug_Power
    type: core.ItemStateChangeTrigger
conditions: []
actions:
  - inputs: {}
    id: "2"
    configuration:
      type: application/vnd.openhab.dsl.rule
      script: >-
        val power = (P110SmartPlug_Power.state as Number).floatValue
        var new = OFF
        if(power > 20)
            new = ON
        if(KuehlschrankAktiv.state != new)
            KuehlschrankAktiv.postUpdate(new.toString)
    type: script.ScriptAction
Die Rule triggert immer, wenn sich der Messwert ändert.
Zunächst wandelt sie den Messwert in eine einfache Zahl und speichert diese in der lokalen Konstanten power.
Anschließend definiert sie eine lokale Variable und füllt sie mit dem State OFF.
Nun folgt ein Vergleich, ob power > 20 ist. Ist das der Fall, wird new auf ON gewechselt.
Zum Schluss wird der Status des Items KuehlschrankAktiv geändert, falls er vom neuen Status abweicht.
Die 20 sind von mir willkürlich ausgesucht, der Wert sollte auf jeden Fall über 0 gewählt werden, am einfachsten prüfst Du die Stromaufnahme bei abgeschaltetem Kompressor und geöffneter Tür und nimmst einen leicht höheren Wert.

Eine weitere Rule kümmert sich darum, die Nachricht zu verschicken:

Code: Alles auswählen

configuration: {}
triggers:
  - id: "1"
    configuration:
      itemName: KuehlschrankAktiv
    type: core.ItemStateChangeTrigger
conditions: []
actions:
  - inputs: {}
    id: "2"
    configuration:
      type: application/vnd.openhab.dsl.rule
      script: >-
        val timestamp = KuehlschrankAktiv.lastUpdate.toEpochSecond
        val iDiff = (now.toEpochSecond - timestamp).intValue
        val iSec  = iDiff % 60
        val iMin  = ((iDiff - iSec) / 60).intValue % 60
        val iHour = ((iDiff - iSec - iMin * 60) / 3600).intValue
        var strDauer = iHour.toString + ":" +
            if(iMin < 10) "0" else "" +
            iMin.toString + ":" +
            if(iSec < 10) "0" else "" +
            iSec.toString
        var strMessage = "Ein"
        if(KuehlschrankAktiv.state == ON)
            strMessage = "Aus"
        var strMessage = strMessage + "schaltdauer des Kühlschranks war " + strDauer
        val telegramAction =   getActions("telegram","telegram:telegramBot:XXXXXXXXXXX")
        telegramAction.sendTelegram(strMessage)
    type: script.ScriptAction
Es wird in jeder Meldung ausgegeben, wie lang die vorherige Phase gedauert hat.
Der Code ist nicht geprüft :) kann also sein, dass er so nicht funktioniert, die Umrechnung von Seklunden in Stunden, Minuten und Sekunden ist manchmal etwas tricky. Zur Not könnte man aber zunächst die Differenz einfach direkt ausgeben, das wären dann halt Sekunden.