--
You received this message because you are subscribed to the Google Groups "Quarkus Development mailing list" group.
To unsubscribe from this group and stop receiving emails from it, send an email to quarkus-dev...@googlegroups.com.
To view this discussion visit https://groups.google.com/d/msgid/quarkus-dev/CAL%3DE%3DjSLV6DQ5mfjgiERLsnjA1fgbN38X5JA-KDzHSxEn3%3DQ7w%40mail.gmail.com.
Unless I'm mistaken, the request context is only stored and propagated via the Vert.x context by APIs that propagate the Vert.x context.I don't think ManagedExecutor propagates the Vert.x context. Here, it uses MP-CP to propagate the CDI request context, via its ThreadContextProvider.If you don't have one for the session context, it won't be propagated.
Why does my custom scope work then? I don't have a ThreadContextProvider implemented for it.
Ok, I'm quite confused about CDI context propagation and I need help.This is what I got:* I'm not using smallrye context propagation
* I activate a session context using Arc.container().sessionContext()* I have a custom scope which I activate* The custom scope uses a io.quarkus.CurrentContext to hold activated context state* I'm running within Vertx (event bus)
This is what doesn't work:* I have a bean that spawns off a worker thread using an injected ManagedExecutor* Within the worker thread, the request context and my custom scope are propagated correctly and work* The session context does *NOT* work
--
To view this discussion visit https://groups.google.com/d/msgid/quarkus-dev/CALbocOkB-bG4rCsSjojzZHvGb%2B94m1bydLpts0eWP_%3DagxXqOw%40mail.gmail.com.
Ok, I figured it out, see below. What I do need answered though is, do I need to implement a ThreadContextProvider or is CurrentContext enough?* VertxCurrentContextFactory for CurrentContext remembers the key for each created CurrentContext [0]* At boot time, Arc creates the request and session CurrentContext* VertxRecorder VertxCurrentContextFactory .keys() and adds them to an ignore list [1]* The top vertx handler loops through ignore list and removes them from local data at runtime [2]* My custom CurrentContext is created lazily so it does not get added to the ignore list. So, my custom scope works, at least within a ManagedExecutor.I believe smallrye context propagation is on by default as I believe ArcContextProvider is being invoked. Without adding log statements to that class, I'm not sure how to find this out?
On Fri, Mar 27, 2026 at 10:14 AM William Burke <bbu...@redhat.com> wrote:Ok, I figured it out, see below. What I do need answered though is, do I need to implement a ThreadContextProvider or is CurrentContext enough?* VertxCurrentContextFactory for CurrentContext remembers the key for each created CurrentContext [0]* At boot time, Arc creates the request and session CurrentContext* VertxRecorder VertxCurrentContextFactory .keys() and adds them to an ignore list [1]* The top vertx handler loops through ignore list and removes them from local data at runtime [2]* My custom CurrentContext is created lazily so it does not get added to the ignore list. So, my custom scope works, at least within a ManagedExecutor.I believe smallrye context propagation is on by default as I believe ArcContextProvider is being invoked. Without adding log statements to that class, I'm not sure how to find this out?
I did a mvn dependency:tree and if you pull in quarkus-vertx, it pulls in quarkus-smallrye-context-propagation as a transitive dependency.So @Ladislav Thon if you saw the other email I wrote, the session context is not being propagated for websocket-next for the reasons above. a ThreadContextProvider needs to be written for it if you want it propagated. I'll test this out to make sure and let you know.
I believe ArC's contexts are propagated because the Vert.x duplicated `Context` is propagated; the `ArcContextProvider` plays no role in it. See https://github.com/quarkusio/quarkus/blob/main/extensions/arc/deployment/src/main/java/io/quarkus/arc/deployment/ArcProcessor.java#L762 -- in fact, it is disabled by default.
On Fri, 27 Mar 2026 at 15:39, Ladislav Thon <lad...@gmail.com> wrote:I believe ArC's contexts are propagated because the Vert.x duplicated `Context` is propagated; the `ArcContextProvider` plays no role in it. See https://github.com/quarkusio/quarkus/blob/main/extensions/arc/deployment/src/main/java/io/quarkus/arc/deployment/ArcProcessor.java#L762 -- in fact, it is disabled by default.I don't think that's true: https://github.com/quarkusio/quarkus/blob/main/extensions/arc/deployment/src/main/java/io/quarkus/arc/deployment/ArcContextPropagationConfig.java#L19This was there for Techempower because Sanne wanted a boost.
I think only Matej can say for certain, but my opinion is that for Vert.x threads, the CDI request context is indeed stored in the vertx context and we're not propagating/restoring it.For thread pools, like ManagedExecutor I think we do propagate the CDI request context using MP-CP because the underlying thread does not have a Vert.x request context.Also, I don't think Vert.x propagates its context from the event loop requests to the worker threads either. They would get separate contexts with separate values.
--Stéphane Épardaud
--
You received this message because you are subscribed to the Google Groups "Quarkus Development mailing list" group.
To unsubscribe from this group and stop receiving emails from it, send an email to quarkus-dev...@googlegroups.com.
To view this discussion visit https://groups.google.com/d/msgid/quarkus-dev/CAKU9E9vhqt-dqm9X_cJ6qnQPEooXVYF7EhCuBYVn53nhyaAXdw%40mail.gmail.com.
pá 27. 3. 2026 v 15:59 odesílatel Stephane Epardaud <stephane...@gmail.com> napsal:On Fri, 27 Mar 2026 at 15:39, Ladislav Thon <lad...@gmail.com> wrote:I believe ArC's contexts are propagated because the Vert.x duplicated `Context` is propagated; the `ArcContextProvider` plays no role in it. See https://github.com/quarkusio/quarkus/blob/main/extensions/arc/deployment/src/main/java/io/quarkus/arc/deployment/ArcProcessor.java#L762 -- in fact, it is disabled by default.I don't think that's true: https://github.com/quarkusio/quarkus/blob/main/extensions/arc/deployment/src/main/java/io/quarkus/arc/deployment/ArcContextPropagationConfig.java#L19This was there for Techempower because Sanne wanted a boost.OMG it is indeed enabled by default :-D My bad. But as Martin says, it should be a noop in most cases.
I think only Matej can say for certain, but my opinion is that for Vert.x threads, the CDI request context is indeed stored in the vertx context and we're not propagating/restoring it.For thread pools, like ManagedExecutor I think we do propagate the CDI request context using MP-CP because the underlying thread does not have a Vert.x request context.Also, I don't think Vert.x propagates its context from the event loop requests to the worker threads either. They would get separate contexts with separate values.I've looked into exactly this a few weeks ago and Vert.x does propagate the duplicated `Context` from an event loop to a worker thread and back. It is still entirely possible to submit a task to a Quarkus worker pool that doesn't have a Vert.x `Context` associated, in which case MP CP would get involved I think.
On Fri, Mar 27, 2026 at 11:47 AM Ladislav Thon <lad...@gmail.com> wrote:pá 27. 3. 2026 v 15:59 odesílatel Stephane Epardaud <stephane...@gmail.com> napsal:On Fri, 27 Mar 2026 at 15:39, Ladislav Thon <lad...@gmail.com> wrote:I believe ArC's contexts are propagated because the Vert.x duplicated `Context` is propagated; the `ArcContextProvider` plays no role in it. See https://github.com/quarkusio/quarkus/blob/main/extensions/arc/deployment/src/main/java/io/quarkus/arc/deployment/ArcProcessor.java#L762 -- in fact, it is disabled by default.I don't think that's true: https://github.com/quarkusio/quarkus/blob/main/extensions/arc/deployment/src/main/java/io/quarkus/arc/deployment/ArcContextPropagationConfig.java#L19This was there for Techempower because Sanne wanted a boost.OMG it is indeed enabled by default :-D My bad. But as Martin says, it should be a noop in most cases.So, I implemented and registered a ThreadContextProvider for the session context and my test example now works and the session context is propagated.Can you explain what you mean by "it should be a noop in most cases"?
I think only Matej can say for certain, but my opinion is that for Vert.x threads, the CDI request context is indeed stored in the vertx context and we're not propagating/restoring it.For thread pools, like ManagedExecutor I think we do propagate the CDI request context using MP-CP because the underlying thread does not have a Vert.x request context.Also, I don't think Vert.x propagates its context from the event loop requests to the worker threads either. They would get separate contexts with separate values.I've looked into exactly this a few weeks ago and Vert.x does propagate the duplicated `Context` from an event loop to a worker thread and back. It is still entirely possible to submit a task to a Quarkus worker pool that doesn't have a Vert.x `Context` associated, in which case MP CP would get involved I think.Without MC-CP there would be no propagation of the request context. See code links I sent in a earlier email response of why. I think you can register ignored Vertx context local data keys. If I find out how to do that, I bet if I ignore my custom scope key, that will also break things without a thread context provider.
--
You received this message because you are subscribed to the Google Groups "Quarkus Development mailing list" group.
To unsubscribe from this group and stop receiving emails from it, send an email to quarkus-dev...@googlegroups.com.
To view this discussion visit https://groups.google.com/d/msgid/quarkus-dev/CAL%3DE%3DjQbh86gTNyGdgeT%3D_-_HakU3dZ60fsMF9n5DJJ%2B9EmFiw%40mail.gmail.com.
Dne pá 27. 3. 2026 23:48 uživatel 'William Burke' via Quarkus Development mailing list <quark...@googlegroups.com> napsal:On Fri, Mar 27, 2026 at 11:47 AM Ladislav Thon <lad...@gmail.com> wrote:pá 27. 3. 2026 v 15:59 odesílatel Stephane Epardaud <stephane...@gmail.com> napsal:On Fri, 27 Mar 2026 at 15:39, Ladislav Thon <lad...@gmail.com> wrote:I believe ArC's contexts are propagated because the Vert.x duplicated `Context` is propagated; the `ArcContextProvider` plays no role in it. See https://github.com/quarkusio/quarkus/blob/main/extensions/arc/deployment/src/main/java/io/quarkus/arc/deployment/ArcProcessor.java#L762 -- in fact, it is disabled by default.I don't think that's true: https://github.com/quarkusio/quarkus/blob/main/extensions/arc/deployment/src/main/java/io/quarkus/arc/deployment/ArcContextPropagationConfig.java#L19This was there for Techempower because Sanne wanted a boost.OMG it is indeed enabled by default :-D My bad. But as Martin says, it should be a noop in most cases.So, I implemented and registered a ThreadContextProvider for the session context and my test example now works and the session context is propagated.Can you explain what you mean by "it should be a noop in most cases"?OK, you're right and I was wrong. It's been a looong time since I last saw `ArcContexrProvider`, so when I was writing "it should be a noop", I was thinking it accesses the `ThreadLocal` directly. It doesn't. So it does some work, but that work should not matter as long as you're always on threads that have a Vert.x `Context` associated.I don't know, maybe the `ManagedExecutor` interferes in that it doesn't propagate the Vert.x `Context`? I know that in a bare Vert.x application, the `Context` is propagated from the event loop thread to the worker thread and back, but I didn't try the various executors that exist in Quarkus yet.
In general, Quarkus currently relies on _two_ APIs to ensure contexts are propagated: MP CP and Vert.x duplicated `Context`. Some contexts use one, some use the other, ArC apparently uses both 🤯 (This is Spartaaaaa!) I'm not sure what to think of my attempt to solve the problem by introducing a third API...
@RequestScoped
public class MyRequest {
private String value = "";
public String get() {
return value;
}
public void set(String value) {
this.value = value;
}
}@Path("/")
public class MyResource {
@Inject
MyRequest request;
@Inject
io.vertx.core.Vertx vertx;
@Inject
io.vertx.mutiny.core.Vertx mutinyVertx;
@Inject
java.util.concurrent.ExecutorService executor;
@Inject
org.eclipse.microprofile.context.ManagedExecutor managedExecutor;
@GET
@Path("/vertx")
public Uni<String> vertx() {
request.set("foobar");
return Uni.createFrom().emitter(em -> {
vertx.executeBlocking(() -> {
Log.info("Vert.x: " + request.get());
em.complete("Vert.x");
return null;
});
});
}
@GET
@Path("/mutiny-vertx")
public Uni<String> mutinyVertx() {
request.set("foobar");
return mutinyVertx.executeBlocking(() -> {
Log.info("Mutiny Vert.x: " + request.get());
return "Mutiny Vert.x";
});
}
@GET
@Path("/executor")
public Uni<String> executor() {
request.set("foobar");
return Uni.createFrom().emitter(em -> {
executor.submit(() -> {
try {
Log.info("Executor: " + request.get());
} catch (Exception e) {
Log.error(e);
}
em.complete("Executor");
});
});
}
@GET
@Path("/managed-executor")
public Uni<String> managedExecutor() {
request.set("foobar");
return Uni.createFrom().emitter(em -> {
managedExecutor.submit(() -> {
try {
Log.info("Managed Executor: " + request.get());
} catch (Exception e) {
Log.error(e);
}
em.complete("Managed Executor");
});
});
}
}
@WebSocket(path = "/ws")
public class MyEndpoint {
@Inject
MyRequest request;
@Inject
MySession session;
@Inject
io.vertx.core.Vertx vertx;
@Inject
io.vertx.mutiny.core.Vertx mutinyVertx;
@Inject
java.util.concurrent.ExecutorService executor;
@Inject
org.eclipse.microprofile.context.ManagedExecutor managedExecutor;
@OnTextMessage
public Uni<String> vertx(String message) {
request.set("foobar");
session.set("quuuux");
return Uni.createFrom().emitter(em -> {
vertx.executeBlocking(() -> {
Log.info("Vert.x: " + request.get());
Log.info("Vert.x: " + session.get());
em.complete("Vert.x");
return null;
});
});
}
public Uni<String> mutinyVertx(String message) {
request.set("foobar");
session.set("quuuux");
return mutinyVertx.executeBlocking(() -> {
Log.info("Mutiny Vert.x: " + request.get());
Log.info("Mutiny Vert.x: " + session.get());
return "Mutiny Vert.x";
});
}
public Uni<String> executor(String message) {
request.set("foobar");
session.set("quuuux");
return Uni.createFrom().emitter(em -> {
executor.submit(() -> {
try {
Log.info("Executor: " + request.get());
} catch (Exception e) {
Log.error(e);
}
try {
Log.info("Executor: " + session.get());
} catch (Exception e) {
Log.error(e);
}
em.complete("Executor");
});
});
}
public Uni<String> managedExecutor(String message) {
request.set("foobar");
session.set("quuuux");
return Uni.createFrom().emitter(em -> {
managedExecutor.submit(() -> {
try {
Log.info("Managed Executor: " + request.get());
} catch (Exception e) {
Log.error(e);
}
try {
Log.info("Managed Executor: " + session.get());
} catch (Exception e) {
Log.error(e);
}
em.complete("Managed Executor");
});
});
}
}
--
You received this message because you are subscribed to the Google Groups "Quarkus Development mailing list" group.
To unsubscribe from this group and stop receiving emails from it, send an email to quarkus-dev...@googlegroups.com.
To view this discussion visit https://groups.google.com/d/msgid/quarkus-dev/CAL%3DE%3DjRRNqzNsLB3%2Bb7fgWTxE0Lga%3DzLJ-NtLwX6SJP5mTOErQ%40mail.gmail.com.
@GET
@Path("/vertx")
public Uni<String> vertx() {
request.set("foobar");
Vertx.currentContext().putLocal("my-id", "bazqux");
return Uni.createFrom().emitter(em -> {
vertx.executeBlocking(() -> {
Log.info("Vert.x: " + request.get());
Log.info("Vert.x: " + Vertx.currentContext().getLocal("my-id"));
em.complete("Vert.x");
return null;
});
});
}
On 3/30/26 09:00, Ladislav Thon wrote:
> It turns out the Vert.x duplicated `Context` /is/ propagated through the
> `ExecutorService` and `ManagedExecutor`, like Bill suspected, and the
> CDI contexts are stripped from that. This makes absolutely zero sense to
> me. Can anyone explain?
If I remember correctly it was introduced here
https://github.com/quarkusio/quarkus/pull/29036 to fix the problem
described in this issue
https://github.com/quarkusio/quarkus/issues/29017#issuecomment-1301992058.
I don't remember the details but maybe Clement (in CC) remembers more.
- the `ArcContextProvider` only propagates the request context, not the session context (this honestly feels like a bug)
On Sat, Mar 28, 2026 at 10:27 AM Ladislav Thon <lad...@gmail.com> wrote:- the `ArcContextProvider` only propagates the request context, not the session context (this honestly feels like a bug)IMO this is a bug. I was going to submit a PR to arc for it.