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

davsclaus pushed a commit to branch CAMEL-26567
in repository https://gitbox.apache.org/repos/asf/camel.git


The following commit(s) were added to refs/heads/CAMEL-26567 by this push:
     new 1c45a20bef99 CAMEL-26567: camel-jms / camel-sjms - text that is not a 
String in a Map body goes in the MapMessage as a String
1c45a20bef99 is described below

commit 1c45a20bef99cabc6fbcbe2477c5f331b5b38bf5
Author: Claus Ibsen <[email protected]>
AuthorDate: Wed Nov 4 10:48:40 2026 +0100

    CAMEL-26567: camel-jms / camel-sjms - text that is not a String in a Map 
body goes in the MapMessage as a String
    
    A MapMessage takes only primitive wrappers, String and byte[], so a Map
    with a StringBuilder or a Groovy GString value failed with a
    MessageFormatException.
    
    Co-Authored-By: Claude Opus 5.5 <[email protected]>
    Signed-off-by: Claus Ibsen <[email protected]>
---
 .../org/apache/camel/component/jms/JmsBinding.java |  5 +++-
 .../component/jms/JmsCharSequenceBodyTest.java     | 27 ++++++++++++++++++++++
 .../camel/component/sjms/jms/JmsBinding.java       |  5 +++-
 .../sjms/producer/CharSequenceBodyTest.java        | 24 +++++++++++++++++++
 4 files changed, 59 insertions(+), 2 deletions(-)

diff --git 
a/components/camel-jms/src/main/java/org/apache/camel/component/jms/JmsBinding.java
 
b/components/camel-jms/src/main/java/org/apache/camel/component/jms/JmsBinding.java
index f4ebe88b999f..df0b4d06ecd2 100644
--- 
a/components/camel-jms/src/main/java/org/apache/camel/component/jms/JmsBinding.java
+++ 
b/components/camel-jms/src/main/java/org/apache/camel/component/jms/JmsBinding.java
@@ -853,7 +853,10 @@ public class JmsBinding {
         for (Entry<?, ?> entry : map.entrySet()) {
             String keyString = CamelContextHelper.convertTo(context, 
String.class, entry.getKey());
             if (keyString != null) {
-                message.setObject(keyString, entry.getValue());
+                Object value = entry.getValue();
+                // JMS takes only primitive wrappers, String and byte[] in a 
MapMessage, so text such as a
+                // StringBuilder or a Groovy GString goes in as a String
+                message.setObject(keyString, value instanceof CharSequence cs 
? cs.toString() : value);
             }
         }
     }
diff --git 
a/components/camel-jms/src/test/java/org/apache/camel/component/jms/JmsCharSequenceBodyTest.java
 
b/components/camel-jms/src/test/java/org/apache/camel/component/jms/JmsCharSequenceBodyTest.java
index c2da066fc170..a618bcd4d7cb 100644
--- 
a/components/camel-jms/src/test/java/org/apache/camel/component/jms/JmsCharSequenceBodyTest.java
+++ 
b/components/camel-jms/src/test/java/org/apache/camel/component/jms/JmsCharSequenceBodyTest.java
@@ -16,6 +16,10 @@
  */
 package org.apache.camel.component.jms;
 
+import java.util.LinkedHashMap;
+import java.util.Map;
+
+import jakarta.jms.MapMessage;
 import jakarta.jms.TextMessage;
 
 import com.example.external.ExternalText;
@@ -64,6 +68,27 @@ public class JmsCharSequenceBodyTest extends AbstractJMSTest 
{
         assertInstanceOf(TextMessage.class, in.getJmsMessage());
     }
 
+    @Test
+    public void testTextInAMapIsSentAsString() throws Exception {
+        MockEndpoint mock = getMockEndpoint("mock:map");
+        mock.expectedMessageCount(1);
+
+        // a Map with text that is not a String, as a Groovy script that 
returns [status: "not enough ${sku}"]
+        Map<String, Object> body = new LinkedHashMap<>();
+        body.put("status", new ExternalText("not enough CAMEL-CAP"));
+        body.put("note", new StringBuilder("back order"));
+        body.put("count", 3);
+        template.sendBody("jms:queue:JmsCharSequenceBodyTest.map", body);
+
+        MockEndpoint.assertIsSatisfied(context);
+        JmsMessage in = 
mock.getReceivedExchanges().get(0).getIn(JmsMessage.class);
+        assertInstanceOf(MapMessage.class, in.getJmsMessage());
+        Map<?, ?> received = in.getBody(Map.class);
+        assertEquals("not enough CAMEL-CAP", received.get("status"));
+        assertEquals("back order", received.get("note"));
+        assertEquals(3, received.get("count"));
+    }
+
     @Test
     public void testTextReply() {
         Object reply = 
template.requestBody("jms:queue:JmsCharSequenceBodyTest.reply?requestTimeout=5000",
 "CAMEL-CAP");
@@ -85,6 +110,8 @@ public class JmsCharSequenceBodyTest extends AbstractJMSTest 
{
             public void configure() {
                 from("jms:queue:JmsCharSequenceBodyTest").to("mock:result");
 
+                from("jms:queue:JmsCharSequenceBodyTest.map").to("mock:map");
+
                 // a reply that is text but not a String, as a route that sets 
the body with a Groovy GString
                 from("jms:queue:JmsCharSequenceBodyTest.reply")
                         .process(e -> e.getMessage().setBody(new 
ExternalText("not enough " + e.getMessage().getBody())));
diff --git 
a/components/camel-sjms/src/main/java/org/apache/camel/component/sjms/jms/JmsBinding.java
 
b/components/camel-sjms/src/main/java/org/apache/camel/component/sjms/jms/JmsBinding.java
index cfc46b6e1036..bea673b2193d 100644
--- 
a/components/camel-sjms/src/main/java/org/apache/camel/component/sjms/jms/JmsBinding.java
+++ 
b/components/camel-sjms/src/main/java/org/apache/camel/component/sjms/jms/JmsBinding.java
@@ -632,7 +632,10 @@ public class JmsBinding {
         for (Map.Entry<?, ?> entry : map.entrySet()) {
             String keyString = CamelContextHelper.convertTo(context, 
String.class, entry.getKey());
             if (keyString != null) {
-                message.setObject(keyString, entry.getValue());
+                Object value = entry.getValue();
+                // JMS takes only primitive wrappers, String and byte[] in a 
MapMessage, so text such as a
+                // StringBuilder or a Groovy GString goes in as a String
+                message.setObject(keyString, value instanceof CharSequence cs 
? cs.toString() : value);
             }
         }
     }
diff --git 
a/components/camel-sjms/src/test/java/org/apache/camel/component/sjms/producer/CharSequenceBodyTest.java
 
b/components/camel-sjms/src/test/java/org/apache/camel/component/sjms/producer/CharSequenceBodyTest.java
index f70eb7c7eace..f1455e4110da 100644
--- 
a/components/camel-sjms/src/test/java/org/apache/camel/component/sjms/producer/CharSequenceBodyTest.java
+++ 
b/components/camel-sjms/src/test/java/org/apache/camel/component/sjms/producer/CharSequenceBodyTest.java
@@ -16,6 +16,10 @@
  */
 package org.apache.camel.component.sjms.producer;
 
+import java.util.LinkedHashMap;
+import java.util.Map;
+
+import jakarta.jms.MapMessage;
 import jakarta.jms.Message;
 import jakarta.jms.MessageConsumer;
 import jakarta.jms.TextMessage;
@@ -36,6 +40,7 @@ public class CharSequenceBodyTest extends JmsTestSupport {
 
     private static final String TEST_DESTINATION_NAME = 
"test.foo.CharSequenceBodyTest";
     private static final String TEST_OTHER_DESTINATION_NAME = 
"test.other.CharSequenceBodyTest";
+    private static final String TEST_MAP_DESTINATION_NAME = 
"test.map.CharSequenceBodyTest";
     private static final String TEST_REPLY_DESTINATION_NAME = 
"test.reply.CharSequenceBodyTest";
 
     @Override
@@ -68,6 +73,25 @@ public class CharSequenceBodyTest extends JmsTestSupport {
         mc.close();
     }
 
+    @Test
+    public void testTextInAMapIsSentAsString() throws Exception {
+        MessageConsumer mc = createQueueConsumer(TEST_MAP_DESTINATION_NAME);
+
+        // a Map with text that is not a String, as a Groovy script that 
returns [status: "not enough ${sku}"]
+        Map<String, Object> body = new LinkedHashMap<>();
+        body.put("status", new ExternalText("not enough CAMEL-CAP"));
+        body.put("note", new StringBuilder("back order"));
+        body.put("count", 3);
+        template.sendBody("sjms:queue:" + TEST_MAP_DESTINATION_NAME, body);
+
+        Message message = mc.receive(5000);
+        MapMessage map = assertInstanceOf(MapMessage.class, message);
+        assertEquals("not enough CAMEL-CAP", map.getObject("status"));
+        assertEquals("back order", map.getObject("note"));
+        assertEquals(3, map.getObject("count"));
+        mc.close();
+    }
+
     @Test
     public void testTextReply() {
         Object reply = template.requestBody("sjms:queue:" + 
TEST_REPLY_DESTINATION_NAME + "?requestTimeout=5000", "CAMEL-CAP");

Reply via email to