一、为什么 Kubernetes 需要可观测性

在传统的单体应用架构中,排查问题往往只需要 SSH 到服务器,查看几台机器的日志即可。但在 Kubernetes 集群中,情况发生了根本性变化:容器是短暂的(ephemeral),Pod 随时可能被调度和重建,服务通过网络调用形成复杂的依赖链。当故障发生时,仅靠"登录服务器看日志"完全行不通。

可观测性(Observability)不同于传统的监控(Monitoring)。监控告诉你系统是否出了问题,而可观测性告诉你系统为什么出了问题。根据 Google SRE 团队的实践数据,一个成熟的可观测性体系可以将故障平均恢复时间(MTTR)从小时级降低到分钟级。

Kubernetes 可观测性面临的核心挑战包括:

  • 动态性:Pod IP 随时变化,容器随时启停业
  • 分布式:一次用户请求可能经过十几个微服务
  • 多维度:需要从指标、日志、追踪多个视角还原问题全貌
  • 规模性:大规模集群每天产生TB级可观测性数据

二、可观测性三大支柱详解

2.1 指标(Metrics)

指标是数值型的时间序列数据,用于回答"系统当前状态如何"这类问题。指标的核心优势是可以高效存储和聚合计算,适合告警和趋势分析。

Kubernetes 指标分类:

  • 基础设施指标:节点 CPU、内存、磁盘、网络使用率
  • 编排层指标:Pod 调度状态、Deployment 副本数、HPA 伸缩事件
  • 应用指标:QPS、请求延迟、错误率、JVM GC 时间
  • 业务指标:订单量、活跃用户数、支付成功率

RED 方法(适用于微服务):Rate(请求速率)、Errors(错误率)、Duration(请求耗时)。这三个指标是微服务健康度的最小充分集合。

USE 方法(适用于资源监控):Utilization(使用率)、Saturation(饱和度)、Errors(错误数)。这三个维度可以覆盖几乎所有基础设施资源的监控需求。

2.2 日志(Logs)

日志是离散的事件记录,记录了系统中发生的每一件事。与指标的聚合特性不同,日志保留了完整的上下文信息,是事后排查问题的关键证据。

Kubernetes 日志层级:

  • 节点级日志:kubelet、container runtime、kube-proxy 的日志,通过 journald 管理
  • 集群级日志:API Server 审计日志、Scheduler 决策日志、Controller 事件
  • 应用级日志:业务程序的 stdout/stderr 输出,由容器运行时采集

日志的最佳实践是输出结构化 JSON 而非纯文本,这样日志系统可以基于字段建立索引查询。例如:

{"ts":"2026-09-20T10:15:30Z","level":"error","trace_id":"abc123","msg":"database connection timeout","service":"order-api","timeout_ms":5000}

2.3 分布式追踪(Distributed Tracing)

分布式追踪回答的问题是:一个请求在系统中经历了什么。它将一次用户请求的所有下游调用串联起来,形成一棵调用链(Trace),每个环节是一个 Span。

Trace 的关键概念:

  • Trace ID:全局唯一标识,贯穿整条调用链
  • Span:一个工作单元(如一次数据库查询、一次 HTTP 调用)
  • Baggage:随调用链传递的键值对,可用于业务上下文传播
  • 采样策略:全量采集对性能有影响,需要合理采样(头部采样/尾部采样)

在 Kubernetes 中,由于服务间调用通常通过 Service 名称进行,Instrumentation 库需要与服务发现集成才能正确记录服务拓扑关系。

三、Kubernetes 可观测性技术栈选型

3.1 Prometheus + Grafana:指标监控的事实标准

Prometheus 是 CNCF 毕业项目,已成为云原生指标监控的事实标准。其核心设计包括:

  • Pull 模型:主动拉取(Pull)而非被动推送,更贴近"监控者"角色
  • PromQL:强大的多维数据查询语言,支持聚合、预测、告警规则
  • Service Discovery:自动发现 Kubernetes 中的 Pod、Service、Node 作为监控目标

Grafana 提供可视化 Dashboard,与 Prometheus 数据源无缝对接。社区已有大量 Kubernetes 监控模板可供直接使用。

3.2 Loki + Promtail:轻量级日志方案

Loki 是 Grafana 实验室推出的日志聚合系统,设计理念是"不索引内容,只索引标签"。相比 Elasticsearch,Loki 的存储成本更低,查询语法与 PromQL 一脉相承(LogQL)。

Promtail 作为日志采集 Agent,通过类似 Prometheus 的服务发现机制自动获取 Pod 标签作为日志标签,实现"指标与日志的无缝关联"——在 Grafana 中可以从指标图表直接下钻到对应时间段的日志。

3.3 OpenTelemetry + Jaeger:统一追踪方案

OpenTelemetry(OTel)是 CNCF 的分布式追踪标准,合并了 OpenTracing 和 OpenCensus 两个项目。它提供了:

  • 统一的 API 规范,与具体实现解耦
  • 自动 Instrumentation(Java Agent、自动注入)
  • Collector 作为数据中转层,支持灵活的数据路由和批处理

Jaeger 是 Uber 开源的分布式追踪后端,支持 Cassandra 和 Elasticsearch 作为存储。它与 OpenTelemetry 完全兼容,可以通过 OTLP 协议接收追踪数据。

四、实战:搭建完整可观测性体系

4.1 部署 Prometheus Stack

使用 kube-prometheus-stack(原 prometheus-operator)一键部署 Prometheus、Grafana、AlertManager 及 Kubernetes 监控规则:

helm repo add prometheus-community https://prometheus-community.github.io/helm-charts
helm repo update
helm install monitoring prometheus-community/kube-prometheus-stack \
  --namespace monitoring --create-namespace \
  --set grafana.adminPassword=admin123 \
  --set prometheus.prometheusSpec.retention=30d

部署完成后,Prometheus 已经通过 ServiceMonitor 和 PodMonitor 自动发现集群中的监控目标。

4.2 部署 Loki 日志栈

helm repo add grafana https://grafana.github.io/helm-charts
helm install loki grafana/loki-stack \
  --namespace monitoring \
  --set promtail.enabled=true \
  --set loki.persistence.enabled=true \
  --set loki.persistence.size=50Gi

部署完成后,在 Grafana 中添加 Loki 数据源,URL 为 http://loki:3100,即可使用 LogQL 查询日志。

4.3 部署 OpenTelemetry Collector 和 Jaeger

# 部署 Jaeger
helm repo add jaegertracing https://jaegertracing.github.io/helm-charts
helm install jaeger jaegertracing/jaeger \
  --namespace monitoring \
  --set provisionDataStore.cassandra=false \
  --set storage.type=elasticsearch \
  --set storage.elasticsearch.host=http://elasticsearch:9200

# 部署 OpenTelemetry Collector
helm install otel-collector open-telemetry/opentelemetry-collector \
  --namespace monitoring \
  --set mode=deployment \
  --set config.receivers.otlp.protocols.grpc.endpoint=0.0.0.0:4317

4.4 应用接入实例(以 Java 微服务为例)

方式一:使用 Java Agent 自动注入(最简方案)

在 Kubernetes Pod 中添加 Annotation 和 Java Agent:

apiVersion: apps/v1
kind: Deployment
spec:
  template:
    metadata:
      annotations:
        sidecar.opentelemetry.io/inject: "true"
        instrumentation.opentelemetry.io/inject-java: "true"
    spec:
      containers:
      - name: my-service
        env:
        - name: OTEL_EXPORTER_OTLP_ENDPOINT
          value: "http://otel-collector.monitoring:4317"
        - name: OTEL_SERVICE_NAME
          value: "order-service"

方式二:代码级手动埋点(更灵活)

import io.opentelemetry.api.trace.Span;
import io.opentelemetry.api.trace.Tracer;

Tracer tracer = openTelemetry.getTracer("order-service");

Span span = tracer.spanBuilder("processOrder").startSpan();
try (Scope scope = span.makeCurrent()) {
    span.setAttribute("order.id", orderId);
    // 业务逻辑
    validateOrder(order);
    processPayment(order);
    updateInventory(order);
} catch (Exception e) {
    span.setStatus(StatusCode.ERROR, e.getMessage());
    span.recordException(e);
    throw e;
} finally {
    span.end();
}

五、生产环境最佳实践

5.1 告警设计原则

告警应关注 Symptoms 而非 Causes。例如,不要设置"CPU 使用率超过 80%就告警",而应该设置"服务 P99 延迟超过 500ms 持续 5 分钟告警"。前者告诉你可能有问题,后者告诉你有确定问题。

告警分级策略:

  • P0(立即响应):服务完全不可用、核心接口错误率 > 5%
  • P1(30分钟内响应):服务降级、非核心接口异常
  • P2(工作时间内处理):容量预警、磁盘使用超过 80%
  • P3(次日处理):信息性通知、构建失败

5.2 采样策略优化

在高流量场景下,全量采集追踪数据会带来显著的性能开销和存储压力。推荐策略:

  • 头部采样(Head-based):随机按比例采样,简单但对偶发错误覆盖不足
  • 尾部采样(Tail-based):先全量收集再筛选(保留错误和慢请求),效果最佳但实现复杂
  • 间隔采样:错误请求100%保留,正常请求按比例采样

5.3 指标与日志的关联设计

在 Grafana 中实现"从指标下钻到日志"的关键是:使用一致的标签体系。Prometheus 的 label 和 Loki 的 label 应包含相同的维度(如 namespace、pod、service),这样 Grafana 可以通过模板变量实现联动查询。

5.4 成本控制

100个节点的 Kubernetes 集群,每天可产生:

  • 指标数据:约 50-100GB(取决于采集频率和目标数)
  • 日志数据:约 200GB-2TB(取决于业务日志量)
  • 追踪数据:约 10-100GB(取决于采样率)

控制成本的关键手段:合理设置采集频率(指标15s足够)、日志分级存储(热数据3天、温数据7天、冷数据30天)、指标降采样(超过7天的数据按5分钟聚合)。

六、常见问题排查速查表

问题现象排查方向关键指标/日志
Pod 频繁重启检查 OOMKilled、健康检查配置container_restart_count、kubelet 日志
服务响应慢链路追踪定位瓶颈P99 Duration、Trace 中耗时 Span
CPU 飙高检查应用 GC、线程池container_cpu_usage_seconds、GC 日志
OOM Kill内存泄漏分析container_memory_usage_bytes、JVM Heap Dump
服务调用失败检查网络策略、Endpoint 状态http_requests_total{status~"5.."}、network policies
磁盘满日志或临时文件清理node_filesystem_available_bytes、Audit 日志大小

七、未来趋势

Kubernetes 可观测性领域正在向以下方向演进:

  • eBPF 技术:无需修改应用即可采集网络、系统调用级别的观测数据,代表项目 Cilium Hubble、Pixie
  • AI 驱动的智能分析:利用机器学习算法自动识别异常模式、关联告警风暴、预测容量瓶颈
  • OpenTelemetry 统一标准:逐步实现指标、日志、追踪三种数据类型的统一收集和处理
  • Continuous Profiling:持续性能分析(如 Pyroscope、Parca),补充追踪数据的不足

八、总结

构建 Kubernetes 可观测性体系不是一蹴而就的工程,建议按以下顺序逐步推进:

  1. 第一步:部署 Prometheus + Grafana,覆盖基础设施监控和核心 RED 指标
  2. 第二步:接入日志系统(Loki 或 ELK),实现日志集中管理和快速查询
  3. 第三步:接入分布式追踪(Jaeger + OpenTelemetry),实现调用链可视化
  4. 第四步:完善告警体系,建立 On-Call 流程和 Runbook
  5. 第五步:引入 AI 智能分析和 eBPF 技术,向自主运维演进

记住:可观测性的终极目标不是收集数据,而是在最短的时间内回答"发生了什么"以及"为什么发生"。工具只是手段,围绕业务场景设计合理的观测策略才是核心。

点赞(0) 打赏

评论列表 共有 0 条评论

暂无评论
立即
投稿

微信公众账号

微信扫一扫加关注

发表
评论
返回
顶部