diff --git a/src/workerd/api/container.c++ b/src/workerd/api/container.c++ index 4e1fb2eebb2..b40ea9941d4 100644 --- a/src/workerd/api/container.c++ +++ b/src/workerd/api/container.c++ @@ -211,6 +211,9 @@ void Container::start(jsg::Lock& js, jsg::Optional maybeOptions) StartupOptions options = kj::mv(maybeOptions).orDefault({}); auto req = rpcClient->startRequest(); + KJ_IF_SOME(spanContext, IoContext::current().getCurrentTraceSpan().toSpanContext()) { + spanContext.toCapnp(req.initSpanContext()); + } KJ_IF_SOME(entrypoint, options.entrypoint) { auto list = req.initEntrypoint(entrypoint.size()); for (auto i: kj::indices(entrypoint)) { @@ -462,6 +465,9 @@ jsg::Promise> Container::exec( auto params = req.initParams(); params.setCombinedOutput(combinedOutput); + KJ_IF_SOME(spanContext, ioContext.getCurrentTraceSpan().toSpanContext()) { + spanContext.toCapnp(params.initSpanContext()); + } // Some basic validation... KJ_IF_SOME(cwd, options.cwd) { @@ -740,6 +746,9 @@ class Container::TcpPortWorkerInterface final: public WorkerInterface { // A lot of the following is copied from // capnp::HttpOverCapnpFactory::KjToCapnpHttpServiceAdapter::connect(). auto req = port.connectRequest(capnp::MessageSize{4, 1}); + KJ_IF_SOME(spanContext, IoContext::current().getCurrentTraceSpan().toSpanContext()) { + spanContext.toCapnp(req.initSpanContext()); + } auto downPipe = kj::newOneWayPipe(); req.setDown(byteStreamFactory.kjToCapnp(kj::mv(downPipe.out))); auto pipeline = req.send(); diff --git a/src/workerd/io/BUILD.bazel b/src/workerd/io/BUILD.bazel index 43ca28d5262..a07d896bbbe 100644 --- a/src/workerd/io/BUILD.bazel +++ b/src/workerd/io/BUILD.bazel @@ -401,6 +401,7 @@ wd_capnp_library( src = "container.capnp", deps = [ ":compatibility-date_capnp", + ":worker-interface_capnp", "@capnp-cpp//src/capnp/compat:byte-stream_capnp", ], ) diff --git a/src/workerd/io/container.capnp b/src/workerd/io/container.capnp index 7fdf41005af..b600310e67c 100644 --- a/src/workerd/io/container.capnp +++ b/src/workerd/io/container.capnp @@ -6,6 +6,7 @@ $Cxx.allowCancellation; using import "/capnp/compat/byte-stream.capnp".ByteStream; using CompatibilityFlags = import "/workerd/io/compatibility-date.capnp".CompatibilityFlags; +using SpanContext = import "/workerd/io/worker-interface.capnp".SpanContext; interface Container @0x9aaceefc06523bca { # RPC interface to talk to a container, for containers attached to Durable Objects. @@ -13,7 +14,7 @@ interface Container @0x9aaceefc06523bca { # When the actor shuts down, workerd will drop the `Container` capability, at which point # the container engine should implicitly destroy the container. - status @0 () -> (running :Bool); + status @0 (spanContext :SpanContext) -> (running :Bool); # Returns the container's current status. The runtime will always call this at DO startup. start @1 StartParams -> (); @@ -53,6 +54,8 @@ interface Container @0x9aaceefc06523bca { containerSnapshotId @7 :Text; # Id of the full container snapshot to restore before the container starts. + + spanContext @8 :SpanContext; } struct Label { @@ -122,6 +125,8 @@ interface Container @0x9aaceefc06523bca { combinedOutput @3 :Bool; # If true, stderr is combined into stdout. If stdout is not set, combined output is discarded. + + spanContext @4 :SpanContext; } struct Process { @@ -168,7 +173,7 @@ interface Container @0x9aaceefc06523bca { interface Port { # Represents a port to which connections can be made. - connect @0 (down :ByteStream) -> (up :ByteStream); + connect @0 (down :ByteStream, spanContext :SpanContext) -> (up :ByteStream); # Forms a raw socket connection to the port. # # Note that when the Durable Object application uses the HTTP-oriented APIs, workerd will diff --git a/src/workerd/io/worker.c++ b/src/workerd/io/worker.c++ index 2394e065b64..f3eb4a28dac 100644 --- a/src/workerd/io/worker.c++ +++ b/src/workerd/io/worker.c++ @@ -3917,7 +3917,11 @@ kj::Promise Worker::Actor::ensureConstructedImpl(IoContext& context, Actor // with starting the script, and also if we could save the status across hibernations. But // that would require some refactoring, and this RPC should (eventally) be local, so it's // not a huge deal. - auto status = co_await c.statusRequest(capnp::MessageSize{4, 0}).send(); + auto statusRequest = c.statusRequest(capnp::MessageSize{4, 0}); + KJ_IF_SOME(spanContext, context.getCurrentTraceSpan().toSpanContext()) { + spanContext.toCapnp(statusRequest.initSpanContext()); + } + auto status = co_await statusRequest.send(); containerRunning = status.getRunning(); }