This is an automated email from the ASF dual-hosted git repository.

pcongiusti pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/camel.git

commit 04fece586e1baeecba6dfd98ab7182ed40768df8
Author: Pasquale Congiusti <[email protected]>
AuthorDate: Tue Sep 23 16:05:11 2025 +0200

    feat(components): Camel MDC
---
 bom/camel-bom/pom.xml                              |  5 ++
 catalog/camel-allcomponents/pom.xml                |  5 ++
 .../main/camel-main-configuration-metadata.json    |  1 +
 .../org/apache/camel/catalog/others.properties     |  1 +
 .../org/apache/camel/catalog/others/mdc.json       | 15 ++++
 components/camel-mdc/pom.xml                       | 63 +++++++++++++++
 .../META-INF/services/org/apache/camel/mdc-service |  2 +
 .../services/org/apache/camel/other.properties     |  7 ++
 .../camel-mdc/src/generated/resources/mdc.json     | 15 ++++
 components/camel-mdc/src/main/docs/mdc.adoc        | 10 +++
 .../main/java/org/apache/camel/mdc/MDCService.java | 89 ++++++++++++++++++++++
 .../camel-mdc/src/test/resources/log4j2.properties | 30 ++++++++
 components/pom.xml                                 |  1 +
 .../java/org/apache/camel/spi/CamelMDCService.java | 27 +++++++
 .../java/org/apache/camel/spi/LogListener.java     | 12 +++
 .../org/apache/camel/processor/LogProcessor.java   | 20 +++++
 .../main/MdcConfigurationPropertiesConfigurer.java | 48 ++++++++++++
 .../camel-main-configuration-metadata.json         |  1 +
 ...rg.apache.camel.main.MdcConfigurationProperties |  2 +
 core/camel-main/src/main/docs/main.adoc            |  9 +++
 .../org/apache/camel/main/BaseMainSupport.java     | 56 +++++++++++++-
 .../camel/main/MainConfigurationProperties.java    | 12 +++
 .../camel/main/MdcConfigurationProperties.java     | 57 ++++++++++++++
 .../camel/support/processor/CamelLogProcessor.java | 22 ++++++
 .../modules/others/examples/json/mdc.json          |  1 +
 docs/components/modules/others/nav.adoc            |  1 +
 docs/components/modules/others/pages/mdc.adoc      |  1 +
 parent/pom.xml                                     |  5 ++
 .../maven/packaging/PrepareCamelMainMojo.java      |  3 +
 29 files changed, 520 insertions(+), 1 deletion(-)

diff --git a/bom/camel-bom/pom.xml b/bom/camel-bom/pom.xml
index 7e3bf987964..fa912d0b1b2 100644
--- a/bom/camel-bom/pom.xml
+++ b/bom/camel-bom/pom.xml
@@ -1477,6 +1477,11 @@
         <artifactId>camel-master</artifactId>
         <version>4.15.0-SNAPSHOT</version>
       </dependency>
+      <dependency>
+        <groupId>org.apache.camel</groupId>
+        <artifactId>camel-mdc</artifactId>
+        <version>4.15.0-SNAPSHOT</version>
+      </dependency>
       <dependency>
         <groupId>org.apache.camel</groupId>
         <artifactId>camel-metrics</artifactId>
diff --git a/catalog/camel-allcomponents/pom.xml 
b/catalog/camel-allcomponents/pom.xml
index dbe1e7a85fd..2b96ba6ae96 100644
--- a/catalog/camel-allcomponents/pom.xml
+++ b/catalog/camel-allcomponents/pom.xml
@@ -1286,6 +1286,11 @@
             <artifactId>camel-master</artifactId>
             <version>${project.version}</version>
         </dependency>
+        <dependency>
+            <groupId>org.apache.camel</groupId>
+            <artifactId>camel-mdc</artifactId>
+            <version>${project.version}</version>
+        </dependency>
         <dependency>
             <groupId>org.apache.camel</groupId>
             <artifactId>camel-metrics</artifactId>
diff --git 
a/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/main/camel-main-configuration-metadata.json
 
b/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/main/camel-main-configuration-metadata.json
index bb1e632f40c..6dbbe63d36a 100644
--- 
a/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/main/camel-main-configuration-metadata.json
+++ 
b/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/main/camel-main-configuration-metadata.json
@@ -21,6 +21,7 @@
     { "name": "camel.opentelemetry", "description": "Camel OpenTelemetry 
configurations", "sourceType": 
"org.apache.camel.main.OtelConfigurationProperties" },
     { "name": "camel.opentelemetry2", "description": "Camel OpenTelemetry 2 
configurations", "sourceType": 
"org.apache.camel.main.Otel2ConfigurationProperties" },
     { "name": "camel.telemetryDev", "description": "Camel Telemetry Dev 
configurations", "sourceType": 
"org.apache.camel.main.TelemetryDevConfigurationProperties" },
+    { "name": "camel.mdc", "description": "Camel MDC configurations", 
"sourceType": "org.apache.camel.main.MdcConfigurationProperties" },
     { "name": "camel.metrics", "description": "Camel Micrometer Metrics 
configurations", "sourceType": 
"org.apache.camel.main.MetricsConfigurationProperties" },
     { "name": "camel.faulttolerance", "description": "Fault Tolerance EIP 
Circuit Breaker configurations", "sourceType": 
"org.apache.camel.main.FaultToleranceConfigurationProperties" },
     { "name": "camel.resilience4j", "description": "Resilience4j EIP Circuit 
Breaker configurations", "sourceType": 
"org.apache.camel.main.Resilience4jConfigurationProperties" },
diff --git 
a/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/others.properties
 
b/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/others.properties
index 39b1e80ca2e..bbd73f057a6 100644
--- 
a/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/others.properties
+++ 
b/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/others.properties
@@ -26,6 +26,7 @@ lra
 mail-microsoft-oauth
 main
 management
+mdc
 micrometer-observability
 micrometer-prometheus
 microprofile-config
diff --git 
a/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/others/mdc.json
 
b/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/others/mdc.json
new file mode 100644
index 00000000000..073d9a5633d
--- /dev/null
+++ 
b/catalog/camel-catalog/src/generated/resources/org/apache/camel/catalog/others/mdc.json
@@ -0,0 +1,15 @@
+{
+  "other": {
+    "kind": "other",
+    "name": "mdc",
+    "title": "Mdc",
+    "description": "Mapped Diagnostic Context component",
+    "deprecated": false,
+    "firstVersion": "4.15.0",
+    "label": "logging",
+    "supportLevel": "Preview",
+    "groupId": "org.apache.camel",
+    "artifactId": "camel-mdc",
+    "version": "4.15.0-SNAPSHOT"
+  }
+}
diff --git a/components/camel-mdc/pom.xml b/components/camel-mdc/pom.xml
new file mode 100644
index 00000000000..978c9d6892c
--- /dev/null
+++ b/components/camel-mdc/pom.xml
@@ -0,0 +1,63 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+
+    Licensed to the Apache Software Foundation (ASF) under one or more
+    contributor license agreements.  See the NOTICE file distributed with
+    this work for additional information regarding copyright ownership.
+    The ASF licenses this file to You under the Apache License, Version 2.0
+    (the "License"); you may not use this file except in compliance with
+    the License.  You may obtain a copy of the License at
+
+         http://www.apache.org/licenses/LICENSE-2.0
+
+    Unless required by applicable law or agreed to in writing, software
+    distributed under the License is distributed on an "AS IS" BASIS,
+    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+    See the License for the specific language governing permissions and
+    limitations under the License.
+
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0"; 
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"; 
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 
http://maven.apache.org/xsd/maven-4.0.0.xsd";>
+
+  <modelVersion>4.0.0</modelVersion>
+
+  <parent>
+    <groupId>org.apache.camel</groupId>
+    <artifactId>components</artifactId>
+    <version>4.15.0-SNAPSHOT</version>
+  </parent>
+
+  <properties>
+    <firstVersion>4.15.0</firstVersion>
+    <label>logging</label>
+    <supportLevel>Preview</supportLevel>
+  </properties>
+
+  <artifactId>camel-mdc</artifactId>
+  <packaging>jar</packaging>
+  <name>Camel :: MDC</name>
+  <description>Mapped Diagnostic Context component</description>
+
+  <dependencies>
+    <dependency>
+      <groupId>org.apache.camel</groupId>
+      <artifactId>camel-support</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.slf4j</groupId>
+      <artifactId>slf4j-api</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.apache.camel</groupId>
+      <artifactId>camel-test-spring-junit5</artifactId>
+      <scope>test</scope>
+    </dependency>
+    <dependency>
+      <groupId>org.mockito</groupId>
+      <artifactId>mockito-core</artifactId>
+      <version>${mockito-version}</version>
+      <scope>test</scope>
+    </dependency>
+
+  </dependencies>
+</project>
diff --git 
a/components/camel-mdc/src/generated/resources/META-INF/services/org/apache/camel/mdc-service
 
b/components/camel-mdc/src/generated/resources/META-INF/services/org/apache/camel/mdc-service
new file mode 100644
index 00000000000..cdc20a7cf74
--- /dev/null
+++ 
b/components/camel-mdc/src/generated/resources/META-INF/services/org/apache/camel/mdc-service
@@ -0,0 +1,2 @@
+# Generated by camel build tools - do NOT edit this file!
+class=org.apache.camel.mdc.MDCService
diff --git 
a/components/camel-mdc/src/generated/resources/META-INF/services/org/apache/camel/other.properties
 
b/components/camel-mdc/src/generated/resources/META-INF/services/org/apache/camel/other.properties
new file mode 100644
index 00000000000..2f66413827f
--- /dev/null
+++ 
b/components/camel-mdc/src/generated/resources/META-INF/services/org/apache/camel/other.properties
@@ -0,0 +1,7 @@
+# Generated by camel build tools - do NOT edit this file!
+name=mdc
+groupId=org.apache.camel
+artifactId=camel-mdc
+version=4.15.0-SNAPSHOT
+projectName=Camel :: MDC
+projectDescription=Mapped Diagnostic Context component
diff --git a/components/camel-mdc/src/generated/resources/mdc.json 
b/components/camel-mdc/src/generated/resources/mdc.json
new file mode 100644
index 00000000000..073d9a5633d
--- /dev/null
+++ b/components/camel-mdc/src/generated/resources/mdc.json
@@ -0,0 +1,15 @@
+{
+  "other": {
+    "kind": "other",
+    "name": "mdc",
+    "title": "Mdc",
+    "description": "Mapped Diagnostic Context component",
+    "deprecated": false,
+    "firstVersion": "4.15.0",
+    "label": "logging",
+    "supportLevel": "Preview",
+    "groupId": "org.apache.camel",
+    "artifactId": "camel-mdc",
+    "version": "4.15.0-SNAPSHOT"
+  }
+}
diff --git a/components/camel-mdc/src/main/docs/mdc.adoc 
b/components/camel-mdc/src/main/docs/mdc.adoc
new file mode 100644
index 00000000000..03ccd90ea33
--- /dev/null
+++ b/components/camel-mdc/src/main/docs/mdc.adoc
@@ -0,0 +1,10 @@
+= Mdc Component
+:doctitle: Mdc
+:shortname: mdc
+:artifactid: camel-mdc
+:description: Mapped Diagnostic Context component
+:since: 4.15
+:supportlevel: Preview
+:tabs-sync-option:
+
+*Since Camel {since}*
diff --git 
a/components/camel-mdc/src/main/java/org/apache/camel/mdc/MDCService.java 
b/components/camel-mdc/src/main/java/org/apache/camel/mdc/MDCService.java
new file mode 100644
index 00000000000..098230b11a0
--- /dev/null
+++ b/components/camel-mdc/src/main/java/org/apache/camel/mdc/MDCService.java
@@ -0,0 +1,89 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.camel.mdc;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.Exchange;
+import org.apache.camel.RuntimeCamelException;
+import org.apache.camel.spi.CamelLogger;
+import org.apache.camel.spi.CamelMDCService;
+import org.apache.camel.spi.LogListener;
+import org.apache.camel.spi.annotations.JdkService;
+import org.apache.camel.support.service.ServiceSupport;
+import org.apache.camel.util.ObjectHelper;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+import org.slf4j.MDC;
+
+@JdkService("mdc-service")
+public class MDCService extends ServiceSupport implements CamelMDCService {
+
+    private static final Logger LOG = 
LoggerFactory.getLogger(MDCService.class);
+
+    private CamelContext camelContext;
+
+    @Override
+    public CamelContext getCamelContext() {
+        return camelContext;
+    }
+
+    @Override
+    public void setCamelContext(CamelContext camelContext) {
+        this.camelContext = camelContext;
+    }
+
+    /**
+     * Registers this {@link MDCService} on the {@link CamelContext} if not 
already registered.
+     */
+    public void init(CamelContext camelContext) {
+        if (!camelContext.hasService(this)) {
+            try {
+                // start this service eager so we init before Camel is 
starting up
+                camelContext.addService(this, true, true);
+            } catch (Exception e) {
+                throw RuntimeCamelException.wrapRuntimeCamelException(e);
+            }
+        }
+    }
+
+    @Override
+    public void doInit() {
+        ObjectHelper.notNull(camelContext, "CamelContext", this);
+        camelContext.getCamelContextExtension().addLogListener(new 
TracingLogListener());
+    }
+
+    private final class TracingLogListener implements LogListener {
+
+        @Override
+        public String onLog(Exchange exchange, CamelLogger camelLogger, String 
message) {
+            try {
+                // MDC setting here
+                MDC.put("exchangeID", exchange.getExchangeId());
+            } catch (Exception t) {
+                // This exception is ignored
+                LOG.warn("MDC: failed to store MDC data. This exception is 
ignored.", t);
+            }
+            return message;
+        }
+
+        @Override
+        public void afterLog(Exchange exchange, CamelLogger camelLogger, 
String message) {
+            MDC.clear();
+        }
+    }
+
+}
diff --git a/components/camel-mdc/src/test/resources/log4j2.properties 
b/components/camel-mdc/src/test/resources/log4j2.properties
new file mode 100644
index 00000000000..c9d7df800c7
--- /dev/null
+++ b/components/camel-mdc/src/test/resources/log4j2.properties
@@ -0,0 +1,30 @@
+## ---------------------------------------------------------------------------
+## Licensed to the Apache Software Foundation (ASF) under one or more
+## contributor license agreements.  See the NOTICE file distributed with
+## this work for additional information regarding copyright ownership.
+## The ASF licenses this file to You under the Apache License, Version 2.0
+## (the "License"); you may not use this file except in compliance with
+## the License.  You may obtain a copy of the License at
+##
+##      http://www.apache.org/licenses/LICENSE-2.0
+##
+## Unless required by applicable law or agreed to in writing, software
+## distributed under the License is distributed on an "AS IS" BASIS,
+## WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+## See the License for the specific language governing permissions and
+## limitations under the License.
+## ---------------------------------------------------------------------------
+appender.console.type = Console
+appender.console.name = console
+appender.console.layout.type = PatternLayout
+appender.console.layout.pattern = %d [%-15.15t] %-5p %-30.30c{1} - %m%n
+
+appender.file.type = File
+appender.file.name = file
+appender.file.fileName = target/camel-telemetry-test.log
+appender.file.append = true
+appender.file.layout.type = PatternLayout
+appender.file.layout.pattern = %d [%-15.15t] %-5p %-30.30c{1} - %m%n
+
+rootLogger.level = INFO
+rootLogger.appenderRef.file.ref = file
diff --git a/components/pom.xml b/components/pom.xml
index 1b87350f836..b4b07ebb810 100644
--- a/components/pom.xml
+++ b/components/pom.xml
@@ -215,6 +215,7 @@
         <module>camel-mail</module>
         <module>camel-mail-microsoft-oauth</module>
         <module>camel-mapstruct</module>
+        <module>camel-mdc</module>
         <module>camel-metrics</module>
         <module>camel-micrometer</module>
         <module>camel-micrometer-observability</module>
diff --git 
a/core/camel-api/src/main/java/org/apache/camel/spi/CamelMDCService.java 
b/core/camel-api/src/main/java/org/apache/camel/spi/CamelMDCService.java
new file mode 100644
index 00000000000..25252052788
--- /dev/null
+++ b/core/camel-api/src/main/java/org/apache/camel/spi/CamelMDCService.java
@@ -0,0 +1,27 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.camel.spi;
+
+import org.apache.camel.CamelContextAware;
+import org.apache.camel.Service;
+
+/**
+ * A Camel MDC service is a factory for Mapped Diagnostic Context service.
+ */
+public interface CamelMDCService extends Service, CamelContextAware {
+
+}
diff --git a/core/camel-api/src/main/java/org/apache/camel/spi/LogListener.java 
b/core/camel-api/src/main/java/org/apache/camel/spi/LogListener.java
index 04a741265fa..ab726f2cbb2 100644
--- a/core/camel-api/src/main/java/org/apache/camel/spi/LogListener.java
+++ b/core/camel-api/src/main/java/org/apache/camel/spi/LogListener.java
@@ -38,4 +38,16 @@ public interface LogListener {
      */
     String onLog(Exchange exchange, CamelLogger camelLogger, String message);
 
+    /**
+     * Invoked right after Log component or Log EIP logs. The method can be 
used for cleaning up any transient
+     * information used during onLog execution.
+     *
+     * @param exchange    camel exchange
+     * @param camelLogger {@link CamelLogger}
+     * @param message     log message
+     */
+    default void afterLog(Exchange exchange, CamelLogger camelLogger, String 
message) {
+        // NO-OP
+    }
+
 }
diff --git 
a/core/camel-core-processor/src/main/java/org/apache/camel/processor/LogProcessor.java
 
b/core/camel-core-processor/src/main/java/org/apache/camel/processor/LogProcessor.java
index 0491209964e..5babd94ca6a 100644
--- 
a/core/camel-core-processor/src/main/java/org/apache/camel/processor/LogProcessor.java
+++ 
b/core/camel-core-processor/src/main/java/org/apache/camel/processor/LogProcessor.java
@@ -78,6 +78,9 @@ public class LogProcessor extends BaseProcessorSupport 
implements Traceable, IdA
                     msg = fireListeners(exchange, msg);
                 }
                 logger.doLog(msg);
+                if (listeners != null && !listeners.isEmpty()) {
+                    closeListeners(exchange, msg);
+                }
             } catch (Exception e) {
                 exchange.setException(e);
             }
@@ -105,6 +108,23 @@ public class LogProcessor extends BaseProcessorSupport 
implements Traceable, IdA
         return message;
     }
 
+    private void closeListeners(Exchange exchange, String message) {
+        for (LogListener listener : listeners) {
+            if (listener == null) {
+                continue;
+            }
+            try {
+                listener.afterLog(exchange, logger, message);
+            } catch (Exception t) {
+                LOG.warn("Ignoring an exception: {} thrown by: {} caused by: 
{}", t.getClass().getName(),
+                        listener.getClass().getName(), t.getMessage());
+                if (LOG.isDebugEnabled()) {
+                    LOG.debug("", t);
+                }
+            }
+        }
+    }
+
     @Override
     public String toString() {
         return id;
diff --git 
a/core/camel-main/src/generated/java/org/apache/camel/main/MdcConfigurationPropertiesConfigurer.java
 
b/core/camel-main/src/generated/java/org/apache/camel/main/MdcConfigurationPropertiesConfigurer.java
new file mode 100644
index 00000000000..9707c284526
--- /dev/null
+++ 
b/core/camel-main/src/generated/java/org/apache/camel/main/MdcConfigurationPropertiesConfigurer.java
@@ -0,0 +1,48 @@
+/* Generated by camel build tools - do NOT edit this file! */
+package org.apache.camel.main;
+
+import javax.annotation.processing.Generated;
+import java.util.Map;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.spi.ExtendedPropertyConfigurerGetter;
+import org.apache.camel.spi.PropertyConfigurerGetter;
+import org.apache.camel.spi.ConfigurerStrategy;
+import org.apache.camel.spi.GeneratedPropertyConfigurer;
+import org.apache.camel.util.CaseInsensitiveMap;
+import org.apache.camel.main.MdcConfigurationProperties;
+
+/**
+ * Generated by camel build tools - do NOT edit this file!
+ */
+@Generated("org.apache.camel.maven.packaging.GenerateConfigurerMojo")
+@SuppressWarnings("unchecked")
+public class MdcConfigurationPropertiesConfigurer extends 
org.apache.camel.support.component.PropertyConfigurerSupport implements 
GeneratedPropertyConfigurer, ExtendedPropertyConfigurerGetter {
+
+    private static final Map<String, Object> ALL_OPTIONS;
+    static {
+        Map<String, Object> map = new CaseInsensitiveMap();
+        ALL_OPTIONS = map;
+    }
+
+    @Override
+    public boolean configure(CamelContext camelContext, Object obj, String 
name, Object value, boolean ignoreCase) {
+        return false;
+    }
+
+    @Override
+    public Map<String, Object> getAllOptions(Object target) {
+        return ALL_OPTIONS;
+    }
+
+    @Override
+    public Class<?> getOptionType(String name, boolean ignoreCase) {
+        return null;
+    }
+
+    @Override
+    public Object getOptionValue(Object obj, String name, boolean ignoreCase) {
+        return null;
+    }
+}
+
diff --git 
a/core/camel-main/src/generated/resources/META-INF/camel-main-configuration-metadata.json
 
b/core/camel-main/src/generated/resources/META-INF/camel-main-configuration-metadata.json
index bb1e632f40c..6dbbe63d36a 100644
--- 
a/core/camel-main/src/generated/resources/META-INF/camel-main-configuration-metadata.json
+++ 
b/core/camel-main/src/generated/resources/META-INF/camel-main-configuration-metadata.json
@@ -21,6 +21,7 @@
     { "name": "camel.opentelemetry", "description": "Camel OpenTelemetry 
configurations", "sourceType": 
"org.apache.camel.main.OtelConfigurationProperties" },
     { "name": "camel.opentelemetry2", "description": "Camel OpenTelemetry 2 
configurations", "sourceType": 
"org.apache.camel.main.Otel2ConfigurationProperties" },
     { "name": "camel.telemetryDev", "description": "Camel Telemetry Dev 
configurations", "sourceType": 
"org.apache.camel.main.TelemetryDevConfigurationProperties" },
+    { "name": "camel.mdc", "description": "Camel MDC configurations", 
"sourceType": "org.apache.camel.main.MdcConfigurationProperties" },
     { "name": "camel.metrics", "description": "Camel Micrometer Metrics 
configurations", "sourceType": 
"org.apache.camel.main.MetricsConfigurationProperties" },
     { "name": "camel.faulttolerance", "description": "Fault Tolerance EIP 
Circuit Breaker configurations", "sourceType": 
"org.apache.camel.main.FaultToleranceConfigurationProperties" },
     { "name": "camel.resilience4j", "description": "Resilience4j EIP Circuit 
Breaker configurations", "sourceType": 
"org.apache.camel.main.Resilience4jConfigurationProperties" },
diff --git 
a/core/camel-main/src/generated/resources/META-INF/services/org/apache/camel/configurer/org.apache.camel.main.MdcConfigurationProperties
 
b/core/camel-main/src/generated/resources/META-INF/services/org/apache/camel/configurer/org.apache.camel.main.MdcConfigurationProperties
new file mode 100644
index 00000000000..a95186bdc04
--- /dev/null
+++ 
b/core/camel-main/src/generated/resources/META-INF/services/org/apache/camel/configurer/org.apache.camel.main.MdcConfigurationProperties
@@ -0,0 +1,2 @@
+# Generated by camel build tools - do NOT edit this file!
+class=org.apache.camel.main.MdcConfigurationPropertiesConfigurer
diff --git a/core/camel-main/src/main/docs/main.adoc 
b/core/camel-main/src/main/docs/main.adoc
index 8dac7ccd593..78a79e8b33a 100644
--- a/core/camel-main/src/main/docs/main.adoc
+++ b/core/camel-main/src/main/docs/main.adoc
@@ -562,6 +562,15 @@ The camel.telemetryDev supports 4 options, which are 
listed below.
 |===
 
 
+=== Camel MDC configurations
+The camel.mdc supports 0 options, which are listed below.
+
+[width="100%",cols="2,5,^1,2",options="header"]
+|===
+| Name | Description | Default | Type
+|===
+
+
 === Camel Micrometer Metrics configurations
 The camel.metrics supports 14 options, which are listed below.
 
diff --git 
a/core/camel-main/src/main/java/org/apache/camel/main/BaseMainSupport.java 
b/core/camel-main/src/main/java/org/apache/camel/main/BaseMainSupport.java
index 2662a60413b..84e69be5b48 100644
--- a/core/camel-main/src/main/java/org/apache/camel/main/BaseMainSupport.java
+++ b/core/camel-main/src/main/java/org/apache/camel/main/BaseMainSupport.java
@@ -67,6 +67,7 @@ import org.apache.camel.spi.AutowiredLifecycleStrategy;
 import org.apache.camel.spi.BacklogTracer;
 import org.apache.camel.spi.CamelBeanPostProcessor;
 import org.apache.camel.spi.CamelEvent;
+import org.apache.camel.spi.CamelMDCService;
 import org.apache.camel.spi.CamelMetricsService;
 import org.apache.camel.spi.CamelTracingService;
 import org.apache.camel.spi.CompileStrategy;
@@ -136,7 +137,7 @@ public abstract class BaseMainSupport extends BaseService {
             "camel.context.", "camel.resilience4j.", "camel.faulttolerance.",
             "camel.rest.", "camel.vault.", "camel.threadpool.", 
"camel.health.",
             "camel.lra.", "camel.opentelemetry2.", "camel.opentelemetry.",
-            "camel.telemetryDev.", "camel.management.", "camel.metrics.", 
"camel.routeTemplate",
+            "camel.telemetryDev.", "camel.management.", "camel.mdc.", 
"camel.metrics.", "camel.routeTemplate",
             "camel.devConsole.", "camel.variable.", "camel.beans.", 
"camel.globalOptions.",
             "camel.server.", "camel.ssl.", "camel.debug.", "camel.trace.", 
"camel.routeController." };
 
@@ -1283,6 +1284,7 @@ public abstract class BaseMainSupport extends BaseService 
{
         OrderedLocationProperties lraProperties = new 
OrderedLocationProperties();
         OrderedLocationProperties otelProperties = new 
OrderedLocationProperties();
         OrderedLocationProperties otel2Properties = new 
OrderedLocationProperties();
+        OrderedLocationProperties mdcProperties = new 
OrderedLocationProperties();
         OrderedLocationProperties telemetryDevProperties = new 
OrderedLocationProperties();
         OrderedLocationProperties metricsProperties = new 
OrderedLocationProperties();
         OrderedLocationProperties routeTemplateProperties = new 
OrderedLocationProperties();
@@ -1359,6 +1361,12 @@ public abstract class BaseMainSupport extends 
BaseService {
                 String option = key.substring(19);
                 validateOptionAndValue(key, option, value);
                 telemetryDevProperties.put(loc, optionKey(option), value);
+            } else if (startsWithIgnoreCase(key, "camel.mdc.")) {
+                // grab the value
+                String value = prop.getProperty(key);
+                String option = key.substring(10);
+                validateOptionAndValue(key, option, value);
+                mdcProperties.put(loc, optionKey(option), value);
             } else if (startsWithIgnoreCase(key, "camel.metrics.")) {
                 // grab the value
                 String value = prop.getProperty(key);
@@ -1525,6 +1533,11 @@ public abstract class BaseMainSupport extends 
BaseService {
             setMetricsProperties(camelContext, metricsProperties, 
mainConfigurationProperties.isAutoConfigurationFailFast(),
                     autoConfiguredProperties);
         }
+        if (!mdcProperties.isEmpty() || 
mainConfigurationProperties.hasMdcConfiguration()) {
+            LOG.debug("Auto-configuring MDC from loaded properties: {}", 
mdcProperties.size());
+            setMdcProperties(camelContext, mdcProperties, 
mainConfigurationProperties.isAutoConfigurationFailFast(),
+                    autoConfiguredProperties);
+        }
         if (!devConsoleProperties.isEmpty()) {
             LOG.debug("Auto-configuring Dev Console from loaded properties: 
{}", devConsoleProperties.size());
             setDevConsoleProperties(camelContext, devConsoleProperties,
@@ -1656,6 +1669,11 @@ public abstract class BaseMainSupport extends 
BaseService {
                 LOG.warn("Property not auto-configured: 
camel.management.{}={}", k, v);
             });
         }
+        if (!mdcProperties.isEmpty()) {
+            mdcProperties.forEach((k, v) -> {
+                LOG.warn("Property not auto-configured: camel.mdc.{}={}", k, 
v);
+            });
+        }
 
         // and call after all properties are set
         DefaultConfigurationConfigurer.afterPropertiesSet(camelContext);
@@ -1851,6 +1869,28 @@ public abstract class BaseMainSupport extends 
BaseService {
         }
     }
 
+    private void setMdcProperties(
+            CamelContext camelContext, OrderedLocationProperties mdcProperties,
+            boolean failIfNotSet, OrderedLocationProperties 
autoConfiguredProperties)
+            throws Exception {
+
+        String loc = mdcProperties.getLocation("enabled");
+        Object obj = mdcProperties.remove("enabled");
+        if (ObjectHelper.isNotEmpty(obj)) {
+            autoConfiguredProperties.put(loc, "camel.mdc.enabled", 
obj.toString());
+        }
+        boolean enabled = obj != null ? 
CamelContextHelper.parseBoolean(camelContext, obj.toString()) : true;
+        if (enabled) {
+            CamelMDCService mdc = resolveMDCService(camelContext);
+            setPropertiesOnTarget(camelContext, mdc, mdcProperties, 
"camel.mdc.", failIfNotSet, true,
+                    autoConfiguredProperties);
+            if (camelContext.hasService(CamelMDCService.class) == null) {
+                // add as service so tracing can be active
+                camelContext.addService(mdc, true, true);
+            }
+        }
+    }
+
     private void setTelemetryDevProperties(
             CamelContext camelContext, OrderedLocationProperties 
telemetryDevProperties,
             boolean failIfNotSet, OrderedLocationProperties 
autoConfiguredProperties)
@@ -2741,6 +2781,20 @@ public abstract class BaseMainSupport extends 
BaseService {
         return answer;
     }
 
+    private static CamelMDCService resolveMDCService(CamelContext 
camelContext) throws Exception {
+        CamelMDCService answer = 
camelContext.hasService(CamelMDCService.class);
+        if (answer == null) {
+            answer = 
camelContext.getRegistry().findSingleByType(CamelMDCService.class);
+        }
+        if (answer == null) {
+            answer = 
camelContext.getCamelContextExtension().getBootstrapFactoryFinder()
+                    .newInstance("mdc-service", CamelMDCService.class)
+                    .orElseThrow(() -> new IllegalArgumentException(
+                            "Cannot find OpenTelemetryTracer2 on classpath. 
Add camel-opentelemetry2 to classpath."));
+        }
+        return answer;
+    }
+
     private static MainHttpServerFactory 
resolveMainHttpServerFactory(CamelContext camelContext) {
         // lookup in service registry first
         MainHttpServerFactory answer = 
camelContext.getRegistry().findSingleByType(MainHttpServerFactory.class);
diff --git 
a/core/camel-main/src/main/java/org/apache/camel/main/MainConfigurationProperties.java
 
b/core/camel-main/src/main/java/org/apache/camel/main/MainConfigurationProperties.java
index 1048cd15014..c95aab73387 100644
--- 
a/core/camel-main/src/main/java/org/apache/camel/main/MainConfigurationProperties.java
+++ 
b/core/camel-main/src/main/java/org/apache/camel/main/MainConfigurationProperties.java
@@ -61,6 +61,7 @@ public class MainConfigurationProperties extends 
DefaultConfigurationProperties<
     private LraConfigurationProperties lraConfigurationProperties;
     private OtelConfigurationProperties otelConfigurationProperties;
     private Otel2ConfigurationProperties otel2ConfigurationProperties;
+    private MdcConfigurationProperties mdcConfigurationProperties;
     private TelemetryDevConfigurationProperties 
telemetryDevConfigurationProperties;
     private MetricsConfigurationProperties metricsConfigurationProperties;
     private ThreadPoolConfigurationProperties threadPoolProperties;
@@ -97,6 +98,10 @@ public class MainConfigurationProperties extends 
DefaultConfigurationProperties<
             telemetryDevConfigurationProperties.close();
             telemetryDevConfigurationProperties = null;
         }
+        if (mdcConfigurationProperties != null) {
+            mdcConfigurationProperties.close();
+            mdcConfigurationProperties = null;
+        }
         if (metricsConfigurationProperties != null) {
             metricsConfigurationProperties.close();
             metricsConfigurationProperties = null;
@@ -237,6 +242,13 @@ public class MainConfigurationProperties extends 
DefaultConfigurationProperties<
         return telemetryDevConfigurationProperties != null;
     }
 
+    /**
+     * Whether there has been any MDC configuration specified
+     */
+    public boolean hasMdcConfiguration() {
+        return mdcConfigurationProperties != null;
+    }
+
     /**
      * To configure Micrometer metrics.
      */
diff --git 
a/core/camel-main/src/main/java/org/apache/camel/main/MdcConfigurationProperties.java
 
b/core/camel-main/src/main/java/org/apache/camel/main/MdcConfigurationProperties.java
new file mode 100644
index 00000000000..4d678032669
--- /dev/null
+++ 
b/core/camel-main/src/main/java/org/apache/camel/main/MdcConfigurationProperties.java
@@ -0,0 +1,57 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.camel.main;
+
+import org.apache.camel.spi.BootstrapCloseable;
+import org.apache.camel.spi.Configurer;
+
+/**
+ * Global configuration for MDC
+ */
+@Configurer(extended = true)
+public class MdcConfigurationProperties implements BootstrapCloseable {
+
+    private MainConfigurationProperties parent;
+
+    private boolean enabled;
+
+    public MdcConfigurationProperties(MainConfigurationProperties parent) {
+        this.parent = parent;
+    }
+
+    public MainConfigurationProperties end() {
+        return parent;
+    }
+
+    @Override
+    public void close() {
+        parent = null;
+    }
+
+    public boolean isEnabled() {
+        return enabled;
+    }
+
+    /**
+     * To enable Mdc
+     */
+    public MdcConfigurationProperties withEnabled(boolean enabled) {
+        this.enabled = enabled;
+        return this;
+    }
+
+}
diff --git 
a/core/camel-support/src/main/java/org/apache/camel/support/processor/CamelLogProcessor.java
 
b/core/camel-support/src/main/java/org/apache/camel/support/processor/CamelLogProcessor.java
index d6c9ec0192d..6162ab3247b 100644
--- 
a/core/camel-support/src/main/java/org/apache/camel/support/processor/CamelLogProcessor.java
+++ 
b/core/camel-support/src/main/java/org/apache/camel/support/processor/CamelLogProcessor.java
@@ -102,6 +102,7 @@ public class CamelLogProcessor extends 
AsyncProcessorSupport implements IdAware,
             }
             output = fireListeners(exchange, output);
             logger.log(output);
+            closeListeners(exchange, output);
         }
         callback.done(true);
         return true;
@@ -115,6 +116,7 @@ public class CamelLogProcessor extends 
AsyncProcessorSupport implements IdAware,
             }
             output = fireListeners(exchange, output);
             logger.log(output, exception);
+            closeListeners(exchange, output);
         }
     }
 
@@ -126,6 +128,7 @@ public class CamelLogProcessor extends 
AsyncProcessorSupport implements IdAware,
             }
             output = fireListeners(exchange, output);
             logger.log(output);
+            closeListeners(exchange, output);
         }
     }
 
@@ -150,6 +153,25 @@ public class CamelLogProcessor extends 
AsyncProcessorSupport implements IdAware,
         return message;
     }
 
+    private void closeListeners(Exchange exchange, String message) {
+        if (listeners == null || listeners.isEmpty()) {
+            return;
+        }
+        for (LogListener listener : listeners) {
+            if (listener == null) {
+                continue;
+            }
+            try {
+                listener.afterLog(exchange, logger, message);
+            } catch (Exception t) {
+                LOG.warn("Ignoring an exception thrown by {}: {}", 
listener.getClass().getName(), t.getMessage());
+                if (LOG.isDebugEnabled()) {
+                    LOG.debug("", t);
+                }
+            }
+        }
+    }
+
     public CamelLogger getLogger() {
         return logger;
     }
diff --git a/docs/components/modules/others/examples/json/mdc.json 
b/docs/components/modules/others/examples/json/mdc.json
new file mode 120000
index 00000000000..0d57f5bed57
--- /dev/null
+++ b/docs/components/modules/others/examples/json/mdc.json
@@ -0,0 +1 @@
+../../../../../../components/camel-mdc/src/generated/resources/mdc.json
\ No newline at end of file
diff --git a/docs/components/modules/others/nav.adoc 
b/docs/components/modules/others/nav.adoc
index 02b181394d9..16495e4d3ac 100644
--- a/docs/components/modules/others/nav.adoc
+++ b/docs/components/modules/others/nav.adoc
@@ -28,6 +28,7 @@
 ** xref:lra.adoc[LRA]
 ** xref:mail-microsoft-oauth.adoc[Mail Microsoft Oauth]
 ** xref:main.adoc[Main]
+** xref:mdc.adoc[Mdc]
 ** xref:observation.adoc[Micrometer Observability]
 ** xref:micrometer-observability.adoc[Micrometer Observability 2]
 ** xref:micrometer-prometheus.adoc[Micrometer Prometheus]
diff --git a/docs/components/modules/others/pages/mdc.adoc 
b/docs/components/modules/others/pages/mdc.adoc
new file mode 120000
index 00000000000..eec3ea2ffd3
--- /dev/null
+++ b/docs/components/modules/others/pages/mdc.adoc
@@ -0,0 +1 @@
+../../../../../components/camel-mdc/src/main/docs/mdc.adoc
\ No newline at end of file
diff --git a/parent/pom.xml b/parent/pom.xml
index 2442a93df2a..2a14a54308d 100644
--- a/parent/pom.xml
+++ b/parent/pom.xml
@@ -1937,6 +1937,11 @@
                 <artifactId>camel-master</artifactId>
                 <version>${project.version}</version>
             </dependency>
+            <dependency>
+                <groupId>org.apache.camel</groupId>
+                <artifactId>camel-mdc</artifactId>
+                <version>${project.version}</version>
+            </dependency>
             <dependency>
                 <groupId>org.apache.camel</groupId>
                 <artifactId>camel-metrics</artifactId>
diff --git 
a/tooling/maven/camel-package-maven-plugin/src/main/java/org/apache/camel/maven/packaging/PrepareCamelMainMojo.java
 
b/tooling/maven/camel-package-maven-plugin/src/main/java/org/apache/camel/maven/packaging/PrepareCamelMainMojo.java
index e919a83c765..324dd3d4176 100644
--- 
a/tooling/maven/camel-package-maven-plugin/src/main/java/org/apache/camel/maven/packaging/PrepareCamelMainMojo.java
+++ 
b/tooling/maven/camel-package-maven-plugin/src/main/java/org/apache/camel/maven/packaging/PrepareCamelMainMojo.java
@@ -443,6 +443,9 @@ public class PrepareCamelMainMojo extends 
AbstractGeneratorMojo {
             model.getGroups().add(new MainGroupModel(
                     "camel.telemetryDev", "Camel Telemetry Dev configurations",
                     
"org.apache.camel.main.TelemetryDevConfigurationProperties"));
+            model.getGroups().add(new MainGroupModel(
+                    "camel.mdc", "Camel MDC configurations",
+                    "org.apache.camel.main.MdcConfigurationProperties"));
             model.getGroups().add(new MainGroupModel(
                     "camel.metrics", "Camel Micrometer Metrics configurations",
                     "org.apache.camel.main.MetricsConfigurationProperties"));


Reply via email to