LOEMIND_observability.md 10 KB

Observability (ClickStack / HyperDX) — ohmu

Loodud 2026-09-25. ClickStack = HyperDX UI + (väline) ClickHouse + kaasas olev OTel-kollektor. Kogu grupp on always-on (ei ole enam experimental).

Ligipääs

Arhitektuur (andmevoog)

node-exporter ─┐
cadvisor ──────┼─► otel-collector (scrape 60s) ─► clickstack:4317 (kaasas kollektor) ─► ClickHouse (default.otel_*)
llama.cpp ─────┘        (main_ai_network)              (opampsupervisor)
  • otel-collector (contrib) skrape'ib node-exporter, cadvisor ja llama.cpp (host.docker.internal:8070/metrics).
  • Kaasas olev kollektor (clickstack konteineris) võtab configu API-lt (opamp, port 4320) ja kirjutab ClickHouse'i otel_* tabelitesse.
  • Kriitiline: clickstack-entry.sh peab käivitama /otel-entrypoint.sh /usr/local/bin/opampsupervisor — muidu OTLP andmed ei püsi.

ClickHouse tabelid (default)

otel_logs, otel_traces, otel_metrics_gauge|sum|histogram|exponential_histogram|summary + rollupid. Skeem luuakse automaatselt schema-seed'iga (goose).

Konfiguratsioon

Fail Sisu
dev/docker-compose.yml clickstack, clickstack-proxy, node-exporter, cadvisor, otel-collector (always-on)
dev/config/otel-collector/config.yaml prometheus receiver (node/cadvisor/llamacpp) + regexp-filter + OTLP eksport
dev/clickstack-entry.sh mongod + OTel-kollektor + HyperDX app
dev/.env HYPERDX_INGEST_KEY (gitignore'itud) — kollektori OTLP auth

ClickStack env (olulised)

  • CLICKHOUSE_ENDPOINT=tcp://clickhouse:9000?dial_timeout=10s
  • CLICKHOUSE_USER=default, CLICKHOUSE_PASSWORD=dev_clickhouse_2026
  • HYPERDX_OTEL_EXPORTER_CLICKHOUSE_DATABASE=default
  • DEFAULT_CONNECTIONS=[{"name":"Local ClickHouse","host":"http://clickhouse:8123","username":"default","password":"dev_clickhouse_2026"}]

ClickHouse ühendus (HyperDX Connections) — ÕIGE seadistus

Ühendusel peavad olema eraldi väljad username/password ja host ilma userinfo'ta (http://clickhouse:8123). Siis lisab CH-proxy X-ClickHouse-User/Key päised.

❗ Local mode peab olema VÄLJAS: NEXT_PUBLIC_IS_LOCAL_MODE=false. Koos välise (mitte-image'sisese) ClickHouse'iga põhjustab true selle, et brauser kasutab lokaalset ühendust (sessionStorage/__ENV.js) ja saadab ise Authorization/ user= → proxy lisab omakorda X-ClickHouse-* → Code 516 või UNKNOWN_USER. Väärtus injekteeritakse runtime'is public/__ENV.js kaudu → piisab docker compose up -d --force-recreate clickstack (kontroll: cat .../public/__ENV.js).

❗ Varasem soovitus hoida username/password tühjad ja panna tunnused host-URL-i (http://default:parool@clickhouse:8123) ei tööta: http-proxy-middleware ei edasta host-URL-i parooli → CH saab kasutaja default tühja parooliga → „Authentication failed: password is incorrect". (Kinnitatud tcpdump -i any 'tcp port 8123'-ga.)

Mongo otsene parandus:

db.connections.updateOne({_id: ObjectId("<conn-id>")},
  {$set:{host:"http://clickhouse:8123", username:"default", password:"dev_clickhouse_2026"}});

Pärast otsest mongo-muudatust taaskäivita clickstack (muidu jääb vahemällu): docker restart clickstack.

Code 516 hoiatus: kui ühendusel on username JA päring sisaldab user= query-param, tuleb Code: 516 ... X-ClickHouse HTTP headers and authentication via parameters simultaneously. Seetõttu ei tohi ühendust anda browseri CH-kliendile koos username'iga; HyperDX metadataklient (W({queryTimeout})) ehitab kliendi ilma username'ita → OK.

Logide kogumine (filelog)

otel-collector loeb Dockeri konteineriloge:

  • receivers.filelog: include: /var/lib/docker/containers/*/*-json.log, container parser, start_at: end
  • service.pipelines.logs: [filelog] → [memory_limiter, batch] → [otlp]
  • Compose: otel-collector vajab mounti /var/lib/docker/containers:/var/lib/docker/containers:ro ja user: "0:0" (mitte-root kasutaja → „open .: permission denied").
  • Kontroll: SELECT count(), max(Timestamp) FROM default.otel_logs.

Metrikad (praegu)

  • Host: RAM (available/total), swap, load, CPU, failisüsteem, võrk (node-exporter).
  • Konteinerid: CPU, mälu (working set/usage), võrk (cadvisor).
  • Mudel: llama.cpp — prompt/ predicted tokens, requests_processing, kv_cache (--metrics).

Dashboardid (retseptid)

HyperDX UI-s: Dashboards → New dashboard → Add tile. Kasuta allolevaid metrikaid (Metrics source) või "SQL" diagrammi. Ajatelje jaoks sobib TimeUnix.

Paneel Mõõdik / SQL
RAM vaba node_memory_MemAvailable_bytes (gauge)
Swap vaba node_memory_SwapFree_bytes (gauge)
Load node_load1 (gauge)
Konteineri mälu container_memory_working_set_bytes (group: Attributes['name'])
Konteineri CPU container_cpu_usage_seconds_total (rate)
Llama tokeneid/s rate(llamacpp:tokens_predicted_total) või pika aja trend
Llama päringud llamacpp:requests_processing (gauge), llamacpp:tokens_predicted_total (sum)
Llama KV-cache llamacpp:kv_cache_usage_ratio (gauge)
Teenus üleval ohmu_service_up (group: Attributes['service'])
Restardid ohmu_container_restarts (group: Attributes['name'])

Näidis-SQL (ClickHouse):

-- Teenuste seis viimase 10 min jooksul
SELECT toStartOfMinute(TimeUnix) AS t, Attributes['service'] AS service, avg(Value) AS up
FROM default.otel_metrics_gauge
WHERE MetricName = 'ohmu_service_up' AND TimeUnix > now() - INTERVAL 10 MINUTE
GROUP BY t, service ORDER BY t;

Teadaolevad UI-nõksud

Metrika-paneeli select skeem (HyperDX 2.37)

Metrika-diagramm ja alert nõuavad, et select[] elemendil oleks: {metricName, metricType, aggFn, isDelta, filters: [], valueExpression: "Value"}, kus metricType ∈ gauge|sum|histogram|summary|exponential histogram. Vana aggCondition-ainult kuju annab no query support for metric type=undefined. valueExpression on vajalik, sest alerti config lisab variables → macro-töötlus loeb select[].valueExpression (puudumisel TypeError: Cannot read properties of undefined (reading 'length')). metricType määra ClickHouse'i tabeli järgi (otel_metrics_gauge|sum|histogram|...): nt llamacpp:tokens_predicted_total → sum, node_load1/ohmu_service_up → gauge.

Alert nõuab number/line/stacked bar paneeli

Alert ei toeta table-paneeli (Unsupported alert source: tile). Kasuta number/line/stacked bar paneeli. Pärast alerti/paneeli otsest mongo-muudatust taaskäivita clickstack (vahemälu).

Heatmap: „Value expression is required for heatmap charts"

Chart Explorer → Heatmap nõuab, et seeria Value expression oleks täidetud (HyperDX valideerib series[0].valueExpression). See on UI-konfiguratsioon, mitte andmeviga.

  • Metrics source: vali metrika (nt node_load1) ja sisesta Value väljale Value (või avg(Value)), lisa filtrisse MetricName.
  • Logs source: Value väljale count(); "Group by" nt ServiceName või SeverityText.
  • Kui metrika valimine ei täida Value välja automaatselt, trüki see käsitsi.

Metrics source peab sisaldama metricTables.exponentialHistogram

Vaikimisi bootstrap võib selle puudumisel metrikate valija katki teha. Kontroll:

docker exec clickstack mongo --quiet hyperdx --eval \
 'printjson(db.sources.findOne({kind:"metric"}).metricTables)'
# vajadusel: db.sources.updateOne({kind:"metric"},{$set:{"metricTables.exponentialHistogram":"otel_metrics_exponential_histogram"}})

Näidis-dashboardid

Loodud 2026-09-25 skriptiga ~/scripts/create_hyperdx_dashboards.py:

  • „Ohmu — süsteem (host)" — RAM vaba, swap vaba, load1, konteinerite mälu (host metrikad)
  • „Ohmu — mudelid (llama.cpp)" — genereeritud/prompt-tokenid, aktiivsed päringud, KV-cache
  • „Ohmu — teenused ja konteinerid" — ohmu_service_up, ohmu_container_restarts

Kordamine: python3 ~/scripts/create_hyperdx_dashboards.py (--delete-tests koristab testid).

API ligipääs: HyperDX väline API v2 on http://<clickstack-ip>:8000/api/v2 (hostilt konteineri IP kaudu; clickstack-proxy ribab /api prefiksi, seega :18080 kaudu ei tööta). Access key: docker exec clickstack mongo --quiet hyperdx --eval 'print(db.users.findOne({email:"admin@odamus.com"}).accessKey)'.

Tile-vorming (API):

{"name":"paneel","x":0,"y":0,"w":6,"h":6,"config":{
  "displayType":"line","sourceId":"<Metrics source id>",
  "select":[{"valueExpression":"Value","aggFn":"avg","where":"MetricName:\"node_load1\""}],
  "groupBy":"name"}}

Alertid (Telegram)

Rakendatud: HyperDX webhook → alert-relay → Telegram.

  • alert-relay konteiner (dev/config/alert-relay/alert_relay.py, python:3.12-slim, port 9099): võtab vastu HyperDX „generic" webhook POST-id ja saadab Telegrami. Token dev/.env-st (TELEGRAM_BOT_TOKEN), chat 5036685258.
  • Webhook: Telegram (ohmu) → http://alert-relay:9099/ (id 6ab760240c9282a5b0fde124).
  • Alert: „Teenus maas (ohmu_service_up)" → dashboardi paneel „Teenused üleval", thresholdType=below, threshold=1, interval=5m, kanal webhook (id 6ab7603c0c9282a5b0fde12d).

Oluline API-piirang: väline API v2 (POST /api/v2/alerts) toetab ainult source: "tile" või "saved_search" — inline alert on ainult sisemise API jaoks. Paneeli-alert viitab: {source:"tile", tileId, dashboardId}; kanal: {"type":"webhook","webhookId":"..."}.

Testimine:

# relay otse (hostilt pole 9099 avaldatud; kasuta konteinerit võrgus):
docker run --rm --network main_ai_network curlimages/curl:latest -s \
  -X POST http://alert-relay:9099/ -d '{"name":"test","state":"ALERT"}'

Tüüpilised täiendavad alertid (sama muster: tile + webhook + below/above):

  • node_memory_MemAvailable_bytes < X (RAM otsas)
  • ohmu_container_restarts > 0 (restart-loop)
  • llamacpp:kv_cache_usage_ratio > 0.9

Seotud

  • Vahejuhtumite audit: ../LOEMIND_seisevad_konteinerid.md
  • Serveri mudelid: ~/servers/LOEMIND/llama-server.md