Trace context across a queue is carried, never ambient

A queue is a process boundary, so the trace context has to travel on the message or the trace ends at the dispatch.

// on dispatch: inject into the payload
$carrier = [];
TraceContextPropagator::getInstance()->inject($carrier);

dispatch(new SyncOrder($order, traceContext: $carrier));

// in the worker: extract, and make it the parent
$context = TraceContextPropagator::getInstance()
    ->extract($this->traceContext);

$span = $tracer->spanBuilder('SyncOrder')
    ->setParent($context)
    ->startSpan();

The W3C traceparent format is the thing to carry rather than a bare id, because it includes the sampling decision — a trace sampled at the edge stays sampled through the worker. A middleware doing this for every job is the only version that survives, since a convention applied by hand is forgotten on the next job class.