This is an automated email from the ASF dual-hosted git repository. gnodet pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/camel.git
commit 63634ae617e84f7beb997deb61ac6035c68f7af4 Author: Guillaume Nodet <gno...@gmail.com> AuthorDate: Tue May 28 15:52:00 2019 +0200 [CAMEL-13564] Move state from ErrorHandlerBuilder to RouteContext --- .../cdi/transaction/JtaTransactionPolicy.java | 2 +- .../camel/spring/spi/SpringTransactionPolicy.java | 2 +- .../java/org/apache/camel/spi/RouteContext.java | 24 ++++++ .../camel/impl/engine/DefaultRouteContext.java | 22 ++++++ .../apache/camel/builder/ErrorHandlerBuilder.java | 23 ------ .../camel/builder/ErrorHandlerBuilderRef.java | 34 +------- .../camel/builder/ErrorHandlerBuilderSupport.java | 50 ++---------- .../camel/impl/AbstractModelCamelContext.java | 5 -- .../apache/camel/reifier/OnExceptionReifier.java | 2 +- .../reifier/errorhandler/ErrorHandlerReifier.java | 11 ++- .../camel/builder/ErrorHandlerBuilderRefTest.java | 90 ---------------------- 11 files changed, 63 insertions(+), 202 deletions(-) diff --git a/components/camel-cdi/src/main/java/org/apache/camel/cdi/transaction/JtaTransactionPolicy.java b/components/camel-cdi/src/main/java/org/apache/camel/cdi/transaction/JtaTransactionPolicy.java index e639526..eaa00c6 100644 --- a/components/camel-cdi/src/main/java/org/apache/camel/cdi/transaction/JtaTransactionPolicy.java +++ b/components/camel-cdi/src/main/java/org/apache/camel/cdi/transaction/JtaTransactionPolicy.java @@ -112,7 +112,7 @@ public abstract class JtaTransactionPolicy implements TransactedPolicy { // use error handlers from the configured builder if (builder != null) { - txBuilder.setErrorHandlers(routeContext, builder.getErrorHandlers(routeContext)); + routeContext.addErrorHandlerFactoryReference(builder, txBuilder); } answer = createTransactionErrorHandler(routeContext, processor, txBuilder); diff --git a/components/camel-spring/src/main/java/org/apache/camel/spring/spi/SpringTransactionPolicy.java b/components/camel-spring/src/main/java/org/apache/camel/spring/spi/SpringTransactionPolicy.java index 982b932..c9d3003 100644 --- a/components/camel-spring/src/main/java/org/apache/camel/spring/spi/SpringTransactionPolicy.java +++ b/components/camel-spring/src/main/java/org/apache/camel/spring/spi/SpringTransactionPolicy.java @@ -104,7 +104,7 @@ public class SpringTransactionPolicy implements TransactedPolicy { txBuilder.setSpringTransactionPolicy(this); if (builder != null) { // use error handlers from the configured builder - txBuilder.setErrorHandlers(routeContext, builder.getErrorHandlers(routeContext)); + routeContext.addErrorHandlerFactoryReference(builder, txBuilder); } answer = createTransactionErrorHandler(routeContext, processor, txBuilder); diff --git a/core/camel-api/src/main/java/org/apache/camel/spi/RouteContext.java b/core/camel-api/src/main/java/org/apache/camel/spi/RouteContext.java index d67feef..48c8967 100644 --- a/core/camel-api/src/main/java/org/apache/camel/spi/RouteContext.java +++ b/core/camel-api/src/main/java/org/apache/camel/spi/RouteContext.java @@ -18,6 +18,7 @@ package org.apache.camel.spi; import java.util.List; import java.util.Map; +import java.util.Set; import org.apache.camel.CamelContext; import org.apache.camel.Endpoint; @@ -253,4 +254,27 @@ public interface RouteContext extends RuntimeConfiguration, EndpointAware { void setOnException(String onExceptionId, Processor processor); + /** + * Adds error handler for the given exception type + * + * @param factory the error handler factory + * @param exception the exception to handle + */ + void addErrorHandler(ErrorHandlerFactory factory, NamedNode exception); + + /** + * Gets the error handlers + * + * @param factory the error handler factory + */ + Set<NamedNode> getErrorHandlers(ErrorHandlerFactory factory); + + /** + * Link the error handlers from a factory to another + * + * @param source the source factory + * @param target the target factory + */ + void addErrorHandlerFactoryReference(ErrorHandlerFactory source, ErrorHandlerFactory target); + } diff --git a/core/camel-base/src/main/java/org/apache/camel/impl/engine/DefaultRouteContext.java b/core/camel-base/src/main/java/org/apache/camel/impl/engine/DefaultRouteContext.java index 5c362ab..14628e3 100644 --- a/core/camel-base/src/main/java/org/apache/camel/impl/engine/DefaultRouteContext.java +++ b/core/camel-base/src/main/java/org/apache/camel/impl/engine/DefaultRouteContext.java @@ -18,8 +18,10 @@ package org.apache.camel.impl.engine; import java.util.ArrayList; import java.util.HashMap; +import java.util.LinkedHashSet; import java.util.List; import java.util.Map; +import java.util.Set; import org.apache.camel.CamelContext; import org.apache.camel.Endpoint; @@ -465,4 +467,24 @@ public class DefaultRouteContext implements RouteContext { properties.put(key, value); } + private Map<ErrorHandlerFactory, Set<NamedNode>> errorHandlers = new HashMap<>(); + + @Override + public void addErrorHandler(ErrorHandlerFactory factory, NamedNode onException) { + getErrorHandlers(factory).add(onException); + } + + @Override + public Set<NamedNode> getErrorHandlers(ErrorHandlerFactory factory) { + return errorHandlers.computeIfAbsent(factory, f -> new LinkedHashSet<>()); + } + + @Override + public void addErrorHandlerFactoryReference(ErrorHandlerFactory source, ErrorHandlerFactory target) { + Set<NamedNode> list = getErrorHandlers(source); + Set<NamedNode> previous = errorHandlers.put(target, list); + if (previous != null && previous != list) { + throw new IllegalStateException("multiple references with different handlers"); + } + } } diff --git a/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilder.java b/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilder.java index e814dba..cc0ec74 100644 --- a/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilder.java +++ b/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilder.java @@ -28,29 +28,6 @@ import org.apache.camel.spi.RouteContext; public interface ErrorHandlerBuilder extends ErrorHandlerFactory { /** - * Adds error handler for the given exception type - * - * @param routeContext the route context - * @param exception the exception to handle - */ - void addErrorHandlers(RouteContext routeContext, OnExceptionDefinition exception); - - /** - * Adds the error handlers for the given list of exception types - * - * @param routeContext the route context - * @param exceptions the list of exceptions to handle - */ - void setErrorHandlers(RouteContext routeContext, List<OnExceptionDefinition> exceptions); - - /** - * Gets the error handlers - * - * @param routeContext the route context - */ - List<OnExceptionDefinition> getErrorHandlers(RouteContext routeContext); - - /** * Whether this error handler supports transacted exchanges. */ boolean supportTransacted(); diff --git a/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilderRef.java b/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilderRef.java index 2d854e3..ebc60e9 100644 --- a/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilderRef.java +++ b/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilderRef.java @@ -32,36 +32,14 @@ import org.apache.camel.util.ObjectHelper; */ public class ErrorHandlerBuilderRef extends ErrorHandlerBuilderSupport { private final String ref; - private final Map<RouteContext, ErrorHandlerBuilder> handlers = new HashMap<>(); private boolean supportTransacted; public ErrorHandlerBuilderRef(String ref) { this.ref = ref; } - @Override - public void addErrorHandlers(RouteContext routeContext, OnExceptionDefinition exception) { - ErrorHandlerBuilder handler = handlers.get(routeContext); - if (handler != null) { - handler.addErrorHandlers(routeContext, exception); - } - super.addErrorHandlers(routeContext, exception); - } - - @Override - public boolean removeOnExceptionList(String id) { - for (RouteContext routeContext : handlers.keySet()) { - if (routeContext.getRouteId().equals(id)) { - handlers.remove(routeContext); - break; - } - } - return super.removeOnExceptionList(id); - } - - public Processor createErrorHandler(RouteContext routeContext, Processor processor) throws Exception { - ErrorHandlerFactory handler = handlers.computeIfAbsent(routeContext, this::createErrorHandler); + ErrorHandlerFactory handler = lookupErrorHandler(routeContext); return ErrorHandlerReifier.reifier(handler).createErrorHandler(routeContext, processor); } @@ -88,19 +66,15 @@ public class ErrorHandlerBuilderRef extends ErrorHandlerBuilderSupport { return ref; } - private ErrorHandlerBuilder createErrorHandler(RouteContext routeContext) { + private ErrorHandlerBuilder lookupErrorHandler(RouteContext routeContext) { ErrorHandlerBuilder handler = (ErrorHandlerBuilder) ErrorHandlerReifier.lookupErrorHandlerFactory(routeContext, getRef()); ObjectHelper.notNull(handler, "error handler '" + ref + "'"); // configure if the handler support transacted supportTransacted = handler.supportTransacted(); - List<OnExceptionDefinition> list = getErrorHandlers(routeContext); - if (list != null) { - for (OnExceptionDefinition exceptionType : list) { - handler.addErrorHandlers(routeContext, exceptionType); - } - } + routeContext.addErrorHandlerFactoryReference(this, handler); + return handler; } diff --git a/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilderSupport.java b/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilderSupport.java index 8e60a61..5058439 100644 --- a/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilderSupport.java +++ b/core/camel-core/src/main/java/org/apache/camel/builder/ErrorHandlerBuilderSupport.java @@ -17,10 +17,10 @@ package org.apache.camel.builder; import java.util.ArrayList; -import java.util.HashMap; import java.util.List; -import java.util.Map; +import java.util.Set; +import org.apache.camel.NamedNode; import org.apache.camel.Predicate; import org.apache.camel.Processor; import org.apache.camel.RuntimeCamelException; @@ -42,21 +42,9 @@ import org.apache.camel.util.ObjectHelper; * Base class for builders of error handling. */ public abstract class ErrorHandlerBuilderSupport implements ErrorHandlerBuilder { - private Map<RouteContext, List<OnExceptionDefinition>> onExceptions = new HashMap<>(); private ExceptionPolicyStrategy exceptionPolicyStrategy; - public void addErrorHandlers(RouteContext routeContext, OnExceptionDefinition exception) { - // only add if we not already have it - List<OnExceptionDefinition> list = onExceptions.computeIfAbsent(routeContext, rc -> new ArrayList<>()); - if (!list.contains(exception)) { - list.add(exception); - } - } - protected void cloneBuilder(ErrorHandlerBuilderSupport other) { - if (!onExceptions.isEmpty()) { - other.onExceptions.putAll(onExceptions); - } other.exceptionPolicyStrategy = exceptionPolicyStrategy; } @@ -70,11 +58,9 @@ public abstract class ErrorHandlerBuilderSupport implements ErrorHandlerBuilder if (handler instanceof ErrorHandlerSupport) { ErrorHandlerSupport handlerSupport = (ErrorHandlerSupport) handler; - List<OnExceptionDefinition> list = onExceptions.get(routeContext); - if (list != null) { - for (OnExceptionDefinition exception : list) { - addExceptionPolicy(handlerSupport, routeContext, exception); - } + Set<NamedNode> list = routeContext.getErrorHandlers(this); + for (NamedNode exception : list) { + addExceptionPolicy(handlerSupport, routeContext, (OnExceptionDefinition) exception); } } if (handler instanceof RedeliveryErrorHandler) { @@ -132,14 +118,6 @@ public abstract class ErrorHandlerBuilderSupport implements ErrorHandlerBuilder return answer; } - public List<OnExceptionDefinition> getErrorHandlers(RouteContext routeContext) { - return onExceptions.get(routeContext); - } - - public void setErrorHandlers(RouteContext routeContext, List<OnExceptionDefinition> exceptions) { - this.onExceptions.put(routeContext, exceptions); - } - /** * Sets the exception policy to use */ @@ -166,22 +144,4 @@ public abstract class ErrorHandlerBuilderSupport implements ErrorHandlerBuilder this.exceptionPolicyStrategy = exceptionPolicyStrategy; } - /** - * Remove the OnExceptionList by look up the route id from the ErrorHandlerBuilder internal map - * @param id the route id - * @return true if the route context is found and removed - */ - public boolean removeOnExceptionList(String id) { - for (RouteContext routeContext : onExceptions.keySet()) { - if (routeContext.getRouteId().equals(id)) { - onExceptions.remove(routeContext); - return true; - } - } - return false; - } - - public Map<RouteContext, List<OnExceptionDefinition>> getOnExceptions() { - return onExceptions; - } } diff --git a/core/camel-core/src/main/java/org/apache/camel/impl/AbstractModelCamelContext.java b/core/camel-core/src/main/java/org/apache/camel/impl/AbstractModelCamelContext.java index 449a2fd..10e4826 100644 --- a/core/camel-core/src/main/java/org/apache/camel/impl/AbstractModelCamelContext.java +++ b/core/camel-core/src/main/java/org/apache/camel/impl/AbstractModelCamelContext.java @@ -287,11 +287,6 @@ public abstract class AbstractModelCamelContext extends AbstractCamelContext imp } protected synchronized void shutdownRouteService(BaseRouteService routeService) throws Exception { - // remove the route from ErrorHandlerBuilder if possible - if (getErrorHandlerFactory() instanceof ErrorHandlerBuilderSupport) { - ErrorHandlerBuilderSupport builder = (ErrorHandlerBuilderSupport) getErrorHandlerFactory(); - builder.removeOnExceptionList(routeService.getId()); - } if (routeService instanceof RouteService) { model.getRouteDefinitions().remove(((RouteService) routeService).getRouteDefinition()); } diff --git a/core/camel-core/src/main/java/org/apache/camel/reifier/OnExceptionReifier.java b/core/camel-core/src/main/java/org/apache/camel/reifier/OnExceptionReifier.java index 98d19f8..eb5d3b9 100644 --- a/core/camel-core/src/main/java/org/apache/camel/reifier/OnExceptionReifier.java +++ b/core/camel-core/src/main/java/org/apache/camel/reifier/OnExceptionReifier.java @@ -73,7 +73,7 @@ class OnExceptionReifier extends ProcessorReifier<OnExceptionDefinition> { // lookup the error handler builder ErrorHandlerBuilder builder = (ErrorHandlerBuilder) routeContext.getErrorHandlerFactory(); // and add this as error handlers - builder.addErrorHandlers(routeContext, definition); + routeContext.addErrorHandler(builder, definition); } @Override diff --git a/core/camel-core/src/main/java/org/apache/camel/reifier/errorhandler/ErrorHandlerReifier.java b/core/camel-core/src/main/java/org/apache/camel/reifier/errorhandler/ErrorHandlerReifier.java index a7649ca..21c9d59 100644 --- a/core/camel-core/src/main/java/org/apache/camel/reifier/errorhandler/ErrorHandlerReifier.java +++ b/core/camel-core/src/main/java/org/apache/camel/reifier/errorhandler/ErrorHandlerReifier.java @@ -19,11 +19,13 @@ package org.apache.camel.reifier.errorhandler; import java.util.HashMap; import java.util.List; import java.util.Map; +import java.util.Set; import java.util.function.Function; import org.apache.camel.CamelContext; import org.apache.camel.ErrorHandlerFactory; import org.apache.camel.ExtendedCamelContext; +import org.apache.camel.NamedNode; import org.apache.camel.Processor; import org.apache.camel.RuntimeCamelException; import org.apache.camel.builder.DeadLetterChannelBuilder; @@ -193,7 +195,7 @@ public abstract class ErrorHandlerReifier<T extends ErrorHandlerBuilderSupport> } // inherit the error handlers from the other as they are to be shared // this is needed by camel-spring when none error handler has been explicit configured - ((ErrorHandlerBuilderSupport) answer).setErrorHandlers(routeContext, other.getErrorHandlers(routeContext)); + routeContext.addErrorHandlerFactoryReference(other, answer); } } else { // use specific configured error handler @@ -250,11 +252,8 @@ public abstract class ErrorHandlerReifier<T extends ErrorHandlerBuilderSupport> if (handler instanceof ErrorHandlerSupport) { ErrorHandlerSupport handlerSupport = (ErrorHandlerSupport) handler; - List<OnExceptionDefinition> list = definition.getOnExceptions().get(routeContext); - if (list != null) { - for (OnExceptionDefinition exception : list) { - ErrorHandlerBuilderSupport.addExceptionPolicy(handlerSupport, routeContext, exception); - } + for (NamedNode exception : routeContext.getErrorHandlers(definition)) { + ErrorHandlerBuilderSupport.addExceptionPolicy(handlerSupport, routeContext, (OnExceptionDefinition) exception); } } if (handler instanceof RedeliveryErrorHandler) { diff --git a/core/camel-core/src/test/java/org/apache/camel/builder/ErrorHandlerBuilderRefTest.java b/core/camel-core/src/test/java/org/apache/camel/builder/ErrorHandlerBuilderRefTest.java deleted file mode 100644 index 2479629..0000000 --- a/core/camel-core/src/test/java/org/apache/camel/builder/ErrorHandlerBuilderRefTest.java +++ /dev/null @@ -1,90 +0,0 @@ -/* - * Licensed to the Apache Software Foundation (ASF) under one or more - * contributor license agreements. See the NOTICE file distributed with - * this work for additional information regarding copyright ownership. - * The ASF licenses this file to You under the Apache License, Version 2.0 - * (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ -package org.apache.camel.builder; - -import java.lang.reflect.Field; -import java.util.Map; -import java.util.UUID; - -import org.apache.camel.CamelContext; -import org.apache.camel.ContextTestSupport; -import org.apache.camel.ExtendedCamelContext; -import org.apache.camel.impl.JndiRegistry; -import org.junit.Test; - -public class ErrorHandlerBuilderRefTest extends ContextTestSupport { - ErrorHandlerBuilderRef errorHandlerBuilderRef = new ErrorHandlerBuilderRef("ref"); - - @Override - public boolean isUseRouteBuilder() { - return true; - } - - @Override - protected JndiRegistry createRegistry() throws Exception { - JndiRegistry registry = super.createRegistry(); - registry.bind("ref", new DefaultErrorHandlerBuilder()); - return registry; - } - - @Override - protected CamelContext createCamelContext() throws Exception { - CamelContext context = super.createCamelContext(); - context.adapt(ExtendedCamelContext.class).setErrorHandlerFactory(errorHandlerBuilderRef); - return context; - } - - @Test - public void testErrorHandlerBuilderRef() throws Exception { - String uuid = UUID.randomUUID().toString(); - context.addRoutes(new TempRouteBuilder(uuid)); - checkObjectSize(2); - context.getRouteController().stopRoute(uuid); - context.removeRoute(uuid); - checkObjectSize(1); - } - - private void checkObjectSize(int size) throws Exception { - assertEquals("Get a wrong size of Route", size, context.getRoutes().size()); - Field field = ErrorHandlerBuilderRef.class.getDeclaredField("handlers"); - field.setAccessible(true); - assertEquals("Get a wrong size of ErrorHandler", size, ((Map<?, ?>) field.get(errorHandlerBuilderRef)).size()); - } - - private static class TempRouteBuilder extends RouteBuilder { - - final String routeId; - - TempRouteBuilder(String routeId) { - this.routeId = routeId; - } - - @Override - public void configure() throws Exception { - from("direct:foo").routeId(routeId).to("mock:foo"); - } - } - - protected RouteBuilder createRouteBuilder() throws Exception { - return new RouteBuilder() { - public void configure() { - from("direct:start").to("mock:result"); - } - }; - } - -}