Skip to main content

Logs

Logs are timestamped events. In avuru obs they become powerful when they carry a trace_id — that's what lets you pivot from a slow trace straight to the lines the service logged during that request.

  • Ingestion — via OTLP logs or the collector's log receivers.
  • Correlation — by trace_id / span_id and resource attributes.

What your service should emit​

With the logs module and node-agent stdout collection enabled, pod logs flow through the gateway. Check the selected project and collection configuration. To get useful logs, emit one JSON object per line carrying these three things:

FieldWhy
levelBecomes SeverityNumber. Both dialects are understood: numeric (pino: 30, 50) and named (logback: "INFO", "ERROR").
trace_idBecomes the TraceId column — this, and only this, is what makes a trace show its logs.
span_idBecomes SpanId, narrowing a log to the operation inside the trace.

Anything else in the object becomes a queryable log attribute, and the raw line stays searchable in full text.

Lines that are not JSON are ingested unchanged rather than rejected, and the node agent still reads a level off them where one is written: a level=warn / lvl= / severity= pair (logfmt, zap console), or the usual upper-case token bounded on both sides — … DEBUG [main] …, [INFO], ERROR: — as Spring, logback and log4j write it. Without any of those, a record's severity stays unset — and severity is a floor comparison, so such a record matches no severity filter at all and is never promoted to an error issue (which keys on ERROR and above). A record that already carries a level, such as one exported over OTLP by an SDK, is left alone. The parsing is on by default and off with sensor.agent.logs.parseSeverity=false.

Getting trace_id onto the line is the language runtime's job:

  • Node / pino — a mixin reading trace.getActiveSpan()?.spanContext(). Do not rely on @opentelemetry/instrumentation-pino in an ESM service: it patches nothing without the loader hook, and the omission is silent.
  • Java / logback — the Micrometer tracing MDC keys, already present in the standard console pattern.

:::note Prefer stdout to OTLP logs A service that also exports logs over OTLP is ingested twice, since the node agent is already reading its stdout. An SDK-emitted record also carries no k8s.namespace.name, so the gateway cannot tell which project it belongs to and files it under the fallback tenant. Set the signal-specific OTEL_EXPORTER_OTLP_TRACES_ENDPOINT rather than the generic OTEL_EXPORTER_OTLP_ENDPOINT, which switches on every signal at once. :::

Explore logs​

The logs explorer is live today:

  • Full-text search over the log body, with severity, tags, sources and a multi-service selector. Suggestions include services known only from logs; Kubernetes workloads include their namespace so namesakes stay distinct. An exact service name can also be entered directly. Every filter is held in the URL for shareable views.
  • One stream or separate panels. The merged view orders all selected services and workloads on one timeline. The panel view gives every selection its own scroll and pagination while keeping the same time, severity, source and text filters. It runs at most four storage requests concurrently.
  • Application and mesh sources together. Application, ztunnel, waypoint and uncategorised records are enabled by default and can be switched independently. Every row names both its emitting service and source. The same explorer is available from Signals → Logs and the mesh's Logs tab.
  • Trace correlation — a log row's trace_id links to its trace, and a trace's spans link back to the logs emitted during that request.
  • Keyset pagination for gap-free scrolling through large time windows.
  • A service's logs, including the mesh's. A service's Logs tab finds its lines even when its pod files them under a different name than its spans carry: the hub ties the service to its workload and reads the same sources as a workload's Logs tab on the mesh screen. When no workload can be tied to it, the tab says which of two things to fix.
  • Take the lines with you. Copy every loaded line, or tick the rows that matter (shift-click extends a range) and copy just those, or download what is loaded as a .log file. Each control says how many lines it will take. The per-row copy button appears on hover and on keyboard focus.

Query the API​

GET /api/v1/logs accepts repeated service parameters and repeated workload=namespace/name parameters. Repeat source, or pass source=app,ztunnel,waypoint,other, to select source families; the subjects are combined with OR, then q, severity and tags are applied with AND. GET /api/v1/logs/services returns the project-scoped service and workload suggestions for the requested time window. See the API reference for cursor and resolution details.

Verify trace correlation​

A structured stdout record can carry these fields:

{"level":"INFO","message":"payment authorized","trace_id":"0123456789abcdef0123456789abcdef","span_id":"0123456789abcdef"}

These IDs are illustrative. In an application, copy them from the active span; never use a fixed ID for real requests. A trace ID has 32 hexadecimal characters and a span ID has 16. Invalid or absent IDs do not identify a request.

Find the record in Logs, open its trace link and verify that the span belongs to the same request. For an executable example, use the Go SDK integration or the synthetic checkout exercise.

If the logs are not attached to a trace​

  • A plain line can remain searchable without having trace context.
  • Service name and timestamp alone are not a trace ID.
  • Check project, time window, retention and the signal's collection module.
  • Choose one ingestion path for a log to avoid collecting the same event twice.

Retention is configured by deployment and project; see scaling and retention.

:::note Release coverage Automatic severity parsing from container stdout and the expanded service-log and copy controls described above are documented on the current development trunk for v0.17. The multi-service explorer and mesh-wide Logs tab are also documented from the current development trunk. OTLP log ingestion and trace-ID correlation are already released. Check feature status and the version you installed. :::