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.builder;
018
019 import java.util.ArrayList;
020 import java.util.List;
021
022 import org.apache.camel.Endpoint;
023 import org.apache.camel.impl.InterceptSendToMockEndpointStrategy;
024 import org.apache.camel.model.ProcessorDefinition;
025 import org.apache.camel.model.RouteDefinition;
026 import org.apache.camel.util.ObjectHelper;
027
028 /**
029 * A {@link RouteBuilder} which has extended capabilities when using
030 * the <a href="http://camel.apache.org/advicewith.html">advice with</a> feature.
031 * <p/>
032 * <b>Important:</b> It is recommended to only advice a given route once (you can of course advice multiple routes).
033 * If you do it multiple times, then it may not work as expected, especially when any kind of error handling is involved.
034 * The Camel team plan for Camel 3.0 to support this as internal refactorings in the routing engine is needed to support this properly.
035 *
036 * @see org.apache.camel.model.RouteDefinition#adviceWith(org.apache.camel.CamelContext, RouteBuilder)
037 */
038 public abstract class AdviceWithRouteBuilder extends RouteBuilder {
039
040 private RouteDefinition originalRoute;
041 private final List<AdviceWithTask> adviceWithTasks = new ArrayList<AdviceWithTask>();
042
043 /**
044 * Sets the original route which we advice.
045 *
046 * @param originalRoute the original route we advice.
047 */
048 public void setOriginalRoute(RouteDefinition originalRoute) {
049 this.originalRoute = originalRoute;
050 }
051
052 /**
053 * Gets the original route we advice.
054 *
055 * @return the original route.
056 */
057 public RouteDefinition getOriginalRoute() {
058 return originalRoute;
059 }
060
061 /**
062 * Gets a list of additional tasks to execute after the {@link #configure()} method has been executed
063 * during the advice process.
064 *
065 * @return a list of additional {@link AdviceWithTask} tasks to be executed during the advice process.
066 */
067 public List<AdviceWithTask> getAdviceWithTasks() {
068 return adviceWithTasks;
069 }
070
071 /**
072 * Mock all endpoints in the route.
073 *
074 * @throws Exception can be thrown if error occurred
075 */
076 public void mockEndpoints() throws Exception {
077 getContext().addRegisterEndpointCallback(new InterceptSendToMockEndpointStrategy(null));
078 }
079
080 /**
081 * Mock all endpoints matching the given pattern.
082 *
083 * @param pattern the pattern(s).
084 * @throws Exception can be thrown if error occurred
085 * @see org.apache.camel.util.EndpointHelper#matchEndpoint(org.apache.camel.CamelContext, String, String)
086 */
087 public void mockEndpoints(String... pattern) throws Exception {
088 for (String s : pattern) {
089 getContext().addRegisterEndpointCallback(new InterceptSendToMockEndpointStrategy(s));
090 }
091 }
092
093 /**
094 * Mock all endpoints matching the given pattern, and <b>skips</b> sending to the original endpoint (detour messages).
095 *
096 * @param pattern the pattern(s).
097 * @throws Exception can be thrown if error occurred
098 * @see org.apache.camel.util.EndpointHelper#matchEndpoint(org.apache.camel.CamelContext, String, String)
099 */
100 public void mockEndpointsAndSkip(String... pattern) throws Exception {
101 for (String s : pattern) {
102 getContext().addRegisterEndpointCallback(new InterceptSendToMockEndpointStrategy(s, true));
103 }
104 }
105
106 /**
107 * Replaces the route from endpoint with a new uri
108 *
109 * @param uri uri of the new endpoint
110 */
111 public void replaceFromWith(String uri) {
112 ObjectHelper.notNull(originalRoute, "originalRoute", this);
113 getAdviceWithTasks().add(AdviceWithTasks.replaceFromWith(originalRoute, uri));
114 }
115
116 /**
117 * Replaces the route from endpoint with a new endpoint
118 *
119 * @param endpoint the new endpoint
120 */
121 public void replaceFromWith(Endpoint endpoint) {
122 ObjectHelper.notNull(originalRoute, "originalRoute", this);
123 getAdviceWithTasks().add(AdviceWithTasks.replaceFrom(originalRoute, endpoint));
124 }
125
126 /**
127 * Weaves by matching id of the nodes in the route.
128 * <p/>
129 * Uses the {@link org.apache.camel.util.EndpointHelper#matchPattern(String, String)} matching algorithm.
130 *
131 * @param pattern the pattern
132 * @return the builder
133 * @see org.apache.camel.util.EndpointHelper#matchPattern(String, String)
134 */
135 public <T extends ProcessorDefinition<?>> AdviceWithBuilder<T> weaveById(String pattern) {
136 ObjectHelper.notNull(originalRoute, "originalRoute", this);
137 return new AdviceWithBuilder<T>(this, pattern, null, null);
138 }
139
140 /**
141 * Weaves by matching the to string representation of the nodes in the route.
142 * <p/>
143 * Uses the {@link org.apache.camel.util.EndpointHelper#matchPattern(String, String)} matching algorithm.
144 *
145 * @param pattern the pattern
146 * @return the builder
147 * @see org.apache.camel.util.EndpointHelper#matchPattern(String, String)
148 */
149 public <T extends ProcessorDefinition<?>> AdviceWithBuilder<T> weaveByToString(String pattern) {
150 ObjectHelper.notNull(originalRoute, "originalRoute", this);
151 return new AdviceWithBuilder<T>(this, null, pattern, null);
152 }
153
154 /**
155 * Weaves by matching type of the nodes in the route.
156 *
157 * @param type the processor type
158 * @return the builder
159 */
160 public <T extends ProcessorDefinition<?>> AdviceWithBuilder<T> weaveByType(Class<T> type) {
161 ObjectHelper.notNull(originalRoute, "originalRoute", this);
162 return new AdviceWithBuilder<T>(this, null, null, type);
163 }
164
165 /**
166 * Weaves by adding the nodes to the start of the route.
167 *
168 * @return the builder
169 */
170 public <T extends ProcessorDefinition<?>> ProcessorDefinition<?> weaveAddFirst() {
171 ObjectHelper.notNull(originalRoute, "originalRoute", this);
172 return new AdviceWithBuilder<T>(this, "*", null, null).selectFirst().before();
173 }
174
175 /**
176 * Weaves by adding the nodes to the end of the route.
177 *
178 * @return the builder
179 */
180 public <T extends ProcessorDefinition<?>> ProcessorDefinition<?> weaveAddLast() {
181 ObjectHelper.notNull(originalRoute, "originalRoute", this);
182 return new AdviceWithBuilder<T>(this, "*", null, null).selectLast().after();
183 }
184
185 }