Splitklima verzögert einschalten

Für welche Projekte verwendet Ihr OpenHAB? Was habt Ihr automatisiert? Stellt eure Projekte hier vor.

Moderatoren: Cyrelian, seppy

Scotty.de
Beiträge: 20
Registriert: 2. Sep 2023 20:53
Answers: 0

Splitklima verzögert einschalten

Beitrag von Scotty.de »

Hallo,

ich habe ein Splitklimagerät welches ich in der Heizperiode nur einschalten will wenn mein Photovoltaik-Überschuss größer 3000 ist.
Das funktioniert auch mit dieser Bedingung":
itemName: SF_Power_total
state: "-3000"

in dieser Rule:
AC rule.jpg
Ich möchte aber noch einen Timer oder Verzögerung als Bedingung hinzufügen.
Dieser sollte 60 Sekunden nachdem "itemName: AC_AUTOMATIC_TEST = state: ON" ist schalten
Aber nur wenn "itemName: AC_AUTOMATIC_TEST" nicht zwischenzeitlich auf OFF geht.

Wie mache ich das am besten (Ich nutze OH4)?

Grüße,
Scotty
Du hast keine ausreichende Berechtigung, um die Dateianhänge dieses Beitrags anzusehen.

Benutzeravatar
udo1toni
Beiträge: 13989
Registriert: 11. Apr 2018 18:05
Answers: 222
Wohnort: Darmstadt

Re: Splitklima verzögert einschalten

Beitrag von udo1toni »

Zunächst einmal wäre es besser, keine Screenshots zu posten, wenn es auch Text gibt (in diesem Fall in der Rule Anzeige auf die Code-Ansicht wechseln, den YAML Code kopieren und hier (ganz wichtig) als Code markiert einfügen (Codemarkierung: Im vollständigen Editor </> anklicken, dies fügt die entsprechenden Tags ein. Du kannst Die Tags auch einfach hin schreiben).
Text ist besser lesbar und nimmt viel weniger Platz ein als das Bild. In technischen Foren gilt oftmals das Gegenteil vom Sprichwort "Ein Bild sagt mehr als tausend Worte" - zumindest wenn es eine Codeansicht gibt.

Du kannst das eventuell mit drei simple Rules lösen, ich behaupte aber, dass es nicht sinnvoll ist.
Als DSL Rule sieht das so aus:

Code: Alles auswählen

var Timer tSplitstart = null

rule "Starte Splitgerät falls Überschuss"
when
    Item SF_Power_total changed
then
    if(AC_AUTOMATIC_TEST.state != ON) {
        tSplitstart?.cancel
        tSplitstart = null
        return;
    }
    val nPower = if(SF_Power_total.state instanceof Number) 
                    - (SF_Power_total.state as Number).floatValue
                 else 
                    0
    if(tSplitstart !== null && nPower < 3000) {
        tSplitstart.cancel
        tSplitstart = null
    } else if(tSplitstart === null && nPower > 3000) {
        tSplitstart = createTimer(now.plusSeconds(60),[|
            Daikin_Onecta_AC_DG_Power.sendCommand(ON)
            tSplitstart = null
        ])
    }
end
Die Rule wird getriggert, wenn die Leistung sich ändert. Ja, man könnte noch zusätzlich den Schalter AC_AUTOMATIC_TEST berücksichtigen, aber vermutlich wird die Rule eh alle paar Sekunden durch eine Wertänderung getriggert (falls nicht, dürfte das Ganze recht schnell sinnlos werden)
Die Rule prüft zunächst, ob der Schalter auf ON steht. Ist dies nicht der Fall, so wird ein evtl. zu diesem Zeitpunkt laufender Timer gestoppt und entfernt. Anschließend beendet sich die Rule. (Dies entspricht dem But only if für den Schalter, kümmert sich aber auch um den Timer. In der simple Variante bräuchtest Du dafür eine weitere Rule)
Läuft die Rule noch, so wird die gemessene Leistung aus dem Item ausgelesen und in einer lokalen Konstante gespeichert, und zwar mit negativem Vorzeichen (Letztlich ist es egal, welches Vorzeichen die Zahl hat...) Sollte das Item aus irgendeinem Grund keine gültige Zahl liefern, so wird der Wert auf 0 gesetzt.
Nun folgen zwei Prüfungen. Die erste prüft, ob ein Timer angelegt ist, aber die Leistung unter 3000 liegt. Ist das der Fall, so wird der Timer gestoppt und entfernt (das könnte im simple Mode die zweite Rule mit übernehmen, die sich auch um den Schalter kümmert, quasi das Gegenteil des Timer Starts)
Die zweite Prüfung (die nur erfolgt, falls die erste nicht zutraf) prüft auf die gegenteiligen Bedingungen (Timer ist nicht angelegt, aber Leistung über 3000). Ist das Der Fall, so wird der Timer angelegt.
Damit ist die Rule beendet.

Läuft der Timer nach 60 Sekunden ab, so wird das Aggregat eingeschaltet (die Rule hätte den Timer ja schon entfernt, wenn die Leistung unter 3000 gesunken wäre).

Falls Du nicht mit DSL Rules arbeiten willst, kannst Du ein ähnliches Verhalten auch mit Blockly erzeugen. Falls Du nur keine Textdateien verwenden willst, aber mit DSL als solcher keine Probleme hast, kannst Du den Code teilweise auch über eine UI Rule verwenden, bis auf den Timer.
Die einfachste Variante wäre dann ein Item, welches mit einer Expiration angelegt ist (add Metadata).
Das läuft dann so, dass das Item von der Rule auf OFF oder ON gesetzt wird, je nachdem, ob die Leistung über oder unter 3000 liegt. (über 3000 -> Status ON, unter 3000 -> Status OF)

Wird der Zustand ON des Items in der eingestellten Zeitspanne nicht mehr von der Rule verändert, so sendet das Item über die Expiration einen Befehl OFF, welcher dann eine weitere Rule triggert, die sich um das Aktivieren des Aggregats kümmert.

Das Expiration Item kannst Du auch mit simple Rules verwenden. aber Du brauchst so mindestens drei Rules, die sich um ein Problem kümmern, während es mit Code sehr einfach mit einer Rule zu erledigen ist.

Weiterhin ist es unschön, dass das Item mit einem Befehl OFF den Timer startet, das lässt sich aber kaum vermeiden. Man könnte das Item auch umgekehrt verwenden, dann wäre der Start des Timers ein OFF, was irgendwie auch nicht schick ist.

Disclaimer: Da ich die DSL Rule nicht extra in openHAB angelegt habe, sind wahrscheinlich irgendwo Tippfehler enthalten :)
KEINe Tippfehler sind !== und ===, da gehören tatsächlich drei Zeichen für den Vergleich hin (identisch/nicht identisch, das ist etwas anderes als gleich/ungleich)
openHAB4.1.2 stable in einem Debian-Container (bookworm) (Proxmox 8.1.5, LXC), mit openHABian eingerichtet

Scotty.de
Beiträge: 20
Registriert: 2. Sep 2023 20:53
Answers: 0

Re: Splitklima verzögert einschalten

Beitrag von Scotty.de »

Danke für die ausführliche Beschreibung.
Das wird doch recht komplex (ich kann jetzt schon kaum folgen).
Wir würde das mit Code und einer einzigen Rule funktionieren?

Ich beschreibe besser das komplette Projekt;
Ich habe 3 Geräte die ich nacheinander einschalten möchte. (Den Code für das erste Gerät ohne Verzögerung habe ich jetzt unten eingefügt).

1. item: Daikin_Onecta_AC_DG_Power (soll laufen wenn "itemName: AC_AUTOMATIC_TEST = ON" und der "itemName: SF_Power_total state: "-3000" für 60 Sekunden größer 3000 ist)
2. item: Daikin_Onecta_AC_1OG_Power (soll laufen wenn "1" läuft und "itemName: SF_Power_total state" für 60 Sekunden größer 2000 ist)
3. item: Daikin_Onecta_AC_EG_Power (soll laufen wenn "2" läuft und "itemName: SF_Power_total state" für 60 Sekunden größer 2500 ist)

Code: Alles auswählen

configuration: {}
triggers:
  - id: "1"
    configuration:
      itemName: AC_AUTOMATIC_TEST
      state: ON
    type: core.ItemStateChangeTrigger
  - id: "2"
    configuration:
      itemName: SF_Power_total
    type: core.ItemStateChangeTrigger
conditions:
  - inputs: {}
    id: "3"
    configuration:
      itemName: AC_AUTOMATIC_TEST
      state: ON
      operator: =
    type: core.ItemStateCondition
  - inputs: {}
    id: "4"
    configuration:
      itemName: SF_Power_total
      state: "-3000"
      operator: <
    type: core.ItemStateCondition
actions:
  - inputs: {}
    id: "5"
    configuration:
      command: ON
      itemName: AC_AUTOMATIC_TEST_LED
    type: core.ItemCommandAction
  - inputs: {}
    id: "6"
    configuration:
      itemName: Daikin_Onecta_AC_DG_Power
      command: ON
    type: core.ItemCommandAction

Benutzeravatar
udo1toni
Beiträge: 13989
Registriert: 11. Apr 2018 18:05
Answers: 222
Wohnort: Darmstadt

Re: Splitklima verzögert einschalten

Beitrag von udo1toni »

Ah. Auch das ließe sich gut in einer einzigen Rule abbilden :)

Code: Alles auswählen

// globale Variablen müssen vor der ersten Rule in der Datei definiert werden!
var Timer tSplitstart = null                                        // Zeiger für Timer

// 1. Rule in der Datei...
rule "Starte Splitgerät falls Überschuss"
when
    Item SF_Power_total changed                                     // Leistung geändert
then
    if(AC_AUTOMATIC_TEST.state != ON) {                             // Automatik inaktiv?
        tSplitstart?.cancel                                         // dann Timer abbrechen
        tSplitstart = null                                          // Zeiger löschen
        return;                                                     // und Rule abbrechen
    }
    val nPower = if(SF_Power_total.state instanceof Number)         // falls gültiger Messwert
                    - (SF_Power_total.state as Number).floatValue   // hole Wert
                 else                                               // ansonsten 
                    0                                               // nimm 0

    var nThreshold = 3000                                           // Schwellwert für 1. Aggregat
    if(Daikin_Onecta_AC_DG_Power.state == ON)                       // falls 1. Aggregat läuft
        nThreshold = 2000                                           // Schwellwert für 2. Aggregat
    if(Daikin_Onecta_AC_1OG_Power.state == ON)                      // falls 2. Aggregat läuft
        nThreshold = 2500                                           // Schwellwert für 3. Aggregat

    if(tSplitstart !== null && nPower < nThreshold) {               // Falls Timer aktiv und Schwellwert unterschritten
        tSplitstart.cancel                                          // Timer abbrechen
        tSplitstart = null                                          // Zeiger löschen
    } else if(tSplitstart === null && nPower > nThreshold) {        // falls Timer inaktiv und Schwellwert überschritten
        tSplitstart = createTimer(now.plusSeconds(60), [|           // lege Timer an
            if(Daikin_Onecta_AC_DG_Power.state != ON)               // Falls Aggregat 1 aus
                Daikin_Onecta_AC_DG_Power.sendCommand(ON)           // schalte Aggregat 1 ein
            else if(Daikin_Onecta_AC_1OG_Power.state != ON)         // ansonsten, falls Aggregat 2 aus
                Daikin_Onecta_AC_1OG_Power.sendCommand(ON)          // schalte Aggregat 2 ein
            else if(Daikin_Onecta_AC_EG_Power.state != ON)          // ansonsten, falls Aggregat 3 aus
                Daikin_Onecta_AC_EG_Power.sendCommand(ON)           // schalte Aggregat 3 ein

            tSplitstart = null                                      // lösche Zeiger
        ])
    }
end
Eventuell wird es einfacher, zu verstehen, was die Rule macht, wenn die einzelnen Schritte inline kommentiert sind :)
Die Rule berücksichtigt nicht, dass jemand die Aggregate manuell in anderer Reihenfolge eingeschaltet haben könnte, z.B. 2. Aggregat läuft, aber 1. nicht, dann ist der Schwellwert 2500, nicht 3000, aber es wird trotzdem das 1. Aggregat eingeschaltet, wenn der Timer abläuft.
Solange der Start jedoch nur über die Automatik erledigt wird, sollte das kein Problem darstellen.

Das größere Problem dürfte aber sein, wie Du die Aggregate wieder ausschaltest - vor allem vor dem Hintergrund, was für Schaltzeiten hier überhaupt zulässig sind - Mindestlaufzeiten der Aggregate einhalten, kurzzeitige Einbrüche der Leistung ignorieren usw.
openHAB4.1.2 stable in einem Debian-Container (bookworm) (Proxmox 8.1.5, LXC), mit openHABian eingerichtet

Scotty.de
Beiträge: 20
Registriert: 2. Sep 2023 20:53
Answers: 0

Re: Splitklima verzögert einschalten

Beitrag von Scotty.de »

Habe alles in DSL eingefügt, die Rule läuft aber startet leider keines der Geräte.
AC_AUTOMATIC_TEST ist auf ON
SF_Power_total < -3000 (seit über 1 Stunde ohne Einbrüche)

Für SF_Power_total gilt das der Wert ein negatives Vorzeichen bei Einspeisung hat.
Einschalten für Aggregat #1: SF_Power_total < -3000

Deswegen habe ich im Code folgendes geändert:
nThreshold = 3000 auf nThreshold = -3000
nThreshold = 2000 auf nThreshold = -2000
nThreshold = 2500 auf nThreshold = -2500

und die beiden Vergleichsoperatoren > < vertauscht.
Funktioniert aber immer noch nicht was mache ich falsch?

Code: Alles auswählen

// globale Variablen müssen vor der ersten Rule in der Datei definiert werden!
var Timer tSplitstart = null                                        // Zeiger für Timer

// 1. Rule in der Datei...
rule "Starte Splitgerät falls Überschuss"
when
    Item SF_Power_total changed                                     // Leistung geändert
then
    if(AC_AUTOMATIC_TEST.state != ON) {                             // Automatik inaktiv?
        tSplitstart?.cancel                                         // dann Timer abbrechen
        tSplitstart = null                                          // Zeiger löschen
        return;                                                     // und Rule abbrechen
    }
    val nPower = if(SF_Power_total.state instanceof Number)         // falls gültiger Messwert
                    - (SF_Power_total.state as Number).floatValue   // hole Wert
                 else                                               // ansonsten 
                    0                                               // nimm 0

    var nThreshold = -3000                                           // Schwellwert für 1. Aggregat
    if(Daikin_Onecta_AC_DG_Power.state == ON)                       // falls 1. Aggregat läuft
        nThreshold = -2000                                           // Schwellwert für 2. Aggregat
    if(Daikin_Onecta_AC_1OG_Power.state == ON)                      // falls 2. Aggregat läuft
        nThreshold = -2500                                           // Schwellwert für 3. Aggregat

    if(tSplitstart !== null && nPower > nThreshold) {               // Falls Timer aktiv und Schwellwert unterschritten
        tSplitstart.cancel                                          // Timer abbrechen
        tSplitstart = null                                          // Zeiger löschen
    } else if(tSplitstart === null && nPower < nThreshold) {        // falls Timer inaktiv und Schwellwert überschritten
        tSplitstart = createTimer(now.plusSeconds(60), [|           // lege Timer an
            if(Daikin_Onecta_AC_DG_Power.state != ON)               // Falls Aggregat 1 aus
                Daikin_Onecta_AC_DG_Power.sendCommand(ON)           // schalte Aggregat 1 ein
            else if(Daikin_Onecta_AC_1OG_Power.state != ON)         // ansonsten, falls Aggregat 2 aus
                Daikin_Onecta_AC_1OG_Power.sendCommand(ON)          // schalte Aggregat 2 ein
            else if(Daikin_Onecta_AC_EG_Power.state != ON)          // ansonsten, falls Aggregat 3 aus
                Daikin_Onecta_AC_EG_Power.sendCommand(ON)           // schalte Aggregat 3 ein

            tSplitstart = null                                      // lösche Zeiger
        ])
    }
end

Benutzeravatar
udo1toni
Beiträge: 13989
Registriert: 11. Apr 2018 18:05
Answers: 222
Wohnort: Darmstadt

Re: Splitklima verzögert einschalten

Beitrag von udo1toni »

Scotty.de hat geschrieben: 11. Sep 2023 09:32 Deswegen habe ich im Code folgendes geändert:
Nein, bitte nicht. Ich habe bei dem Wert das Vorzeichen gedreht, die Vergleichswerte sollen also positiv sein und überschritten werden

Das Problem ist hier, wenn der Wert SF_Power_total sich nicht ändert, wird die Rule auch nicht getriggert. Lösung: Ändere changed zu received update

Code: Alles auswählen

... when
    Item SF_Power_total received update                                     // Leistung aktualisiert
then ...
openHAB4.1.2 stable in einem Debian-Container (bookworm) (Proxmox 8.1.5, LXC), mit openHABian eingerichtet

Scotty.de
Beiträge: 20
Registriert: 2. Sep 2023 20:53
Answers: 0

Re: Splitklima verzögert einschalten

Beitrag von Scotty.de »

SF_Power_total ändert sich aber alle paar Sekunden (je nach Sonneneinstrahlung).

Benutzeravatar
udo1toni
Beiträge: 13989
Registriert: 11. Apr 2018 18:05
Answers: 222
Wohnort: Darmstadt

Re: Splitklima verzögert einschalten

Beitrag von udo1toni »

Gut. Dann frage ich mal: WO hast Du die Rule eingefügt?
Der Code muss in einer Datei stehen, die mit der Endung .rules benannt ist und im Ordner $OPENHAB_CONF/rules/ liegt.
Die Rule wird dann in der UI als nur lesbar angezeigt.
openHAB4.1.2 stable in einem Debian-Container (bookworm) (Proxmox 8.1.5, LXC), mit openHABian eingerichtet

Scotty.de
Beiträge: 20
Registriert: 2. Sep 2023 20:53
Answers: 0

Re: Splitklima verzögert einschalten

Beitrag von Scotty.de »

Unter Scripts -> auf "+" und dann weiter mit "Scripting Method Rule DSL"

Scotty.de
Beiträge: 20
Registriert: 2. Sep 2023 20:53
Answers: 0

Re: Splitklima verzögert einschalten

Beitrag von Scotty.de »

Danke, nachdem ich die Datei erstellt habe scheint es zu laufen. Werde das jetzt noch ausführlich testen.

Antworten