This is an automated email from the ASF dual-hosted git repository.
davsclaus pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/camel.git
The following commit(s) were added to refs/heads/main by this push:
new cb59f8fed39c CAMEL-25950: camel-sjms - SjmsMessage keeps the
attachments when the exchange is copied (#28644)
cb59f8fed39c is described below
commit cb59f8fed39c3bd14749cffb25af8d5a5e9a59b4
Author: allthingssecurity <[email protected]>
AuthorDate: Thu Oct 29 13:32:11 2026 +0530
CAMEL-25950: camel-sjms - SjmsMessage keeps the attachments when the
exchange is copied (#28644)
Co-Authored-By: Claude Opus 5.5 <[email protected]>
---
.../apache/camel/component/sjms/SjmsMessage.java | 8 ++
.../sjms/SjmsMessageCopyAttachmentsTest.java | 103 +++++++++++++++++++++
2 files changed, 111 insertions(+)
diff --git
a/components/camel-sjms/src/main/java/org/apache/camel/component/sjms/SjmsMessage.java
b/components/camel-sjms/src/main/java/org/apache/camel/component/sjms/SjmsMessage.java
index 30d316930fb7..9da0217163c7 100644
---
a/components/camel-sjms/src/main/java/org/apache/camel/component/sjms/SjmsMessage.java
+++
b/components/camel-sjms/src/main/java/org/apache/camel/component/sjms/SjmsMessage.java
@@ -17,6 +17,7 @@
package org.apache.camel.component.sjms;
import java.io.File;
+import java.util.LinkedHashMap;
import java.util.Map;
import jakarta.jms.Destination;
@@ -126,6 +127,13 @@ public class SjmsMessage extends DefaultMessage {
if (that.hasHeaders()) {
getHeaders().putAll(that.getHeaders());
}
+
+ // copy attachments, as MessageSupport.copyFrom does (which this
method does not call)
+ @SuppressWarnings("unchecked")
+ Map<String, Object> attachments = (Map<String, Object>)
that.getPayloadForTrait(MessageTrait.ATTACHMENTS);
+ if (attachments != null) {
+ setPayloadForTrait(MessageTrait.ATTACHMENTS, new
LinkedHashMap<>(attachments));
+ }
}
public JmsBinding getBinding() {
diff --git
a/components/camel-sjms/src/test/java/org/apache/camel/component/sjms/SjmsMessageCopyAttachmentsTest.java
b/components/camel-sjms/src/test/java/org/apache/camel/component/sjms/SjmsMessageCopyAttachmentsTest.java
new file mode 100644
index 000000000000..f76323a58e18
--- /dev/null
+++
b/components/camel-sjms/src/test/java/org/apache/camel/component/sjms/SjmsMessageCopyAttachmentsTest.java
@@ -0,0 +1,103 @@
+/*
+ * 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.component.sjms;
+
+import java.util.LinkedHashMap;
+import java.util.Map;
+
+import org.apache.camel.Exchange;
+import org.apache.camel.Message;
+import org.apache.camel.builder.RouteBuilder;
+import org.apache.camel.component.mock.MockEndpoint;
+import org.apache.camel.component.sjms.support.JmsTestSupport;
+import org.apache.camel.trait.message.MessageTrait;
+import org.junit.jupiter.api.Test;
+
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertInstanceOf;
+import static org.junit.jupiter.api.Assertions.assertNotNull;
+import static org.junit.jupiter.api.Assertions.assertNotSame;
+import static org.junit.jupiter.api.Assertions.assertNull;
+
+/**
+ * Attachments of a message received from sjms (an {@link SjmsMessage}) are
kept when the exchange is copied, such as by
+ * the Multicast EIP. The attachments are the {@link MessageTrait#ATTACHMENTS}
payload of the message, which is where
+ * camel-attachments (AttachmentMessage) keeps them.
+ */
+class SjmsMessageCopyAttachmentsTest extends JmsTestSupport {
+
+ @Test
+ void multicastCopyKeepsTheAttachmentsOfAnSjmsMessage() throws Exception {
+ MockEndpoint copy = getMockEndpoint("mock:copy");
+ copy.expectedMessageCount(1);
+
+ template.sendBody("sjms:SjmsMessageCopyAttachmentsTest", "Hello
World");
+
+ MockEndpoint.assertIsSatisfied(context);
+ Message received = copy.getReceivedExchanges().get(0).getMessage();
+ assertInstanceOf(SjmsMessage.class, received);
+ Map<String, Object> attachments = attachmentsOf(received);
+ assertNotNull(attachments, "the copy made by the multicast must keep
the attachments");
+ assertEquals("Hello attachment", attachments.get("hello.txt"));
+ }
+
+ @Test
+ void copyKeepsTheAttachments() {
+ Exchange exchange =
context.getEndpoint("sjms:SjmsMessageCopyAttachmentsTest").createExchange();
+ SjmsMessage message = new SjmsMessage(exchange, null, null, null);
+ message.setBody("Hello World");
+ Map<String, Object> attachments = new LinkedHashMap<>();
+ attachments.put("hello.txt", "Hello attachment");
+ message.setPayloadForTrait(MessageTrait.ATTACHMENTS, attachments);
+
+ Message copy = message.copy();
+
+ Map<String, Object> copied = attachmentsOf(copy);
+ assertNotNull(copied, "copy() must keep the attachments");
+ assertEquals(attachments, copied);
+ assertNotSame(attachments, copied, "the copy has its own attachment
map");
+ }
+
+ @Test
+ void copyOfAMessageWithoutAttachmentsHasNone() {
+ Exchange exchange =
context.getEndpoint("sjms:SjmsMessageCopyAttachmentsTest").createExchange();
+ SjmsMessage message = new SjmsMessage(exchange, null, null, null);
+ message.setBody("Hello World");
+
+ assertNull(attachmentsOf(message.copy()));
+ }
+
+ @SuppressWarnings("unchecked")
+ private static Map<String, Object> attachmentsOf(Message message) {
+ return (Map<String, Object>)
message.getPayloadForTrait(MessageTrait.ATTACHMENTS);
+ }
+
+ @Override
+ protected RouteBuilder createRouteBuilder() {
+ return new RouteBuilder() {
+ public void configure() {
+ from("sjms:SjmsMessageCopyAttachmentsTest")
+ .process(e -> {
+ Map<String, Object> attachments = new
LinkedHashMap<>();
+ attachments.put("hello.txt", "Hello attachment");
+
e.getMessage().setPayloadForTrait(MessageTrait.ATTACHMENTS, attachments);
+ })
+ .multicast().to("mock:copy");
+ }
+ };
+ }
+}