protected Processor createErrorHandler( RouteContext routeContext, Exchange exchange, Processor processor) { Processor answer; boolean tryBlock = exchange.getProperty(Exchange.TRY_ROUTE_BLOCK, false, boolean.class); // do not wrap in error handler if we are inside a try block if (!tryBlock && routeContext != null) { // wrap the producer in error handler so we have fine grained error handling on // the output side instead of the input side // this is needed to support redelivery on that output alone and not doing redelivery // for the entire multicast block again which will start from scratch again // create key for cache final PreparedErrorHandler key = new PreparedErrorHandler(routeContext, processor); // lookup cached first to reuse and preserve memory answer = errorHandlers.get(key); if (answer != null) { LOG.trace("Using existing error handler for: {}", processor); return answer; } LOG.trace("Creating error handler for: {}", processor); ErrorHandlerFactory builder = routeContext.getRoute().getErrorHandlerBuilder(); // create error handler (create error handler directly to keep it light weight, // instead of using ProcessorDefinition.wrapInErrorHandler) try { processor = builder.createErrorHandler(routeContext, processor); // and wrap in unit of work processor so the copy exchange also can run under UoW answer = createUnitOfWorkProcessor(routeContext, processor, exchange); boolean child = exchange.getProperty(Exchange.PARENT_UNIT_OF_WORK, UnitOfWork.class) != null; // must start the error handler ServiceHelper.startServices(answer); // here we don't cache the child unit of work if (!child) { // add to cache errorHandlers.putIfAbsent(key, answer); } } catch (Exception e) { throw ObjectHelper.wrapRuntimeCamelException(e); } } else { // and wrap in unit of work processor so the copy exchange also can run under UoW answer = createUnitOfWorkProcessor(routeContext, processor, exchange); } return answer; }
protected void stopChildService(Route route, Set<Service> services, boolean shutdown) throws Exception { for (Service service : services) { LOG.debug( "{} child service on route: {} -> {}", new Object[] {shutdown ? "Shutting down" : "Stopping", route.getId(), service}); if (service instanceof ErrorHandler) { // special for error handlers for (LifecycleStrategy strategy : camelContext.getLifecycleStrategies()) { strategy.onErrorHandlerRemove( route.getRouteContext(), (Processor) service, route.getRouteContext().getRoute().getErrorHandlerBuilder()); } } else { for (LifecycleStrategy strategy : camelContext.getLifecycleStrategies()) { strategy.onServiceRemove(camelContext, service, route); } } if (shutdown) { ServiceHelper.stopAndShutdownService(service); } else { ServiceHelper.stopService(service); } removeChildService(service); } }
public synchronized void warmUp() throws Exception { if (endpointDone.compareAndSet(false, true)) { // endpoints should only be started once as they can be reused on other routes // and whatnot, thus their lifecycle is to start once, and only to stop when Camel shutdown for (Route route : routes) { // ensure endpoint is started first (before the route services, such as the consumer) ServiceHelper.startService(route.getEndpoint()); } } if (warmUpDone.compareAndSet(false, true)) { for (Route route : routes) { // warm up the route first route.warmUp(); LOG.debug("Starting services on route: {}", route.getId()); List<Service> services = route.getServices(); // callback that we are staring these services route.onStartingServices(services); // gather list of services to start as we need to start child services as well Set<Service> list = new LinkedHashSet<Service>(); for (Service service : services) { list.addAll(ServiceHelper.getChildServices(service)); } // split into consumers and child services as we need to start the consumers // afterwards to avoid them being active while the others start List<Service> childServices = new ArrayList<Service>(); for (Service service : list) { // inject the route if (service instanceof RouteAware) { ((RouteAware) service).setRoute(route); } if (service instanceof Consumer) { inputs.put(route, (Consumer) service); } else { childServices.add(service); } } startChildService(route, childServices); // fire event EventHelper.notifyRouteAdded(camelContext, route); } // ensure lifecycle strategy is invoked which among others enlist the route in JMX for (LifecycleStrategy strategy : camelContext.getLifecycleStrategies()) { strategy.onRoutesAdd(routes); } // add routes to camel context camelContext.addRouteCollection(routes); } }
@Override public void afterPoll() throws Exception { LOG.trace("After poll {}", getEndpoint()); // suspend or stop our self if (!ServiceHelper.suspendService(this)) { ServiceHelper.stopService(this); } }
@Override public long beforePoll(long timeout) throws Exception { LOG.trace("Before poll {}", getEndpoint()); // resume or start our self if (!ServiceHelper.resumeService(this)) { ServiceHelper.startService(this); } // ensure at least timeout is as long as one poll delay return Math.max(timeout, getDelay()); }
@Override protected void doStart() throws Exception { ServiceHelper.startServices(output, outputAsync, deadLetter); // use a shared scheduler if (executorService == null || executorService.isShutdown()) { // camel context will shutdown the executor when it shutdown so no need to shut it down when // stopping if (executorServiceRef != null) { executorService = camelContext .getExecutorServiceStrategy() .lookupScheduled(this, "ErrorHandlerRedeliveryTask", executorServiceRef); if (executorService == null) { throw new IllegalArgumentException( "ExecutorServiceRef " + executorServiceRef + " not found in registry."); } } else { executorService = camelContext .getExecutorServiceStrategy() .newScheduledThreadPool(this, "ErrorHandlerRedeliveryTask"); } } // determine if redeliver is enabled or not redeliveryEnabled = determineIfRedeliveryIsEnabled(); if (log.isDebugEnabled()) { log.debug("Redelivery enabled: {} on error handler: {}", redeliveryEnabled, this); } }
@Override @After protected void tearDown() throws Exception { ServiceHelper.stopServices(context2, template2); super.tearDown(); }
@Test public void testScheduledResumeRoutePolicy() throws Exception { MockEndpoint success = context.getEndpoint("mock:success", MockEndpoint.class); success.expectedMessageCount(1); context .getComponent("quartz2", QuartzComponent.class) .setPropertiesFile("org/apache/camel/routepolicy/quartz2/myquartz.properties"); context.addRoutes( new RouteBuilder() { public void configure() { CronScheduledRoutePolicy policy = new CronScheduledRoutePolicy(); policy.setRouteResumeTime("*/3 * * * * ?"); from("direct:start").routeId("test").routePolicy(policy).to("mock:success"); } }); context.start(); ServiceHelper.suspendService(context.getRoute("test").getConsumer()); Thread.sleep(5000); assertTrue(context.getRouteStatus("test") == ServiceStatus.Started); template.sendBody("direct:start", "Ready or not, Here, I come"); success.assertIsSatisfied(); }
@Override protected void doShutdown() throws Exception { for (Route route : routes) { LOG.debug("Shutting down services on route: {}", route.getId()); // gather list of services to stop as we need to start child services as well Set<Service> services = gatherChildServices(route, true); // shutdown services stopChildService(route, services, true); // shutdown the route itself ServiceHelper.stopAndShutdownServices(route); // endpoints should only be stopped when Camel is shutting down // see more details in the warmUp method ServiceHelper.stopAndShutdownServices(route.getEndpoint()); // invoke callbacks on route policy if (route.getRouteContext().getRoutePolicyList() != null) { for (RoutePolicy routePolicy : route.getRouteContext().getRoutePolicyList()) { routePolicy.onRemove(route); } } // fire event EventHelper.notifyRouteRemoved(camelContext, route); } // need to call onRoutesRemove when the CamelContext is shutting down or Route is shutdown for (LifecycleStrategy strategy : camelContext.getLifecycleStrategies()) { strategy.onRoutesRemove(routes); } // remove the routes from the inflight registry for (Route route : routes) { camelContext.getInflightRepository().removeRoute(route.getId()); } // remove the routes from the collections camelContext.removeRouteCollection(routes); // clear inputs on shutdown inputs.clear(); warmUpDone.set(false); endpointDone.set(false); }
protected void onJobExecute(Action action, Route route) throws Exception { LOG.debug( "Scheduled Event notification received. Performing action: {} on route: {}", action, route.getId()); ServiceStatus routeStatus = route.getRouteContext().getCamelContext().getRouteStatus(route.getId()); if (action == Action.START) { if (routeStatus == ServiceStatus.Stopped) { startRoute(route); // here we just check the states of the Consumer } else if (ServiceHelper.isSuspended(route.getConsumer())) { startConsumer(route.getConsumer()); } } else if (action == Action.STOP) { if ((routeStatus == ServiceStatus.Started) || (routeStatus == ServiceStatus.Suspended)) { stopRoute(route, getRouteStopGracePeriod(), getTimeUnit()); } else { LOG.warn( "Route is not in a started/suspended state and cannot be stopped. The current route state is {}", routeStatus); } } else if (action == Action.SUSPEND) { if (routeStatus == ServiceStatus.Started) { stopConsumer(route.getConsumer()); } else { LOG.warn( "Route is not in a started state and cannot be suspended. The current route state is {}", routeStatus); } } else if (action == Action.RESUME) { if (routeStatus == ServiceStatus.Started) { if (ServiceHelper.isSuspended(route.getConsumer())) { startConsumer(route.getConsumer()); } else { LOG.warn("The Consumer {} is not suspended and cannot be resumed.", route.getConsumer()); } } else { LOG.warn( "Route is not in a started state and cannot be resumed. The current route state is {}", routeStatus); } } }
@Override protected void doStart() throws Exception { super.doStart(); if (producerCache == null) { producerCache = new ProducerCache(this, getCamelContext(), cacheSize); } ServiceHelper.startService(producerCache); }
@Override protected void doStart() throws Exception { super.doStart(); // validate that if backoff multiplier is in use, the threshold values is set correclty if (backoffMultiplier > 0) { if (backoffIdleThreshold <= 0 && backoffErrorThreshold <= 0) { throw new IllegalArgumentException( "backoffIdleThreshold and/or backoffErrorThreshold must be configured to a positive value when using backoffMultiplier"); } LOG.debug( "Using backoff[multiplier={}, idleThreshold={}, errorThreshold={}] on {}", new Object[] { backoffMultiplier, backoffIdleThreshold, backoffErrorThreshold, getEndpoint() }); } if (scheduler == null) { scheduler = new DefaultScheduledPollConsumerScheduler(); } scheduler.setCamelContext(getEndpoint().getCamelContext()); scheduler.onInit(this); scheduler.scheduleTask(this); // configure scheduler with options from this consumer Map<String, Object> properties = new HashMap<String, Object>(); IntrospectionSupport.getProperties(this, properties, null); IntrospectionSupport.setProperties( getEndpoint().getCamelContext().getTypeConverter(), scheduler, properties); if (schedulerProperties != null && !schedulerProperties.isEmpty()) { // need to use a copy in case the consumer is restarted so we keep the properties Map<String, Object> copy = new HashMap<String, Object>(schedulerProperties); IntrospectionSupport.setProperties( getEndpoint().getCamelContext().getTypeConverter(), scheduler, copy); if (copy.size() > 0) { throw new FailedToCreateConsumerException( getEndpoint(), "There are " + copy.size() + " scheduler parameters that couldn't be set on the endpoint." + " Check the uri if the parameters are spelt correctly and that they are properties of the endpoint." + " Unknown parameters=[" + copy + "]"); } } ObjectHelper.notNull(scheduler, "scheduler", this); ObjectHelper.notNull(pollStrategy, "pollStrategy", this); ServiceHelper.startService(scheduler); if (isStartScheduler()) { startScheduler(); } }
protected void startChildService(Route route, List<Service> services) throws Exception { for (Service service : services) { LOG.debug("Starting child service on route: {} -> {}", route.getId(), service); for (LifecycleStrategy strategy : camelContext.getLifecycleStrategies()) { strategy.onServiceAdd(camelContext, service, route); } ServiceHelper.startService(service); addChildService(service); } }
protected void doStop() throws Exception { // if we are stopping CamelContext then we are shutting down boolean isShutdownCamelContext = camelContext.isStopping(); if (isShutdownCamelContext || isRemovingRoutes()) { // need to call onRoutesRemove when the CamelContext is shutting down or Route is shutdown for (LifecycleStrategy strategy : camelContext.getLifecycleStrategies()) { strategy.onRoutesRemove(routes); } } for (Route route : routes) { LOG.debug("Stopping services on route: {}", route.getId()); // gather list of services to stop as we need to start child services as well Set<Service> services = gatherChildServices(route, true); // stop services stopChildService(route, services, isShutdownCamelContext); // stop the route itself if (isShutdownCamelContext) { ServiceHelper.stopAndShutdownServices(route); } else { ServiceHelper.stopServices(route); } // invoke callbacks on route policy if (route.getRouteContext().getRoutePolicyList() != null) { for (RoutePolicy routePolicy : route.getRouteContext().getRoutePolicyList()) { routePolicy.onStop(route); } } // fire event EventHelper.notifyRouteStopped(camelContext, route); } if (isRemovingRoutes()) { camelContext.removeRouteCollection(routes); } // need to warm up again warmUpDone.set(false); }
/** * The consumer is to be suspended because it exceeded the limit * * @param consumer the consumer * @param endpoint the endpoint * @throws Exception is thrown if error suspending the consumer */ protected void onSuspend(Consumer consumer, Endpoint endpoint) throws Exception { log.warn( "Suspending consumer " + consumer + " after " + limit + " attempts to consume from " + endpoint + ". You have to manually resume the consumer!"); ServiceHelper.suspendService(consumer); }
private void internalBeforeStop() { try { if (camelTemplate != null) { ServiceHelper.stopService(camelTemplate); camelTemplate = null; } } catch (Exception e) { LOG.debug( "Error stopping camelTemplate due " + e.getMessage() + ". This exception is ignored.", e); } }
@Override protected void doStop() throws Exception { ServiceHelper.stopService(scheduler); // clear counters backoffCounter = 0; idleCounter = 0; errorCounter = 0; super.doStop(); }
@Override public void onCompleted() { if (producer != null) { try { ServiceHelper.stopService(producer); } catch (Exception e) { throw new RuntimeCamelRxException(e); } finally { producer = null; } } }
protected void doStop() throws Exception { if (log.isDebugEnabled()) { log.debug("Stopping service pool: " + this); } for (BlockingQueue<Service> entry : pool.values()) { Collection<Service> values = new ArrayList<Service>(); entry.drainTo(values); ServiceHelper.stopServices(values); entry.clear(); } pool.clear(); }
@Override protected void doShutdown() throws Exception { ServiceHelper.stopAndShutdownServices(processors, errorHandlers, aggregationStrategy); // only clear error handlers when shutting down errorHandlers.clear(); if (shutdownExecutorService && executorService != null) { getCamelContext().getExecutorServiceManager().shutdownNow(executorService); } if (aggregateExecutorService != null) { getCamelContext().getExecutorServiceManager().shutdownNow(aggregateExecutorService); } }
@Override protected void doStart() throws Exception { super.doStart(); if (cacheManagerFactory == null) { InputStream is = null; if (configurationFile != null) { is = ResourceHelper.resolveMandatoryResourceAsInputStream( getCamelContext().getClassResolver(), configurationFile); } cacheManagerFactory = new DefaultCacheManagerFactory(is, configurationFile); } ServiceHelper.startService(cacheManagerFactory); }
@Override protected void doStart() throws Exception { ObjectHelper.notNull(camelContext, "camelContext", this); if (endpoint == null && endpointUri == null) { throw new IllegalArgumentException("Either endpoint or endpointUri must be configured"); } if (endpoint == null) { endpoint = camelContext.getEndpoint(endpointUri); } producer = endpoint.createProducer(); ServiceHelper.startService(producer); }
protected void doStart() throws Exception { if (consumerCache == null) { // create consumer cache if we use dynamic expressions for computing the endpoints to poll if (cacheSize < 0) { consumerCache = new EmptyConsumerCache(this, camelContext); LOG.debug("PollEnrich {} is not using ConsumerCache", this); } else if (cacheSize == 0) { consumerCache = new ConsumerCache(this, camelContext); LOG.debug("PollEnrich {} using ConsumerCache with default cache size", this); } else { consumerCache = new ConsumerCache(this, camelContext, cacheSize); LOG.debug("PollEnrich {} using ConsumerCache with cacheSize={}", this, cacheSize); } } ServiceHelper.startServices(consumerCache, aggregationStrategy); }
@Override @Before protected void setUp() throws Exception { super.setUp(); context2 = new DefaultCamelContext(); template2 = context2.createProducerTemplate(); ServiceHelper.startServices(template2, context2); // add routes after CamelContext has been started RouteBuilder routeBuilder = createRouteBuilderForSecondContext(); if (routeBuilder != null) { context2.addRoutes(routeBuilder); } }
@Override protected void doStart() throws Exception { // inject CamelContext before starting if (jsonMarshal instanceof CamelContextAware) { ((CamelContextAware) jsonMarshal).setCamelContext(camelContext); } if (jsonUnmarshal instanceof CamelContextAware) { ((CamelContextAware) jsonUnmarshal).setCamelContext(camelContext); } if (xmlMarshal instanceof CamelContextAware) { ((CamelContextAware) xmlMarshal).setCamelContext(camelContext); } if (xmlUnmarshal instanceof CamelContextAware) { ((CamelContextAware) xmlUnmarshal).setCamelContext(camelContext); } ServiceHelper.startServices(jsonMarshal, jsonUnmarshal, xmlMarshal, xmlUnmarshal); }
/** Gather all child services */ private Set<Service> gatherChildServices(Route route, boolean includeErrorHandler) { // gather list of services to stop as we need to start child services as well List<Service> services = new ArrayList<Service>(); services.addAll(route.getServices()); // also get route scoped services doGetRouteScopedServices(services, route); Set<Service> list = new LinkedHashSet<Service>(); for (Service service : services) { list.addAll(ServiceHelper.getChildServices(service)); } if (includeErrorHandler) { // also get route scoped error handler (which must be done last) doGetRouteScopedErrorHandler(list, route); } Set<Service> answer = new LinkedHashSet<Service>(); answer.addAll(list); return answer; }
protected void doStart() throws Exception { // ensure we are warmed up before starting the route warmUp(); for (Route route : routes) { // start the route itself ServiceHelper.startService(route); // invoke callbacks on route policy if (route.getRouteContext().getRoutePolicyList() != null) { for (RoutePolicy routePolicy : route.getRouteContext().getRoutePolicyList()) { routePolicy.onStart(route); } } // fire event EventHelper.notifyRouteStarted(camelContext, route); } }
protected void doStart() throws Exception { if (isParallelProcessing() && executorService == null) { throw new IllegalArgumentException( "ParallelProcessing is enabled but ExecutorService has not been set"); } if (timeout > 0 && !isParallelProcessing()) { throw new IllegalArgumentException( "Timeout is used but ParallelProcessing has not been enabled"); } if (isParallelProcessing() && aggregateExecutorService == null) { // use unbounded thread pool so we ensure the aggregate on-the-fly task always will have // assigned a thread // and run the tasks when the task is submitted. If not then the aggregate task may not be // able to run // and signal completion during processing, which would lead to what would appear as a // dead-lock or a slow processing String name = getClass().getSimpleName() + "-AggregateTask"; aggregateExecutorService = createAggregateExecutorService(name); } ServiceHelper.startServices(aggregationStrategy, processors); }
@Test public void testScheduledResumeRoutePolicy() throws Exception { MockEndpoint success = (MockEndpoint) context.getEndpoint("mock:success"); success.expectedMessageCount(1); context .getComponent("quartz", QuartzComponent.class) .setPropertiesFile("org/apache/camel/routepolicy/quartz/myquartz.properties"); context.getComponent("quartz", QuartzComponent.class).start(); context.addRoutes( new RouteBuilder() { public void configure() { SimpleScheduledRoutePolicy policy = new SimpleScheduledRoutePolicy(); long startTime = System.currentTimeMillis() + 3000L; policy.setRouteResumeDate(new Date(startTime)); policy.setRouteResumeRepeatCount(1); policy.setRouteResumeRepeatInterval(3000); from("direct:start").routeId("test").routePolicy(policy).to("mock:success"); } }); context.start(); ServiceHelper.suspendService(context.getRoute("test").getConsumer()); try { template.sendBody("direct:start", "Ready or not, Here, I come"); } catch (CamelExecutionException e) { LOG.debug("Consumer successfully suspended"); } Thread.sleep(4000); template.sendBody("direct:start", "Ready or not, Here, I come"); context.getComponent("quartz", QuartzComponent.class).stop(); success.assertIsSatisfied(); }
protected void doStop() throws Exception { ServiceHelper.stopServices(consumer, aggregationStrategy); }