先把当时的情况摆出来。网关、应用、模型调用三段日志都在,但应用侧打印的 trace_id 是空字符串,按 id 检索只能查到网关那一段,排查时只能靠时间戳猜。

真正麻烦的地方在于,几个原因的现象几乎一样。网关注入的请求头名字与应用读取的不一致。也可能是异步任务里上下文没传递,取到的是空值。

还有一种情况,SDK 自动埋点另起了一个 trace。另外,日志格式里字段缺失时打印空而不是继承上游。

先看网关实际下发的请求头名字

python -c "print({'x-trace-id':'abc123','traceparent':'00-abc123-...'})"

再往下在入口中间件统一读取并写入上下文

python -c "import uuid;print(uuid.uuid4().hex)"

异步任务提交时显式带上 trace_id

python worker.py --propagate-trace

末了用同一个 id 在三段日志里各查一次

python logq.py --trace abc123 --sources gw,app,llm

怎么算真的好了,看的是同一批现象。同一个 id 能串起网关、应用、模型三段日志,缺 id 时由入口生成并回写响应头,异步链路也能带上。

trace_id 断在异步边界最常见,入口生成一次、全链路透传,比在每个组件里各自生成可靠得多。同一份配置在测试环境跑通,不代表线上没事,两边的默认值经常不一样。

作者 9823189