Rule Astro Binding, now > DuskStart_Time

Einrichtung der openHAB Umgebung und allgemeine Konfigurationsthemen.

Moderatoren: seppy, udo1toni

EmptySoft
Beiträge: 247
Registriert: 7. Jan 2020 14:45
Answers: 2
Kontaktdaten:

Rule Astro Binding, now > DuskStart_Time

Beitrag von EmptySoft »

Hi.!

Ich bin wieder einmal zu deppert um die Rule richtig zu schreiben...
Mein Server läuft auf UTC und ich möchte in der Rule wissen, ob es jetzt später als DuskStart_Time ist

Code: Alles auswählen

rule "RollosPosSoll"
 when
  Time cron "5 * * * * ?"
 then
  val fName="Rollos.rules,RollosPosSoll"
  logInfo(fName,"-started")
  logInfo(fName,"   Abend? now(vienna) {} > DuskStart_Time: {}",now(ZoneId.of("Europe/Vienna")),(DuskStart_Time.state as DateTimeType).getZonedDateTime())
  if(now(ZoneId.of("Europe/Vienna")) > (DuskStart_Time.state as DateTimeType).getZonedDateTime())
    {
    logInfo(fName,"    Abend -> pos=0")
    }

  logInfo(fName,"-ended")
end

und das kommt im Logging

Code: Alles auswählen

2025-01-06 15:58:05.602 [INFO ] [script.Rollos.rules,RollosPosSoll] - -started
2025-01-06 15:58:05.604 [INFO ] [script.Rollos.rules,RollosPosSoll] -    Abend? now(vienna) 2025-01-06T16:58:05.604219890+01:00[Europe/Vienna] > DuskStart_Time: 2025-01-06T16:39Z
2025-01-06 15:58:05.604 [INFO ] [script.Rollos.rules,RollosPosSoll] -     noch nicht Abend
2025-01-06 15:58:05.607 [INFO ] [script.Rollos.rules,RollosPosSoll] - -ended
wie schreibe ich die Rule richtig? Danke im voraus für Eure Hilfe.
BYe
Harald

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

Re: Rule Astro Binding, now > DuskStart_Time

Beitrag von udo1toni »

Frage 1: welche exakte Version von openHAB nutzt Du?
Frage 2: Warum überhaupt UTC?
Frage 3: Und wenn schon UTC, warum dann nicht überall?

Die Zeitzone kannst Du sowohl im OS als auch in den Regional Settings von openHAB einstellen, beides sollte immer identisch gesetzt sein.
Weiterhin kannst Du z.B. im NTP Binding ebenfalls eine Zeitzone setzen.
Wenn Du Zeitstempel vergleichst, solltest Du immer darauf achten, dass die Zeitstempel für die gleiche Zeitzone ausgewertet werden.
Außerdem ist > bei Zeit so eine Sache. Besser wäre vermutlich zeitstempel1.isAfter(zeitstempel2).
Weiterhin muss man (abhängig von der eingesetzten Version von openHAB) mit den Datentypen aufpassen. Eine detaillierte Erklärung hierzu liefert https://github.com/openhab/openhab-core/pull/3583, was darauf hinausläuft, dass Du .getZonedDateTime() immer mit einer konkreten Zeitzone aufrufen solltest.
openHAB4.3.3 stable in einem Debian-Container (bookworm) (Proxmox 8.3.5, LXC), mit openHABian eingerichtet

EmptySoft
Beiträge: 247
Registriert: 7. Jan 2020 14:45
Answers: 2
Kontaktdaten:

Re: Rule Astro Binding, now > DuskStart_Time

Beitrag von EmptySoft »

1: Ich verwende openHAB 4.2.2 im Docker
2: UTC am Server benötige ich wegen anderen Programmen
3: Zeitzone in OpenHAB steht auf GMT ETC/Universal, sonst fehlen in den Grafiken die Stunden der Zeitverschiebung

Was bringt mir das NTP Binding? Mein Server hat eine synchronisierte Zeit?

zeitstempel1.isAfter(zeitstempel2) habe ich probiert, scheitere an den Typen

Code: Alles auswählen

logInfo(fName,"   DuskStart_Time: {} now: {}",DuskStart_Time.state.isAfter(now))

Code: Alles auswählen

2025-01-07 05:19:06.716 [ERROR] [internal.handler.ScriptActionHandler] - Script execution of rule with UID 'Rollos-1' failed: 'isAfter' is not a member of 'org.openhab.core.types.State'
githublink sehe ich mir an, Danke
BYe
Harald

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

Re: Rule Astro Binding, now > DuskStart_Time

Beitrag von udo1toni »

Na, Du musst schon den Datentyp vorher auf DateTimeType casten (kann auch sein, dass es eine Instant sein muss, bin grad zu faul, es auszuprobieren):

Code: Alles auswählen

logInfo(fName,"   DuskStart erreicht: {} ",(DuskStart_Time.state as DateTimeType).isAfter(now))
Und so ist es natürlich risikobehaftet ;) weil ja nicht sichergestellt ist, dass der Status sich tatsächlich in DateTimeType umwandeln lässt. Sauber also eher so:

Code: Alles auswählen

if(DuskStart_Time.state instanceof DateTimeType)
    logInfo("calcDusk","DuskStart erreicht: {}",(DuskStart_Time.state as DateTimeType).isAfter(now))
else
    logWarn("calcDusk","DuskStart enthält keinen gültigen Zeitstempel!")
Vermutlich sind weitere angehängte Parameter nicht mehr optional, wenn Du Substitution nutzt (die {} im 2. String). der erste String im log-Befehl ist der letzte Teil des Loggernamens und sollte sich an die Namenskonventionen halten. Alle Loggernamen bezüglich Rules beginnen mit "org.openhab.core.model.script.", und dies ist auch exklusiv, d.h. dieser Namensteil wird nur für Rules auftauchen. Man kann natürlich nicht direkt danach suchen, weil ein Teil dieser Zeichenkette evtl. abgeschnitten wird, aber mindestens die Endung des Dateinamens .rules ist damit unnötig. Bitte möglichst keine Sonderzeichen oder Umlaute verwenden (nur [A-Z],[a-z],[0-9],[._]), auch wenn das funktioniert.
openHAB4.3.3 stable in einem Debian-Container (bookworm) (Proxmox 8.3.5, LXC), mit openHABian eingerichtet

EmptySoft
Beiträge: 247
Registriert: 7. Jan 2020 14:45
Answers: 2
Kontaktdaten:

Re: Rule Astro Binding, now > DuskStart_Time

Beitrag von EmptySoft »

Hi udo1toni.!

Vielen Dank für Deine Hilfe und Geduld. Ich haben Deinen Code in eine neue Rule zum testen kopiert

Code: Alles auswählen

rule "RollosTest"
 when
  Time cron "5/10 * * * * ?"
 then
  val fName="Rollos.rules,RollosTest"
  logInfo(fName,"-started")

  if(DuskStart_Time.state instanceof DateTimeType)
   {
   logInfo(fName," DuskStart is instanceof DateTimeType")

   logInfo(fName,"DuskStart erreicht: {}",(DuskStart_Time.state as DateTimeType).isAfter(now))
   }
  else
   logWarn(fName,"DuskStart enthält keinen gültigen Zeitstempel!")

  logInfo(fName,"-ended")
 end

die ersten Zeilen sind OK

Code: Alles auswählen

2025-01-07 07:18:45.048 [INFO ] [model.script.Rollos.rules,RollosTest] - -started
2025-01-07 07:18:45.048 [INFO ] [model.script.Rollos.rules,RollosTest] -  DuskStart is instanceof DateTimeType
leider bringt

Code: Alles auswählen

(DuskStart_Time.state as DateTimeType).isAfter(now)
noch immer den Fehler

Code: Alles auswählen

2025-01-07 07:21:15.049 [ERROR] [internal.handler.ScriptActionHandler] - Script execution of rule with UID 'Rollos-1' failed: 'isAfter' is not a member of 'org.openhab.core.library.types.DateTimeType'; line 14, column 43, length 51 in Rollos
das Item ist so konfiguriert

Code: Alles auswählen

DateTime                DuskStart_Time          "Astronomische Abenddämmerung start [%1$tH:%1$tM]"      <moon>          { channel="astro:sun:home:astroDusk#start" }
BYe
Harald

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

Re: Rule Astro Binding, now > DuskStart_Time

Beitrag von udo1toni »

Ja, wie immer bei DateTime ist das mit den Datentypen eher komplex. Nachdem ich es ausprobiert habe...:

isAfter() (genau wie isBefore() oder gar isEqual()) ist Teil des Datentyps ZonedDateTime.
Deshalb muss der Code so aussehen:

Code: Alles auswählen

if(DuskStart_Time.state instanceof DateTimeType) {
    val zdtStamp = DuskStart_Time.state as DateTimeType).getZonedDateTime(ZoneId.systemDefault)
    logInfo("calcDusk","DuskStart erreicht: {}",(zdtStamp.isAfter(now))
    }
else
    logWarn("calcDusk","DuskStart enthält keinen gültigen Zeitstempel!")
Und als Ausgabe kommt dann true oder false, Du kannst also direkt mit if(zdtOne.isAfter(zdtTwo)) arbeiten.

getZonedDateTime() ohne Angabe einer Zeitzone ist deprecated (funktioniert aber noch in OH4.3.1). ZoneId.systemDefault sollte in Deinem Fall UTC entsprechen, bzw. ist eben die Zeitzone, die im System (oder hier vermutlich in der Java Umgebung) vorgegeben ist.

Diese Frage hatte ich noch nicht beantwortet:
EmptySoft hat geschrieben: 7. Jan 2025 06:22 Was bringt mir das NTP Binding? Mein Server hat eine synchronisierte Zeit?
Das NTP Binding bringt Dir die Zeit auf den Bus. Dabei kannst Du beliebig viele Things anlegen, es wäre so z.B. kein Problem, eine Weltzeituhr zu bauen, jeder Ort bekommt ein Item. Da die Zeitzone hier für jedes Thing getrennt gesetzt wird, ist die angegebene Uhrzeit stets korrekt, egal an welchem Tag, egal an welchem Ort.
Ich nutze das, um die Buszeit von knx zu synchronisieren.
openHAB4.3.3 stable in einem Debian-Container (bookworm) (Proxmox 8.3.5, LXC), mit openHABian eingerichtet

EmptySoft
Beiträge: 247
Registriert: 7. Jan 2020 14:45
Answers: 2
Kontaktdaten:

Re: Rule Astro Binding, now > DuskStart_Time

Beitrag von EmptySoft »

Hi udo1toni.!
udo1toni hat geschrieben: 7. Jan 2025 20:05 Ja, wie immer bei DateTime ist das mit den Datentypen eher komplex. Nachdem ich es ausprobiert habe...:
Ja, Java (somit auch OpenHAB) bringt mich mit seinen Typen regelmässsig zum verzweifeln. Vielen Dank, dass Du mir immer wieder hilfst
udo1toni hat geschrieben: 7. Jan 2025 20:05 isAfter() (genau wie isBefore() oder gar isEqual()) ist Teil des Datentyps ZonedDateTime.
Deshalb muss der Code so aussehen:

Code: Alles auswählen

if(DuskStart_Time.state instanceof DateTimeType) {
    val zdtStamp = (DuskStart_Time.state as DateTimeType).getZonedDateTime(ZoneId.systemDefault)
    logInfo("calcDusk","DuskStart erreicht: {}",(zdtStamp.isAfter(now))
    }
else
    logWarn("calcDusk","DuskStart enthält keinen gültigen Zeitstempel!")
Und als Ausgabe kommt dann true oder false, Du kannst also direkt mit if(zdtOne.isAfter(zdtTwo)) arbeiten.

getZonedDateTime() ohne Angabe einer Zeitzone ist deprecated (funktioniert aber noch in OH4.3.1). ZoneId.systemDefault sollte in Deinem Fall UTC entsprechen, bzw. ist eben die Zeitzone, die im System (oder hier vermutlich in der Java Umgebung) vorgegeben ist.
Der Code lauft jetzt einmal ohne Fehler. Am Abend werde ich dann sehen, wann die Rollos zufahren :D

Vielen Dank, Harald
BYe
Harald

EmptySoft
Beiträge: 247
Registriert: 7. Jan 2020 14:45
Answers: 2
Kontaktdaten:

Re: Rule Astro Binding, now > DuskStart_Time

Beitrag von EmptySoft »

Leider funktioniert die Rule noch nicht, weil now immer als isAfter erlannt wird ..

hier die ganze Rule

Code: Alles auswählen

rule "RollosTest"
 when
  Time cron "5/10 * * * * ?"
 then
  val fName="Rollos.rules,RollosTest"
  logInfo(fName,"-started")

  logInfo(fName," now: {}",now)
  logInfo(fName," DuskStart_Time: {}",DuskStart_Time.state)

  val zdtDuskStart_Time = (DuskStart_Time.state as DateTimeType).getZonedDateTime(ZoneId.systemDefault)
  logInfo(fName," zdtDuskStart_Time: {}",zdtDuskStart_Time)

  if(DuskStart_Time.state instanceof DateTimeType)
   {
   logInfo(fName," DuskStart is instanceof DateTimeType")
   if(zdtDuskStart_Time.isAfter(now))
    logInfo(fName,"  isAfter: danach")
   else
    logInfo(fName,"  isAfter: zuvor")

   if(zdtDuskStart_Time > now)
    logInfo(fName,"  >: danach")
   else
    logInfo(fName,"  >: zuvor")
   }
  else
   logWarn(fName,"DuskStart enthält keinen gültigen Zeitstempel!")

  logInfo(fName,"-ended")
 end

und hier der output

Code: Alles auswählen

2025-01-08 04:38:35.499 [INFO ] [model.script.Rollos.rules,RollosTest] - -started
2025-01-08 04:38:35.499 [INFO ] [model.script.Rollos.rules,RollosTest] -  now: 2025-01-08T04:38:35.499548167Z[GMT]
2025-01-08 04:38:35.499 [INFO ] [model.script.Rollos.rules,RollosTest] -  DuskStart_Time: 2025-01-08T16:41:00.000+0000
2025-01-08 04:38:35.499 [INFO ] [model.script.Rollos.rules,RollosTest] -  zdtDuskStart_Time: 2025-01-08T16:41Z
2025-01-08 04:38:35.499 [INFO ] [model.script.Rollos.rules,RollosTest] -  DuskStart is instanceof DateTimeType
2025-01-08 04:38:35.499 [INFO ] [model.script.Rollos.rules,RollosTest] -   isAfter: danach
2025-01-08 04:38:35.499 [INFO ] [model.script.Rollos.rules,RollosTest] -   >: danach
2025-01-08 04:38:35.500 [INFO ] [model.script.Rollos.rules,RollosTest] - -ended
BYe
Harald

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

Re: Rule Astro Binding, now > DuskStart_Time

Beitrag von udo1toni »

Das ist seltsam, bei mir funktioniert das so korrekt.
Eine andere Frage: Warum machst Du das überhaupt über die Zeit? Der direkte Weg wäre über den Trigger Channel.
openHAB4.3.3 stable in einem Debian-Container (bookworm) (Proxmox 8.3.5, LXC), mit openHABian eingerichtet

EmptySoft
Beiträge: 247
Registriert: 7. Jan 2020 14:45
Answers: 2
Kontaktdaten:

Re: Rule Astro Binding, now > DuskStart_Time

Beitrag von EmptySoft »

udo1toni hat geschrieben: 8. Jan 2025 06:34 Das ist seltsam, bei mir funktioniert das so korrekt.
Eine andere Frage: Warum machst Du das überhaupt über die Zeit? Der direkte Weg wäre über den Trigger Channel.
OK, ich bin es eh gewohnt, daß bei mir die Sachen anders sind :shock:

Die Rule macht noch viele andere Sachen (Beschatten, Fenster vor Regen schützen) und das soll sie in vielen Abhängigkeiten machen (soll ja nicht die Langschläfer aufwecken, ich hätte es aber gerne hell)

Bin auf Plan B umgestiegen und verwende ein LuxMeter statt dem AstroBinding. Danke noch einmal für Deine Hilfe
BYe
Harald

Antworten