Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
6.6 KiB
name, kind, lang, domain, version, purity, signature, description, tags, uses_functions, uses_types, returns, returns_optional, error_type, imports, params, output, tested, test_file_path, tests
| name | kind | lang | domain | version | purity | signature | description | tags | uses_functions | uses_types | returns | returns_optional | error_type | imports | params | output | tested | test_file_path | tests | |||||||||||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| parse_nats_monitor | function | go | infra | 1.0.0 | impure | func ParseNatsMonitor(node string, varz, connz, jsz []byte) ([]PromSample, error) | Convierte las respuestas JSON del endpoint de monitoring HTTP embebido de un nats-server (puerto 8222, loopback) en una serie de PromSample lista para empujar a VictoriaMetrics. Hermana de ParseUnibusHealth pero para las métricas server-level de NATS/JetStream: msgs/s, bytes, conexiones, slow consumers, memoria RSS, start epoch (proxy de reinicios), streams/messages/bytes/memory/storage de JetStream, y por stream nats_stream_messages/bytes, nats_jetstream_raft_leader y kv_bucket_msgs para los buckets KV_. Adjunta labels node e instance a cada serie. varz es el core (error si no parsea); connz y jsz son best-effort (se omiten sin abortar). La consume el unibus_exporter de fleet_monitoring como scraper local por nodo. |
|
|
true | error_go_core |
|
|
slice de PromSample con labels base {node,instance}: nats_msgs_in/out_total, nats_bytes_in/out_total, nats_connections, nats_slow_consumers, nats_mem_bytes, nats_subscriptions, nats_server_start_seconds (omitida si start no parsea), nats_jetstream_streams/messages/bytes/memory_bytes/storage_bytes; y por stream nats_stream_messages{stream}, nats_stream_bytes{stream}, nats_jetstream_raft_leader{stream} (1 si cluster.leader==node) y, para streams KV_, kv_bucket_msgs{bucket} con el prefijo KV_ recortado. Error solo si varz no es JSON válido. | true | functions/infra/parse_nats_monitor_test.go |
|
parse_nats_monitor
Función de transformación (clasificada impure porque devuelve error al fallar el
unmarshal del core; no hace I/O ni red por sí misma) que traduce las métricas
server-level de un nats-server a series Prometheus. Es la hermana de
parse_unibus_health_go_infra: aquella lee el /healthz de membershipd (posture),
esta lee el monitoring embebido de NATS (puerto 8222) para las métricas profundas que
/healthz no expone: msgs/s, conexiones, RAFT leader por stream, memoria, KV buckets.
Pertenece al grupo de capacidad fleet-metrics: se compone con
format_prom_exposition_go_infra (serializar) y push_prom_remote_go_infra (empujar a
VictoriaMetrics). La consume el unibus_exporter de fleet_monitoring en modo scraper
local por nodo, que hace los tres GET y le pasa los cuerpos crudos.
Ejemplo
package main
import (
"fmt"
"io"
"net/http"
"time"
"fn-registry/functions/infra"
)
func get(url string) []byte {
resp, err := http.Get(url)
if err != nil {
return nil // best-effort: connz/jsz pueden faltar
}
defer resp.Body.Close()
b, _ := io.ReadAll(resp.Body)
return b
}
func main() {
base := "http://127.0.0.1:8222"
varz := get(base + "/varz")
connz := get(base + "/connz")
jsz := get(base + "/jsz?streams=1")
samples, err := infra.ParseNatsMonitor("magnus", varz, connz, jsz)
if err != nil {
panic(err) // varz es el core: sin él no hay métricas
}
fmt.Print(infra.FormatPromExposition(samples, time.Now().UnixMilli()))
// nats_msgs_in_total{instance="magnus",node="magnus"} 17 ...
// kv_bucket_msgs{bucket="UNIBUS_users",instance="magnus",node="magnus"} 2 ...
// nats_jetstream_raft_leader{instance="magnus",node="magnus",stream="KV_UNIBUS_users"} 1 ...
}
Cuando usarla
Úsala dentro de un exporter que monitoriza un nats-server con el monitoring HTTP
embebido activado (http: 127.0.0.1:8222 en la config de NATS): tras hacer
GET /varz, GET /connz y GET /jsz?streams=1 contra loopback, pasa los tres cuerpos
crudos a esta función para obtener todas las series server-level del nodo. Llámala como
scraper local por nodo (cada nodo expone su 8222 solo en loopback), no centralizado.
Gotchas
- Impura por contrato: solo devuelve
errorsivarzno es JSON válido (es el core).connzyjszson best-effort: si vienen vacíos o no parsean, sus series se omiten sin abortar. Esto hace al scraper resistente a que un endpoint falle de forma puntual. - Monitoring loopback-only sin auth: el puerto 8222 de NATS no tiene autenticación; por
eso debe bindearse a
127.0.0.1y scrapearse localmente en cada nodo, nunca exponerse a la red. El push agregado a VictoriaMetrics lo hace el exporter, no esta función. /jsznecesita?streams=1para traeraccount_details[].stream_detail[]. Sin ese parámetro el cuerpo trae los totales pero no el detalle por stream, y entonces no salennats_stream_*,nats_jetstream_raft_leadernikv_bucket_msgs.nats_connections: prefiereconnz.num_connections; siconnzno parsea, cae avarz.connectionspara no perder la serie.- RAFT leader en standalone: en un nats-server sin clúster, el objeto
clusterpuede faltar oleadervenir vacío; en ese casonats_jetstream_raft_leadersale 0 salvo quecluster.leader == node. Es esperado: en standalone no hay quorum RAFT real. kv_bucket_msgssolo se emite para streams cuyo nombre empieza porKV_, recortando el prefijo (streamKV_UNIBUS_users→ bucketUNIBUS_users).nats_server_start_secondses el epoch Unix del campostart(RFC3339): sirve como proxy de reinicios (un cambio de valor = el server reinició). Si el campo no parsea como fecha válida, la serie se omite en lugar de abortar.