From 34234294bbb10585fba73d6932e432283e818de7 Mon Sep 17 00:00:00 2001 From: Matt Pavlovich Date: Tue, 4 Aug 2026 08:52:37 -0500 Subject: [PATCH] [#2434] Avoid per-command MDC add+remove in TransportConnection.service --- .../apache/activemq/broker/TransportConnection.java | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) diff --git a/activemq-broker/src/main/java/org/apache/activemq/broker/TransportConnection.java b/activemq-broker/src/main/java/org/apache/activemq/broker/TransportConnection.java index 26a14c8cfef..40b7d32a824 100644 --- a/activemq-broker/src/main/java/org/apache/activemq/broker/TransportConnection.java +++ b/activemq-broker/src/main/java/org/apache/activemq/broker/TransportConnection.java @@ -128,6 +128,8 @@ public class TransportConnection implements Connection, Task, CommandVisitor { private final Transport transport; private MessageAuthorizationPolicy messageAuthorizationPolicy; private WireFormatInfo wireFormatInfo; + // Cached connector URI for the MDC tag; connector.getUri() is stable once started. + private String connectorUriString = "unset"; // Used to do async dispatch.. this should perhaps be pushed down into the // transport layer.. private boolean inServiceException; @@ -329,7 +331,14 @@ public void serviceException(Throwable e) { @Override public Response service(Command command) { - MDC.put("activemq.connector", connector.getUri().toString()); + // MDC entries are copy-on-write maps in log4j2 — a put per command is a + // full thread-context map copy per message. Put only when this thread's + // tag actually changes and leave it sticky between commands (same + // lifecycle-scoped pattern as the activemq.broker MDC entry), so the + // steady-state per-command cost is a single allocation-free MDC.get. + if (!connectorUriString.equals(MDC.get("activemq.connector"))) { + MDC.put("activemq.connector", connectorUriString); + } Response response = null; boolean responseRequired = command.isResponseRequired(); int commandId = command.getCommandId(); @@ -379,7 +388,6 @@ public Response service(Command command) { } context = null; } - MDC.remove("activemq.connector"); return response; } @@ -1132,6 +1140,7 @@ public void start() throws Exception { if (status.compareAndSet(NEW, STARTING)) { try { synchronized (this) { + connectorUriString = connector.getUri().toString(); if (taskRunnerFactory != null) { taskRunner = taskRunnerFactory.createTaskRunner(this, "ActiveMQ Connection Dispatcher: " + getRemoteAddress());