Three Signals, Three Questions
each answers a different questionObservability is three tools, and the mistake is treating them as interchangeable. Each answers one question, and the art is escalating from cheap to expensive: a metric tells you something's wrong, a trace tells you where, and a log tells you exactly what.
METRICS โโถ "Is something wrong?" cheap, aggregated numbers, alertable
โ (error rate spiked)
โผ something's wrong โ where?
TRACES โโถ "Where in the chain?" one request across services
โ (the payment call is timing out)
โผ which call โ what happened?
LOGS โโถ "What exactly happened?" rich, detailed, expensive, searchable
(stack trace, the bad input)
Metrics
the golden signals, and why averages lieMetrics are cheap aggregated numbers over time โ counters (requests served), gauges (current connections), histograms (latency distribution). The framework to name is the four golden signals: latency, traffic, errors, saturation. Instrument those per service and you can see health at a glance.
WHY PERCENTILES, NOT AVERAGES:
1000 requests. 990 at 50ms, 10 at 5000ms.
average = 99ms โ looks fine, hides everything
p99 = 5000ms โ the truth: 1 in 100 users waited 5 seconds
average smears the outliers away; p99 / p999 expose the tail users feel.
Logs
rich detail, expensive at volumeLogs are the detailed record of what actually happened โ the stack trace, the offending input, the exact sequence. Rich but expensive, so a few practices keep them useful at scale.
| Practice | Why |
|---|---|
| Structured logging | JSON fields, not free text โ so you can query and aggregate, not grep |
| Centralized aggregation | Ship logs off the box to one searchable place; a dead server's logs survive |
| Sampling under volume | Keep all errors, sample the routine โ full logging at scale is unaffordable |
| Correlation IDs | One ID threaded through a request ties its logs together across services |
Distributed Tracing
where the time went, across servicesIn a microservices system, one user request fans out across many services, and "which one was slow?" isn't answerable from any single service's view. A trace stitches the whole path together: each unit of work is a span, spans nest into a tree, and the trace shows where every millisecond went.
ONE TRACE (one request): gateway โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโค 120ms auth โโโโโค 8ms orders โโโโโโโโโโโโโโโโโโโโโโโโค 70ms payment โโโโโโโโโโโโโโโโโค 55ms โ the culprit db โโโโค 9ms each bar is a SPAN; trace context is propagated so spans link into one tree
The key mechanism is context propagation: the trace ID travels with the request across service and queue boundaries, so an async job triggered by a message still links back to the request that caused it. OpenTelemetry is the standard for this. Because tracing every request is costly, you sample โ head-based (decide at the start) or tail-based (decide after, keeping the slow and failed ones, which are the interesting ones).
In the Interview
cheap points at wrap-upObservability is rarely the focus of a design question, which is exactly why one crisp sentence at the end scores easy points few candidates claim. It signals you think about running the system, not just building it.
Quick Reference
the three signals compared| Metrics | Logs | Traces | |
|---|---|---|---|
| Answers | Is something wrong? | What exactly happened? | Where in the chain? |
| Cost | Cheap | Expensive at volume | Moderate, sampled |
| Cardinality | Must stay low | High is fine | Per-request |
| Alertable? | Yes โ the primary signal | Rarely directly | No |
| Scope | Aggregated over time | One event | One request, cross-service |