1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.kuali.rice.ksb.messaging.exceptionhandling;
17
18 import javax.xml.namespace.QName;
19
20 import org.apache.commons.lang.StringUtils;
21 import org.apache.log4j.Logger;
22 import org.kuali.rice.core.api.exception.RiceRuntimeException;
23 import org.kuali.rice.core.api.reflect.ObjectDefinition;
24 import org.kuali.rice.core.api.resourceloader.GlobalResourceLoader;
25 import org.kuali.rice.ksb.api.KsbApiServiceLocator;
26 import org.kuali.rice.ksb.api.bus.Endpoint;
27 import org.kuali.rice.ksb.api.bus.ServiceBus;
28 import org.kuali.rice.ksb.api.messaging.AsynchronousCall;
29 import org.kuali.rice.ksb.messaging.PersistedMessageBO;
30 import org.kuali.rice.ksb.messaging.quartz.MessageServiceExecutorJob;
31 import org.kuali.rice.ksb.messaging.quartz.MessageServiceExecutorJobListener;
32 import org.kuali.rice.ksb.service.KSBServiceLocator;
33 import org.quartz.JobDataMap;
34 import org.quartz.JobDetail;
35 import org.quartz.Scheduler;
36 import org.quartz.SimpleTrigger;
37 import org.quartz.Trigger;
38
39
40
41
42
43
44
45
46
47
48 public class DefaultExceptionServiceImpl implements ExceptionRoutingService {
49
50 private static final Logger LOG = Logger.getLogger(DefaultExceptionServiceImpl.class);
51
52 public void placeInExceptionRouting(Throwable throwable, PersistedMessageBO message, Object service) throws Exception {
53 LOG.error("Exception caught processing message " + message.getRouteQueueId() + " " + message.getServiceName() + ": " + throwable);
54
55
56 AsynchronousCall methodCall = null;
57 if (message.getMethodCall() != null) {
58 methodCall = message.getMethodCall();
59 } else {
60 methodCall = message.getPayload().getMethodCall();
61 }
62 message.setMethodCall(methodCall);
63 MessageExceptionHandler exceptionHandler = getMessageExceptionHandler(methodCall.getServiceConfiguration().getServiceName());
64 exceptionHandler.handleException(throwable, message, service);
65 }
66
67 public void placeInExceptionRoutingLastDitchEffort(Throwable throwable, PersistedMessageBO message, Object service) throws Exception {
68 LOG.error("Exception caught processing message " + message.getRouteQueueId() + " " + message.getServiceName() + ": " + throwable);
69
70 AsynchronousCall methodCall = null;
71 if (message.getMethodCall() != null) {
72 methodCall = message.getMethodCall();
73 } else {
74 methodCall = message.getPayload().getMethodCall();
75 }
76 message.setMethodCall(methodCall);
77 MessageExceptionHandler exceptionHandler = getMessageExceptionHandler(methodCall.getServiceConfiguration().getServiceName());
78 exceptionHandler.handleExceptionLastDitchEffort(throwable, message, service);
79 }
80
81 protected MessageExceptionHandler getMessageExceptionHandler(QName serviceName) {
82 ServiceBus serviceBus = KsbApiServiceLocator.getServiceBus();
83 Endpoint endpoint = serviceBus.getEndpoint(serviceName);
84 if (endpoint == null) {
85 throw new RiceRuntimeException("No services found for name " + serviceName);
86 }
87 String messageExceptionHandlerName = endpoint.getServiceConfiguration().getMessageExceptionHandler();
88 if (messageExceptionHandlerName == null) {
89 messageExceptionHandlerName = DefaultMessageExceptionHandler.class.getName();
90 }
91 return (MessageExceptionHandler) GlobalResourceLoader.getObject(new ObjectDefinition(messageExceptionHandlerName));
92 }
93
94
95
96 public void scheduleExecution(Throwable throwable, PersistedMessageBO message, String description) throws Exception {
97 KSBServiceLocator.getMessageQueueService().delete(message);
98 PersistedMessageBO messageCopy = message.copy();
99 Scheduler scheduler = KSBServiceLocator.getScheduler();
100 JobDataMap jobData = new JobDataMap();
101 jobData.put(MessageServiceExecutorJob.MESSAGE_KEY, messageCopy);
102 JobDetail jobDetail = new JobDetail("Exception_Message_Job " + Math.random(), "Exception Messaging",
103 MessageServiceExecutorJob.class);
104 jobDetail.setJobDataMap(jobData);
105 if (!StringUtils.isBlank(description)) {
106 jobDetail.setDescription(description);
107 }
108 jobDetail.addJobListener(MessageServiceExecutorJobListener.NAME);
109 Trigger trigger = new SimpleTrigger("Exception_Message_Trigger " + Math.random(), "Exception Messaging", messageCopy
110 .getQueueDate());
111 trigger.setJobDataMap(jobData);
112 scheduler.scheduleJob(jobDetail, trigger);
113 }
114
115 }