1
2
3
4
5
6
7 package org.mule.transport;
8
9 import org.mule.DefaultMuleEvent;
10 import org.mule.MessageExchangePattern;
11 import org.mule.OptimizedRequestContext;
12 import org.mule.ResponseOutputStream;
13 import org.mule.api.MuleEvent;
14 import org.mule.api.MuleException;
15 import org.mule.api.MuleMessage;
16 import org.mule.api.MuleSession;
17 import org.mule.api.config.MuleProperties;
18 import org.mule.api.construct.FlowConstruct;
19 import org.mule.api.context.WorkManager;
20 import org.mule.api.endpoint.EndpointURI;
21 import org.mule.api.endpoint.InboundEndpoint;
22 import org.mule.api.lifecycle.CreateException;
23 import org.mule.api.lifecycle.InitialisationException;
24 import org.mule.api.processor.MessageProcessor;
25 import org.mule.api.routing.filter.FilterUnacceptedException;
26 import org.mule.api.transaction.Transaction;
27 import org.mule.api.transformer.Transformer;
28 import org.mule.api.transport.Connector;
29 import org.mule.api.transport.MessageReceiver;
30 import org.mule.api.transport.PropertyScope;
31 import org.mule.api.transport.ReplyToHandler;
32 import org.mule.context.notification.EndpointMessageNotification;
33 import org.mule.session.DefaultMuleSession;
34 import org.mule.session.LegacySessionHandler;
35 import org.mule.transaction.TransactionCoordination;
36 import org.mule.util.ClassUtils;
37 import org.mule.util.ObjectUtils;
38
39 import java.io.OutputStream;
40 import java.util.List;
41
42 import org.apache.commons.lang.SerializationException;
43
44
45
46
47
48
49 public abstract class AbstractMessageReceiver extends AbstractTransportMessageHandler implements MessageReceiver
50 {
51
52
53
54 protected FlowConstruct flowConstruct;
55
56
57
58
59
60
61 protected MessageProcessor listener;
62
63
64
65
66
67 protected String receiverKey = null;
68
69
70
71
72
73
74
75 private EndpointURI endpointUri;
76
77 protected List<Transformer> defaultInboundTransformers;
78 protected List<Transformer> defaultResponseTransformers;
79
80 protected ReplyToHandler replyToHandler;
81
82
83
84
85
86
87
88
89
90
91
92
93
94 public AbstractMessageReceiver(Connector connector, FlowConstruct flowConstruct, InboundEndpoint endpoint)
95 throws CreateException
96 {
97 super(endpoint);
98
99 if (flowConstruct == null)
100 {
101 throw new IllegalArgumentException("FlowConstruct cannot be null");
102 }
103 this.flowConstruct = flowConstruct;
104 }
105
106 @Override
107 protected ConnectableLifecycleManager createLifecycleManager()
108 {
109 return new ConnectableLifecycleManager<MessageReceiver>(getReceiverKey(), this);
110 }
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125 @Override
126 public final void initialise() throws InitialisationException
127 {
128 endpointUri = endpoint.getEndpointURI();
129
130 defaultInboundTransformers = connector.getDefaultInboundTransformers(endpoint);
131 defaultResponseTransformers = connector.getDefaultResponseTransformers(endpoint);
132
133 replyToHandler = getReplyToHandler();
134
135 super.initialise();
136 }
137
138 public FlowConstruct getFlowConstruct()
139 {
140 return flowConstruct;
141 }
142
143 public final MuleEvent routeMessage(MuleMessage message) throws MuleException
144 {
145 Transaction tx = TransactionCoordination.getInstance().getTransaction();
146 return routeMessage(message, tx, null);
147 }
148
149 public final MuleEvent routeMessage(MuleMessage message, Transaction trans)
150 throws MuleException
151 {
152 return routeMessage(message, trans, null);
153 }
154
155 public final MuleEvent routeMessage(MuleMessage message,
156 Transaction trans,
157 OutputStream outputStream) throws MuleException
158 {
159 return routeMessage(message, new DefaultMuleSession(connector.getMuleContext()), trans,
160 outputStream);
161 }
162
163 public final MuleEvent routeMessage(MuleMessage message,
164 MuleSession session,
165 Transaction trans,
166 OutputStream outputStream) throws MuleException
167 {
168
169 final Object o = message.getInboundProperty(MuleProperties.MULE_REMOTE_SYNC_PROPERTY);
170 if (ObjectUtils.getBoolean(o, false) && !endpoint.getExchangePattern().hasResponse())
171 {
172 logger.warn("MuleClient.send() was used but inbound endpoint "
173 + endpoint.getEndpointURI().getUri().toString()
174 + " is not 'request-response'. No response will be returned.");
175 }
176
177 message.removeProperty(MuleProperties.MULE_REMOTE_SYNC_PROPERTY, PropertyScope.INBOUND);
178
179 MuleEvent muleEvent = createMuleEvent(message, outputStream);
180 muleEvent = OptimizedRequestContext.unsafeSetEvent(muleEvent);
181
182 if (!endpoint.isDisableTransportTransformer())
183 {
184 applyInboundTransformers(muleEvent);
185 }
186 MuleEvent resultEvent = listener.process(muleEvent);
187 if (resultEvent != null && resultEvent.getMessage() != null
188 && resultEvent.getMessage().getExceptionPayload() != null
189 && resultEvent.getMessage().getExceptionPayload().getException() instanceof FilterUnacceptedException)
190 {
191 handleUnacceptedFilter(muleEvent.getMessage());
192 return muleEvent;
193 }
194
195 if (resultEvent != null)
196 {
197 connector.getSessionHandler().storeSessionInfoToMessage(resultEvent.getSession(), resultEvent.getMessage());
198 }
199
200 if (endpoint.getExchangePattern()== MessageExchangePattern.REQUEST_RESPONSE && resultEvent != null && resultEvent.getMessage() != null && !endpoint.isDisableTransportTransformer())
201 {
202 applyResponseTransformers(resultEvent);
203 }
204
205 if (connector.isEnableMessageEvents() && endpoint.getExchangePattern().hasResponse() && resultEvent != null)
206 {
207 connector.fireNotification(new EndpointMessageNotification(
208 resultEvent.getMessage(), endpoint, resultEvent
209 .getFlowConstruct().getName(),
210 EndpointMessageNotification.MESSAGE_RESPONSE));
211 }
212
213 return resultEvent;
214 }
215
216 protected void applyInboundTransformers(MuleEvent event) throws MuleException
217 {
218 event.getMessage().applyTransformers(event, defaultInboundTransformers);
219 }
220
221 protected void applyResponseTransformers(MuleEvent event) throws MuleException
222 {
223 event.getMessage().applyTransformers(event, defaultResponseTransformers);
224 }
225
226 protected MuleMessage handleUnacceptedFilter(MuleMessage message)
227 {
228 if (logger.isDebugEnabled())
229 {
230 String messageId;
231 messageId = message.getUniqueId();
232 logger.debug("Message " + messageId + " failed to pass filter on endpoint: " + endpoint
233 + ". Message is being ignored");
234 }
235 return message;
236 }
237
238 protected MuleEvent createMuleEvent(MuleMessage message, OutputStream outputStream)
239 throws MuleException
240 {
241 ResponseOutputStream ros = null;
242 if (outputStream != null)
243 {
244 if (outputStream instanceof ResponseOutputStream)
245 {
246 ros = (ResponseOutputStream) outputStream;
247 }
248 else
249 {
250 ros = new ResponseOutputStream(outputStream);
251 }
252 }
253 MuleSession session;
254 try
255 {
256 session = connector.getSessionHandler().retrieveSessionInfoFromMessage(message);
257 }
258 catch (SerializationException se)
259 {
260 try
261 {
262
263 session = new LegacySessionHandler().retrieveSessionInfoFromMessage(message);
264 }
265 catch (Exception e)
266 {
267
268 throw se;
269 }
270 }
271 if (session != null)
272 {
273 session.setFlowConstruct(flowConstruct);
274 }
275 else
276 {
277 session = new DefaultMuleSession(flowConstruct, connector.getMuleContext());
278 }
279 if (message.getReplyTo() != null)
280 {
281 return new DefaultMuleEvent(message, getEndpoint(), session, ros, null, replyToHandler);
282 }
283 else
284 {
285 return new DefaultMuleEvent(message, getEndpoint(), session, ros, null, null);
286 }
287 }
288
289 public EndpointURI getEndpointURI()
290 {
291 return endpointUri;
292 }
293
294 @Override
295 public String getConnectionDescription()
296 {
297 return endpoint.getEndpointURI().toString();
298 }
299
300 protected String getConnectEventId()
301 {
302 return connector.getName() + ".receiver (" + endpoint.getEndpointURI() + ")";
303 }
304
305
306 public void setReceiverKey(String receiverKey)
307 {
308 this.receiverKey = receiverKey;
309 }
310
311 public String getReceiverKey()
312 {
313 return receiverKey;
314 }
315
316 @Override
317 public InboundEndpoint getEndpoint()
318 {
319 return (InboundEndpoint) super.getEndpoint();
320 }
321
322
323 public void setEndpoint(InboundEndpoint endpoint)
324 {
325 super.setEndpoint(endpoint);
326 }
327
328 @Override
329 protected WorkManager getWorkManager()
330 {
331 try
332 {
333 return connector.getReceiverWorkManager();
334 }
335 catch (MuleException e)
336 {
337 logger.error(e);
338 return null;
339 }
340 }
341
342 @Override
343 public String toString()
344 {
345 final StringBuffer sb = new StringBuffer(80);
346 sb.append(ClassUtils.getSimpleName(this.getClass()));
347 sb.append("{this=").append(Integer.toHexString(System.identityHashCode(this)));
348 sb.append(", receiverKey=").append(receiverKey);
349 sb.append(", endpoint=").append(endpoint.getEndpointURI());
350 sb.append('}');
351 return sb.toString();
352 }
353
354 public void setListener(MessageProcessor processor)
355 {
356 this.listener = processor;
357 }
358
359 @Override
360 protected void doDispose()
361 {
362 this.listener = null;
363 this.flowConstruct = null;
364 super.doDispose();
365 }
366
367 protected ReplyToHandler getReplyToHandler()
368 {
369 return ((AbstractConnector) endpoint.getConnector()).getReplyToHandler(endpoint);
370 }
371 }