Ankündigung

Einklappen
Keine Ankündigung bisher.

Pumpenüberwachung

Einklappen
X
 
  • Filter
  • Zeit
  • Anzeigen
Alles löschen
neue Beiträge

    Pumpenüberwachung

    Hallo zusammen,

    ich habe 3-4 Pumpen im Haus, welche ich über den Stromverbrauch überwachen möchte.
    1. Hauswasserwerk für Gartenbewässerung und Toilettenspülung
    2. Entwässerung vor dem Kellerfenster (dort steigt seit 3 Jahren aussen das Wasser zu hoch)
    3. Hebeanlage Hauptpumpe
    4. Hebeanlage Backup Pumpe (kommt aber noch)
    Derzeit habe ich schon 2 Pumpen auf entsprechende Aktorkanäle gelegt, aber (es kommt wie es kommen muss) es funktionier leider noch nicht richtig
    Da die Pumpen natürlich auch zeitgleich laufen können, arbeite ich mit 2 timern und Routinen.

    Items
    Code:
    Switch Steckd_KG_Links_Pumpe    "Hauswasserwerk"                (KG_Hausanschluss)        {channel="knx:device:bridge:ABB_0_0_10:ch8"}
    Number Wasserwerk_Strom        "Hauswasserwerk Stromverbrauch [%f Wh]"        (Strom, Electricity_Chart)    {channel="knx:device:bridge:ABB_0_0_10:ch8A"}
    Switch Steckd_Pumpe        "Entwässerungspumpe"                                {channel="knx:device:bridge:ABB_0_0_15:ch1"}
    Number Drainage_Power        "Entwässerungspumpe Stromverbrauch [%f Wh]"    (Strom, Electricity_Chart)    {channel="knx:device:bridge:ABB_0_0_15:ch1A"}
    Rule
    Code:
    var Timer t_waterscurity = null        //Timer, zur Überwachung des Hauswasserwerks
    var Timer t_drainagescurity = null    //Timer, zur Überwachung der Entwässerungspumpe
    
    rule WaterSecurity
    when
        Item Wasserwerk_Strom changed or
        Item Drainage_Power changed
    then
        if (Wasserwerk_Strom.previousState.state == (0) && Wasserwerk_Strom.state > 0 && GhostMode.state == CLOSED && myIrrigationSwitchVis.state == ON) {
            pushNotification("Note", "Hauswasserwerk zieht Strom")
            if (t_waterscurity === null) {
                t_waterscurity = createTimer(now.plusSeconds(10))[|
                    if (Wasserwerk_Strom.state > 0) {
                        pushNotification("ALARM: " + now, "Hauswasserwerk zieht immer noch Strom: " + Wasserwerk_Strom.state.toString + " mA")
                        t_waterscurity.reschedule(now.plusSeconds(10))
                    } else {
                        pushNotification("Entwarnung: " + now, "Hauswasserwerk bei " + Wasserwerk_Strom.state.toString + " mA")
                        t_waterscurity.cancel
                        t_waterscurity = null
                        return;
                    }
                ]
            }
        } else if (Drainage_Power.previousState.state == (0) && Drainage_Power.state > 0) {
            pushNotification("Note", "Entwässerungspumpe zieht Strom")
            if (t_drainagescurity === null) {
                t_drainagescurity = createTimer(now.plusSeconds(10))[|
                    if (Drainage_Power.state > 0) {
                        pushNotification("ALARM: " + now, "Entwässerungspumpe zieht immer noch Strom: " + Drainage_Power.state.toString + " mA")
                        t_drainagescurity.reschedule(now.plusSeconds(10))
                    } else {
                        pushNotification("Entwarnung: " + now, "Entwässerungspumpe bei " + Drainage_Power.state.toString + " mA")
                        t_drainagescurity.cancel
                        t_drainagescurity = null
                        return;
                    }
                ]
            }
        }
    end
    Im Grundsatz funktioniert dies, jedoch wird bei jedem Durchlauf die Erstnachricht gesendet "pushNotification("Note", "Entwässerungspumpe zieht Strom")", obwohl dann ja nicht mehr der previous.state 0 sein kann? Wenn die entsprechende Pumpe abschaltet, kommt auch die korrekte Meldung.

    Seht ihr meinen Denkfehler??

    Viele Grüße,

    Jörg

    #2
    "Item Drainage_Power changed" könnte die Regel auslösen, auch wenn "Wasserwerk_Strom.previousState.state" unverändert bleibt.

    Kommentar


      #3
      Zitat von wknx Beitrag anzeigen
      "Item Drainage_Power changed" könnte die Regel auslösen, auch wenn "Wasserwerk_Strom.previousState.state" unverändert bleibt.
      Ja, aber dies müsste ja über xxx_Power.state > 0 abgefangen sein und funktioniert ja auch (zumindest scheinbar). Es läuft derzeit ab und an die Entwässerungspumpe und es wird dann nur der Teil abgearbeitet. Aber eben kommt dann alle 10 Sekunden die Eingangsmeldung UND die Meldung ‚Pumpe läuft immer noch‘

      Kommentar


        #4
        Wie oft wir die Regel denn überhaupt aufgerufen?

        Und hat es einen besonderen Grund warum Du nicht für jedes der Items eine eigene Regel definierst?
        In der aktuellen Variante würde der Teil fürs Wasserwerk ggf. mehrfach ausgeführt werden, wenn sich nur die Drainage-Pumpe ändert. U.U. könnte das aktivieren der Drainage sogar unerkannt durchrutschen.

        Wenn Dein Strommess-Aktor das unterstützt, dann würde ich auch dazu tendieren die Aktivierung der Pumpe direkt von diesem erkennen zu lassen. Dann könntest Du Dich in OpenHab auf die Behandlung dieser Status-Wechsel beschränken (beim Einschalten den Warn-Timer starten und beim ausschalten den Timer vorzeitig stoppen).

        Kommentar


          #5
          Zitat von wknx Beitrag anzeigen
          Wie oft wir die Regel denn überhaupt aufgerufen?
          Derzeit läuft die Drainage Pumpe ca. alle 45 Min für ca. 1 Minute an. Das Hauswasserwerk wird ja "nur" überwacht, wenn keiner zu Hause ist und zur Bewässerung des Gartens genutzt wird. Diese reagiert auf Druckabfall, durch das öffnen der Ventile und falls diese dann zu lange läuft, scheint es ein Leck zu geben. Damit dann nicht x m³ einfach sonstwo hingepumpt werden, überwache ich die und kann die dann zur Not remote abschalten.

          Zitat von wknx Beitrag anzeigen
          Und hat es einen besonderen Grund warum Du nicht für jedes der Items eine eigene Regel definierst?
          Ich möchte Regeln - da wo möglich - zusammenfassen und optimiert abarbeiten lassen

          Zitat von wknx Beitrag anzeigen
          In der aktuellen Variante würde der Teil fürs Wasserwerk ggf. mehrfach ausgeführt werden, wenn sich nur die Drainage-Pumpe ändert. U.U. könnte das aktivieren der Drainage sogar unerkannt durchrutschen.
          Dies sollte über die entprechenden if/else if Schleifen abgefangen sein.

          Zitat von wknx Beitrag anzeigen
          Wenn Dein Strommess-Aktor das unterstützt, dann würde ich auch dazu tendieren die Aktivierung der Pumpe direkt von diesem erkennen zu lassen. Dann könntest Du Dich in OpenHab auf die Behandlung dieser Status-Wechsel beschränken (beim Einschalten den Warn-Timer starten und beim ausschalten den Timer vorzeitig stoppen).
          Ich nutze die ABB SA/S 2.16.5S und 16.16.5S.
          Leider habe ich bei diesen beiden keine andere Option gefunden, als über die Stromerkennung.

          Kommentar


            #6
            Zitat von JoergA Beitrag anzeigen
            Ich nutze die ABB SA/S 2.16.5S und 16.16.5S.
            Leider habe ich bei diesen beiden keine andere Option gefunden, als über die Stromerkennung.
            Habe die Applikation aus Neugier mal in die ETS geladen. Sehe dort spontan eine Option "Strom-Schwellwert(e) freigeben", die wohl einen entsprechenden Binärwert senden könnte.


            Zitat von JoergA Beitrag anzeigen
            Ich möchte Regeln - da wo möglich - zusammenfassen und optimiert abarbeiten lassen
            […]
            Dies sollte über die entprechenden if/else if Schleifen abgefangen sein.
            Beispiel-Sequenz:
            1. Wasserwerk_Strom = 0
            2. Drainage_Power = 0
            3. Wasserwerk_Strom = 1000 -> Wasserwerk_Strom.previous = 0
            4. Drainage_Power = 1000 -> Drainage_Power.previous = 0
            Bei Ereignis 3 würde der If-Block ausgeführt (sofern die Nebenbedingungen erfüllt sind), bei Ereignis 4 wenn Nebenbedingungen weiterhin gelten erneut. Nur wenn die Nebenbedingungen zwischenzeitlich nicht mehr gelten sollten wird der else-if Teil greifen. Solltest also lieber zwei unabhängige If-Blöcke verwenden, bzw. dieses Problem Bestände nicht mit separaten Regeln.

            Ansonsten hatte ich die Aussagen zu OpenHAB eher so verstanden, dass die einzelnen Regeln möglichst selten und kurz laufen sollten. Da können andere die die Philosophie von OpenHAB besser verstanden haben als ich aber vielleicht bessere Aussagen treffen?

            Kommentar


              #7
              Zitat von wknx Beitrag anzeigen
              Habe die Applikation aus Neugier mal in die ETS geladen. Sehe dort spontan eine Option "Strom-Schwellwert(e) freigeben", die wohl einen entsprechenden Binärwert senden könnte.
              Ja, diesen habe ich auch gesehen, aber mir hat sich nicht erschlossen, wie ich diesen Wert anders oder gar besser nutzen könnte, da dort die Schwellwerte überschritten werden müssten. Die Kanäle werden eigentlich ja nie geschaltet, sondern dienen ausschließlich der Überwachung der fliessenden Stroms um dann - speziell wenn dies zu lange dauert - Aktionen ausführen zu können. Daher bringt mir der Schwellwert an der Stelle nichts, da ich jede Änderung von 0 benötige

              Zitat von wknx Beitrag anzeigen
              Ansonsten hatte ich die Aussagen zu OpenHAB eher so verstanden, dass die einzelnen Regeln möglichst selten und kurz laufen sollten. Da können andere die die Philosophie von OpenHAB besser verstanden haben als ich aber vielleicht bessere Aussagen treffen?
              Die Regel wird eigentlich sehr schnell durchlaufen, es bleibt lediglich ein "längerer" Threat. Diesr sollte aber auch nicht länger als 30 Sekunden laufen und wenn, dann habe ich ein Problem. Wenn einer der beiden Pumpen anläuft, wird der entsprechende threat und timer gestartet und die rule ist beendet. Bei der nöchsten Änderung wird die natürlich wieder durchlaufen, stellt fest das der Timer läuft und beendet sch (sollte auch schnell gehen). Der letzte Durchlauf ist dann die Änderung nach 0, der Timer läuft in der Regel immer noch und nach Ablauf wird der Threat auch geschlossen. OK, so habe ich einen Verzug van bis zu 9,9999 Sekunden zwischen letztem Durchlauf und beenden der Warnung, aber dies ist für mich vertretbar, bin aber für Optimierungsempfehlungen offen ;-)

              Ich habe nun die Reihenfolge der Meldungen geändert und nun kommt die "Startmeldung" auch nur noch beim Start ;-)

              Code:
              rule WaterSecurity
              when
              Item Wasserwerk_Strom changed or
              Item Drainage_Power changed
              then
              if (Wasserwerk_Strom.previousState.state == (0) && Wasserwerk_Strom.state > 0) {
              if (t_waterscurity === null) {
              pushNotification("Note: ", "Hauswasserwerk zieht Strom")
              t_waterscurity = createTimer(now.plusSeconds(10))[|
              if (Wasserwerk_Strom.state > 0) {
              pushNotification("ALARM: " + now, "Hauswasserwerk zieht immer noch Strom: " + Wasserwerk_Strom.state.toString + " mA")
              t_waterscurity.reschedule(now.plusSeconds(10))
              } else {
              pushNotification("Entwarnung: " + now, "Hauswasserwerk bei " + Wasserwerk_Strom.state.toString + " mA")
              t_waterscurity.cancel
              t_waterscurity = null
              return;
              }
              ]
              }
              } else if (Drainage_Power.previousState.state == (0) && Drainage_Power.state > 0) {
              if (t_drainagescurity === null) {
              pushNotification("Note: " + now, "Entwässerungspumpe zieht Strom")
              logInfo("Water", "Note: Entwässerungspumpe zieht Strom")
              t_drainagescurity = createTimer(now.plusSeconds(10))[|
              if (Drainage_Power.state > 0) {
              logInfo("Water", "ALARM: " + now + " Entwässerungspumpe zieht immer noch Strom: " + Drainage_Power.state.toString + " mA")
              pushNotification("ALARM: " + now, "Entwässerungspumpe zieht immer noch Strom: " + Drainage_Power.state.toString + " mA")
              t_drainagescurity.reschedule(now.plusSeconds(10))
              } else {
              logInfo("Water", "Entwarnung: " + now + " Entwässerungspumpe bei " + Drainage_Power.state.toString + " mA")
              pushNotification("Entwarnung: " + now, "Entwässerungspumpe bei " + Drainage_Power.state.toString + " mA")
              t_drainagescurity.cancel
              t_drainagescurity = null
              return;
              }
              ]
              }
              }
              end
              Dies funktioniert bisher, ich muss jetzt mal sehen, ob ich das forcieren kann, dass beide Pumpen gleichzeitig laufen.

              Parallel versuche ich mal mit einer Gruppe zu arbeiten und dann über Filterung entsprechede Aktionen die obige Regel zu starten

              Code:
              rule PumpMonitor
              when
              Member of gPump received update
              then
              pushNotification("Pump Monitor: " + now, gPump.triggeringItem)
              end
              Zuletzt geändert von JoergA; 12.01.2020, 13:00. Grund: Korrektur der Regel PumpMonitor

              Kommentar


                #8
                Zitat von JoergA Beitrag anzeigen
                Ja, diesen habe ich auch gesehen, aber mir hat sich nicht erschlossen, wie ich diesen Wert anders oder gar besser nutzen könnte, da dort die Schwellwerte überschritten werden müssten. Die Kanäle werden eigentlich ja nie geschaltet, sondern dienen ausschließlich der Überwachung der fliessenden Stroms um dann - speziell wenn dies zu lange dauert - Aktionen ausführen zu können. Daher bringt mir der Schwellwert an der Stelle nichts, da ich jede Änderung von 0 benötige
                Geht denn der Stromwert tatsächlich bis auf 0mA runter und steigt beim Laufen der Pumpe nicht über 100mA (niedrigster Schwellwert) an? (Du hast in Deinen Items übrigens Wh drinstehen...)
                Alternativ könntest Du mit item changed from/to 0 als trigger arbeiten. Dann sollte die Regel auch nur noch beim Ein- und Ausschalten aufgerufen werden.


                Zitat von JoergA Beitrag anzeigen
                Ich habe nun die Reihenfolge der Meldungen geändert und nun kommt die "Startmeldung" auch nur noch beim Start ;-)
                Das spricht dafür, dass die Regel offensichtlich häufiger aufgerufen wird als erwartet. Setzt da dort auch mal ein logInfo rein. Würde aber vor allem auch mal die OpenHab-Logs zu den betroffenen Items durchsuchen.


                Zitat von JoergA Beitrag anzeigen
                Dies funktioniert bisher, ich muss jetzt mal sehen, ob ich das forcieren kann, dass beide Pumpen gleichzeitig laufen.
                Du könntest stattdesen auch einfach mal von Hand die entsprechenden GAs beschreiben ;-)


                Zitat von JoergA Beitrag anzeigen
                Parallel versuche ich mal mit einer Gruppe zu arbeiten und dann über Filterung entsprechede Aktionen die obige Regel zu starten
                Damit lässt vielleicht auch eine mehrfache Implementierung vermeiden wie aktuell. Habe ich bislang allerdings auch noch nicht genutzt.

                Kommentar


                  #9
                  Also, von einer Optimierung kann hier ja wohl nicht die Rede sein

                  Grundsätzlich könnte man bei geschickter Wahl der Itemnamen mit einer Rule für mehrere Pumpen auskommen, indem man Gruppen verwendet. Problematisch wird das, wenn die einzelnen Pumpen unterschiedlich gehandhabt werden müssen (Stichwort GhostMode und myIrrigationSwitchVis - ich hab mir aber nicht im einzelnen angeschaut, was die Rule da so macht).

                  Ob man nun eine Rule mit zig Triggern und riesigem Body schreibt, oder viele kleine Rules mit kleinem Body, bleibt sich gleich.
                  Wichtig ist aber, den Code so zu gestalten, dass nur die Teile ausgeführt werden, die auch ausgeführt werden sollen.
                  Konkret: wenn Du 4 Items hast, auf welche die Rule triggern soll, prüfe mittels des impliziten Objekts triggeringItem nach, welcher Trigger ausgelöst hat und verzweige in den entsprechenden Code.
                  Verwende bei Changed Events die implizite Variable previousState anstatt Item.previousState.state, welches eventuell noch gar nicht auf dem korrekten Stand ist.

                  Noch ein Grundsatz: Wenn man mehrere gleichartige Items hat, bietet es sich an, diese formatiert anzuordnen, gerade in Postings, das erhöht die Übersicht. also statt so
                  Code:
                  Switch Steckd_KG_Links_Pumpe    "Hauswasserwerk"                (KG_Hausanschluss)        {channel="knx:device:bridge:ABB_0_0_10:ch8"}
                  Number Wasserwerk_Strom        "Hauswasserwerk Stromverbrauch [%f Wh]"        (Strom, Electricity_Chart)    {channel="knx:device:bridge:ABB_0_0_10:ch8A"}
                  Switch Steckd_Pumpe        "Entwässerungspumpe"                                {channel="knx:device:bridge:ABB_0_0_15:ch1"}
                  Number Drainage_Power        "Entwässerungspumpe Stromverbrauch [%f Wh]"    (Strom, Electricity_Chart)    {channel="knx:device:bridge:ABB_0_0_15:ch1A"}
                  lieber so
                  Code:
                  Switch Steckd_KG_Links_Pumpe "Hauswasserwerk"     (KG_Hausanschluss) {channel="knx:device:bridge:ABB_0_0_10:ch8"}
                  Switch Steckd_Pumpe          "Entwässerungspumpe"                    {channel="knx:device:bridge:ABB_0_0_15:ch1"}
                  
                  Number Wasserwerk_Strom "Hauswasserwerk Stromverbrauch [%f Wh]"     (Strom, Electricity_Chart) {channel="knx:device:bridge:ABB_0_0_10:ch8A"}
                  Number Drainage_Power   "Entwässerungspumpe Stromverbrauch [%f Wh]" (Strom, Electricity_Chart) {channel="knx:device:bridge:ABB_0_0_15:ch1A"}
                  Ich bezweifle übrigens, dass die Label auf einer Sitemap vollständig angezeigt werden. In der Kürze liegt die Würze
                  Zuletzt geändert von udo1toni; 15.01.2020, 01:03.

                  Kommentar


                    #10
                    Zitat von udo1toni Beitrag anzeigen
                    Also, von einer Optimierung kann hier ja wohl nicht die Rede sein
                    Ja, noch nicht aber erst einmal wollte/musste ich mit dem Grundsatz beginnen um diesen dann (hoffentlich) zu optimieren

                    Zitat von udo1toni Beitrag anzeigen
                    Grundsätzlich könnte man bei geschickter Wahl der Itemnamen mit einer Rule für mehrere Pumpen auskommen, indem man Gruppen verwendet. Problematisch wird das, wenn die einzelnen Pumpen unterschiedlich gehandhabt werden müssen (Stichwort GhostMode und myIrrigationSwitchVis - ich hab mir aber nicht im einzelnen angeschaut, was die Rule da so macht).
                    OK, das Hauswasserwerk wollte ich nur überwachen, wenn keiner zu Hause ist => GhostMode und die automatische Bewässerung nicht aktiv ist. Das sind diese beiden Items

                    Zitat von udo1toni Beitrag anzeigen
                    Konkret: wenn Du 4 Items hast, auf welche die Rule triggern soll, prüfe mittels des impliziten Objekts triggeringItem nach, welcher Trigger ausgelöst hat und verzweige in den entsprechenden Code.
                    Verwende bei Changed Events die implizite Variable previousState anstatt Item.previousState.state, welches eventuell noch gar nicht auf dem korrekten Stand ist.
                    Dies hatte ich bereits versucht, war aber bei triggeringItem nicht weiter gekommen und dachte schon ich hätte dies falsch verwendet. Jedoch habe ich gerade dies gefunden und versuche das nun noch einmal.
                    Code:
                    Limitations
                    
                    As mentioned above, “triggeringItem” does not add group support on its own. In the rule below the “triggeringItem” implicit variable will always be the group SwitchLights.
                    Code:
                    Feature: “Member of” Rule Triggers
                    
                    New rule trigger options have been added that allow rules to operate on items that are members of groups. Group member based events use one or more of the following trigger formats.
                    Ich habe dann mal folgenden Test gemacht.
                    Code:
                    rule CheckItemTrigger
                    when
                          Member of gShutterOG received command
                    then
                         logInfo("TestLog", triggeringItem.name)
                         logInfo("TestLog", previousState.toString)
                    end
                    Die liefert mir zumindest schon mal ein das Item, welches die Gruppe getriggered hat, leider nicht den previousState
                    22:44:13.740 [INFO ] [smarthome.event.ItemCommandEvent ] - Item 'Eltern_Widerkehr_Rollo' received command UP
                    22:44:13.756 [INFO ] [clipse.smarthome.model.script.TestLog] - Eltern_Widerkehr_Rollo
                    22:44:13.756 [ERROR] [untime.internal.engine.RuleEngineImpl] - Rule 'CheckItemTrigger': An error occurred during the script execution: index=0, size=0
                    22:44:14.896 [INFO ] [smarthome.event.ItemCommandEvent ] - Item 'Eltern_Widerkehr_Rollo' received command STOP
                    22:44:14.912 [INFO ] [clipse.smarthome.model.script.TestLog] - Eltern_Widerkehr_Rollo
                    22:44:14.928 [ERROR] [untime.internal.engine.RuleEngineImpl] - Rule 'CheckItemTrigger': An error occurred during the script execution: index=0, size=0
                    22:44:15.365 [INFO ] [smarthome.event.ItemStateChangedEvent] - Eltern_Widerkehr_Rollo changed from 100 to 95
                    22:44:15.381 [INFO ] [home.event.GroupItemStateChangedEvent] - gShutterOG changed from 99.33333300 to 98.50000000 through Eltern_Widerkehr_Rollo
                    Zitat von udo1toni Beitrag anzeigen
                    Noch ein Grundsatz: Wenn man mehrere gleichartige Items hat, bietet es sich an, diese formatiert anzuordnen, gerade in Postings, das erhöht die Übersicht.
                    Valider Punkt, da bin ich leider etwas schlampig und habe die nun angepasst und stimme zu, sieht aufgeräumter aus. Das passiert mir leider häufig, wenn ich neue Items mal eben hinzufüge und mit Tests anfange. Meist mache ich dann im Anschluß die finale Anordnung.

                    Zitat von udo1toni Beitrag anzeigen
                    Ich bezweifle übrigens, dass die Label auf einer Sitemap vollständig angezeigt werden. In der Kürze liegt die Würze
                    Ja, man durfte das Handy in dieser Ansicht bereits quer nehmen, dann passt es noch. Auf dem iPad kein Problem, habe die dennoch eingekürzt und bereits die Namen angepasst.

                    Code:
                    Switch Steckd_PumpWater     "Hauswasserwerk"                           (KG_Hausanschluss)                          {channel="knx:device:bridge:ABB_0_0_20:ch8"}
                    Switch Steckd_PumpDrainage "Entwässerungspumpe"                                                                               {channel="knx:device:bridge:ABB_0_0_105:ch1"}
                    
                    Number PumpWater_Power      "Hauswasserwerk [%f Wh]"          (gPump, Electricity, Electricity_Chart) {channel="knx:device:bridge:ABB_0_0_20:ch8A"}
                    Number PumpDrainage_Power "Entwässerungspumpe [%f Wh]" (gPump, Electricity, Electricity_Chart) {channel="knx:device:bridge:ABB_0_0_105:ch1A"}

                    Kommentar


                      #11
                      TriggeringItem sollte eigentlich immer gesetzt sein, unabhängig davon, ob nun member of oder Item der Trigger ist - schließlich kann man mehrere einzelne Items als Trigger aufführen.

                      Aber das Ziel sollte tatsächlich eher sein, es über Gruppen zu optimieren. Wenn einzelne Items hier unterschiedlich behandelt werden sollen, wäre mein erster Versuch sicher, diese Items außen vor zu lassen und erst mal die gleich zu behandelnden Items zu gruppieren.der erste Schritt ist auf jeden Fall, alle Items, die logisch zusammen gehören (also eine Pumpe betreffen) mit einem identischen Teilnamen zu versehen. Dann braucht es noch einen weiteren Teilnamen, den sich jeweils alle Items mit gleicher Funktion teilen. Nun hat man die Wahl, alle Items in eine gemeinsame Gruppe zu packen, oder alle Items einer Funktion in eine Gruppe zu packen.
                      Die Rule triggert nun auf die eine Gruppe, innerhalb der Rule werden in Abhängigkeit vom triggernden Item die zugehörigen Items herausgesucht und passend manipuliert.
                      Eine Herausforderung können dabei globale Variablen sein (also z.B. Timer), die muss man dann über eine Hashmap bereitstellen. Hab ich glücklicherweise noch nicht gebraucht geht aber auch. Timer mal weggelassen:
                      Code:
                      Group eins
                      Group zwei
                      Switch eins_1 (eins)
                      Switch eins_2 (eins)
                      Number zwei_1 (zwei)
                      Number zwei_2 (zwei)
                      Zwei Schalter, zwei Zähler. Jedesmal, wenn ein Schalter eingeschaltet wird, soll der Zähler des entsprechenden Items um eins erhöht werden:
                      Code:
                      rule "gruppiert bearbeitet"
                      when
                          Member of eins changed
                      then
                          myItem = zwei.members.filter[i | i.name.contains(triggeringItem.name.split("_").get(1))].head
                          if(triggeringItem.state == ON)
                              myItem.postUpdate(if(myItem.state instanceof Number) 1+ (myItem.state as Number) else 1)
                      end
                      Wenn ich nun zwei weitere Schalter und Zähler definiere, müssen sie nur zu den beiden Gruppen gehören, die Rule muss nicht erweitert werden. Der ternäre Operator ist für den Fall eingebaut, dass ein Zähler nochnicht mit einer gültigen Zahl initialisiert ist.

                      Kommentar


                        #12
                        Hallo Udo,
                        besten Dank für Deine Mühe, aber die Switch Item benötige ich ja nicht. Ich nutze den Aktor Kanal ausschließlich zur Stromerkennung und bestenfalls schalte ich den ab, damit mir die Pumpe nicht den Garten oder Keller flutet, bzw. die DrainagePumpe trocken läuft.

                        Ich muss erreichen, dass ich erkenne ob eine der Pumpen Strom zieht und dann entsprechend welche davon. Natürlich schwankt der Strom, ausgehend von 0 und die Pumpe ist entsprechend aus, wenn der entsprechende Stromfluß wieder auf 0 gesunken ist. Die abzuleitende Aktion sollte dann zunächst eine zyklische Meldung sein, alle 10 Sekunden ,sowie eine "Entwarunung" wenn die Pumpe wieder ausgeschaltet ist. Im Moment habe ich einer weitere Zeitschleife eingebaut, welche bei der Entwässerungspumpe nach 2 Minuten Dauerlauf (was untypisch ist) und wenn ich zu Hause bin das Licht im Schalfzimmer einschaltet. Dann kann ich schön - direkt beleuchtet - nach unten trotten und nach der pumpe schauen, warum die so lange läuft. (sollte hoffentlich nicht assieren, aber gestern hat z.B. der Schwimmerschalter gehangen )

                        Folgende Gruppe habe ich erstellt für die entsprechenden Items
                        Code:
                        Group:Number gPump "Pumpen"
                        
                        Number PumpWater_Power      "Hauswasserwerk [%f Wh]"          (gPump, Electricity, Electricity_Chart) {channel="knx:device:bridge:ABB_0_0_20:ch8A"}
                        Number PumpDrainage_Power "Entwässerungspumpe [%f Wh]" (gPump, Electricity, Electricity_Chart) {channel="knx:device:bridge:ABB_0_0_105:ch1A"}
                        Im Log bekomme ich beim starten der Pumpen folgende Meldungen für die beiden Pumpen
                        Code:
                        2020-01-16 23:47:58.003 [vent.ItemStateChangedEvent] - PumpWater_Power changed from 0.0 to 31.900000000000002
                        2020-01-16 23:47:58.050 [GroupItemStateChangedEvent] - gPump changed from 0.0 to UNDEF through PumpWater_Power
                        2020-01-16 23:48:07.108 [vent.ItemStateChangedEvent] - PumpWater_Power changed from 31.900000000000002 to 20.3
                        2020-01-16 23:48:35.038 [vent.ItemStateChangedEvent] - PumpWater_Power changed from 20.3 to 0.0
                        2020-01-16 23:48:35.069 [GroupItemStateChangedEvent] - gPump changed from UNDEF to 0.0 through PumpWater_Power
                        
                        2020-01-16 23:50:40.032 [vent.ItemStateChangedEvent] - PumpDrainage_Power changed from 0.0 to 11.46
                        2020-01-16 23:50:40.063 [GroupItemStateChangedEvent] - gPump changed from 0.0 to UNDEF through PumpDrainage_Power
                        2020-01-16 23:50:42.595 [vent.ItemStateChangedEvent] - PumpDrainage_Power changed from 11.46 to 10.74
                        2020-01-16 23:50:47.910 [vent.ItemStateChangedEvent] - PumpDrainage_Power changed from 10.74 to 10.66
                        2020-01-16 23:50:49.675 [vent.ItemStateChangedEvent] - PumpDrainage_Power changed from 10.66 to 0.0
                        2020-01-16 23:50:49.738 [GroupItemStateChangedEvent] - gPump changed from UNDEF to 0.0 through PumpDrainage_Power
                        Deinen Tipp oben habe ich versucht für mein Vorhaben anzupassen, jedoch läuft es dann wahrscheinlich doch auf verschiedene If else Abfragen heraus, zumindest für die Unterschiede zwischen den Pumpen. Derzeit scheitere ich aber schon an der generellen Zusammenfassung.

                        1) Welche Pumpe hat das die Gruppe ausgelöst
                        2) Wie bekomme ich den Namen des triggernden Items in die Abfrage <= hier würde ich mal über eine lokale Variable (MyItem) gehen und den .state abfragen
                        3) Warum wird die Gruppe UNDEF => Hier muss ich noch einmal in die Gruppendefinition gehen, obwohl, diesen Wert benötige ich ja nicht und der kann ja bei gleichzeitigem Anlauf der Pumpen auch beliebig sein :-/

                        Kommentar


                          #13
                          Mein Code oben war eigentlich nur als Beispiel gemeint.
                          Den Namen des triggernden Items hast Du in triggeringItem,name, den Status in triggeringItem.state. Nehmen wir an, Du hast vier Pumpen:
                          Code:
                          Group:Number gPump "Pumpen"
                          
                          Number PumpWater_Power    "Hauswasserwerk [%f Wh]"     (gPump)
                          Number PumpDrainage_Power "Entwässerungspumpe [%f Wh]" (gPump)
                          Number Pump3_Power        "Pumpe 3 [%f Wh]"            (gPump)
                          Number Pump4_Power        "Pumpe 4 [%f Wh]"            (gPump)
                          Und Du willst jeweils bei Überschreiten eines Schwellwertes eine Meldung ausgeben:
                          Code:
                          rule "pumpe melden"
                          when
                              Member of gPump changed
                          then
                              if(triggeringItem.state > 100 && previousState < 50) {
                                  logInfo("pumpe","Die Pumpe {} läuft.",triggeringItem.name)
                              }
                          end
                          Die Meldung wird nun individuell für alle vier Pumpen generiert. Nehmen wir an, wir speichern den Zustand für jede Pumpe in einem eigenen Item:
                          Code:
                          Group:Switch gPumpOn "Pumpen"
                          
                          Switch PumpWater_Switch    "Hauswasserwerk [%s]"     (gPumpOn)
                          Switch PumpDrainage_Switch "Entwässerungspumpe [%s]" (gPumpOn)
                          SwitchPump3_Switch        "Pumpe 3 [%s]"            (gPumpOn)
                          SwitchPump4_Switch        "Pumpe 4 [%s]"            (gPumpOn)
                          Jetzt kann die Rule den entsprechenden Schalter ein- und Ausschalten:
                          Code:
                          rule "pumpe melden"
                          when
                              Member of gPump changed
                          then
                              val myPump = gPumpOn.members.filter[i|i.name.contains(triggeringItem.name.split("_").get(0))].head
                              if(triggeringItem.state > 100 && myPump.state != ON) {
                                  myPump.postUpdate(ON)
                              } else if(triggeringItem.state < 10 && myPump.state != OFF) {
                                  myPump.postUpdate(OFF)
                              }
                          end
                          Nun hast Du einen Schalter, der anzeigt, ob die Pumpe gerade läuft.
                          Die Schalter könnte man nun persistieren und mit einer weiteren Rule prüfen, ob ein Schalter länger als zwei Minuten eingeschaltet ist.

                          Kommentar


                            #14
                            Zitat von udo1toni Beitrag anzeigen
                            Mein Code oben war eigentlich nur als Beispiel gemeint.
                            Ja, das habe ich mit diesem Beispiel ja "experimentiert" und versucht dies für meine Zwecke zu nutzen.

                            Nun habe ich das neue Beispiel angepasst, aber bei mir gibt es immer einen Fehler mit previousState

                            Mein Testscript
                            Code:
                            rule CheckItemTrigger
                              when
                            Member of gPump changed
                              then
                                logInfo("TestLog", triggeringItem.state)
                                if (triggeringItem.state > 0 && previousState == 0) {
                               logInfo("TestLog", "Die Pumpe {} ist angelaufen.", triggeringItem.name)
                                } else if (triggeringItem.state > 0 && previousState > 0) {
                                logInfo("TestLog", "Die Pumpe {} zieht derzeit {} mA.", triggeringItem.name, triggeringItem.state)
                                } else if (triggeringItem.state == 0 && previousState > 0) {
                                logInfo("TestLog", "Die Pumpe {} hat abgeschaltet.", triggeringItem.name)
                                }
                            end
                            Bei der 0 musste ich 2x "=" setzen, da es sonst eine Fehlermeldung gab.

                            Wenn dann die Pumpe anläuft, erhalte ich folgende Meldungen
                            Code:
                            2020-01-17 16:22:46.369 [INFO ] [eclipse.smarthome.model.script.Water] - PumpWater_Power aktiv!
                            2020-01-17 16:22:49.884 [ERROR] [ntime.internal.engine.RuleEngineImpl] - Rule 'CheckItemTrigger': An error occurred during the script execution: Could not invoke method: org.eclipse.smarthome.model.script.actions.LogActi on.logInfo(java.lang.String,java.lang.String,java. lang.Object[]) on instance: null
                            2020-01-17 16:22:49.884 [INFO ] [eclipse.smarthome.model.script.Water] - PumpWater_Power aktiv!
                            2020-01-17 16:22:49.916 [ERROR] [ntime.internal.engine.RuleEngineImpl] - Rule 'CheckItemTrigger': An error occurred during the script execution: Could not invoke method: org.eclipse.smarthome.model.script.actions.LogActi on.logInfo(java.lang.String,java.lang.String,java. lang.Object[]) on instance: null
                            2020-01-17 16:23:19.181 [INFO ] [eclipse.smarthome.model.script.Water] - PumpWater_Power aktiv!
                            2020-01-17 16:23:19.197 [ERROR] [ntime.internal.engine.RuleEngineImpl] - Rule 'CheckItemTrigger': An error occurred during the script execution: Could not invoke method: org.eclipse.smarthome.model.script.actions.LogActi on.logInfo(java.lang.String,java.lang.String,java. lang.Object[]) on instance: null
                            2020-01-17 16:23:31.994 [INFO ] [eclipse.smarthome.model.script.Water] - PumpWater_Power aktiv!
                            2020-01-17 16:23:32.009 [ERROR] [ntime.internal.engine.RuleEngineImpl] - Rule 'CheckItemTrigger': An error occurred during the script execution: Could not invoke method: org.eclipse.smarthome.model.script.actions.LogActi on.logInfo(java.lang.String,java.lang.String,java. lang.Object[]) on instance: null
                            2020-01-17 16:23:59.571 [INFO ] [eclipse.smarthome.model.script.Water] - PumpDrainage_Power aktiv!
                            2020-01-17 16:23:59.586 [ERROR] [ntime.internal.engine.RuleEngineImpl] - Rule 'CheckItemTrigger': An error occurred during the script execution: Could not invoke method: org.eclipse.smarthome.model.script.actions.LogActi on.logInfo(java.lang.String,java.lang.String,java. lang.Object[]) on instance: null


                            Wenn dies soweit läuft würde ich mich an die Dummy Schalter und Routine sowie schauen, wie ich eine Hashmap für Timer erstelle

                            Kommentar


                              #15
                              Schon die erste Zeile mit logInfo ist so nicht korrekt.
                              Code:
                              logInfo("TestLog", triggeringItem.state)
                              logInfo() erwartet zwei Strings als Argumente, Du sendest aber einen String und einen Status. Korrekt wäre die Zeile so:
                              Code:
                              logInfo("TestLog", triggeringItem.state.toString)
                              Von dieser Zeile stammt auch der Fehler (einfach zu erkennen, da die Meldung nicht ausgegeben wird und der Fehler bei einem logInfo(blabliblub) auftritt) Im Anschluss bricht die Rule natürlich ab.
                              Beim dritten logInfo() könnte es eventuell nötig sein, an das triggeringItem.state noch ein as Number anzuhängen, es kann aber auch ohne funktionieren

                              Gleichheitszeichen:
                              = -> Wertzuweisung, z.B. i = 4
                              == -> Vergleich, z.B. if(i == 4), falls i gleich 4 ist.
                              === -> Prüfung auf identisch, z.B. if(i === null), falls i identisch mit null ist. Diese Prüfung testet, ob der Zeiger, der auf den Inhalt der Variablen verweist, auf die gleiche Speicherzelle verweist, im deutschen ist dies also der Unterschied zwischen "das gleiche" und "das selbe".
                              Beim Vergleich kann man auch auf Ungleichheit prüfen, dann wird das 1. Gleichheitszeichen durch ein NOT ersetzt (das ist ein !), also
                              != -> ungleich
                              !== -> nicht identisch

                              Kommentar

                              Lädt...
                              X