AlinsRan commented on code in PR #12686: URL: https://github.com/apache/apisix/pull/12686#discussion_r2767337686
########## docs/zh/latest/plugins/opentelemetry.md: ########## @@ -152,37 +167,152 @@ curl "http://127.0.0.1:9080/anything" ```text 2024-02-18T17:14:03.825Z info ResourceSpans #0 -Resource SchemaURL: -Resource attributes: - -> telemetry.sdk.language: Str(lua) - -> telemetry.sdk.name: Str(opentelemetry-lua) - -> telemetry.sdk.version: Str(0.1.1) - -> hostname: Str(e34673e24631) - -> service.name: Str(APISIX) ScopeSpans #0 ScopeSpans SchemaURL: InstrumentationScope opentelemetry-lua Span #0 - Trace ID : fbd0a38d4ea4a128ff1a688197bc58b0 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 905f850f13e32bfb + ID : 5a3835b61110d942 + Name : http_router_match + Kind : Internal + Start time : 2025-10-24 06:58:04.430430976 +0000 UTC + End time : 2025-10-24 06:58:04.431542016 +0000 UTC + Status code : Unset + Status message : +Span #1 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 905f850f13e32bfb + ID : 4ab25e2b92f394e1 + Name : resolve_dns + Kind : Internal + Start time : 2025-10-24 06:58:04.432521984 +0000 UTC + End time : 2025-10-24 06:58:04.44903296 +0000 UTC + Status code : Unset + Status message : +Span #2 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 905f850f13e32bfb + ID : 3620c0f05dd2be4f + Name : apisix.phase.header_filter + Kind : Internal + Start time : 2025-10-24 06:58:06.960481024 +0000 UTC + End time : 2025-10-24 06:58:06.960510976 +0000 UTC + Status code : Unset + Status message : +Span #3 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 4c5f3476f62a7e8a + ID : a9bfad7bb6986e41 + Name : apisix.phase.body_filter + Kind : Internal + Start time : 2025-10-24 06:58:06.960579072 +0000 UTC + End time : 2025-10-24 06:58:06.96059008 +0000 UTC + Status code : Unset + Status message : +Span #4 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : b2994675df6baa83 + ID : 26705f9c47584a5b + Name : apisix.phase.delayed_body_filter.opentelemetry + Kind : Internal + Start time : 2025-10-24 06:58:06.960613888 +0000 UTC + End time : 2025-10-24 06:58:06.960687104 +0000 UTC + Status code : Unset + Status message : +Span #5 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 4c5f3476f62a7e8a + ID : b2994675df6baa83 + Name : apisix.phase.delayed_body_filter + Kind : Internal + Start time : 2025-10-24 06:58:06.96059904 +0000 UTC + End time : 2025-10-24 06:58:06.960692992 +0000 UTC + Status code : Unset + Status message : +Span #6 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 905f850f13e32bfb + ID : 4c5f3476f62a7e8a + Name : apisix.phase.body_filter + Kind : Server + Start time : 2025-10-24 06:58:06.96056704 +0000 UTC + End time : 2025-10-24 06:58:06.960698112 +0000 UTC + Status code : Unset + Status message : +Span #7 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 2024d73d32cbd81b + ID : 223c64fb691a24e8 + Name : apisix.phase.body_filter + Kind : Internal + Start time : 2025-10-24 06:58:06.961624064 +0000 UTC + End time : 2025-10-24 06:58:06.961635072 +0000 UTC + Status code : Unset + Status message : +Span #8 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : fd193dd24c618f60 + ID : 8729ad6e0d94a23b + Name : apisix.phase.delayed_body_filter.opentelemetry + Kind : Internal + Start time : 2025-10-24 06:58:06.961648896 +0000 UTC + End time : 1970-01-01 00:00:00 +0000 UTC + Status code : Unset + Status message : +Span #9 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 2024d73d32cbd81b + ID : fd193dd24c618f60 + Name : apisix.phase.delayed_body_filter + Kind : Internal + Start time : 2025-10-24 06:58:06.961641984 +0000 UTC + End time : 1970-01-01 00:00:00 +0000 UTC + Status code : Unset + Status message : +Span #10 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 905f850f13e32bfb + ID : 2024d73d32cbd81b + Name : apisix.phase.body_filter + Kind : Server + Start time : 2025-10-24 06:58:06.960980992 +0000 UTC + End time : 1970-01-01 00:00:00 +0000 UTC + Status code : Unset + Status message : +Span #11 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : cfb0b4603dc2e385 + ID : 905f850f13e32bfb + Name : apisix.phase.access + Kind : Server + Start time : 2025-10-24 06:58:04.427932928 +0000 UTC + End time : 1970-01-01 00:00:00 +0000 UTC + Status code : Unset + Status message : +Span #12 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a Parent ID : - ID : af3dc7642104748a - Name : GET /anything + ID : cfb0b4603dc2e385 + Name : GET /headers Kind : Server - Start time : 2024-02-18 17:14:03.763244032 +0000 UTC - End time : 2024-02-18 17:14:03.920229888 +0000 UTC + Start time : 2025-10-24 06:58:04.432427008 +0000 UTC + End time : 2025-10-24 06:58:06.962299904 +0000 UTC Status code : Unset Status message : Attributes: - -> net.host.name: Str(127.0.0.1) - -> http.method: Str(GET) - -> http.scheme: Str(http) - -> http.target: Str(/anything) - -> http.user_agent: Str(curl/7.64.1) - -> apisix.route_id: Str(otel-tracing-route) - -> apisix.route_name: Empty() - -> http.route: Str(/anything) - -> http.status_code: Int(200) -{"kind": "exporter", "data_type": "traces", "name": "debug"} + -> net.host.name: Str(127.0.0.1) + -> http.method: Str(GET) + -> http.scheme: Str(http) + -> http.target: Str(/headers) + -> http.user_agent: Str(curl/8.16.0) + -> apisix.route_id: Str(otel-tracing-route) + -> apisix.route_name: Empty() + -> http.route: Str(/headers) + -> http.status_code: Int(200) Review Comment: fixed. ########## docs/en/latest/plugins/opentelemetry.md: ########## @@ -153,37 +168,152 @@ In OpenTelemetry collector's log, you should see information similar to the foll ```text 2024-02-18T17:14:03.825Z info ResourceSpans #0 -Resource SchemaURL: -Resource attributes: - -> telemetry.sdk.language: Str(lua) - -> telemetry.sdk.name: Str(opentelemetry-lua) - -> telemetry.sdk.version: Str(0.1.1) - -> hostname: Str(e34673e24631) - -> service.name: Str(APISIX) ScopeSpans #0 ScopeSpans SchemaURL: InstrumentationScope opentelemetry-lua Span #0 - Trace ID : fbd0a38d4ea4a128ff1a688197bc58b0 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 905f850f13e32bfb + ID : 5a3835b61110d942 + Name : http_router_match + Kind : Internal + Start time : 2025-10-24 06:58:04.430430976 +0000 UTC + End time : 2025-10-24 06:58:04.431542016 +0000 UTC + Status code : Unset + Status message : +Span #1 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 905f850f13e32bfb + ID : 4ab25e2b92f394e1 + Name : resolve_dns + Kind : Internal + Start time : 2025-10-24 06:58:04.432521984 +0000 UTC + End time : 2025-10-24 06:58:04.44903296 +0000 UTC + Status code : Unset + Status message : +Span #2 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 905f850f13e32bfb + ID : 3620c0f05dd2be4f + Name : apisix.phase.header_filter + Kind : Internal + Start time : 2025-10-24 06:58:06.960481024 +0000 UTC + End time : 2025-10-24 06:58:06.960510976 +0000 UTC + Status code : Unset + Status message : +Span #3 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 4c5f3476f62a7e8a + ID : a9bfad7bb6986e41 + Name : apisix.phase.body_filter + Kind : Internal + Start time : 2025-10-24 06:58:06.960579072 +0000 UTC + End time : 2025-10-24 06:58:06.96059008 +0000 UTC + Status code : Unset + Status message : +Span #4 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : b2994675df6baa83 + ID : 26705f9c47584a5b + Name : apisix.phase.delayed_body_filter.opentelemetry + Kind : Internal + Start time : 2025-10-24 06:58:06.960613888 +0000 UTC + End time : 2025-10-24 06:58:06.960687104 +0000 UTC + Status code : Unset + Status message : +Span #5 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 4c5f3476f62a7e8a + ID : b2994675df6baa83 + Name : apisix.phase.delayed_body_filter + Kind : Internal + Start time : 2025-10-24 06:58:06.96059904 +0000 UTC + End time : 2025-10-24 06:58:06.960692992 +0000 UTC + Status code : Unset + Status message : +Span #6 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 905f850f13e32bfb + ID : 4c5f3476f62a7e8a + Name : apisix.phase.body_filter + Kind : Server + Start time : 2025-10-24 06:58:06.96056704 +0000 UTC + End time : 2025-10-24 06:58:06.960698112 +0000 UTC + Status code : Unset + Status message : +Span #7 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 2024d73d32cbd81b + ID : 223c64fb691a24e8 + Name : apisix.phase.body_filter + Kind : Internal + Start time : 2025-10-24 06:58:06.961624064 +0000 UTC + End time : 2025-10-24 06:58:06.961635072 +0000 UTC + Status code : Unset + Status message : +Span #8 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : fd193dd24c618f60 + ID : 8729ad6e0d94a23b + Name : apisix.phase.delayed_body_filter.opentelemetry + Kind : Internal + Start time : 2025-10-24 06:58:06.961648896 +0000 UTC + End time : 1970-01-01 00:00:00 +0000 UTC + Status code : Unset + Status message : +Span #9 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 2024d73d32cbd81b + ID : fd193dd24c618f60 + Name : apisix.phase.delayed_body_filter + Kind : Internal + Start time : 2025-10-24 06:58:06.961641984 +0000 UTC + End time : 1970-01-01 00:00:00 +0000 UTC + Status code : Unset + Status message : +Span #10 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : 905f850f13e32bfb + ID : 2024d73d32cbd81b + Name : apisix.phase.body_filter + Kind : Server + Start time : 2025-10-24 06:58:06.960980992 +0000 UTC + End time : 1970-01-01 00:00:00 +0000 UTC + Status code : Unset + Status message : +Span #11 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a + Parent ID : cfb0b4603dc2e385 + ID : 905f850f13e32bfb + Name : apisix.phase.access + Kind : Server + Start time : 2025-10-24 06:58:04.427932928 +0000 UTC + End time : 1970-01-01 00:00:00 +0000 UTC + Status code : Unset + Status message : +Span #12 + Trace ID : 95a1644afaaf65e1f0193b1f193b990a Parent ID : - ID : af3dc7642104748a - Name : GET /anything + ID : cfb0b4603dc2e385 + Name : GET /headers Kind : Server - Start time : 2024-02-18 17:14:03.763244032 +0000 UTC - End time : 2024-02-18 17:14:03.920229888 +0000 UTC + Start time : 2025-10-24 06:58:04.432427008 +0000 UTC + End time : 2025-10-24 06:58:06.962299904 +0000 UTC Status code : Unset Status message : Attributes: -> net.host.name: Str(127.0.0.1) -> http.method: Str(GET) -> http.scheme: Str(http) - -> http.target: Str(/anything) - -> http.user_agent: Str(curl/7.64.1) + -> http.target: Str(/headers) + -> http.user_agent: Str(curl/8.16.0) -> apisix.route_id: Str(otel-tracing-route) -> apisix.route_name: Empty() - -> http.route: Str(/anything) + -> http.route: Str(/headers) -> http.status_code: Int(200) Review Comment: fixed. ########## apisix/plugins/opentelemetry.lua: ########## @@ -376,49 +377,101 @@ function _M.rewrite(conf, api_ctx) ngx_var.opentelemetry_span_id = span_context.span_id end + if not ctx:span():is_recording() and ngx.ctx.tracing then + ngx.ctx.tracing.skip = true + end + api_ctx.otel_context_token = ctx:attach() -- inject trace context into the headers of upstream HTTP request trace_context_propagator:inject(ctx, ngx.req) end -function _M.delayed_body_filter(conf, api_ctx) - if api_ctx.otel_context_token and ngx.arg[2] then - local ctx = context:current() - ctx:detach(api_ctx.otel_context_token) - api_ctx.otel_context_token = nil +local function create_child_span(tracer, parent_span_ctx, spans, span_idx) + local span = spans[span_idx] + if not span or span.finished then + return + end + span.finished = true + local new_span_ctx, new_span = tracer:start(parent_span_ctx, span.name, + { + kind = span.kind, + attributes = span.attributes, + }) + new_span.start_time = span.start_time + + for _, idx in ipairs(span.child_ids or {}) do + create_child_span(tracer, new_span_ctx, spans, idx) + end + if span.status then + new_span:set_status(span.status.code, span.status.message) + end + new_span:finish(span.end_time) +end - -- get span from current context - local span = ctx:span() - local upstream_status = core.response.get_upstream_status(api_ctx) - if upstream_status and upstream_status >= 500 then - span:set_status(span_status.ERROR, - "upstream response status: " .. upstream_status) - end - span:set_attributes(attr.int("http.status_code", upstream_status)) +local function inject_core_spans(root_span_ctx, api_ctx, conf) + local tracing = api_ctx.ngx_ctx.tracing + if not tracing then + return + end - span:finish() + local span = root_span_ctx:span() + + local metadata = plugin.plugin_metadata(plugin_name) + local plugin_info = metadata.value + if span and not span:is_recording() then + return + end + local inject_conf = { + sampler = { + name = "always_on", + options = conf.sampler.options + }, + additional_attributes = conf.additional_attributes, + additional_header_prefix_attributes = conf.additional_header_prefix_attributes + } + local tracer, err = core.lrucache.plugin_ctx(lrucache, api_ctx, nil, + create_tracer_obj, inject_conf, plugin_info) + if not tracer then + core.log.error("failed to fetch tracer object: ", err) + return + end + + if #tracing.spans == 0 then + return + end + span.start_time = tracing.spans[1].start_time + for i, _ in ipairs(tracing.spans or {}) do + create_child_span(tracer, root_span_ctx, tracing.spans, i) end end --- body_filter maybe not called because of empty http body response --- so we need to check if the span has finished in log phase function _M.log(conf, api_ctx) if api_ctx.otel_context_token then -- ctx:detach() is not necessary, because of ctx is stored in ngx.ctx local upstream_status = core.response.get_upstream_status(api_ctx) -- get span from current context - local span = context:current():span() + local ctx = context:current() + local span = ctx:span() if upstream_status and upstream_status >= 500 then span:set_status(span_status.ERROR, "upstream response status: " .. upstream_status) end + inject_core_spans(ctx, api_ctx, conf) + span:set_attributes(attr.int("http.status_code", upstream_status)) Review Comment: fixed. -- This is an automated message from the Apache Git Service. To respond to the message, please log on to GitHub and use the URL above to go to the specific comment. To unsubscribe, e-mail: [email protected] For queries about this service, please contact Infrastructure at: [email protected]
