Troubleshooting Broken Traces and Context Propagation: OTCA practice questions
A trace stays connected only when every hop passes the current trace ID and span ID to the next one. Inside a process this travels in a Context object; across a network it is serialized into a carrier, usually HTTP headers, by a propagator.
By Ibrahim Yesilay · Published · Updated
Independent community practice, not affiliated with or endorsed by CNCF or The Linux Foundation.
What Troubleshooting Broken Traces and Context Propagation covers in OTCA
A trace stays connected only when every hop passes the current trace ID and span ID to the next one. Inside a process this travels in a Context object; across a network it is serialized into a carrier, usually HTTP headers, by a propagator. When a backend shows one request split into several unrelated traces, the cause is almost always a hop where that hand-off failed.
Start with configuration. The SDK environment variable OTEL_PROPAGATORS takes a comma-separated list, and its default is tracecontext,baggage, meaning W3C Trace Context plus W3C Baggage. Other known values are b3 for the B3 single-header format, b3multi for the B3 multi-header format, jaeger (deprecated), xray (third party) and ottrace (deprecated). Two services that speak different formats cannot read each other: a service that only extracts W3C headers sees nothing useful in B3 headers and starts a new trace. Listing several values builds a composite propagator that runs each one in order, which is the usual fix during a migration. A related B3 detail: the B3 propagator injects the single b3 header by default, so a legacy peer that only reads the X-B3 headers needs b3multi.
Remember also that the API itself uses no-op propagators until something configures them. Creating a TracerProvider and an exporter does not install a propagator on its own, so code-based setups must register one, while SDK auto-configuration reads OTEL_PROPAGATORS. Setting OTEL_SDK_DISABLED to true does not change propagators configured through OTEL_PROPAGATORS.
Extraction is designed to be forgiving. If a propagator cannot parse a value from the carrier, it must not throw and must not store a new value in the Context, so any earlier valid value is kept. A malformed incoming header therefore produces a span without a remote parent rather than an error, which hides the problem unless you inspect the raw headers.
In-process breaks are just as common. In Java the default ContextStorage keeps the current Context in a thread local, so work submitted to a plain executor runs on another thread with an empty Context and its spans become roots. The Context API offers wrappers for executors, runnables and suppliers that make the captured Context current before the task runs.
Infrastructure in the path matters too. The Propagators API expects instrumentation to extract and inject context on all remote calls, so any hop that rebuilds a request without injecting or forwarding the headers ends the trace there. Protocols without a metadata field need the context injected by hand and removed again on the receiving side before the payload is processed. On the other side, the context propagation docs suggest ignoring or sanitizing incoming context from untrusted external callers, and avoiding sensitive data in outgoing baggage.
Finally, baggage is often misread as a broken pipeline. Baggage entries are propagated next to the trace context, but they are a separate key-value store and do not become span, metric or log attributes until code, or a Baggage Span Processor in languages that ship one, copies them.
Key points
- OTEL_PROPAGATORS defaults to tracecontext,baggage and accepts a comma-separated list that becomes a composite propagator.
- Services using different formats, such as B3 and W3C, start separate traces unless both formats are configured.
- The API uses no-op propagators until propagation is explicitly configured.
- A propagator that cannot parse incoming headers must not throw and leaves the Context unchanged.
- Baggage is propagated automatically but is not copied into span attributes unless code or a Baggage Span Processor does it.
Three sample questions
8 OTCA questions on Troubleshooting Broken Traces and Context Propagation, 8 with explanations. How practice works
Question 1
traceparent headers with the sampled flag set, which inflates tracing volume and mixes foreign trace IDs into your data. What do the OpenTelemetry and W3C guidance recommend?- A.Remove "tracecontext" from OTEL_PROPAGATORS on all internal services
- B.Ignore or sanitize context from untrusted callers, e.g. restart the trace
- C.Rely on the sampled flag, because W3C requires every receiver to honour it
- D.Move the trace ID into baggage so external callers cannot change it at all
Correct answer: B
Sources: OpenTelemetry docs: Context propagation, W3C Trace Context
Question 2
X-B3-*) context with legacy services. Which OTEL_PROPAGATORS value configures this?- A.w3c,baggage,zipkin
- B.traceparent,tracestate,b3
- C.tracecontext;baggage;b3-multi
- D.tracecontext,baggage,b3multi
Correct answer: D
Sources: OpenTelemetry spec: SDK environment variables, OpenTelemetry spec: Propagators API
Question 3
ExecutorService created with Executors.newFixedThreadPool(4). Spans created inside the submitted tasks show up as separate root spans instead of children of the request span. What explains this, and what fixes it?- A.Context is stored thread-locally by default; wrap the executor or task with Context.wrap
- B.No traceparent header is sent between threads, so each task needs a TextMapPropagator inject call first
- C.The tracer sampled the child spans out, which makes the backend show them as root spans
- D.OTEL_PROPAGATORS is unset, so in-process context cannot be shared across thread pools
Correct answer: A
Sources: OpenTelemetry docs: Java API (Context), OpenTelemetry spec: Context
Practice this topic
Focus mode keeps every question on Troubleshooting Broken Traces and Context Propagation until you leave it. 10 free guest answers, then a free account; no credit card.
Or open OTCA practice across all topics.
Sources
The explanation above was checked against these official documents.
- OpenTelemetry docs: Context propagation (checked 2026-10-28)
- OpenTelemetry spec: Propagators API (checked 2026-10-28)
- OpenTelemetry spec: SDK environment variables (checked 2026-10-28)
- OpenTelemetry docs: Baggage (checked 2026-10-28)
- OpenTelemetry docs: Java API (Context) (checked 2026-10-28)
Frequently asked questions
Why do spans created in a thread pool show up as root spans?
The current Context is stored per thread by default, so a task on a pool thread does not see the caller's span. Wrapping the executor or the task with the Context utilities makes the captured Context current when the task runs.
What is the difference between b3 and b3multi?
Both extract either B3 encoding, but b3 injects the single b3 header while b3multi injects the separate X-B3 headers.