Die Verbindung zur solarLog-Datenbank steht den ganzen Tag ungenutzt herum
und wird vom Server irgendwann geschlossen; das Lesen der Sonnenzeiten war
dann der erste Zugriff, der ins Leere lief. Ein ping(reconnect=True) davor
holt sie zurueck.
Ausserdem stehen die abgefangenen Fehler jetzt mit %r im Protokoll: bei
manchen Ausnahmen ist str() leer, und dann stand dort eine Warnung ohne
Grund.
logrotate dreht monatlich statt taeglich, dafuer schon ab 10 MB.
Erster Teil der Abloesung von auto_watering.py im Web-Repo. Das Skript
dort entschied bisher selbst: stuendlich den Regen holen, mit Schwellen
aus einer ZONES-Tabelle vergleichen, schalten. Kuenftig entscheidet der
AutoAction-Runner, und die Schwellen stehen im Editor statt im Quelltext.
Dieser Sammler liefert dafuer nur noch die Zahl. Alle dreissig Minuten
holt er die Niederschlagsdaten von Open-Meteo und legt sie als retained
JSON nach Wetter/Regen:
{"tage1": 0.4, ..., "tage7": 3.4, "stand": "04.09.2026 09:00:00"}
"tageN" ist die Summe ueber N Tage, wobei der heutige, noch laufende Tag
als letzter zaehlt - dieselbe Rechnung wie accumulated_rain() im alten
Skript. Der heutige Tag kommt aus den Stundenwerten und nicht aus der
Tagessumme: die traegt die Vorhersage fuer den Rest des Tages mit, und
Regen, der erst am Abend kommen soll, hat eine Bewaesserung am Morgen
nicht zu verhindern.
Veroeffentlicht werden immer alle sieben Fenster. Welche davon als
Messwert auftauchen, entscheidet allein das Discovery-Modul im Web-Repo -
so muessen sich die beiden Repositorien nicht ueber eine Fensterliste
einigen, und eine vierte Zone mit einem vierten Zeitraum kostet hier
keine Aenderung.
Ein Dauerlaeufer und kein Cronjob, weil der alte Wert nicht einfach
stehenbleiben darf, wenn Open-Meteo ausfaellt: eine retained "0,0 mm" von
gestern wuerde den Runner bei naechster Gelegenheit giessen lassen. Der
letzte Wert gilt deshalb nur, solange er juenger als max_alter_stunden
ist, danach werden leere Werte geschickt - eine Bedingung auf einem
leeren Messwert gilt im Runner als nicht erfuellt. auto_watering.py tat
dasselbe, nur mit sys.exit(1).
Der Runner selbst bleibt unangetastet: Wetter/Regen ist fuer ihn ein ganz
gewoehnliches MQTT-Geraet.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
wattpilotshell.log hatte 329 MB erreicht - die wattpilotshell meldet
seit Monaten im Sekundentakt denselben Verbindungsfehler, und rotiert
wurde nie. logs_rotieren.sh mit logrotate.conf raeumt das jetzt taeglich
auf: vierzehn Staende, alles ueber 20 MB sofort, damit ein Prozess in
einer Fehlerschleife nicht an einem Tag das Volume fuellt. Der erste Lauf
hat aus den 329 MB 61 KB gemacht, verloren ist nichts.
Nicht in /etc/logrotate.d abgelegt - das ist DSM-Gebiet und beim
naechsten Systemupdate weg. Der Zustand kommt aus einer eigenen Datei
statt aus /var/lib/logrotate, wo der von DSM liegt.
Die Startskripte leiten dafuer mit ">>" um statt mit "&>". Die Prozesse
laufen monatelang durch und sollen fuer eine Rotation nicht neu starten
muessen, deshalb copytruncate - der Inhalt wird weggeschrieben und die
Datei geleert, waehrend sie offen bleibt. Ohne Anhaengemodus schriebe der
Prozess danach an seiner alten Stelle weiter und die Datei bekaeme vorn
ein Loch aus Nullbytes.
Nebenbei behoben: startWecker.sh leerte seine Logdatei bei jedem Start,
und gestartet wird der Wecker jede Nacht um drei. Was er am Vortag
gemeldet hatte, war morgens nicht mehr nachzulesen.
Die Skripte bekommen ausserdem ihr Ausfuehrungsrecht in den Index - ueber
die Windows-Freigabe sieht Git keine Unix-Rechte, ein frischer Checkout
haette sie nicht starten koennen.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>