1
2
3
4
5
6
7
8
9
10
11 package org.mule.transport.jms;
12
13 import java.io.IOException;
14 import java.io.InputStream;
15 import java.io.ObjectOutputStream;
16 import java.io.Serializable;
17 import java.util.Enumeration;
18 import java.util.Hashtable;
19 import java.util.Iterator;
20 import java.util.List;
21 import java.util.Map;
22 import java.util.Vector;
23
24 import javax.jms.BytesMessage;
25 import javax.jms.Destination;
26 import javax.jms.JMSException;
27 import javax.jms.MapMessage;
28 import javax.jms.Message;
29 import javax.jms.MessageEOFException;
30 import javax.jms.ObjectMessage;
31 import javax.jms.Queue;
32 import javax.jms.Session;
33 import javax.jms.StreamMessage;
34 import javax.jms.TextMessage;
35 import javax.jms.Topic;
36
37 import org.apache.commons.io.output.ByteArrayOutputStream;
38 import org.mule.util.ArrayUtils;
39 import org.mule.util.ClassUtils;
40 import org.mule.util.StringUtils;
41
42
43
44
45
46 public class JmsMessageUtils
47 {
48 public static final char REPLACEMENT_CHAR = '_';
49
50
51
52
53
54
55
56 public static String encodeHeader(String name)
57 {
58 if (StringUtils.isEmpty(name))
59 {
60 throw new IllegalArgumentException("Header name to encode must not be null or empty");
61 }
62
63 int i = 0, length = name.length();
64 while (i < length && Character.isJavaIdentifierPart(name.charAt(i)))
65 {
66
67 i++;
68 }
69
70 if (i == length)
71 {
72
73 return name;
74 }
75 else
76 {
77
78 StringBuffer sb = new StringBuffer(name);
79 for (int j = i; j < length; j++)
80 {
81 if (!Character.isJavaIdentifierPart(sb.charAt(j)))
82 {
83 sb.setCharAt(j, REPLACEMENT_CHAR);
84 }
85 }
86 return sb.toString();
87 }
88 }
89
90 public static Message toMessage(Object object, Session session) throws JMSException
91 {
92 if (object instanceof Message)
93 {
94 return (Message)object;
95 }
96 else if (object instanceof String)
97 {
98 return session.createTextMessage((String)object);
99 }
100 else if (object instanceof Map)
101 {
102 MapMessage mMsg = session.createMapMessage();
103 Map src = (Map)object;
104
105 for (Iterator i = src.entrySet().iterator(); i.hasNext();)
106 {
107 Map.Entry entry = (Map.Entry)i.next();
108 mMsg.setObject(entry.getKey().toString(), entry.getValue());
109 }
110
111 return mMsg;
112 }
113 else if (object instanceof InputStream)
114 {
115 StreamMessage sMsg = session.createStreamMessage();
116 InputStream temp = (InputStream)object;
117
118 byte[] buffer = new byte[4096];
119 int len;
120
121 try
122 {
123 while ((len = temp.read(buffer)) != -1)
124 {
125 sMsg.writeBytes(buffer, 0, len);
126 }
127 }
128 catch (IOException e)
129 {
130 throw new JMSException("Failed to read input stream to create a stream message: " + e);
131 }
132
133 return sMsg;
134 }
135 else if (object instanceof List)
136 {
137 StreamMessage sMsg = session.createStreamMessage();
138 List list = (List) object;
139 for (Iterator iter = list.iterator(); iter.hasNext();)
140 {
141 sMsg.writeObject(iter.next());
142 }
143 return sMsg;
144 }
145 else if (object instanceof byte[])
146 {
147 BytesMessage bMsg = session.createBytesMessage();
148 bMsg.writeBytes((byte[])object);
149 return bMsg;
150 }
151 else if (object instanceof Serializable)
152 {
153 ObjectMessage oMsg = session.createObjectMessage();
154 oMsg.setObject((Serializable)object);
155 return oMsg;
156 }
157 else
158 {
159 throw new JMSException(
160 "Source was not of a supported type, data must be Serializable, String, byte[], Map or InputStream, " +
161 "but was " + ClassUtils.getShortClassName(object, "<null>"));
162 }
163 }
164
165 public static Object toObject(Message source, String jmsSpec) throws JMSException, IOException
166 {
167 if (source instanceof ObjectMessage)
168 {
169 return ((ObjectMessage)source).getObject();
170 }
171 else if (source instanceof MapMessage)
172 {
173 Hashtable map = new Hashtable();
174 MapMessage m = (MapMessage)source;
175
176 for (Enumeration e = m.getMapNames(); e.hasMoreElements();)
177 {
178 String name = (String)e.nextElement();
179 Object obj = m.getObject(name);
180 map.put(name, obj);
181 }
182
183 return map;
184 }
185 else if (source instanceof TextMessage)
186 {
187 return ((TextMessage)source).getText();
188 }
189 else if (source instanceof BytesMessage)
190 {
191 return toByteArray(source, jmsSpec);
192 }
193 else if (source instanceof StreamMessage)
194 {
195 Vector result = new Vector();
196 try
197 {
198 StreamMessage sMsg = (StreamMessage)source;
199 Object obj;
200 while ((obj = sMsg.readObject()) != null)
201 {
202 result.addElement(obj);
203 }
204 }
205 catch (MessageEOFException eof)
206 {
207
208 }
209 catch (Exception e)
210 {
211 throw new JMSException("Failed to extract information from JMS Stream Message: " + e);
212 }
213 return result;
214 }
215
216
217 return source;
218 }
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234 public static byte[] toByteArray(Message message, String jmsSpec) throws JMSException, IOException
235 {
236 if (message instanceof BytesMessage)
237 {
238 BytesMessage bMsg = (BytesMessage)message;
239 bMsg.reset();
240
241 if (JmsConstants.JMS_SPECIFICATION_11.equals(jmsSpec))
242 {
243 long bmBodyLength = bMsg.getBodyLength();
244 if (bmBodyLength > Integer.MAX_VALUE)
245 {
246 throw new JMSException("Size of BytesMessage exceeds Integer.MAX_VALUE; "
247 + "please consider using JMS StreamMessage instead");
248 }
249
250 if (bmBodyLength > 0)
251 {
252 byte[] bytes = new byte[(int)bmBodyLength];
253 bMsg.readBytes(bytes);
254 return bytes;
255 }
256 else
257 {
258 return ArrayUtils.EMPTY_BYTE_ARRAY;
259 }
260 }
261 else
262 {
263 ByteArrayOutputStream baos = new ByteArrayOutputStream(4096);
264 byte[] buffer = new byte[4096];
265 int len;
266
267 while ((len = bMsg.readBytes(buffer)) != -1)
268 {
269 baos.write(buffer, 0, len);
270 }
271
272 if (baos.size() > 0)
273 {
274 return baos.toByteArray();
275 }
276 else
277 {
278 return ArrayUtils.EMPTY_BYTE_ARRAY;
279 }
280 }
281 }
282 else if (message instanceof StreamMessage)
283 {
284 StreamMessage sMsg = (StreamMessage)message;
285 sMsg.reset();
286
287 ByteArrayOutputStream baos = new ByteArrayOutputStream(4096);
288 byte[] buffer = new byte[4096];
289 int len;
290
291 while ((len = sMsg.readBytes(buffer)) != -1)
292 {
293 baos.write(buffer, 0, len);
294 }
295
296 return baos.toByteArray();
297 }
298 else if (message instanceof ObjectMessage)
299 {
300 ObjectMessage oMsg = (ObjectMessage)message;
301 ByteArrayOutputStream baos = new ByteArrayOutputStream();
302 ObjectOutputStream os = new ObjectOutputStream(baos);
303 os.writeObject(oMsg.getObject());
304 os.flush();
305 os.close();
306 return baos.toByteArray();
307 }
308 else if (message instanceof TextMessage)
309 {
310 TextMessage tMsg = (TextMessage)message;
311 String tMsgText = tMsg.getText();
312
313 if (null == tMsgText)
314 {
315
316
317 return ArrayUtils.EMPTY_BYTE_ARRAY;
318 }
319 else
320 {
321 return tMsgText.getBytes();
322 }
323 }
324 else
325 {
326 throw new JMSException("Cannot get bytes from Map Message");
327 }
328 }
329
330 public static String getNameForDestination(Destination dest) throws JMSException
331 {
332 if (dest instanceof Queue)
333 {
334 return ((Queue)dest).getQueueName();
335 }
336 else if (dest instanceof Topic)
337 {
338 return ((Topic)dest).getTopicName();
339 }
340 else
341 {
342 return null;
343 }
344 }
345
346 public static Message copyJMSProperties(Message from, Message to, JmsConnector connector)
347 throws JMSException
348 {
349 if (connector.supportsProperty(JmsConstants.JMS_CORRELATION_ID))
350 {
351 to.setJMSCorrelationID(from.getJMSCorrelationID());
352 }
353 if (connector.supportsProperty(JmsConstants.JMS_DELIVERY_MODE))
354 {
355 to.setJMSDeliveryMode(from.getJMSDeliveryMode());
356 }
357 if (connector.supportsProperty(JmsConstants.JMS_DESTINATION))
358 {
359 to.setJMSDestination(from.getJMSDestination());
360 }
361 if (connector.supportsProperty(JmsConstants.JMS_EXPIRATION))
362 {
363 to.setJMSExpiration(from.getJMSExpiration());
364 }
365 if (connector.supportsProperty(JmsConstants.JMS_MESSAGE_ID))
366 {
367 to.setJMSMessageID(from.getJMSMessageID());
368 }
369 if (connector.supportsProperty(JmsConstants.JMS_PRIORITY))
370 {
371 to.setJMSPriority(from.getJMSPriority());
372 }
373 if (connector.supportsProperty(JmsConstants.JMS_REDELIVERED))
374 {
375 to.setJMSRedelivered(from.getJMSRedelivered());
376 }
377 if (connector.supportsProperty(JmsConstants.JMS_REPLY_TO))
378 {
379 to.setJMSReplyTo(from.getJMSReplyTo());
380 }
381 if (connector.supportsProperty(JmsConstants.JMS_TIMESTAMP))
382 {
383 to.setJMSTimestamp(from.getJMSTimestamp());
384 }
385 if (connector.supportsProperty(JmsConstants.JMS_TYPE))
386 {
387 to.setJMSType(from.getJMSType());
388 }
389 return to;
390 }
391
392 }