001 /** 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017 package org.apache.camel.model; 018 019 import java.util.ArrayList; 020 import java.util.List; 021 import java.util.Collection; 022 import javax.xml.bind.annotation.XmlAccessType; 023 import javax.xml.bind.annotation.XmlAccessorType; 024 import javax.xml.bind.annotation.XmlElement; 025 import javax.xml.bind.annotation.XmlElementRef; 026 import javax.xml.bind.annotation.XmlRootElement; 027 import javax.xml.bind.annotation.XmlTransient; 028 029 import org.apache.camel.Processor; 030 import org.apache.camel.Route; 031 import org.apache.camel.builder.ErrorHandlerBuilder; 032 import org.apache.camel.impl.RouteContext; 033 import org.apache.camel.processor.CatchProcessor; 034 import org.apache.camel.processor.RedeliveryPolicy; 035 import org.apache.camel.util.ObjectHelper; 036 037 /** 038 * @version $Revision: 1.1 $ 039 */ 040 @XmlRootElement(name = "onException") 041 @XmlAccessorType(XmlAccessType.FIELD) 042 public class ExceptionType extends ProcessorType { 043 @XmlElementRef 044 private List<InterceptorType> interceptors = new ArrayList<InterceptorType>(); 045 @XmlElement(name = "exception") 046 private List<String> exceptions = new ArrayList<String>(); 047 @XmlElement(name = "redeliveryPolicy", required = false) 048 private RedeliveryPolicyType redeliveryPolicy; 049 @XmlElementRef 050 private List<ProcessorType> outputs = new ArrayList<ProcessorType>(); 051 @XmlTransient 052 private List<Class> exceptionClasses; 053 @XmlTransient 054 private Processor errorHandler; 055 056 public ExceptionType() { 057 } 058 059 public ExceptionType(List<Class> exceptionClasses) { 060 this.exceptionClasses = exceptionClasses; 061 } 062 063 public ExceptionType(Class exceptionType) { 064 exceptionClasses = new ArrayList<Class>(); 065 exceptionClasses.add(exceptionType); 066 } 067 068 @Override 069 public String toString() { 070 return "Exception[ " + getExceptionClasses() + " -> " + getOutputs() + "]"; 071 } 072 073 /** 074 * Allows an exception handler to create a new redelivery policy for this exception type 075 * @param parentPolicy the current redelivery policy 076 * @return a newly created redelivery policy, or return the original policy if no customization is required 077 * for this exception handler. 078 */ 079 public RedeliveryPolicy createRedeliveryPolicy(RedeliveryPolicy parentPolicy) { 080 if (redeliveryPolicy != null) { 081 return redeliveryPolicy.createRedeliveryPolicy(parentPolicy); 082 } 083 else if (errorHandler != null) { 084 // lets create a new error handler that has no retries 085 RedeliveryPolicy answer = parentPolicy.copy(); 086 answer.setMaximumRedeliveries(0); 087 return answer; 088 } 089 return parentPolicy; 090 } 091 092 public void addRoutes(RouteContext routeContext, Collection<Route> routes) throws Exception { 093 // lets attach a processor to an error handler 094 errorHandler = routeContext.createProcessor(this); 095 ErrorHandlerBuilder builder = routeContext.getRoute().getErrorHandlerBuilder(); 096 builder.addErrorHandlers(this); 097 } 098 099 @Override 100 public CatchProcessor createProcessor(RouteContext routeContext) throws Exception { 101 Processor childProcessor = routeContext.createProcessor(this); 102 return new CatchProcessor(getExceptionClasses(), childProcessor); 103 } 104 105 106 // Fluent API 107 //------------------------------------------------------------------------- 108 public ExceptionType backOffMultiplier(double backOffMultiplier) { 109 getOrCreateRedeliveryPolicy().backOffMultiplier(backOffMultiplier); 110 return this; 111 } 112 113 public ExceptionType collisionAvoidanceFactor(double collisionAvoidanceFactor) { 114 getOrCreateRedeliveryPolicy().collisionAvoidanceFactor(collisionAvoidanceFactor); 115 return this; 116 } 117 118 public ExceptionType collisionAvoidancePercent(short collisionAvoidancePercent) { 119 getOrCreateRedeliveryPolicy().collisionAvoidancePercent(collisionAvoidancePercent); 120 return this; 121 } 122 123 public ExceptionType initialRedeliveryDelay(long initialRedeliveryDelay) { 124 getOrCreateRedeliveryPolicy().initialRedeliveryDelay(initialRedeliveryDelay); 125 return this; 126 } 127 128 public ExceptionType maximumRedeliveries(int maximumRedeliveries) { 129 getOrCreateRedeliveryPolicy().maximumRedeliveries(maximumRedeliveries); 130 return this; 131 } 132 133 public ExceptionType useCollisionAvoidance() { 134 getOrCreateRedeliveryPolicy().useCollisionAvoidance(); 135 return this; 136 } 137 138 public ExceptionType useExponentialBackOff() { 139 getOrCreateRedeliveryPolicy().useExponentialBackOff(); 140 return this; 141 } 142 143 144 // Properties 145 //------------------------------------------------------------------------- 146 public List<InterceptorType> getInterceptors() { 147 return interceptors; 148 } 149 150 public void setInterceptors(List<InterceptorType> interceptors) { 151 this.interceptors = interceptors; 152 } 153 154 public List<ProcessorType> getOutputs() { 155 return outputs; 156 } 157 158 public void setOutputs(List<ProcessorType> outputs) { 159 this.outputs = outputs; 160 } 161 162 public List<Class> getExceptionClasses() { 163 if (exceptionClasses == null) { 164 exceptionClasses = createExceptionClasses(); 165 } 166 return exceptionClasses; 167 } 168 169 public void setExceptionClasses(List<Class> exceptionClasses) { 170 this.exceptionClasses = exceptionClasses; 171 } 172 173 public List<String> getExceptions() { 174 return exceptions; 175 } 176 177 public void setExceptions(List<String> exceptions) { 178 this.exceptions = exceptions; 179 } 180 181 public Processor getErrorHandler() { 182 return errorHandler; 183 } 184 185 public RedeliveryPolicyType getRedeliveryPolicy() { 186 return redeliveryPolicy; 187 } 188 189 public void setRedeliveryPolicy(RedeliveryPolicyType redeliveryPolicy) { 190 this.redeliveryPolicy = redeliveryPolicy; 191 } 192 193 // Implementation methods 194 //------------------------------------------------------------------------- 195 protected RedeliveryPolicyType getOrCreateRedeliveryPolicy() { 196 if (redeliveryPolicy == null) { 197 redeliveryPolicy = new RedeliveryPolicyType(); 198 } 199 return redeliveryPolicy; 200 } 201 202 protected List<Class> createExceptionClasses() { 203 List<String> list = getExceptions(); 204 List<Class> answer = new ArrayList<Class>(list.size()); 205 for (String name : list) { 206 Class type = ObjectHelper.loadClass(name, getClass().getClassLoader()); 207 answer.add(type); 208 } 209 return answer; 210 } 211 }