# Sesja 2026-06-22 — decyzja: Prometheus jako źródło prawdy dla liveness floty ## Cel Rozstrzygnięcie architektoniczne: czym zastąpić obecną rurę wykrywania liveness floty `node-agent → rsync/ssh → observer` (warstwa sensoryczno-transportowa będąca przyczyną większości nawracających awarii). Plus precondition infrastrukturalny pod nowy serwis na VPS (swap). --- ## DECYZJA: Prometheus (pull, `up{}`) zastępuje WYKRYWANIE liveness ### Co zastępujemy (warstwa sensoryczno-transportowa) Prometheus pull + metryka `up{}` przejmuje rolę dotychczasowej rury: - **node-agent** jako shipper eventów, - **rsync/ssh** transport, - pliki eventów, - observer **prune/checkpoint**, - egzekwowanie **TTL** liveness. To była przyczyna większości nawracających awarii: - `uid 1004 != 1000` — strict ownership check OpenSSH wywalał shipping, - ślepy ssh-mount (LUSTRO, `/root/.ssh` vs `/home/homelab/.ssh`), - bloat (~242k eventów na VPS), - race `prune` ↔ `checkpoint` w observerze, - `NOMINAL`-bez-TTL (martwy node pokazywany jako zdrowy). Pull eliminuje całą warstwę push: brak kluczy, brak ownership, brak event-store do prune'owania, brak ręcznego TTL — `up==0` przez czas `for:` jest stanem prawdy. ### Świadoma granica zakresu — co ZOSTAJE Prometheus zastępuje **wykrywanie**, NIE cały system. Nietknięte: - **supervisor** — remediacja (`container_restart` / `redeploy`), - **observer / panel** `agents.okit.pl` — do przepięcia na źródło Prometheus (OTWARTE, największy znak zapytania przy cutoverze), - **ha-diag-agent** — logika domenowa HA (diff `system_health`, encje `unavailable`, WS heartbeat) — Prometheus tego nie widzi, - historia incydentów / lifecycle, - out-of-band watchdog. ### BEZ Alertmanagera — świadoma decyzja Jeden kanał Telegram (`@okitaialerts_bot`). Rolę dostarczania przejmuje **brain-watchdog**: dochodzi mu **drugie wejście** — odpytanie Prometheus `/api/v1/alerts` — obok obecnego pingu mózgu. Reguły alertowe z histerezą (`for:`) po stronie Prometheusa; watchdog pozostaje cienki (odczyt `firing` + Telegram). Nie wprowadzamy osobnego Alertmanagera, żeby nie mnożyć kanałów ani komponentu do utrzymania. > Uwaga: ta decyzja **zastępuje** wcześniejszy szkic z sesji 2026-06-17 > (blackbox_exporter + Alertmanager). Wybrano pull `up{}` + watchdog jako tor alertu. --- ## Osobny fleet-Prometheus pod GitOps — NIE adopcja domowego instance Stawiamy **osobny** Prometheus floty, zarządzany przez GitOps. NIE adoptujemy domowego instance na PIHA. Powód — domowy prom na PIHA to liability nie wart adopcji: - LAN-only (scrape `192.168.31.x`), mija nody tylko-Tailscale (VPS, chelsty), - poza repo (`/home/pi/monitoring/prometheus.yml`, konfigurowany ręcznie), - bez alertingu (`alerting:` i `rule_files:` puste), - sekrety plaintext w configu (long-lived token HAOS + bearer watchtower — do rotacji). Adopcja = dziedziczenie liability (migracja, ekstrakcja sekretów) **plus** blast-radius na działający monitoring bezpieczeństwa domu (crowdsec / fail2ban / haos) za znikomą wygraną. Osobny instance izoluje flotę od domu. ## Placement: VPS - Host: VPS (`ubuntu-4gb-hel1-1`, `100.95.58.48`). - Out-of-band zachowane: **watchdog na PIHA pilnuje VPS z innej maszyny** — Prometheus na VPS nie jest sędzią własnej śmierci. - VPS ma już `node_exporter` (role: metrics-exporter) = pierwszy target floty gotowy. --- ## ZROBIONE w tej sesji ### Swap 4 GB na VPS — precondition pod Prometheusa - `/swapfile` aktywny i **trwały** (wpis w `/etc/fstab`). - `vm.swappiness=10` ustawione na żywo i w `/etc/sysctl.conf`. - **Weryfikacja**: `free -h` → `Swap: 4.0Gi (0B used)`; `/proc/swaps` zawiera `/swapfile`. - Powód: VPS ma 3.7 GB RAM, wcześniej `swap=0` — przyczyna OOM 2026-06-01. Prometheus jest RAM-głodny; swap to bufor bezpieczeństwa. - ⚠️ To **host-level one-off** — nie czysto GitOps-owalne, wykonane świadomie gotowcem. Zapisane jako celowy host-state w `hosts/vps/host.yaml`, żeby przy odtwarzaniu VPS nie zniknęło cicho (wzorzec jak uid/grupy po 8-dniowej awarii). --- ## Plan następnych kroków (OTWARTE — NIE realizowane w tej sesji) Kolejność = priorytet: 1. **Scaffold serwisu `fleet-prometheus` pod GitOps** — worktree `task/fleet-prometheus`, wzorzec `services/vikunja/`: `docker-compose.yml` + `env.example` + `service.yaml` + `README.md` + `healthcheck.sh`. Rejestracja w `hosts/vps/services.yaml` + `inventory/topology.yaml`. Exposure: `tailscale-internal`. Pusty scrape na start (self + lokalny `node_exporter` VPS). 2. **Inwentaryzacja nodów floty `100.x`** do scrape (osobny krok). 3. **Container-layer exporter** (cAdvisor lub lekki docker-state) — brakujący klocek; `node_exporter` nie widzi kontenerów. 4. **Reguły liveness** (`up==0 for: 5m`) w Prometheusie. 5. **brain-watchdog: drugie wejście** — odpyt Prometheus `firing` → Telegram, bez ruszania działającego toru `token → chat_id`. 6. **Rotacja tokenu HAOS** w domowym prom (plaintext). 7. **Przepięcie observer / panel `agents.okit.pl`** na Prometheus jako źródło — największy znak zapytania przy cutoverze. 8. **Parallel-run** obok rury eventowej; **cutover dopiero** gdy Prometheus-truth się udowodni. --- ## Wnioski - Klasa awarii (push shipping: klucze, ownership, bloat, race, TTL) znika nie przez kolejny fix, lecz przez zmianę modelu transportu na **pull** — Prometheus widzi martwy target jako `up==0`, bez warstwy dostarczania do zepsucia. - Granica zakresu trzymana świadomie: Prometheus = **wykrywanie**, nie remediacja ani logika domenowa HA. Zastępujemy sensor, nie mózg. - Osobny instance > adopcja: nie dziedziczy się liability ani blast-radius na monitoring bezpieczeństwa domu dla wygody współdzielenia. - BEZ Alertmanagera: cienki watchdog z drugim wejściem zamiast nowego komponentu — jeden kanał Telegram pozostaje jeden. - Swap = precondition, nie cel — odblokowuje RAM-ciasny VPS pod nowy serwis; udokumentowany jako celowy host-state, nie ukryta ręczna zmiana.