Observability Patterns
When to Use
- Setting up monitoring and alerting for applications
- Implementing centralized logging
- Adding distributed tracing to microservices
- Designing SLOs/SLIs and error budgets
- Creating dashboards and runbooks
Three Pillars of Observability
| Pillar |
Purpose |
Tools |
| Metrics |
Quantitative measurements over time |
Prometheus, CloudWatch, Datadog, Grafana |
| Logs |
Discrete events with context |
ELK, Loki, CloudWatch Logs, Splunk |
| Traces |
Request flow across services |
Jaeger, Zipkin, X-Ray, Tempo |
Stack Detection
Check which observability stack the project uses:
prometheus.yml or ServiceMonitor → Prometheus
fluent-bit.conf or fluentd.conf → Fluent Bit/Fluentd
otel-collector-config.yaml → OpenTelemetry
- AWS with
aws_cloudwatch_* resources → CloudWatch
datadog-agent or DD_* env vars → Datadog
Use context7 to look up stack-specific configuration syntax.
Solution Decision Matrix
Metrics Stack
| Scenario |
Recommended Solution |
| Kubernetes-native, cost-sensitive |
Prometheus + Grafana |
| AWS-native, simple setup |
CloudWatch Metrics |
| Multi-cloud, enterprise |
Datadog or New Relic |
| OpenTelemetry-first |
Prometheus with OTLP receiver |
Logging Stack
| Scenario |
Recommended Solution |
| Kubernetes, cost-sensitive |
Loki + Grafana |
| AWS-native |
CloudWatch Logs |
| High volume, complex queries |
Elasticsearch (ELK) |
| Multi-cloud, managed |
Datadog Logs or Splunk |
Tracing Stack
| Scenario |
Recommended Solution |
| Kubernetes, open-source |
Jaeger or Tempo |
| AWS-native |
X-Ray |
| Multi-cloud, correlated |
Datadog APM |
| Vendor-agnostic |
OpenTelemetry → any backend |
Kubernetes Observability Pattern
┌─────────────────────────────────────────────────────┐
│ Applications │
│ (instrumented with OpenTelemetry SDK or auto-inst) │
└──────────────────────┬──────────────────────────────┘
│ OTLP
▼
┌─────────────────────────────────────────────────────┐
│ OpenTelemetry Collector │
│ (receives, processes, exports telemetry) │
└───────┬─────────────────┬─────────────────┬─────────┘
│ │ │
▼ ▼ ▼
Prometheus Loki Tempo/Jaeger
(metrics) (logs) (traces)
│ │ │
└────────────────┬┴─────────────────┘
▼
Grafana
(visualization)
SLO/SLI Framework
Key Metrics (RED Method for Services)
| Metric |
Description |
Example SLI |
| Rate |
Requests per second |
rate(http_requests_total[5m]) |
| Errors |
Failed requests |
rate(http_requests_total{status=~"5.."}[5m]) |
| Duration |
Latency distribution |
histogram_quantile(0.99, rate(http_request_duration_seconds_bucket[5m])) |
Key Metrics (USE Method for Resources)
| Metric |
Description |
Example |
| Utilization |
% time resource is busy |
CPU usage, memory usage |
| Saturation |
Queue depth, waiting |
Pod pending, connection pool |
| Errors |
Error count |
OOM kills, disk errors |
SLO Definition Template
# Example: API availability SLO
slo:
name: api-availability
description: "API returns successful responses"
sli:
metric: |
sum(rate(http_requests_total{status!~"5.."}[5m]))
/
sum(rate(http_requests_total[5m]))
target: 99.9%
window: 30d
error_budget: 0.1% # ~43 minutes/month downtime allowed
Alerting Strategy
Alert Severity Levels
| Severity |
Response |
Example |
| Critical |
Page on-call immediately |
Service down, data loss risk |
| Warning |
Investigate within hours |
Error rate elevated, disk 80% |
| Info |
Review during business hours |
Deployment completed, scaling event |
Alert Quality Rules
- Actionable: Every alert must have a clear response action
- Relevant: Alert on symptoms (user impact), not causes
- Unique: Avoid duplicate alerts for same incident
- Timely: Alert early enough to prevent impact
Alert Template (Prometheus)
groups:
- name: api-alerts
rules:
- alert: HighErrorRate
expr: |
sum(rate(http_requests_total{status=~"5.."}[5m]))
/
sum(rate(http_requests_total[5m])) > 0.01
for: 5m
labels:
severity: warning
annotations:
summary: "High error rate detected"
description: "Error rate is {{ $value | humanizePercentage }} (threshold: 1%)"
runbook_url: "https://runbooks.example.com/high-error-rate"
Structured Logging
Log Format (JSON)
{
"timestamp": "2024-01-15T10:30:00Z",
"level": "error",
"message": "Payment processing failed",
"service": "payment-api",
"trace_id": "abc123",
"span_id": "def456",
"user_id": "user-789",
"error": {
"type": "PaymentGatewayError",
"message": "Connection timeout"
},
"context": {
"payment_id": "pay-123",
"amount": 99.99
}
}
Required Log Fields
| Field |
Purpose |
Correlation |
timestamp |
When event occurred |
Time-based queries |
level |
Severity (debug/info/warn/error) |
Filtering |
service |
Source service name |
Service filtering |
trace_id |
Distributed trace identifier |
Cross-service correlation |
message |
Human-readable description |
Search |
Process
- Discover context → Check existing observability setup (Prometheus, CloudWatch, etc.)
- Choose stack → Use decision matrix based on environment and requirements
- Instrument apps → Add OpenTelemetry SDK or auto-instrumentation
- Configure collection → Set up collectors, exporters, and storage
- Define SLOs → Establish SLIs, targets, and error budgets
- Create alerts → Implement actionable alerts with runbooks
- Build dashboards → Create service and infrastructure dashboards
- Document runbooks → Write response procedures for each alert
Checklist
Anti-Patterns
| Don't |
Do |
| Alert on every metric threshold |
Alert on user-impacting symptoms |
| Log everything at DEBUG in production |
Use appropriate log levels |
| Unstructured log messages |
Structured JSON logging |
| Missing trace context |
Propagate trace IDs across services |
| Dashboards with 50+ panels |
Focused dashboards per service/domain |
| Alerts without runbooks |
Every alert links to response procedure |
| Store logs indefinitely |
Define retention based on compliance needs |
Related Skills
tsh-implementing-kubernetes - For K8s-native observability setup
tsh-implementing-ci-cd - For pipeline observability integration
tsh-managing-secrets - For secure credential storage for observability tools
1---2name: tsh-implementing-observability3description: Observability patterns for logging, monitoring, alerting, and distributed tracing. Use when implementing metrics collection, log aggregation, alerting rules, or distributed tracing across services.4---56# Observability Patterns78## When to Use910- Setting up monitoring and alerting for applications11- Implementing centralized logging12- Adding distributed tracing to microservices13- Designing SLOs/SLIs and error budgets14- Creating dashboards and runbooks1516## Three Pillars of Observability1718| Pillar | Purpose | Tools |19|--------|---------|-------|20| **Metrics** | Quantitative measurements over time | Prometheus, CloudWatch, Datadog, Grafana |21| **Logs** | Discrete events with context | ELK, Loki, CloudWatch Logs, Splunk |22| **Traces** | Request flow across services | Jaeger, Zipkin, X-Ray, Tempo |2324## Stack Detection2526Check which observability stack the project uses:27- `prometheus.yml` or `ServiceMonitor` → Prometheus28- `fluent-bit.conf` or `fluentd.conf` → Fluent Bit/Fluentd29- `otel-collector-config.yaml` → OpenTelemetry30- AWS with `aws_cloudwatch_*` resources → CloudWatch31- `datadog-agent` or `DD_*` env vars → Datadog3233Use `context7` to look up stack-specific configuration syntax.3435## Solution Decision Matrix3637### Metrics Stack3839| Scenario | Recommended Solution |40|----------|---------------------|41| Kubernetes-native, cost-sensitive | Prometheus + Grafana |42| AWS-native, simple setup | CloudWatch Metrics |43| Multi-cloud, enterprise | Datadog or New Relic |44| OpenTelemetry-first | Prometheus with OTLP receiver |4546### Logging Stack4748| Scenario | Recommended Solution |49|----------|---------------------|50| Kubernetes, cost-sensitive | Loki + Grafana |51| AWS-native | CloudWatch Logs |52| High volume, complex queries | Elasticsearch (ELK) |53| Multi-cloud, managed | Datadog Logs or Splunk |5455### Tracing Stack5657| Scenario | Recommended Solution |58|----------|---------------------|59| Kubernetes, open-source | Jaeger or Tempo |60| AWS-native | X-Ray |61| Multi-cloud, correlated | Datadog APM |62| Vendor-agnostic | OpenTelemetry → any backend |6364## Kubernetes Observability Pattern6566```67┌─────────────────────────────────────────────────────┐68│ Applications │69│ (instrumented with OpenTelemetry SDK or auto-inst) │70└──────────────────────┬──────────────────────────────┘71 │ OTLP72 ▼73┌─────────────────────────────────────────────────────┐74│ OpenTelemetry Collector │75│ (receives, processes, exports telemetry) │76└───────┬─────────────────┬─────────────────┬─────────┘77 │ │ │78 ▼ ▼ ▼79 Prometheus Loki Tempo/Jaeger80 (metrics) (logs) (traces)81 │ │ │82 └────────────────┬┴─────────────────┘83 ▼84 Grafana85 (visualization)86```8788## SLO/SLI Framework8990### Key Metrics (RED Method for Services)9192| Metric | Description | Example SLI |93|--------|-------------|-------------|94| **R**ate | Requests per second | `rate(http_requests_total[5m])` |95| **E**rrors | Failed requests | `rate(http_requests_total{status=~"5.."}[5m])` |96| **D**uration | Latency distribution | `histogram_quantile(0.99, rate(http_request_duration_seconds_bucket[5m]))` |9798### Key Metrics (USE Method for Resources)99100| Metric | Description | Example |101|--------|-------------|---------|102| **U**tilization | % time resource is busy | CPU usage, memory usage |103| **S**aturation | Queue depth, waiting | Pod pending, connection pool |104| **E**rrors | Error count | OOM kills, disk errors |105106### SLO Definition Template107108```yaml109# Example: API availability SLO110slo:111 name: api-availability112 description: "API returns successful responses"113 sli:114 metric: |115 sum(rate(http_requests_total{status!~"5.."}[5m]))116 /117 sum(rate(http_requests_total[5m]))118 target: 99.9%119 window: 30d120 error_budget: 0.1% # ~43 minutes/month downtime allowed121```122123## Alerting Strategy124125### Alert Severity Levels126127| Severity | Response | Example |128|----------|----------|---------|129| **Critical** | Page on-call immediately | Service down, data loss risk |130| **Warning** | Investigate within hours | Error rate elevated, disk 80% |131| **Info** | Review during business hours | Deployment completed, scaling event |132133### Alert Quality Rules134135- **Actionable**: Every alert must have a clear response action136- **Relevant**: Alert on symptoms (user impact), not causes137- **Unique**: Avoid duplicate alerts for same incident138- **Timely**: Alert early enough to prevent impact139140### Alert Template (Prometheus)141142```yaml143groups:144 - name: api-alerts145 rules:146 - alert: HighErrorRate147 expr: |148 sum(rate(http_requests_total{status=~"5.."}[5m]))149 /150 sum(rate(http_requests_total[5m])) > 0.01151 for: 5m152 labels:153 severity: warning154 annotations:155 summary: "High error rate detected"156 description: "Error rate is {{ $value | humanizePercentage }} (threshold: 1%)"157 runbook_url: "https://runbooks.example.com/high-error-rate"158```159160## Structured Logging161162### Log Format (JSON)163164```json165{166 "timestamp": "2024-01-15T10:30:00Z",167 "level": "error",168 "message": "Payment processing failed",169 "service": "payment-api",170 "trace_id": "abc123",171 "span_id": "def456",172 "user_id": "user-789",173 "error": {174 "type": "PaymentGatewayError",175 "message": "Connection timeout"176 },177 "context": {178 "payment_id": "pay-123",179 "amount": 99.99180 }181}182```183184### Required Log Fields185186| Field | Purpose | Correlation |187|-------|---------|-------------|188| `timestamp` | When event occurred | Time-based queries |189| `level` | Severity (debug/info/warn/error) | Filtering |190| `service` | Source service name | Service filtering |191| `trace_id` | Distributed trace identifier | Cross-service correlation |192| `message` | Human-readable description | Search |193194## Process1951961. **Discover context** → Check existing observability setup (Prometheus, CloudWatch, etc.)1972. **Choose stack** → Use decision matrix based on environment and requirements1983. **Instrument apps** → Add OpenTelemetry SDK or auto-instrumentation1994. **Configure collection** → Set up collectors, exporters, and storage2005. **Define SLOs** → Establish SLIs, targets, and error budgets2016. **Create alerts** → Implement actionable alerts with runbooks2027. **Build dashboards** → Create service and infrastructure dashboards2038. **Document runbooks** → Write response procedures for each alert204205## Checklist206207- [ ] All services emit metrics, logs, and traces208- [ ] Trace IDs propagated across service boundaries209- [ ] Structured logging with consistent format (JSON)210- [ ] SLOs defined with error budgets211- [ ] Alerts are actionable with runbook links212- [ ] Dashboards show service health at a glance213- [ ] Log retention policy configured214- [ ] PII/sensitive data excluded from logs215- [ ] On-call rotation defined for critical alerts216217## Anti-Patterns218219| Don't | Do |220|-------|-----|221| Alert on every metric threshold | Alert on user-impacting symptoms |222| Log everything at DEBUG in production | Use appropriate log levels |223| Unstructured log messages | Structured JSON logging |224| Missing trace context | Propagate trace IDs across services |225| Dashboards with 50+ panels | Focused dashboards per service/domain |226| Alerts without runbooks | Every alert links to response procedure |227| Store logs indefinitely | Define retention based on compliance needs |228229## Related Skills230231- `tsh-implementing-kubernetes` - For K8s-native observability setup232- `tsh-implementing-ci-cd` - For pipeline observability integration233- `tsh-managing-secrets` - For secure credential storage for observability tools