Summer time / Zeitzonen mit InfluxDB

Weg ist sie, die eine Stunde, aber wir bekommen sie ja wieder am Ende der Sommerzeit:

2018/03/25 00:09:04,   8.108,  4.9, 50.1, 4.30
2018/03/25 01:06:31,   8.108,  4.5, 53.8, 4.31
2018/03/25 03:03:53,   8.111,  4.2, 59.9, 4.30
2018/03/25 04:01:07,   8.106,  3.2, 76.2, 4.17

Bei der Umstellung im Frühjahr ist die Geschichte noch recht einfach, da “fehlen” einfach Werte. Beim zurückstellen im Herbst haben wir aber eine Stunde “doppelte Werte”.

Meine Nodes laufen großteils alle auf Sommerzeit, da die RTC den timestamp mitliefert. Eine automatische Umstellung ist theoretisch auch möglich. Die Arduino-Lib dafür braucht aber komischerweise viel Speicher.

Mögliche Lösungen wären:

  • timestamping immer auf dem Server
  • eine Bibliothek passt auf dem node Sommer-/Winterzeit an
  • der node läuft immer auf einer Zeit (Sommer/Winter) oder gar UTC, für alle Zeitzonen - das macht es aber wieder beim debuggen schwierig, daher dann doch CET

.

2 Likes

In jedem Fall ist’s so, daß influxdb seinen eigenen Zeitstempel in UTC beim Speichern der message vergibt. @Andreas, wie war das: - außer, es kommt in der Nachricht explizit ein ts mit, dann wird dieser ‘bevorzugt’ ? (letzteres wäre mal wieder zu überprüfen, ich weiß gerade nicht, ob das noch jemand hier macht und ob es aktuell funktioniert). Insofern also Entwarnung, es klappt in jedem Fall: es geht mindestens durch daylight saving time-Mist nichts extra verloren.

Nein, wir haben zwei Stunden lang ‘einfache Werte’ - insofern fehlen auch keine im Frühjahr, da es influxdb als time series database egal ist, wie wir die Marken am Zeitstrahl benennen
(hier exemplarisch @mois Beute am 29.10.17) :

Und hier das ganze, wenn man dieses dashboard auf UTC umstellt (was grafana oben rechts im Zeitbereich auch vermerkt) :

In den time options bei Grafana (pro dashboard und organization) lassen sich bislang nur default , local browser time und UTC auswählen, das ist nicht viel - aber mit UTC und browser time ist alles dabei, was man braucht. Ganz generell kennst Du meine Meinung: die Datenbank selbst schreibt mit UTC timestamps, und die lokale Zeitzone (und damit auch DST-Aspekte) wird erst bei der Anzeige/Ausgabe hereingebracht - ganz so, wie es jetzt schon ist! :)

Man kann zwar im query eine tz übergeben und merkt, wenn man sich dabei verschreibt, daß das geparsed und als tz erkannt wird - aber es bleibt ohne Wirkung:

SELECT ... WHERE $timeFilter GROUP BY time($__interval) tz('Europe/Berlin')

Insgesamt wünschen sich viele die komplette Einbindung der Zeitzonen in Grafana, da sind sie für ElasticSearch als backend etwas weiter, man findet etliche feature requests dazu, den hier z.B.. Mit UTC kann ich gut leben: die db speichert ohnehin ‘nur’ in UTC, und bei der Anzeige ist die lokale Zeit eine Modalität der client-Seite ;) , durch EInstellung auf meine local time des browsers die ‘richtige Zeit’ im Grafana anzuzeigen.

Und wenn Du mit Grafana (nicht Export per kotori-API ) unter ‘more’ im Titel eines Panel einen csv-dump machst, dann wird auch in jedem Fall die Zeitzone als offset zu UTC angegeben (das ist beim export das Z des time format am Ende) :

2018-03-25T01:59:50+01:00;
2018-03-25T03:00:00+02:00;

und im Herbst entsprechend

2017-10-29T02:59:55+02:00;
2017-10-29T02:00:00+01:00;

Da passen dann auch Zeitzonen mit Teilen von ganzen Stunden, sowas wie z.B. Kabul mit UTC+04:30 …

Für das backend und Visualisierung bin ich zufrieden mit dem Zeitzonen-betreffenden Zustand, ein einzelner node ohne RTC ist damit hinreichend versorgt. Die RTC muß nicht präzise wie eine DS3231 sein, wenn sie nur zum Aufwecken des Prozessors zu dienen braucht und die Daten nach Erhebung gleich verschickt werden (können). In anderen Fällen (keine Verbindung/kein upload möglich … oder auch ein lokales gateway für kleine nodes ohne WWAN), bei denen kein zeitlich vertretbarer Abstand zwischen Erheben und Versenden möglich ist, muß mit lokalem Zeitstempel am gate oder node gespeichert werden … anderes Thema ;)

Achja, und die in Deinem Browser eingestellten Sprachen entscheiden darüber, wann im panel die Woche losgeht bei Zeiträumen z.B. von “this week so far” , siehe bei uns: Grafana: Woche von Montag bis Sonntag?

3 Likes

Nachtrag: Verwendung von tz() in influxdb

The Time Zone Clause

The tz() clause returns the UTC offset for the specified timezone.

Syntax

SELECT_clause [INTO_clause] FROM_clause [WHERE_clause] [GROUP_BY_clause] [ORDER_BY_clause] [LIMIT_clause] [OFFSET_clause] [SLIMIT_clause] [SOFFSET_clause] tz('<time_zone>')

Description of Syntax

By default, InfluxDB stores and returns timestamps in UTC. The tz() clause includes the UTC offset or, if applicable, the UTC Daylight Savings Time (DST) offset to the query’s returned timestamps. The returned timestamps must be in RFC3339 format for the UTC offset or UTC DST to appear. The time_zone parameter follows the TZ syntax in the Internet Assigned Numbers Authority time zone database and it requires single quotes.
Examples

Example 1: Return the UTC offset for Chicago’s time zone

SELECT "water_level" FROM "h2o_feet" WHERE "location" = 'santa_monica' AND time >= '2015-08-18T00:00:00Z' AND time <= '2015-08-18T00:18:00Z' tz('America/Chicago')
time                       water_level
----                       -----------
2015-08-17T19:00:00-05:00  2.064
2015-08-17T19:06:00-05:00  2.116
2015-08-17T19:12:00-05:00  2.028
2015-08-17T19:18:00-05:00  2.126

The query results include the UTC offset (-05:00) for the America/Chicago time zone in the timestamps.

(aus: Data exploration using InfluxQL | InfluxData Documentation)

1 Like

Hmm… tatsächlich: wie schaffst Du das?! 8)

Deine firmware erzeugt aber auch das Gegenteil: ich habe mir mal einige OpenHive-Meßwerte verschiedener Stationen von heute nacht angesehen:

hiveeyes-open-hive-test01-comparison-load-cells (Anzeige in UTC; doppelte Werte, in der Stunde danach keine Werte):

gleicher Zeitbereich bei @peterthiemer (CEST; fehlende Werte bei eigenen Mesungen; DWD-Werte werden hingegen richtig einsortiert):

Sieht aus wie ein klares Plädoyer für timestamping auf dem server, wenn die nodes kein sinnvolles daylight saving time - management haben. Vielleicht müssen wir uns damit ja auchnicht mehr soo häufig beschäftigen… ;)

test01/node001 ist ein WiFi-node und schickt keinen Timestamp mit den Daten, timestamp wird vom Server gemacht. Der von Peter ist ein GSM-node und schickt mit den Daten ein Timestamp der Timestamp ist immer Sommer oder Winterzeit und es wird nur die Zeit ohne ein Offset mitgeschickt oder eine spezielle Angabe von Zeitzonen. Was @Andreas’ Weiterleitungs-PHP-Skript mit der Zeit macht weiß ich gerade nicht.

Das sind meine Daten, die ankommen:

2018/10/28 01:24:51,  49.491,  6.8, 62.7,  6.5, 4.39
2018/10/28 01:44:08,  49.491,  6.8, 62.7,  6.6, 4.38
2018/10/28 02:03:25,  49.490,  6.7, 63.6,  6.6, 4.38
2018/10/28 02:22:32,  49.492,  6.7, 63.8,  6.4, 4.38
2018/10/28 02:41:51,  49.490,  6.6, 64.3,  6.2, 4.39
2018/10/28 02:01:08,  49.490,  6.5, 64.7,  6.2, 4.38
2018/10/28 02:20:24,  49.493,  6.4, 65.3,  6.1, 4.38
2018/10/28 02:39:39,  49.490,  6.4, 66.0,  6.2, 4.38
2018/10/28 02:58:58,  49.493,  6.4, 66.4,  6.1, 4.36
2018/10/28 03:18:15,  49.493,  6.4, 66.9,  6.1, 4.38

Ich denke wenn da noch CEST oder eben CET stehen würde könnte es – in Grafana – auch passen und die würden richtig ingested. Mein PHP-Skript müsste ich dann aber anpassen oder die jetzt laufenden nodes updaten … aber vielleicht hat sich das Problem tatächlich bald erledigt! ;-) 17:30 h und dunkel wie in der Nacht! Ich mag keine Winterzeit!

Hallo in die Runde,

vielen Dank für Eure Nachforschungen!

Es ist derzeit genau so implementiert, wie @weef es beschreibt:

Im Detail finden dabei ein paar heuristische Regeln Anwendung.

Datenerfassung

  • Wenn ein Datenfeld namens "time", "datetime" oder "dateTime" übermittelt wird, wird dieser Zeitstempel bevorzugt - richtig. Entsprechende Stellen im Code sind unter extract timestamp field from ingress data sowie process timestamp from ingress data zu finden.
  • Bei Daten, die über HTTP reinkommen, werden zusätzlich die Feldnamen "Date/Time", "Date", "Datum/Zeit" sowie "timestamp" honoriert, siehe http.py#L351.
  • Um Daten im Beelogger CSV Format verarbeiten zu können, darf der Zeitstempel auch in zwei diskreten Feldern "Datum,Uhrzeit" übertragen werden, hier wird dann automatisch UTC angenommen, siehe http.py#L337.
  • Die Verarbeitung des Zeitstempels erfolgt schlussendlich in der Routine parse_timestamp, deren Regeln im folgenden Abschnitt beschrieben werden.

Zeitzone und Normalzeit vs. Sommerzeit

Das Handling der Zeitzone erfolgt ebenfalls heuristisch.

  • Falls im Timestamp Feld eine der Zeichenketten Z, +, CET oder CEST zu finden ist, wird von einem qualifizierten Zeitstempel ausgegangen, ansonsten wird per default CET angenommen, also mitteleuropäische Sommerzeit.
  • Per "Z" lassen sich also wie gewohnt Zeitstempel in UTC qualifizieren, per "+" beliebige Offsets ggü. UTC und als Komfortvariante wird für unsere Regionen "CET" sowie "CEST" verstanden.

Änderungswünsche

Wir können an dieser Stelle gerne weitergehende, aber auch grundlegende Änderungswünsche berücksichtigen.

Beispielsweise wurde die Regel unqualified == CET vor allem deshalb implementiert, weil Meßknoten, die einen Zeitstempel mitsenden, meist während der Sommerzeit in Betrieb genommen werden, deshalb war diese Heuristik am nähesten an der Realität dran. Technisch wäre ein default von UTC aber vermutlich sinnvoller und universeller.

Viele Grüße,
Andreas.

Die Umsetzung von der Open Hive Apiary Software auf das Hiveeyes Backend (terkin-http.php, hiveeyes.php) unternimmt nichts mit den Zeitstempeln, allerdings schicken die Meßknoten mit der Open Hive Firmware laut datasetHeader[] Definition in node-gprs-http.ino ein CSV Feld namens "Datum/Zeit" mit, nicht?

Genau, aber unqualified

D.h. es wird auch zur Normalzeit Sommerzeit angenommen. Stimmt ja auch, da die Meßknoten vermutlich keine Zeitumstellung vornehmen, richtig? Also natürlich nur dann, wenn sie im Sommer mit der jeweiligen bei uns gültigen Lokalzeit in Betrieb genommen wurden, wovon ich damals ausging und laut den Daten auch plausibel erschien.

Oh, der Code implementiert natürlich genau das Gegenteil. Bei unqualified Zeitstempeln wird CET angenommen, also die Normalzeit, die im Winter gültig ist. Es sollte an dieser Stelle innerhalb meiner Argumentation wohl eher CEST sein. Sollen wir das einstweilen ändern, bis alle Knoten qualifizierte Zeitstempel mitsenden?

Irgendwas passt nicht, die Theorie oder die Daten? Das wird bei mir z.B. geschickt:

2018/10/24 10:46:05,   8.268, 10.1, 81.8, 3.74
2018/10/24 11:06:05,   8.272, 10.5, 70.0, 3.74  <==
2018/10/24 11:26:05,   8.277, 11.0, 56.4, 3.79

und in Grafana wird das auch in der Sommerzeit richtig zugeordne:

2018-10-28%2020_21_16-Greenshot

Das ist ein GSM-Node, der timestamps (unqualifiziert) mitschickt.

Hier ein paar Beispiele aus dem Livebetrieb der Open Hive Meßknoten, wie sie seit ca. 20:15 Uhr in dieser Reihenfolge reinkamen:

hiveeyes/open-hive-test01/default/2/data.json    {"time": "2018/10/28 20:19:09", "Gewicht": 49.471, "Aussen-Temperatur": 7.5, "Aussen-Feuchtigkeit": 70.2, "Brut-Temperatur": 7.5, "Spannung": 4.38}
hiveeyes/open-hive-test01/default/5/data.json    {"time": "2018/10/28 20:20:56", "Weight": 34.81, "Outside Temp": 6.8, "Voltage": 4.39}
hiveeyes/open-hive-kay/default/2/data.json       {"time": "2018/10/28 21:25:09", "Gewicht": 31.088, "Aussen-Temperatur": 2.8, "Aussen-Feuchtigkeit": 99.9, "Spannung": 4.15}
hiveeyes/open-hive-test01/default/3/data.json    {"time": "2018/10/28 20:22:42", "Gewicht": 45.84}
hiveeyes/open-hive-test01/default/6/data.json    {"time": "2018/10/28 20:24:01", "Weight": 29.502, "Voltage": 4.41}
hiveeyes/open-hive-michi/default/1/data.json     {"time": "2018/10/28 21:26:26", "Gewicht": 56.448, "Aussen-Temperatur": 2.9, "Aussen-Feuchtigkeit": 99.9, "Spannung": 4.12}
hiveeyes/open-hive-christian/default/1/data.json {"time": "2018/10/28 20:31:51", "Gewicht": 48.942, "Aussen-Temperatur": "", "Aussen-Feuchtigkeit": "", "Innen-Temperatur": 11.2, "Innen-Feuchtigkeit": 73.4, "Spannung": 4.64}
hiveeyes/open-hive-test01/default/4/data.json    {"time": "2018/10/28 21:35:19", "Weight": 42.31, "Outside Temp": 7.6, "Outside Humid": 73.0, "H1 Temp": 7.7, "H2 Temp": 7.8, "H3 Temp": 7.5, "H4 Temp": 6.8, "H5 Temp": 6.8, "Voltage": 3.83}
hiveeyes/open-hive-clemens/default/2/data.json   {"time": "2018/10/28 22:06:05", "Gewicht": 8.215, "Aussen-Temperatur": 8.7, "Aussen-Feuchtigkeit": 75.7, "Spannung": 3.83}

Fünf der Meßknoten funken also bereits mit Normalzeit, hier würde die Interpretation als CET (die seit gestern Nacht gültig ist) also jetzt tatsächlich stimmen. Drei der Meßknoten funken offensichtlich auf Sommerzeit und ein weiterer steht wohl in Moskau.

Die Test-Nodes sind WLAN-Nodes und übertragen keine Zeit, timestamp by server, die anderen sind GSM.

Clemens 2 ist super spannen, der funkt immer um xx:06:05 und wenn wir hier mal schauen macht er das schon ab 2018/02/05, d.h. der offset ist entweder die Zeit, die die Uhr seit damals zu schnell geht – oder ich habe die damals schlichtweg falsch eingestellt! ;-)

Korrektur:
Grafana zeigt es lediglich so an, weil Deine Voreinstellung “local browser time” ist - daher wirst Du kaum was Anderes sehen im dashboard, und daher wird das ‘richtig zugeordnet’:

image

Yeah, timezones are tricky.

image

xkcd: Supervillain Plan


There’s more to come, see also Morocco abruptly drops clock change [two days before daylight saving changeover].

1 Like

Ich denke gerade an die Lösung, die auch für Autoradios empfohlen wir, pennen doch eh jetzt unsere Viecher ;-)

1 Like