1 /* 2 * Copyright 2005-2010 the original author or authors. 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package org.springframework.ws.server.endpoint; 18 19 import java.util.Set; 20 21 import org.springframework.core.Ordered; 22 import org.springframework.ws.context.MessageContext; 23 import org.springframework.ws.server.EndpointExceptionResolver; 24 25 import org.apache.commons.logging.Log; 26 import org.apache.commons.logging.LogFactory; 27 28 /** 29 * Abstract base class for {@link EndpointExceptionResolver EndpointExceptionResolvers}. 30 * <p/> 31 * <p>Provides a set of mapped endpoints that the resolver should map. 32 * 33 * @author Arjen Poutsma 34 * @author Tareq Abed Rabbo 35 * @since 1.0.0 36 */ 37 public abstract class AbstractEndpointExceptionResolver implements EndpointExceptionResolver, Ordered { 38 39 /** Shared {@link Log} for subclasses to use. */ 40 protected final Log logger = LogFactory.getLog(getClass()); 41 42 private int order = Integer.MAX_VALUE; // default: same as non-Ordered 43 44 private Set<?> mappedEndpoints; 45 46 private Log warnLogger; 47 48 /** 49 * Specify the set of endpoints that this exception resolver should map. <p>The exception mappings and the default 50 * fault will only apply to the specified endpoints. 51 * <p/> 52 * If no endpoints are set, both the exception mappings and the default fault will apply to all handlers. This means 53 * that a specified default fault will be used as fallback for all exceptions; any further 54 * <code>EndpointExceptionResolvers</code> in the chain will be ignored in this case. 55 */ 56 public void setMappedEndpoints(Set<?> mappedEndpoints) { 57 this.mappedEndpoints = mappedEndpoints; 58 } 59 60 /** 61 * Set the log category for warn logging. The name will be passed to the underlying logger implementation through 62 * Commons Logging, getting interpreted as log category according to the logger's configuration. 63 * <p/> 64 * Default is no warn logging. Specify this setting to activate warn logging into a specific category. 65 * Alternatively, override the {@link #logException} method for custom logging. 66 * 67 * @see org.apache.commons.logging.LogFactory#getLog(String) 68 * @see org.apache.log4j.Logger#getLogger(String) 69 * @see java.util.logging.Logger#getLogger(String) 70 */ 71 public void setWarnLogCategory(String loggerName) { 72 this.warnLogger = LogFactory.getLog(loggerName); 73 } 74 75 /** 76 * Specify the order value for this mapping. 77 * <p/> 78 * Default value is {@link Integer#MAX_VALUE}, meaning that it's non-ordered. 79 * 80 * @see org.springframework.core.Ordered#getOrder() 81 */ 82 public final void setOrder(int order) { 83 this.order = order; 84 } 85 86 public final int getOrder() { 87 return order; 88 } 89 90 /** 91 * Default implementation that checks whether the given <code>endpoint</code> is in the set of {@link 92 * #setMappedEndpoints mapped endpoints}. 93 * 94 * @see #resolveExceptionInternal(MessageContext,Object,Exception) 95 */ 96 public final boolean resolveException(MessageContext messageContext, Object endpoint, Exception ex) { 97 Object mappedEndpoint = endpoint instanceof MethodEndpoint ? ((MethodEndpoint) endpoint).getBean() : endpoint; 98 if (mappedEndpoints != null && !mappedEndpoints.contains(mappedEndpoint)) { 99 return false; 100 } 101 // Log exception, both at debug log level and at warn level, if desired. 102 if (logger.isDebugEnabled()) { 103 logger.debug("Resolving exception from endpoint [" + endpoint + "]: " + ex); 104 } 105 logException(ex, messageContext); 106 return resolveExceptionInternal(messageContext, endpoint, ex); 107 } 108 109 /** 110 * Log the given exception at warn level, provided that warn logging has been activated through the {@link 111 * #setWarnLogCategory "warnLogCategory"} property. 112 * <p/> 113 * Calls {@link #buildLogMessage} in order to determine the concrete message to log. Always passes the full 114 * exception to the logger. 115 * 116 * @param ex the exception that got thrown during handler execution 117 * @param messageContext current message context request 118 * @see #setWarnLogCategory 119 * @see #buildLogMessage 120 * @see org.apache.commons.logging.Log#warn(Object, Throwable) 121 */ 122 protected void logException(Exception ex, MessageContext messageContext) { 123 if (this.warnLogger != null && this.warnLogger.isWarnEnabled()) { 124 this.warnLogger.warn(buildLogMessage(ex, messageContext), ex); 125 } 126 } 127 128 /** 129 * Build a log message for the given exception, occured during processing the given message context. 130 * 131 * @param ex the exception that got thrown during handler execution 132 * @param messageContext the message context 133 * @return the log message to use 134 */ 135 protected String buildLogMessage(Exception ex, MessageContext messageContext) { 136 return "Endpoint execution resulted in exception"; 137 } 138 139 /** 140 * Template method for resolving exceptions that is called by {@link #resolveException}. 141 * 142 * @param messageContext current message context 143 * @param endpoint the executed endpoint, or <code>null</code> if none chosen at the time of the exception 144 * @param ex the exception that got thrown during endpoint execution 145 * @return <code>true</code> if resolved; <code>false</code> otherwise 146 * @see #resolveException(MessageContext,Object,Exception) 147 */ 148 protected abstract boolean resolveExceptionInternal(MessageContext messageContext, Object endpoint, Exception ex); 149 150 }