ARTICLE DETAIL

资讯详情

深耕郑州网站建设与运营推广的一线实战洞察。

Envoy可观测性三件套落地指南:访问日志、指标监控与链路追踪

Envoy可观测性三件套落地指南:访问日志、指标监控与链路追踪 上个月处理了一个线上事故到现在印象还很深。入口网关集群的 5xx 突然上涨CPU、内存、连接数看着都正常但业务侧就是有请求打不通。更难受的是网关的访问日志没配格式规范指标只有机器层的CPU和内存链路追踪压根没接最后靠抓包手工看了一个下午才算定位。那次之后我把 Envoy 的可观测性从“能跑就行”彻底重构成了“三件套齐全”也就是日志、指标、链路追踪三件事同时落地。这篇内容就是那次重构的完整记录从格式设计、采集方案、告警阈值到链路打通都有适合正在做网关、服务网格或者 Sidecar 接入的运维和开发同学参考。1. 先理清楚 Envoy 的可观测性到底在观测什么很多人一上来就急着配 Prometheus、搞 Jaeger结果发现告警不准、链路不全最后变成一堆数据躺在那里没人看。问题的根源在于没有先想清楚每种数据回答什么问题以及数据从哪来、在哪配置、能不能动态更新。1.1 三种数据各回答什么问题Envoy 的数据面会产出三种核心观测数据访问日志、统计指标、分布式链路追踪。它们的定位分别对应三个问题访问日志回答“某个具体请求发生了什么”。谁的请求、来了哪个域名、被路由到哪个集群、选中了哪台上游、返回什么状态码、耗时多少、有没有触发重试或熔断。关键时候它是最细颗粒度的证据。指标回答“整体趋势如何”。请求量、错误率、延迟分位数、活跃连接数、熔断器是否打开、健康检查是否在失败。它能告诉你系统正在变好还是变坏是告警的主要数据源。链路追踪回答“请求的全链路视图”。从入口网关到内部服务的调用路径每一跳的耗时分布哪个环节最慢哪些调用是失败的。它能把多个组件的日志串成一条线。用生活化的类比日志像每个航班的起降记录指标像飞机仪表盘上的油量、高度、速度链路追踪像一张完整航线图。做可观测性就是要同时有记录、有仪表、有地图缺一个都会在排障时抓瞎。1.2 数据从哪产生、在哪个配置文件里控制Envoy 的观测配置分散在三个位置这里必须搞清楚否则后面动配置的时候很容易触发重启事故。第一是 bootstrap 静态配置里面管的是stats_flush_interval、stats_config、stats_sinks以及tracing的 provider 定义。这部分一旦启动后就不能通过 xDS 动态修改改完必须重启实例。很多团队接链路追踪时没想清楚上线后要换 zipkin 为 otel collector结果发现要滚动重启整个网关这就是配置规划没到位。第二是 Listener 和 HttpConnectionManagerHCM这一层管理的是访问日志的开关和格式、请求 ID 的生成方式、采样率。这部分可以通过 LDS/RDS 动态下发所以日志格式、采样策略可以在运行期调整不需要重启线上调整成本低很多。第三是 Cluster 层管理的是熔断、异常驱逐这些参数它们本身不是观测配置但会直接影响指标的含义比如outlier_detection触发后的upstream_rq_5xx曲线会出现阶梯变化在看指标时要能识别出来。下面这张表是我自己整理的配置位置速查表排查问题的时候能少走不少弯路。观测能力配置位置是否可动态更新改动影响访问日志开关与格式Listener / HCM是通过LDS/RDS日志格式变化采集端需要同步指标 flush 间隔bootstrap stats_config否需重启影响 Prometheus 抓取精度指标 tag 拆分规则bootstrap stats_config否需重启影响 label 维度链路追踪 providerbootstrap tracing否需重启影响全链路接入协议链路采样率HCM tracing是通过LDS影响成本与数据量1.3 日志作用域这个概念先掰扯清楚热词里有个“日志作用域”在 Envoy 语境里其实有两条线索很多人混在一起理解。一条是 access log 的生效范围。访问日志可以在 HCM 上配置代表对所有进入该监听器的请求生效也可以在 VirtualHost 或 Route 级别覆盖代表只对特定域名、特定路径生效。实际业务里常见做法是全局配置一份完整格式然后对健康检查路径、静态资源路径单独加 filter 降噪。我见过有人为了排查某个接口直接在 Route 里加了一条 debug 级别的详细日志查完再移除这种用法就是作用域的实际价值。另一条是 Envoy 内部 error log 的日志级别。它通过--log-level启动参数控制也可以在运行时通过 admin 接口的/logging动态调整。注意这条日志讲的是 Envoy 自身的运行情况比如配置文件解析失败、上游连接异常、内部断言错误和业务访问日志是两套完全独立的东西。热词里提到“日志面板”通常就是指 admin 页面里的 logging 管理面板可以按 logger 名称逐项调整级别排查期间开到 debug结束必须调回不然磁盘会被内部日志打爆。这两条作用域在排障时有一个连贯的使用逻辑先看访问日志确认请求走到了哪里再看内部日志确认 Envoy 处理的哪个环节出了问题最后用链路数据串起来。顺序反了容易陷入“一直在看日志却不知道在看什么”的状态。2. 访问日志落地格式、采样与采集访问日志是排障的第一现场。很多团队刚开始接入 Envoy 时根本不配 access log或者用默认的 CLF 格式扔到 stdout等人去 grep。这种做法在小流量下勉强能用流量一起来就是灾难。这块的完整落地包括格式设计、采样策略、磁盘保护、采集链路四个部分。2.1 日志格式设计从 CLF 到 JSONEnvoy 默认不输出访问日志要在 HCM 里显式配置。最简单的写法是用默认的 CLF 格式但我不推荐任何人直接用默认格式它适合人眼看不适合机器解析字段多了以后还会漏字段。我的习惯是从第一天就用 JSON 格式每一个字段都是明确的 key采集端解析、检索、告警都能直接复用。下面是一个可用的 JSON access log 配置放在 HCM 的http_filters前后都可以字段按需要增删access_log: - name: envoy.access_loggers.file typed_config: type: type.googleapis.com/envoy.extensions.access_loggers.file.v3.FileAccessLog path: /var/log/envoy/access.log log_format: json_format: start_time: %START_TIME% req_method: %REQ(:METHOD)% req_path: %REQ(X-ENVOY-ORIGINAL-PATH?:PATH)% req_host: %REQ(:AUTHORITY)% req_user_agent: %REQ(USER-AGENT)% upstream_host: %UPSTREAM_HOST% upstream_cluster: %UPSTREAM_CLUSTER% response_code: %RESPONSE_CODE% response_code_details: %RESPONSE_CODE_DETAILS% duration_ms: %DURATION% bytes_sent: %RESPONSE_BYTES_SIZE% bytes_received: %REQUEST_BODY_BYTES% trace_id: %REQ(X-REQUEST-ID)% route_name: %ROUTE_NAME% upstream_response_time: %RESPONSE_DURATION%有两个字段我想特别强调。%UPSTREAM_HOST%一定要保留线上 5xx 如果集中在一台上游靠这个字段就能立刻锁定目标机器。%RESPONSE_CODE_DETAILS%是 Envoy 自己生成的状态码说明比如via_upstream、upstream_reset_before_response_started、local_rate_limit比裸看状态码有价值得多能直接告诉你这个 4xx/5xx 到底是业务返回的还是网络层重置的。格式定了以后下一步就该考虑降噪。访问日志会记录所有请求包括健康检查、探针、静态资源。我的建议是加一个过滤条件只记录需要关心的请求。比如下面的配置只记录非健康检查且状态码不小于 400 的请求配合采样参数使用效果更好access_log: - name: envoy.access_loggers.file typed_config: type: type.googleapis.com/envoy.extensions.access_loggers.file.v3.FileAccessLog path: /var/log/envoy/access.log log_format: json_format: response_code: %RESPONSE_CODE% req_path: %REQ(:PATH)% upstream_cluster: %UPSTREAM_CLUSTER% duration_ms: %DURATION% filter: status_code_filter: comparison: op: GE value: default_value: 4002.2 采样与磁盘保护日志是成本不是越多越好有人觉得日志越全越好这个想法在 Envoy 这里要吃大亏。访问日志单条 JSON 大约 300 字节左右如果是 1000 QPS 的入口网关一天就是 300 × 1000 × 86400约 25GB。这个量级在排障时基本没法直接 grep在存储侧也是不小的成本。所以我强烈建议给访问日志加采样。Envoy 的 access_log 支持sampled参数写在 access_log 条目上0.01 表示只记录 1% 的请求。实际操作中我会按两个维度分策略错误请求永远全量采样正常请求按比例采样。比如先在全局配置sampled: 0.1再用 status_code_filter 保证错误请求一定会被记录因为 filter 是在采样之后进行过滤的这个细节要自己测一下不同版本行为有差异我的经验是 v1.26 中采样后再过滤会出现“错误请求也被采样掉”的情况所以更稳妥的做法是配置两条 access_log一条全量但不落盘一条采样后落盘。看起来浪费配置但换来的是错误请求一条不漏。磁盘保护是另一个容易忽略的点。Envoy 的 file access logger 本身不负责日志轮转需要靠外部 logrotate 或容器化平台的日志轮转机制处理。我在生产环境用的是独立路径/var/log/envoy/配合 logrotate按天切割、保留 7 天。这里要提醒一句不要把 access.log 直接写到根分区或和系统日志混在一起日志膨胀会把整个磁盘打满最后连 ssh 都登不上去。2.3 Filebeat 采集与解析过滤、状态与常见坑日志写进了文件下一步就是采集。我没有用 Envoy 自带的 gRPC access log serviceALS直接推到 Kafka主要原因是团队已经有一套基于 Elasticsearch 的日志平台Filebeat 是最成熟稳定的一条链路不需要额外改 Envoy 配置。Filebeat 采集配置的核心是filestream输入注意 8.x 已经不建议用老的log输入了filestream 对文件轮转和位置跟踪做得更好。一个可用的配置filebeat.inputs: - type: filestream id: envoy-access-log paths: - /var/log/envoy/access.log parsers: - ndjson: target: add_error_key: true message_key: req_path fields: log_source: envoy_access fields_under_root: true output.elasticsearch: hosts: [es01:9200] index: envoy-access-%{yyyy.MM.dd}用ndjsonparser 可以自动把 JSON 每一行拆开成独立字段fields_under_root把自定义的log_source提升到根级方便后续按来源过滤。这里有一个很容易翻车的点Filebeat 解析失败时默认会丢弃有问题的行配置add_error_key: true可以保留错误标记排查格式变更时能很快看出来。Filebeat 的 offset 状态也是一个常见的坑。它把已读位置存在data/registry/filebeat/log.json里如果容器被重建但状态目录没持久化Filebeat 会从文件头重新读取导致日志重复入库。反过来如果文件被轮转但状态没跟上也可能漏日志。我在 K8s 里会把 Filebeat 的 data 目录做成 emptyDir 以外的持久化卷避免频繁重复。2.4 内部日志的运维admin 接口和级别控制Envoy 自身的错误日志和访问日志一定要区分看待。内部日志通过--log-level info控制运行期可以在 admin 接口上用POST /logging?leveldebug调整。admin 接口默认监听 9901 端口我在生成环境会把它绑定到内网地址加一层访问控制绝不直接暴露公网。在生产排查时内部日志级别通常保持 info 就够了。只有在定位配置热更新问题、上游连接异常这类场景下才临时调到 debug。调完之后记得切回来否则可能一个小时产生几百 MB 的 debug 日志。热词里有“日志分析”落到 Envoy 场景最实用的习惯是定期看一眼/logging面板下有没有 error 级别的持续输出这些往往预示着配置错误或连接池异常比业务指标更能提前暴露隐患。3. 指标监控与告警阈值从 stats 到 Prometheus日志解决了个案指标解决趋势。Envoy 自带的 stats 体系非常成熟但第一次接触的人会被它的字段数量吓到。一个什么都没做的网关光/stats输出的指标就有几千行。这些指标不是都要盯关键是理解模型、会接、会定阈值。3.1 stats 模型先过一遍Envoy 的 stats 有三种基础类型Counter 是单调递增计数适合统计总请求量、总错误量Gauge 是可变数值适合统计当前活跃连接数Histogram 是分位数统计适合统计延迟。Prometheus 接入后Counter 会变成_totalHistogram 会展开成多个_bucket和_sum、_count。指标命名一般以cluster.、listener.、http.开头。比如cluster.ratings.upstream_rq_5xx是 ratings 集群的 5xx 响应数listener.ingress_http.downstream_cx_active是入口监听器当前的活跃连接数。我这里提醒一个必改的配置stats_config里要打开use_all_listener_tags否则多个 listener 的指标会被合并端口标签会丢失排障时根本分不清是哪个入口在报错。还有一个参数是stats_flush_interval默认 5 秒。Prometheus 抓取时如果抓取间隔大于 flush 间隔会漏掉一部分中间峰值。我的经验是把stats_flush_interval设为 5sPrometheusscrape_interval也设为 5s两者匹配否则会出现明明 QPS 在涨但曲线是平的这种怪象。3.2 Prometheus 接入方式两种路径都讲Prometheus 接入 Envoy 有两种主流方式。第一种是用 admin 端点/stats/prometheusPrometheus 直接抓取。这种最简单但要小心 admin 端口的暴露风险。第二种是新建一个内部 listener 专门暴露 metrics。我在生产上更推荐第二种虽然配置多几行但可以把抓取链路和 admin 管理面分离。一个精简的内部 listener 方式static_resources: listeners: - name: envoy_metrics_listener address: socket_address: address: 0.0.0.0 port_value: 9901 filter_chains: - filters: - name: envoy.filters.network.http_connection_manager typed_config: type: type.googleapis.com/envoy.extensions.filters.network.http_connection_manager.v3.HttpConnectionManager stat_prefix: metrics route_config: name: local_route virtual_hosts: - name: admin domains: [*] routes: - match: prefix: /stats/prometheus route: cluster: prometheus_stats http_filters: - name: envoy.filters.http.router clusters: - name: prometheus_stats connect_timeout: 0.25s type: static load_assignment: cluster_name: prometheus_stats endpoints: - lb_endpoints: - endpoint: address: socket_address: address: 127.0.0.1 port_value: 9901Prometheus 侧的抓取配置scrape_configs: - job_name: envoy metrics_path: /stats/prometheus scrape_interval: 5s static_configs: - targets: [envoy-metrics:9901] labels: component: ingress-gateway注意这里的静态集群其实还是把请求转发到 admin 的/stats/prometheus但通过独立的 listener 收口后就不需要把 admin 端口暴露给 Prometheus 了网络策略也可以收敛到一条。3.3 必盯指标与阈值经验值指标不是全采就完事关键是要给核心指标定告警阈值。我自己整理了一套最小清单按优先级分三档。第一档是业务健康类直接决定是否被 pager指标含义经验阈值cluster.*.upstream_rq_5xx / cluster.*.upstream_rq_total5xx 错误率连续 5 分钟 1% 告警 5% 高优cluster.*.upstream_rq_timeP99上游服务延迟分位数按业务基线超过基线 P99 的 2 倍告警cluster.*.upstream_rq_retry / cluster.*.upstream_rq_total重试率重试率 10% 且持续 5 分钟告警cluster.*.upstream_cx_active活跃连接数增长速率 基线 2 倍告警listener.*.downstream_cx_active入口活跃连接数增长速率异常告警第二档是容量饱和类不直接报错但预示着即将出问题指标含义经验阈值cluster.*.upstream_cx_overflow连接池溢出次数出现即关注配合熔断器检查cluster.*.lb_healthy_panic进入 panic 模式出现即高优告警cluster.*.circuit_breakers.*.remaining熔断器剩余容量低于 20% 告警cluster.*.health_check.*.failure健康检查失败数持续失败告警第三档是资源类一般是机器或容器层监控但 Envoy 自身的server.*指标也要带一个server.live是否在存活server.uptime是否被频繁重启阈值不能光用固定值。我在实践中感受最深的是固定阈值在小流量集群上极度不友好流量低时任何波动都是成倍的。所以我的方案是告警表达式里尽量用“比值基线”的组合比如sum(rate(envoy_cluster_upstream_rq_5xx[5m])) / sum(rate(envoy_cluster_upstream_rq_total[5m])) 0.01延迟 P99 的表达式histogram_quantile(0.99, sum(rate(envoy_cluster_upstream_rq_time_bucket[5m])) by (le) ) 0.5这里的0.5秒是示例值真实要根据业务接口压测结果来定。而且要注意不同接口的延迟差异很大聚合到一个表达式里会导致误报生产上建议按 Route 或 Cluster 拆分。3.4 指标口径与告警风暴几个容易翻车的地方告警规则写完不代表就能躺平。我踩过几个比较深的坑每次都是线上告警风暴后总结出来的。第一个坑是 label 变化导致告警断裂。Envoy 集群重命名后所有以cluster.名字开头的指标 label 都会变化旧的告警规则会因为找不到指标而变成无数据。所以集群命名规范必须提前定死比如业务线-服务-环境上线后禁止改名。第二个坑是 histogram 桶的精度。Prometheus 的histogram_quantile是基于 bucket 估算的如果 Envoy 上报的 bucket 边界不适合你的业务延迟范围P99 会严重失真。比如业务延迟大部分在 20ms 左右但 bucket 在 100ms 以下只有一个点算出来的 P99 可能直接跳到 100ms。需要根据业务延迟分布调整 bucket 边界。第三个坑是告警太多等于没有告警。刚配完的那一周我收到了上百条告警通知全是各种细碎指标的抖动。后来把所有观察类告警全部降级成 warning只有 pager 级别的保留错误率、可用性、容量三类。这样处理之后告警反而被重视了。4. 链路追踪把请求串起来看日志和指标能定位“哪里出了问题”但回答不了“为什么慢”。链路追踪的作用是把一次请求经过的每个组件串起来看清每一跳的耗时和状态。Envoy 是数据面的第一跳也是最后一跳它在链路追踪里的角色很特殊。4.1 Envoy 在 trace 里的角色是什么很多人以为接入了 Envoy 就自动有了应用全链路追踪这是个误解。Envoy 本身不做业务埋点它做的是三件事生成或透传 trace 上下文、生成入口的 server span 和上游调用的 client span、在 span 上记录结果信息。应用服务如果没接 SDK链路到服务内部就会断掉Envoy 只能看到“请求到了我这转给了某台机器花了多少毫秒”看不到业务代码内部的调用过程。所以落地链路追踪的时候要跟应用团队约定入口网关由 Envoy 负责打 span下游服务接入 zipkin/otel 的 SDK 并透传 trace header。没有这个约定后期排查链路断裂会非常痛。我见过最典型的场景是运维把 Envoy 的 trace 配好后开发反馈说“链路还是断的”最后查下来是应用框架把 b3 header 给过滤掉了。4.2 tracing provider 配置示例与采样策略Envoy 的 tracing provider 是在 bootstrap 里静态配置的这点和日志、指标都不同改 provider 必须重启实例。我用的是 zipkin 协议对接 Jaeger配置如下注意不同小版本字段名会有差别这是 1.26 左右的写法tracing: http: name: envoy.tracers.zipkin typed_config: type: type.googleapis.com/envoy.config.trace.v3.ZipkinConfig collector_cluster: zipkin collector_endpoint: /api/v2/spans collector_endpoint_version: HTTP_JSON shared_span_context: false在 HCM 里还要加采样率。注意 HCM 的 tracing 配置是可以动态更新的所以采样率可以随时调整tracing: random_sampling: percent: 1采样率怎么定要看成本和需求的平衡。全链路 100% 采样带来的存储成本可能比日志还高尤其 QPS 大的网关。我的经验是入口 1% 采样就足够保障可用性类排查了如果某次线上事故需要针对特定用户、特定接口抓取全量链路可以临时调到 100%排查完再调回去。这里有一个体系设计的概念就是头部采样和尾部采样Envoy 只能做头部采样也就是在请求入口就决定采不采样真正理想的方案是配合链路后端做尾部采样先全量接收再按需保留异常链路但成本会高一个量级。小团队不必一上来就上尾部采样。4.3 用 trace_id 把日志、指标、链路串成一个闭环链路追踪最大的价值不是看那张拓扑图而是让日志可以围绕一次请求组织起来。Envoy 会为每个请求生成x-request-id配置 zipkin 后还会生成 traceId。我在访问日志里专门留了trace_id字段取的是%REQ(X-REQUEST-ID)%。这样整个排障路径就是闭环的先从 Prometheus 上看到某条路由的 5xx 上涨。进 Jaeger 按 service 和时间段找到异常 trace。拿到 traceId 后去 ES 里搜访问日志看到 Envoy 记录的response_code、upstream_host、duration_ms。如果请求走到了下游拿同一个 traceId 去下游服务的日志平台查应用日志。这个闭环做好之后排障时间可以从小时级降到分钟级。实际落地时有个小技巧Elasticsearch 里给trace_id字段建 keyword 索引否则精确搜索会退化成全文本搜索慢得没法用。还有一个经验是日志里不光记 traceId最好把upstream_host也记下来。因为 Envoy 会重试请求到不同的上游单看一份日志可能看不出哪台机器有问题但结合 trace 就可以确认某次重试是不是打到了同一条不健康的链路上。4.4 常见链路断链原因先查这几个地方链路断链是接入后最普遍的问题我整理了一个排查顺序照着检查基本能覆盖 80% 的场景。第一查协议头。Envoy 用的 zipkin 传播头是 b3全称x-b3-traceid、x-b3-spanid、x-b3-parentspanid、x-b3-sampled。应用 SDK 是否读取和透传了这些头是链路能不能连续的第一前提。有的框架默认会清洗未知 header需要显式放行。第二查采样一致性。如果入口 Envoy 采样率是 1%但下游服务自己的采样率是 100%就会出现 traceId 一样的 span 只有一部分的情况。反过来入口采了但下游没采链路也会断。最好全局统一一套采样配置或者用服务端尾部采样。第三查 span 的 parentId。进入 Jaeger 后如果一个 trace 里有多个根 span说明客户端和服务端没有共享上下文通常是因为shared_span_context配置不一致或者应用端自己起了新的 root span。我在配置 Envoy 时用shared_span_context: false是为了避免冲突但这个字段要结合下游 SDK 行为一起确定。第四查版本兼容。zipkin v1 和 v2 的 span 格式有差异Jaeger 的默认端口虽然是 9411但不同版本支持的 endpoint 不同。如果配置里写的是/api/v1/spans而 Jaeger 只收 v2链路会显示“服务在线但无数据”。5. 实战中那些绕不开的坑三段数据体系都落地之后还有一堆运维层面的坑单独拿出来分享。这些坑不是文档里会告诉你的但几乎每个团队都会踩。5.1 日志没写出来的排查路径环境配好发现日志文件永远是空的首先检查 HCM 里有没有真的挂上 access_log。很多人是在旧版本配置里写的access_log_path升级到 v3 API 后这个字段已经废弃配置直接静默失效。其次检查文件路径的权限。Envoy 进程在容器里通常以非 root 用户运行如果挂载的日志目录权限是 755 而目录属主是 root会写失败。我的做法是在镜像里预先创建/var/log/envoy并chown给 envoy 用户或者直接写到 stdout 由容器运行时接管。第三个原因是 filter 过滤太狠。我见过有人把status_code_filter配成了只记录 500结果排查 400 问题时日志里什么都没有。回答“为什么没日志”之前先问自己在 filter 里写了什么。5.2 指标为空的排查方法/stats/prometheus能打开但 Prometheus 里看到up是 1target 却拿不到数据这类问题通常和 flush 间隔、tag 配置有关。如果指标页面能打开但只有envoy_server_*少数几个指标大概率是 admin 端口权限或路径重定向的问题。还有一个容易被忽略的点cluster_name里带有特殊字符时Envoy 生成的 metrics name 会出现转义比如.变成_。如果 Prometheus 规则里写的是原始 cluster 名会匹配不上。解决方法是先在/stats/prometheus页面上搜一下实际的 metrics 名字再写规则。5.3 日志重复、乱序、延迟Filebeat 重复读日志我刚才提到了 registry 状态的持久化问题。还有一个更隐蔽的场景logrotate 把旧文件改名后Filebeat 的 filestream 输入如果没有正确处理close_inactive和ignore_older会在文件轮转瞬间产生重复读取或丢失。我在轮转配置里会保证create 0644 envoy envoy让 Filebeat 对 old 文件和新文件都有明确的 inode 跟踪。日志乱序则要区分接收端还是发送端的问题。Envoy 写文件是有序的但 Filebeat 多线程输出到 ES 时可能出现乱序。如果需要严格排序单条日志里一定要带%START_TIME%时间字段ES 侧用时间字段排序而不是依赖摄入时间。5.4 一个速查表备查把上面这些经验汇总成一张速查表贴在团队 wiki 里很有用现象可能原因排查动作access.log 为空HCM 未配置 access_log 或配置了旧字段检查配置中的access_log是否存在access.log 写入失败目录权限不足ls -l /var/log/envoy调整属主Filebeat 重复入库registry 状态丢失检查 Filebeat data 目录持久化Prometheus 指标缺失cluster 名特殊字符或 tag 未拆分在 /stats/prometheus 里搜实际名称告警无数据label 变化导致旧规则失效确认 cluster 名称和 namespace 标签链路全断应用未透传 b3 header检查应用框架的 header 白名单链路部分断采样率不一致或 span 根节点多个统一采样率检查 shared_span_contexttraceId 和日志对不上日志里取错了 header 字段确认%REQ(X-REQUEST-ID)%与 trace 工具的实际值这套速查表是当时踩坑后整理的现在每次 Envoy 升级或者团队新增成员都会先过一遍这些场景。可观测性的价值不在配置本身而在于这些配置能不能在你需要的时候最快地把真相带到你面前。我自己最大的体会是可观测性不是一次性工程而是一个持续演进的基础设施。先保证日志和指标可用再逐步把链路、告警、采样策略调优不要试图第一天就做到完美那是永远等不到的。先从一份规范的 JSON 访问日志、一套能响的告警开始剩下的坑等踩到了再填。
返回列表