You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Spring Boot 3与Micrometer中创建独立新Trace

独立新Trace的实现需求

在部分场景下,需要创建完全独立于父TraceContext或ObservationContext的新Trace。比如某API启动100个项的处理流程,每个项包含Feign调用、Spring Cloud Stream跳转等操作,Spring会自动基于API生成ObservationContext,导致API调用和所有项的处理共用同一个Trace。用Kibana排查错误时,按traceId过滤会返回所有项的日志,没法有效关联单个项的问题;spanId也因为频繁创建新Span,无法用来关联单个项的完整流程。

因此在特定可控场景下,希望为每个项创建独立的新Trace,即便丢失和原API调用的关联也可以接受。尝试过ObservationRegistry、ContextSnapshot等方式,但代码始终会继承父ObservationContext或TracingContext。

理想的执行流程是:

  • 备份当前链路上下文
  • 从零创建新的链路上下文
  • 使用新上下文执行目标代码
  • 恢复原上下文

之前用Sleuth可以轻松实现,但现在切换到新的观测框架后遇到了困难。期望实现一个runWithNewTrace方法,示例代码如下:

List<String> traceIds = new ArrayList<>();

Observation.createNotStarted("test.traceObservation", observationRegistry) // 1
        .contextualName("create test with Observation API") // 2
        .observe(() -> {
            traceIds.add(getCurrentTraceId());
            runWithNewTrace("test", () -> traceIds.add(getCurrentTraceId()));
            traceIds.add(getCurrentTraceId());
        });

String traceIdBefore = traceIds.get(0);
String traceIdThatShouldBeDifferent = traceIds.get(1);
String traceIdAfterThatShouldBeSameAsBefore = traceIds.get(2);

assertThat(traceIdThatShouldBeDifferent).isNotNull().isNotEqualTo("no-trace");
assertThat(traceIdBefore).isNotEqualTo(traceIdThatShouldBeDifferent);
assertThat(traceIdBefore).isEqualTo(traceIdAfterThatShouldBeSameAsBefore);

getCurrentTraceId方法的实现如下:

public String getCurrentTraceId() {
    Span currentSpan = tracer.currentSpan();
    if (currentSpan != null && currentSpan.context() != null) {
        return currentSpan.context().traceId();
    }
    return "no-trace";
}

内容的提问来源于stack exchange,提问作者Sébastien Nussbaumer

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.10 19:45:15