You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@camel.apache.org by da...@apache.org on 2015/07/20 13:53:06 UTC

[1/4] camel git commit: CAMEL-8966: Added toD as a simpler dynamic to as people often need this, and today they must use recipientList.

Repository: camel
Updated Branches:
  refs/heads/master 164022d25 -> 56a06b014


CAMEL-8966: Added toD as a simpler dynamic to as people often need this, and today they must use recipientList.


Project: http://git-wip-us.apache.org/repos/asf/camel/repo
Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/dfe2dae8
Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/dfe2dae8
Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/dfe2dae8

Branch: refs/heads/master
Commit: dfe2dae8cdc61a51870ff25824a42fecd780a8b6
Parents: 164022d
Author: Claus Ibsen <da...@apache.org>
Authored: Mon Jul 20 11:23:27 2015 +0200
Committer: Claus Ibsen <da...@apache.org>
Committed: Mon Jul 20 11:54:26 2015 +0200

----------------------------------------------------------------------
 .../camel/impl/DefaultLanguageResolver.java     |   2 +
 .../apache/camel/model/DynamicToDefinition.java | 186 +++++++++++++++++
 .../apache/camel/model/ProcessorDefinition.java |  33 ++-
 .../org/apache/camel/model/ToDefinition.java    |   2 +-
 .../camel/processor/DynamicSendProcessor.java   | 208 +++++++++++++++++++
 .../apache/camel/processor/SendProcessor.java   |   4 +-
 .../resources/org/apache/camel/model/jaxb.index |   1 +
 .../management/ManagedSendProcessorTest.java    |   2 +-
 .../camel/processor/ToDynamicIgnoreTest.java    |  53 +++++
 ...amicLanguageSimpleAndXPathAndHeaderTest.java |  44 ++++
 .../ToDynamicLanguageSimpleAndXPathTest.java    |  44 ++++
 .../processor/ToDynamicLanguageXPathTest.java   |  44 ++++
 .../apache/camel/processor/ToDynamicTest.java   |  55 +++++
 .../processor/SpringToDynamicIgnoreTest.java    |  30 +++
 ...amicLanguageSimpleAndXPathAndHeaderTest.java |  30 +++
 ...ringToDynamicLanguageSimpleAndXPathTest.java |  30 +++
 .../SpringToDynamicLanguageXPathTest.java       |  31 +++
 .../spring/processor/SpringToDynamicTest.java   |  30 +++
 .../processor/SpringToDynamicIgnoreTest.xml     |  34 +++
 ...namicLanguageSimpleAndXPathAndHeaderTest.xml |  34 +++
 ...pringToDynamicLanguageSimpleAndXPathTest.xml |  34 +++
 .../SpringToDynamicLanguageXPathTest.xml        |  34 +++
 .../spring/processor/SpringToDynamicTest.xml    |  34 +++
 23 files changed, 993 insertions(+), 6 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/main/java/org/apache/camel/impl/DefaultLanguageResolver.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/impl/DefaultLanguageResolver.java b/camel-core/src/main/java/org/apache/camel/impl/DefaultLanguageResolver.java
index 5201136..161e1d9 100644
--- a/camel-core/src/main/java/org/apache/camel/impl/DefaultLanguageResolver.java
+++ b/camel-core/src/main/java/org/apache/camel/impl/DefaultLanguageResolver.java
@@ -87,6 +87,8 @@ public class DefaultLanguageResolver implements LanguageResolver {
             type = findLanguageResolver("default", context);
         } catch (NoFactoryAvailableException e) {
             // ignore
+        } catch (ClassNotFoundException e) {
+            // ignore
         } catch (Exception e) {
             throw new IllegalArgumentException("Invalid URI, no LanguageResolver registered for scheme: " + name, e);
         }

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/main/java/org/apache/camel/model/DynamicToDefinition.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/model/DynamicToDefinition.java b/camel-core/src/main/java/org/apache/camel/model/DynamicToDefinition.java
new file mode 100644
index 0000000..fc1a2f7
--- /dev/null
+++ b/camel-core/src/main/java/org/apache/camel/model/DynamicToDefinition.java
@@ -0,0 +1,186 @@
+/**
+ * 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.model;
+
+import java.util.ArrayList;
+import java.util.List;
+import javax.xml.bind.annotation.XmlAccessType;
+import javax.xml.bind.annotation.XmlAccessorType;
+import javax.xml.bind.annotation.XmlAttribute;
+import javax.xml.bind.annotation.XmlRootElement;
+
+import org.apache.camel.ExchangePattern;
+import org.apache.camel.Expression;
+import org.apache.camel.NoSuchLanguageException;
+import org.apache.camel.Processor;
+import org.apache.camel.builder.ExpressionBuilder;
+import org.apache.camel.processor.DynamicSendProcessor;
+import org.apache.camel.spi.Language;
+import org.apache.camel.spi.Metadata;
+import org.apache.camel.spi.RouteContext;
+import org.apache.camel.util.ObjectHelper;
+
+/**
+ * Sends the message to a dynamic endpoint (uri supports languages)
+ * <p/>
+ * You can specify multiple languages in the uri separated by the plus sign, such as <tt>mock:+xpath:/order/@uri</tt>
+ * where <tt>mock:</tt> would be a prefix to a xpath expression.
+ * <p/>
+ * For more dynamic behavior use <a href="http://camel.apache.org/recipient-list.html">Recipient List</a> or
+ * <a href="http://camel.apache.org/dynamic-router.html">Dynamic Router</a> EIP instead.
+ */
+@Metadata(label = "eip,endpoint,routing")
+@XmlRootElement(name = "toD")
+@XmlAccessorType(XmlAccessType.FIELD)
+public class DynamicToDefinition extends NoOutputDefinition<DynamicToDefinition> {
+    @XmlAttribute @Metadata(required = "true")
+    private String uri;
+    @XmlAttribute
+    private ExchangePattern pattern;
+    @XmlAttribute
+    private Integer cacheSize;
+    @XmlAttribute
+    private Boolean ignoreInvalidEndpoint;
+
+    public DynamicToDefinition() {
+    }
+
+    public DynamicToDefinition(String uri) {
+        this.uri = uri;
+    }
+
+    @Override
+    public Processor createProcessor(RouteContext routeContext) throws Exception {
+        List<Expression> list = new ArrayList<Expression>();
+        String[] parts = uri.split("\\+");
+        for (String part : parts) {
+            // the part may have optional language to use, so you can mix languages
+            String before = ObjectHelper.before(part, ":");
+            String after = ObjectHelper.after(part, ":");
+            if (before != null && after != null) {
+                // maybe its a language
+                try {
+                    Language partLanguage = routeContext.getCamelContext().resolveLanguage(before);
+                    Expression exp = partLanguage.createExpression(after);
+                    list.add(exp);
+                    continue;
+                } catch (NoSuchLanguageException e) {
+                    // ignore
+                }
+            }
+            // fallback and use simple language
+            Language lan = routeContext.getCamelContext().resolveLanguage("simple");
+            Expression exp = lan.createExpression(part);
+            list.add(exp);
+        }
+
+        Expression exp;
+        if (list.size() == 1) {
+            exp = list.get(0);
+        } else {
+            exp = ExpressionBuilder.concatExpression(list);
+        }
+
+        DynamicSendProcessor processor = new DynamicSendProcessor(exp);
+        processor.setPattern(pattern);
+        if (cacheSize != null) {
+            processor.setCacheSize(cacheSize);
+        }
+        if (ignoreInvalidEndpoint != null) {
+            processor.setIgnoreInvalidEndpoint(ignoreInvalidEndpoint);
+        }
+        return processor;
+    }
+
+    @Override
+    public String toString() {
+        return "DynamicTo[" + getLabel() + "]";
+    }
+
+    // Fluent API
+    // -------------------------------------------------------------------------
+
+    /**
+     * Sets the optional {@link ExchangePattern} used to invoke this endpoint
+     */
+    public DynamicToDefinition pattern(ExchangePattern pattern) {
+        setPattern(pattern);
+        return this;
+    }
+
+    /**
+     * Sets the maximum size used by the {@link org.apache.camel.impl.ConsumerCache} which is used
+     * to cache and reuse consumers when using this pollEnrich, when uris are reused.
+     *
+     * @param cacheSize  the cache size, use <tt>0</tt> for default cache size, or <tt>-1</tt> to turn cache off.
+     * @return the builder
+     */
+    public DynamicToDefinition cacheSize(int cacheSize) {
+        setCacheSize(cacheSize);
+        return this;
+    }
+
+    /**
+     * Ignore the invalidate endpoint exception when try to create a producer with that endpoint
+     *
+     * @return the builder
+     */
+    public DynamicToDefinition ignoreInvalidEndpoint() {
+        setIgnoreInvalidEndpoint(true);
+        return this;
+    }
+
+    // Properties
+    // -------------------------------------------------------------------------
+
+    public String getUri() {
+        return uri;
+    }
+
+    /**
+     * The uri of the endpoint to send to. The uri can be dynamic computed using the {@link org.apache.camel.language.simple.SimpleLanguage} expression.
+     */
+    public void setUri(String uri) {
+        this.uri = uri;
+    }
+
+    public ExchangePattern getPattern() {
+        return pattern;
+    }
+
+    public void setPattern(ExchangePattern pattern) {
+        this.pattern = pattern;
+    }
+
+    public Integer getCacheSize() {
+        return cacheSize;
+    }
+
+    public void setCacheSize(Integer cacheSize) {
+        this.cacheSize = cacheSize;
+    }
+
+    public Boolean getIgnoreInvalidEndpoint() {
+        return ignoreInvalidEndpoint;
+    }
+
+    public void setIgnoreInvalidEndpoint(Boolean ignoreInvalidEndpoint) {
+        this.ignoreInvalidEndpoint = ignoreInvalidEndpoint;
+    }
+
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/main/java/org/apache/camel/model/ProcessorDefinition.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/model/ProcessorDefinition.java b/camel-core/src/main/java/org/apache/camel/model/ProcessorDefinition.java
index 2359774..5d6bc36 100644
--- a/camel-core/src/main/java/org/apache/camel/model/ProcessorDefinition.java
+++ b/camel-core/src/main/java/org/apache/camel/model/ProcessorDefinition.java
@@ -606,8 +606,37 @@ public abstract class ProcessorDefinition<Type extends ProcessorDefinition<Type>
     public Type to(String uri) {
         addOutput(new ToDefinition(uri));
         return (Type) this;
-    }   
-    
+    }
+
+    /**
+     * Sends the exchange to the given dynamic endpoint
+     *
+     * @param uri  the dynamic endpoint to send to (resolved using simple language by default)
+     * @return the builder
+     */
+    @SuppressWarnings("unchecked")
+    public Type toD(String uri) {
+        DynamicToDefinition answer = new DynamicToDefinition();
+        answer.setUri(uri);
+        addOutput(answer);
+        return (Type) this;
+    }
+
+    /**
+     * Sends the exchange to the given dynamic endpoint
+     *
+     * @param uri  the dynamic endpoint to send to (resolved using simple language by default)
+     * @return the builder
+     */
+    @SuppressWarnings("unchecked")
+    public Type toD(String uri, boolean ignoreInvalidEndpoint) {
+        DynamicToDefinition answer = new DynamicToDefinition();
+        answer.setUri(uri);
+        answer.setIgnoreInvalidEndpoint(ignoreInvalidEndpoint);
+        addOutput(answer);
+        return (Type) this;
+    }
+
     /**
      * Sends the exchange to the given endpoint
      *

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/main/java/org/apache/camel/model/ToDefinition.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/model/ToDefinition.java b/camel-core/src/main/java/org/apache/camel/model/ToDefinition.java
index d3724fd..4720e98 100644
--- a/camel-core/src/main/java/org/apache/camel/model/ToDefinition.java
+++ b/camel-core/src/main/java/org/apache/camel/model/ToDefinition.java
@@ -26,7 +26,7 @@ import org.apache.camel.ExchangePattern;
 import org.apache.camel.spi.Metadata;
 
 /**
- * Sends the message to an endpoint
+ * Sends the message to a static endpoint
  *
  * @version 
  */

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/main/java/org/apache/camel/processor/DynamicSendProcessor.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/processor/DynamicSendProcessor.java b/camel-core/src/main/java/org/apache/camel/processor/DynamicSendProcessor.java
new file mode 100644
index 0000000..523ed9e
--- /dev/null
+++ b/camel-core/src/main/java/org/apache/camel/processor/DynamicSendProcessor.java
@@ -0,0 +1,208 @@
+/**
+ * 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.processor;
+
+import org.apache.camel.AsyncCallback;
+import org.apache.camel.AsyncProcessor;
+import org.apache.camel.AsyncProducerCallback;
+import org.apache.camel.CamelContext;
+import org.apache.camel.CamelContextAware;
+import org.apache.camel.Endpoint;
+import org.apache.camel.Exchange;
+import org.apache.camel.ExchangePattern;
+import org.apache.camel.Expression;
+import org.apache.camel.NoTypeConversionAvailableException;
+import org.apache.camel.Producer;
+import org.apache.camel.impl.EmptyProducerCache;
+import org.apache.camel.impl.ProducerCache;
+import org.apache.camel.spi.IdAware;
+import org.apache.camel.support.ServiceSupport;
+import org.apache.camel.util.AsyncProcessorHelper;
+import org.apache.camel.util.EndpointHelper;
+import org.apache.camel.util.ExchangeHelper;
+import org.apache.camel.util.ServiceHelper;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+/**
+ * Processor for forwarding exchanges to a dynamic endpoint destination.
+ *
+ * @see org.apache.camel.processor.SendProcessor
+ */
+public class DynamicSendProcessor extends ServiceSupport implements AsyncProcessor, IdAware, CamelContextAware {
+    protected static final Logger LOG = LoggerFactory.getLogger(DynamicSendProcessor.class);
+    protected CamelContext camelContext;
+    protected final Expression expression;
+    protected ExchangePattern pattern;
+    protected ProducerCache producerCache;
+    protected String id;
+    protected boolean ignoreInvalidEndpoint;
+    protected int cacheSize;
+
+    public DynamicSendProcessor(Expression expression) {
+        this.expression = expression;
+    }
+
+    @Override
+    public String toString() {
+        return "sendTo(" + getExpression() + ")";
+    }
+
+    public String getId() {
+        return id;
+    }
+
+    public void setId(String id) {
+        this.id = id;
+    }
+
+    public void process(final Exchange exchange) throws Exception {
+        AsyncProcessorHelper.process(this, exchange);
+    }
+
+    public boolean process(Exchange exchange, final AsyncCallback callback) {
+        if (!isStarted()) {
+            exchange.setException(new IllegalStateException("SendProcessor has not been started: " + this));
+            callback.done(true);
+            return true;
+        }
+
+        // we should preserve existing MEP so remember old MEP
+        // if you want to permanently to change the MEP then use .setExchangePattern in the DSL
+        final ExchangePattern existingPattern = exchange.getPattern();
+
+        // which endpoint to send to
+        final Endpoint endpoint;
+        final ExchangePattern destinationExchangePattern;
+
+        // use dynamic endpoint so calculate the endpoint to use
+        Object recipient = null;
+        try {
+            recipient = expression.evaluate(exchange, Object.class);
+            endpoint = resolveEndpoint(exchange, recipient);
+            destinationExchangePattern = EndpointHelper.resolveExchangePatternFromUrl(endpoint.getEndpointUri());
+        } catch (Throwable e) {
+            if (isIgnoreInvalidEndpoint()) {
+                if (LOG.isDebugEnabled()) {
+                    LOG.debug("Endpoint uri is invalid: " + recipient + ". This exception will be ignored.", e);
+                }
+            } else {
+                exchange.setException(e);
+            }
+            callback.done(true);
+            return true;
+        }
+
+        // send the exchange to the destination using the producer cache
+        return producerCache.doInAsyncProducer(endpoint, exchange, pattern, callback, new AsyncProducerCallback() {
+            public boolean doInAsyncProducer(Producer producer, AsyncProcessor asyncProducer, final Exchange exchange,
+                                             ExchangePattern pattern, final AsyncCallback callback) {
+                final Exchange target = configureExchange(exchange, pattern, destinationExchangePattern, endpoint);
+                LOG.debug(">>>> {} {}", endpoint, exchange);
+                return asyncProducer.process(target, new AsyncCallback() {
+                    public void done(boolean doneSync) {
+                        // restore previous MEP
+                        target.setPattern(existingPattern);
+                        // signal we are done
+                        callback.done(doneSync);
+                    }
+                });
+            }
+        });
+    }
+
+    protected static Endpoint resolveEndpoint(Exchange exchange, Object recipient) throws NoTypeConversionAvailableException {
+        // trim strings as end users might have added spaces between separators
+        if (recipient instanceof String) {
+            recipient = ((String) recipient).trim();
+        } else if (recipient instanceof Endpoint) {
+            return (Endpoint) recipient;
+        } else {
+            // convert to a string type we can work with
+            recipient = exchange.getContext().getTypeConverter().mandatoryConvertTo(String.class, exchange, recipient);
+        }
+
+        return ExchangeHelper.resolveEndpoint(exchange, recipient);
+    }
+
+    protected Exchange configureExchange(Exchange exchange, ExchangePattern pattern, ExchangePattern destinationExchangePattern, Endpoint endpoint) {
+        // destination exchange pattern overrides pattern
+        if (destinationExchangePattern != null) {
+            exchange.setPattern(destinationExchangePattern);
+        } else if (pattern != null) {
+            exchange.setPattern(pattern);
+        }
+        // set property which endpoint we send to
+        exchange.setProperty(Exchange.TO_ENDPOINT, endpoint.getEndpointUri());
+        return exchange;
+    }
+
+    protected void doStart() throws Exception {
+        if (producerCache == null) {
+            if (cacheSize < 0) {
+                producerCache = new EmptyProducerCache(this, camelContext);
+                LOG.debug("DynamicSendTo {} is not using ProducerCache", this);
+            } else if (cacheSize == 0) {
+                producerCache = new ProducerCache(this, camelContext);
+                LOG.debug("DynamicSendTo {} using ProducerCache with default cache size", this);
+            } else {
+                producerCache = new ProducerCache(this, camelContext, cacheSize);
+                LOG.debug("DynamicSendTo {} using ProducerCache with cacheSize={}", this, cacheSize);
+            }
+        }
+    }
+
+    protected void doStop() throws Exception {
+        ServiceHelper.stopServices(producerCache);
+    }
+
+    public CamelContext getCamelContext() {
+        return camelContext;
+    }
+
+    public void setCamelContext(CamelContext camelContext) {
+        this.camelContext = camelContext;
+    }
+
+    public Expression getExpression() {
+        return expression;
+    }
+
+    public ExchangePattern getPattern() {
+        return pattern;
+    }
+
+    public void setPattern(ExchangePattern pattern) {
+        this.pattern = pattern;
+    }
+
+    public boolean isIgnoreInvalidEndpoint() {
+        return ignoreInvalidEndpoint;
+    }
+
+    public void setIgnoreInvalidEndpoint(boolean ignoreInvalidEndpoint) {
+        this.ignoreInvalidEndpoint = ignoreInvalidEndpoint;
+    }
+
+    public int getCacheSize() {
+        return cacheSize;
+    }
+
+    public void setCacheSize(int cacheSize) {
+        this.cacheSize = cacheSize;
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/main/java/org/apache/camel/processor/SendProcessor.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/processor/SendProcessor.java b/camel-core/src/main/java/org/apache/camel/processor/SendProcessor.java
index 3ab90d6..0304af9 100644
--- a/camel-core/src/main/java/org/apache/camel/processor/SendProcessor.java
+++ b/camel-core/src/main/java/org/apache/camel/processor/SendProcessor.java
@@ -46,9 +46,9 @@ import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
 /**
- * Processor for forwarding exchanges to an endpoint destination.
+ * Processor for forwarding exchanges to a static endpoint destination.
  *
- * @version 
+ * @see org.apache.camel.processor.DynamicSendProcessor
  */
 public class SendProcessor extends ServiceSupport implements AsyncProcessor, Traceable, EndpointAware, IdAware {
     protected static final Logger LOG = LoggerFactory.getLogger(SendProcessor.class);

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/main/resources/org/apache/camel/model/jaxb.index
----------------------------------------------------------------------
diff --git a/camel-core/src/main/resources/org/apache/camel/model/jaxb.index b/camel-core/src/main/resources/org/apache/camel/model/jaxb.index
index 7bd585a..7f54628 100644
--- a/camel-core/src/main/resources/org/apache/camel/model/jaxb.index
+++ b/camel-core/src/main/resources/org/apache/camel/model/jaxb.index
@@ -25,6 +25,7 @@ DataFormatDefinition
 DelayDefinition
 DescriptionDefinition
 DynamicRouterDefinition
+DynamicToDefinition
 EnrichDefinition
 ExpressionSubElementDefinition
 FilterDefinition

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/test/java/org/apache/camel/management/ManagedSendProcessorTest.java
----------------------------------------------------------------------
diff --git a/camel-core/src/test/java/org/apache/camel/management/ManagedSendProcessorTest.java b/camel-core/src/test/java/org/apache/camel/management/ManagedSendProcessorTest.java
index eed43c6..ad1b8a9 100644
--- a/camel-core/src/test/java/org/apache/camel/management/ManagedSendProcessorTest.java
+++ b/camel-core/src/test/java/org/apache/camel/management/ManagedSendProcessorTest.java
@@ -76,7 +76,7 @@ public class ManagedSendProcessorTest extends ManagementTestSupport {
 
         String json = (String) mbeanServer.invoke(on, "informationJson", null, null);
         assertNotNull(json);
-        assertTrue(json.contains("\"description\": \"Sends the message to an endpoint\""));
+        assertTrue(json.contains("\"description\": \"Sends the message to a static endpoint\""));
         assertTrue(json.contains(" \"uri\": { \"kind\": \"attribute\", \"required\": \"false\", \"type\": \"string\", \"javaType\": \"java.lang.String\","
                 + " \"deprecated\": \"false\", \"value\": \"mock:result\""));
     }

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/test/java/org/apache/camel/processor/ToDynamicIgnoreTest.java
----------------------------------------------------------------------
diff --git a/camel-core/src/test/java/org/apache/camel/processor/ToDynamicIgnoreTest.java b/camel-core/src/test/java/org/apache/camel/processor/ToDynamicIgnoreTest.java
new file mode 100644
index 0000000..9f5dfd6
--- /dev/null
+++ b/camel-core/src/test/java/org/apache/camel/processor/ToDynamicIgnoreTest.java
@@ -0,0 +1,53 @@
+/**
+ * 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.processor;
+
+import org.apache.camel.ContextTestSupport;
+import org.apache.camel.builder.RouteBuilder;
+
+public class ToDynamicIgnoreTest extends ContextTestSupport {
+
+    public void testToDynamic() throws Exception {
+        getMockEndpoint("mock:foo").expectedBodiesReceived("Hello Camel");
+        getMockEndpoint("mock:bar").expectedBodiesReceived("Hello World");
+
+        template.sendBodyAndHeader("direct:start", "Hello Camel", "foo", "foo");
+        template.sendBodyAndHeader("direct:start", "Hello World", "foo", "bar");
+
+        assertMockEndpointsSatisfied();
+    }
+
+    public void testToDynamicInvalid() throws Exception {
+        getMockEndpoint("mock:foo").expectedBodiesReceived("Hello Camel");
+
+        template.sendBodyAndHeader("direct:start", "Hello Camel", "foo", "foo");
+        template.sendBody("direct:start", "Hello World");
+
+        assertMockEndpointsSatisfied();
+    }
+
+    @Override
+    protected RouteBuilder createRouteBuilder() throws Exception {
+        return new RouteBuilder() {
+            @Override
+            public void configure() throws Exception {
+                from("direct:start")
+                    .toD("mock:${header.foo}", true);
+            }
+        };
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageSimpleAndXPathAndHeaderTest.java
----------------------------------------------------------------------
diff --git a/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageSimpleAndXPathAndHeaderTest.java b/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageSimpleAndXPathAndHeaderTest.java
new file mode 100644
index 0000000..0c48286
--- /dev/null
+++ b/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageSimpleAndXPathAndHeaderTest.java
@@ -0,0 +1,44 @@
+/**
+ * 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.processor;
+
+import org.apache.camel.ContextTestSupport;
+import org.apache.camel.builder.RouteBuilder;
+
+public class ToDynamicLanguageSimpleAndXPathAndHeaderTest extends ContextTestSupport {
+
+    public void testToDynamic() throws Exception {
+        getMockEndpoint("mock:foo-123").expectedBodiesReceived("<order uri=\"foo\"/>");
+        getMockEndpoint("mock:bar-456").expectedBodiesReceived("<order uri=\"bar\"/>");
+
+        template.sendBodyAndHeader("direct:start", "<order uri=\"foo\"/>", "sub", "-123");
+        template.sendBodyAndHeader("direct:start", "<order uri=\"bar\"/>", "sub", "-456");
+
+        assertMockEndpointsSatisfied();
+    }
+
+    @Override
+    protected RouteBuilder createRouteBuilder() throws Exception {
+        return new RouteBuilder() {
+            @Override
+            public void configure() throws Exception {
+                from("direct:start")
+                    .toD("mock:+xpath:/order/@uri+header:sub");
+            }
+        };
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageSimpleAndXPathTest.java
----------------------------------------------------------------------
diff --git a/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageSimpleAndXPathTest.java b/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageSimpleAndXPathTest.java
new file mode 100644
index 0000000..4827f18
--- /dev/null
+++ b/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageSimpleAndXPathTest.java
@@ -0,0 +1,44 @@
+/**
+ * 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.processor;
+
+import org.apache.camel.ContextTestSupport;
+import org.apache.camel.builder.RouteBuilder;
+
+public class ToDynamicLanguageSimpleAndXPathTest extends ContextTestSupport {
+
+    public void testToDynamic() throws Exception {
+        getMockEndpoint("mock:foo").expectedBodiesReceived("<order uri=\"foo\"/>");
+        getMockEndpoint("mock:bar").expectedBodiesReceived("<order uri=\"bar\"/>");
+
+        template.sendBody("direct:start", "<order uri=\"foo\"/>");
+        template.sendBody("direct:start", "<order uri=\"bar\"/>");
+
+        assertMockEndpointsSatisfied();
+    }
+
+    @Override
+    protected RouteBuilder createRouteBuilder() throws Exception {
+        return new RouteBuilder() {
+            @Override
+            public void configure() throws Exception {
+                from("direct:start")
+                    .toD("mock:+xpath:/order/@uri");
+            }
+        };
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageXPathTest.java
----------------------------------------------------------------------
diff --git a/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageXPathTest.java b/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageXPathTest.java
new file mode 100644
index 0000000..b0ea183
--- /dev/null
+++ b/camel-core/src/test/java/org/apache/camel/processor/ToDynamicLanguageXPathTest.java
@@ -0,0 +1,44 @@
+/**
+ * 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.processor;
+
+import org.apache.camel.ContextTestSupport;
+import org.apache.camel.builder.RouteBuilder;
+
+public class ToDynamicLanguageXPathTest extends ContextTestSupport {
+
+    public void testToDynamic() throws Exception {
+        getMockEndpoint("mock:foo").expectedBodiesReceived("<order uri=\"mock:foo\"/>");
+        getMockEndpoint("mock:bar").expectedBodiesReceived("<order uri=\"mock:bar\"/>");
+
+        template.sendBody("direct:start", "<order uri=\"mock:foo\"/>");
+        template.sendBody("direct:start", "<order uri=\"mock:bar\"/>");
+
+        assertMockEndpointsSatisfied();
+    }
+
+    @Override
+    protected RouteBuilder createRouteBuilder() throws Exception {
+        return new RouteBuilder() {
+            @Override
+            public void configure() throws Exception {
+                from("direct:start")
+                    .toD("xpath:/order/@uri");
+            }
+        };
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/camel-core/src/test/java/org/apache/camel/processor/ToDynamicTest.java
----------------------------------------------------------------------
diff --git a/camel-core/src/test/java/org/apache/camel/processor/ToDynamicTest.java b/camel-core/src/test/java/org/apache/camel/processor/ToDynamicTest.java
new file mode 100644
index 0000000..fc639e3
--- /dev/null
+++ b/camel-core/src/test/java/org/apache/camel/processor/ToDynamicTest.java
@@ -0,0 +1,55 @@
+/**
+ * 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.processor;
+
+import org.apache.camel.CamelExecutionException;
+import org.apache.camel.ContextTestSupport;
+import org.apache.camel.ResolveEndpointFailedException;
+import org.apache.camel.builder.RouteBuilder;
+
+public class ToDynamicTest extends ContextTestSupport {
+
+    public void testToDynamic() throws Exception {
+        getMockEndpoint("mock:foo").expectedBodiesReceived("Hello Camel");
+        getMockEndpoint("mock:bar").expectedBodiesReceived("Hello World");
+
+        template.sendBodyAndHeader("direct:start", "Hello Camel", "foo", "foo");
+        template.sendBodyAndHeader("direct:start", "Hello World", "foo", "bar");
+
+        assertMockEndpointsSatisfied();
+    }
+
+    public void testToDynamicInvalid() throws Exception {
+        try {
+            template.sendBody("direct:start", "Hello Camel");
+            fail("Should fail");
+        } catch (CamelExecutionException e) {
+            assertIsInstanceOf(ResolveEndpointFailedException.class, e.getCause());
+        }
+    }
+
+    @Override
+    protected RouteBuilder createRouteBuilder() throws Exception {
+        return new RouteBuilder() {
+            @Override
+            public void configure() throws Exception {
+                from("direct:start")
+                    .toD("mock:${header.foo}");
+            }
+        };
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicIgnoreTest.java
----------------------------------------------------------------------
diff --git a/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicIgnoreTest.java b/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicIgnoreTest.java
new file mode 100644
index 0000000..22107dd
--- /dev/null
+++ b/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicIgnoreTest.java
@@ -0,0 +1,30 @@
+/**
+ * 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.spring.processor;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.processor.ToDynamicIgnoreTest;
+
+import static org.apache.camel.spring.processor.SpringTestHelper.createSpringCamelContext;
+
+public class SpringToDynamicIgnoreTest extends ToDynamicIgnoreTest {
+
+    protected CamelContext createCamelContext() throws Exception {
+        return createSpringCamelContext(this, "org/apache/camel/spring/processor/SpringToDynamicIgnoreTest.xml");
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathAndHeaderTest.java
----------------------------------------------------------------------
diff --git a/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathAndHeaderTest.java b/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathAndHeaderTest.java
new file mode 100644
index 0000000..c4820d1
--- /dev/null
+++ b/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathAndHeaderTest.java
@@ -0,0 +1,30 @@
+/**
+ * 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.spring.processor;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.processor.ToDynamicLanguageSimpleAndXPathAndHeaderTest;
+
+import static org.apache.camel.spring.processor.SpringTestHelper.createSpringCamelContext;
+
+public class SpringToDynamicLanguageSimpleAndXPathAndHeaderTest extends ToDynamicLanguageSimpleAndXPathAndHeaderTest {
+
+    protected CamelContext createCamelContext() throws Exception {
+        return createSpringCamelContext(this, "org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathAndHeaderTest.xml");
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathTest.java
----------------------------------------------------------------------
diff --git a/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathTest.java b/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathTest.java
new file mode 100644
index 0000000..4a751e6
--- /dev/null
+++ b/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathTest.java
@@ -0,0 +1,30 @@
+/**
+ * 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.spring.processor;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.processor.ToDynamicLanguageSimpleAndXPathTest;
+
+import static org.apache.camel.spring.processor.SpringTestHelper.createSpringCamelContext;
+
+public class SpringToDynamicLanguageSimpleAndXPathTest extends ToDynamicLanguageSimpleAndXPathTest {
+
+    protected CamelContext createCamelContext() throws Exception {
+        return createSpringCamelContext(this, "org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathTest.xml");
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageXPathTest.java
----------------------------------------------------------------------
diff --git a/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageXPathTest.java b/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageXPathTest.java
new file mode 100644
index 0000000..401f6c2
--- /dev/null
+++ b/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicLanguageXPathTest.java
@@ -0,0 +1,31 @@
+/**
+ * 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.spring.processor;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.processor.ToDynamicIgnoreTest;
+import org.apache.camel.processor.ToDynamicLanguageXPathTest;
+
+import static org.apache.camel.spring.processor.SpringTestHelper.createSpringCamelContext;
+
+public class SpringToDynamicLanguageXPathTest extends ToDynamicLanguageXPathTest {
+
+    protected CamelContext createCamelContext() throws Exception {
+        return createSpringCamelContext(this, "org/apache/camel/spring/processor/SpringToDynamicLanguageXPathTest.xml");
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicTest.java
----------------------------------------------------------------------
diff --git a/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicTest.java b/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicTest.java
new file mode 100644
index 0000000..37c8709
--- /dev/null
+++ b/components/camel-spring/src/test/java/org/apache/camel/spring/processor/SpringToDynamicTest.java
@@ -0,0 +1,30 @@
+/**
+ * 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.spring.processor;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.processor.ToDynamicTest;
+
+import static org.apache.camel.spring.processor.SpringTestHelper.createSpringCamelContext;
+
+public class SpringToDynamicTest extends ToDynamicTest {
+
+    protected CamelContext createCamelContext() throws Exception {
+        return createSpringCamelContext(this, "org/apache/camel/spring/processor/SpringToDynamicTest.xml");
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicIgnoreTest.xml
----------------------------------------------------------------------
diff --git a/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicIgnoreTest.xml b/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicIgnoreTest.xml
new file mode 100644
index 0000000..0e8d21e
--- /dev/null
+++ b/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicIgnoreTest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+    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.
+-->
+<beans xmlns="http://www.springframework.org/schema/beans"
+       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+       xsi:schemaLocation="
+       http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
+       http://camel.apache.org/schema/spring http://camel.apache.org/schema/spring/camel-spring.xsd
+    ">
+
+  <!-- START SNIPPET: e1 -->
+  <camelContext xmlns="http://camel.apache.org/schema/spring">
+    <route>
+      <from uri="direct:start"/>
+      <toD uri="mock:${header.foo}" ignoreInvalidEndpoint="true"/>
+    </route>
+  </camelContext>
+  <!-- END SNIPPET: e1 -->
+
+</beans>

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathAndHeaderTest.xml
----------------------------------------------------------------------
diff --git a/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathAndHeaderTest.xml b/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathAndHeaderTest.xml
new file mode 100644
index 0000000..64ba8f5
--- /dev/null
+++ b/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathAndHeaderTest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+    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.
+-->
+<beans xmlns="http://www.springframework.org/schema/beans"
+       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+       xsi:schemaLocation="
+       http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
+       http://camel.apache.org/schema/spring http://camel.apache.org/schema/spring/camel-spring.xsd
+    ">
+
+  <!-- START SNIPPET: e1 -->
+  <camelContext xmlns="http://camel.apache.org/schema/spring">
+    <route>
+      <from uri="direct:start"/>
+      <toD uri="mock:+xpath:/order/@uri+header:sub"/>
+    </route>
+  </camelContext>
+  <!-- END SNIPPET: e1 -->
+
+</beans>

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathTest.xml
----------------------------------------------------------------------
diff --git a/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathTest.xml b/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathTest.xml
new file mode 100644
index 0000000..c498672
--- /dev/null
+++ b/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageSimpleAndXPathTest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+    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.
+-->
+<beans xmlns="http://www.springframework.org/schema/beans"
+       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+       xsi:schemaLocation="
+       http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
+       http://camel.apache.org/schema/spring http://camel.apache.org/schema/spring/camel-spring.xsd
+    ">
+
+  <!-- START SNIPPET: e1 -->
+  <camelContext xmlns="http://camel.apache.org/schema/spring">
+    <route>
+      <from uri="direct:start"/>
+      <toD uri="mock:+xpath:/order/@uri"/>
+    </route>
+  </camelContext>
+  <!-- END SNIPPET: e1 -->
+
+</beans>

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageXPathTest.xml
----------------------------------------------------------------------
diff --git a/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageXPathTest.xml b/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageXPathTest.xml
new file mode 100644
index 0000000..ca17736
--- /dev/null
+++ b/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicLanguageXPathTest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+    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.
+-->
+<beans xmlns="http://www.springframework.org/schema/beans"
+       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+       xsi:schemaLocation="
+       http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
+       http://camel.apache.org/schema/spring http://camel.apache.org/schema/spring/camel-spring.xsd
+    ">
+
+  <!-- START SNIPPET: e1 -->
+  <camelContext xmlns="http://camel.apache.org/schema/spring">
+    <route>
+      <from uri="direct:start"/>
+      <toD uri="xpath:/order/@uri"/>
+    </route>
+  </camelContext>
+  <!-- END SNIPPET: e1 -->
+
+</beans>

http://git-wip-us.apache.org/repos/asf/camel/blob/dfe2dae8/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicTest.xml
----------------------------------------------------------------------
diff --git a/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicTest.xml b/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicTest.xml
new file mode 100644
index 0000000..0b27fbc
--- /dev/null
+++ b/components/camel-spring/src/test/resources/org/apache/camel/spring/processor/SpringToDynamicTest.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+    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.
+-->
+<beans xmlns="http://www.springframework.org/schema/beans"
+       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+       xsi:schemaLocation="
+       http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
+       http://camel.apache.org/schema/spring http://camel.apache.org/schema/spring/camel-spring.xsd
+    ">
+
+  <!-- START SNIPPET: e1 -->
+  <camelContext xmlns="http://camel.apache.org/schema/spring">
+    <route>
+      <from uri="direct:start"/>
+      <toD uri="mock:${header.foo}"/>
+    </route>
+  </camelContext>
+  <!-- END SNIPPET: e1 -->
+
+</beans>


[2/4] camel git commit: CAMEL-8966: Add mbean for toD

Posted by da...@apache.org.
CAMEL-8966: Add mbean for toD


Project: http://git-wip-us.apache.org/repos/asf/camel/repo
Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/90f7feca
Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/90f7feca
Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/90f7feca

Branch: refs/heads/master
Commit: 90f7feca932b6e7cf8bfc9dfade45913edffcae1
Parents: dfe2dae
Author: Claus Ibsen <da...@apache.org>
Authored: Mon Jul 20 12:09:18 2015 +0200
Committer: Claus Ibsen <da...@apache.org>
Committed: Mon Jul 20 12:09:18 2015 +0200

----------------------------------------------------------------------
 .../mbean/ManagedDynamicSendProcessorMBean.java | 35 ++++++++
 .../DefaultManagementObjectStrategy.java        |  4 +
 .../mbean/ManagedDynamicSendProcessor.java      | 74 +++++++++++++++
 .../apache/camel/model/DynamicToDefinition.java |  7 +-
 .../camel/processor/DynamicSendProcessor.java   |  8 +-
 .../ManagedDynamicSendProcessorTest.java        | 95 ++++++++++++++++++++
 6 files changed, 219 insertions(+), 4 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/camel/blob/90f7feca/camel-core/src/main/java/org/apache/camel/api/management/mbean/ManagedDynamicSendProcessorMBean.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/api/management/mbean/ManagedDynamicSendProcessorMBean.java b/camel-core/src/main/java/org/apache/camel/api/management/mbean/ManagedDynamicSendProcessorMBean.java
new file mode 100644
index 0000000..7482cb8
--- /dev/null
+++ b/camel-core/src/main/java/org/apache/camel/api/management/mbean/ManagedDynamicSendProcessorMBean.java
@@ -0,0 +1,35 @@
+/**
+ * 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.api.management.mbean;
+
+import org.apache.camel.api.management.ManagedAttribute;
+
+public interface ManagedDynamicSendProcessorMBean extends ManagedProcessorMBean {
+
+    @ManagedAttribute(description = "The uri of the endpoint to send to. The uri can be dynamic computed using the expressions.", mask = true)
+    String getUri();
+
+    @ManagedAttribute(description = "Message Exchange Pattern")
+    String getMessageExchangePattern();
+
+    @ManagedAttribute(description = "Sets the maximum size used by the ProducerCacheN which is used to cache and reuse producers.")
+    Integer getCacheSize();
+
+    @ManagedAttribute(description = "Ignore the invalidate endpoint exception when try to create a producer with that endpoint")
+    Boolean isIgnoreInvalidEndpoint();
+
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/camel/blob/90f7feca/camel-core/src/main/java/org/apache/camel/management/DefaultManagementObjectStrategy.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/management/DefaultManagementObjectStrategy.java b/camel-core/src/main/java/org/apache/camel/management/DefaultManagementObjectStrategy.java
index 76a169c..3832d1c 100644
--- a/camel-core/src/main/java/org/apache/camel/management/DefaultManagementObjectStrategy.java
+++ b/camel-core/src/main/java/org/apache/camel/management/DefaultManagementObjectStrategy.java
@@ -38,6 +38,7 @@ import org.apache.camel.management.mbean.ManagedCamelContext;
 import org.apache.camel.management.mbean.ManagedComponent;
 import org.apache.camel.management.mbean.ManagedConsumer;
 import org.apache.camel.management.mbean.ManagedDelayer;
+import org.apache.camel.management.mbean.ManagedDynamicSendProcessor;
 import org.apache.camel.management.mbean.ManagedEndpoint;
 import org.apache.camel.management.mbean.ManagedErrorHandler;
 import org.apache.camel.management.mbean.ManagedEventNotifier;
@@ -55,6 +56,7 @@ import org.apache.camel.management.mbean.ManagedThroughputLogger;
 import org.apache.camel.model.ModelCamelContext;
 import org.apache.camel.model.ProcessorDefinition;
 import org.apache.camel.processor.Delayer;
+import org.apache.camel.processor.DynamicSendProcessor;
 import org.apache.camel.processor.ErrorHandler;
 import org.apache.camel.processor.SendProcessor;
 import org.apache.camel.processor.Throttler;
@@ -181,6 +183,8 @@ public class DefaultManagementObjectStrategy implements ManagementObjectStrategy
                 answer = new ManagedDelayer(context, (Delayer) target, definition);
             } else if (target instanceof Throttler) {
                 answer = new ManagedThrottler(context, (Throttler) target, definition);
+            } else if (target instanceof DynamicSendProcessor) {
+                answer = new ManagedDynamicSendProcessor(context, (DynamicSendProcessor) target, definition);
             } else if (target instanceof SendProcessor) {
                 SendProcessor sp = (SendProcessor) target;
                 // special for sending to throughput logger

http://git-wip-us.apache.org/repos/asf/camel/blob/90f7feca/camel-core/src/main/java/org/apache/camel/management/mbean/ManagedDynamicSendProcessor.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/management/mbean/ManagedDynamicSendProcessor.java b/camel-core/src/main/java/org/apache/camel/management/mbean/ManagedDynamicSendProcessor.java
new file mode 100644
index 0000000..7b32007
--- /dev/null
+++ b/camel-core/src/main/java/org/apache/camel/management/mbean/ManagedDynamicSendProcessor.java
@@ -0,0 +1,74 @@
+/**
+ * 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.management.mbean;
+
+import org.apache.camel.CamelContext;
+import org.apache.camel.api.management.ManagedResource;
+import org.apache.camel.api.management.mbean.ManagedDynamicSendProcessorMBean;
+import org.apache.camel.model.ProcessorDefinition;
+import org.apache.camel.processor.DynamicSendProcessor;
+import org.apache.camel.spi.ManagementStrategy;
+import org.apache.camel.util.URISupport;
+
+/**
+ * @version 
+ */
+@ManagedResource(description = "Managed DynamicSendProcessor")
+public class ManagedDynamicSendProcessor extends ManagedProcessor implements ManagedDynamicSendProcessorMBean {
+    private final DynamicSendProcessor processor;
+    private String uri;
+
+    public ManagedDynamicSendProcessor(CamelContext context, DynamicSendProcessor processor, ProcessorDefinition<?> definition) {
+        super(context, processor, definition);
+        this.processor = processor;
+    }
+
+    public void init(ManagementStrategy strategy) {
+        super.init(strategy);
+        boolean sanitize = strategy.getManagementAgent().getMask() != null ? strategy.getManagementAgent().getMask() : false;
+        if (sanitize) {
+            uri = URISupport.sanitizeUri(processor.getUri());
+        } else {
+            uri = processor.getUri();
+        }
+    }
+
+    public DynamicSendProcessor getProcessor() {
+        return processor;
+    }
+
+    public String getUri() {
+        return uri;
+    }
+
+    public String getMessageExchangePattern() {
+        if (processor.getPattern() != null) {
+            return processor.getPattern().name();
+        } else {
+            return null;
+        }
+    }
+
+    public Integer getCacheSize() {
+        return processor.getCacheSize();
+    }
+
+    public Boolean isIgnoreInvalidEndpoint() {
+        return processor.isIgnoreInvalidEndpoint();
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/90f7feca/camel-core/src/main/java/org/apache/camel/model/DynamicToDefinition.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/model/DynamicToDefinition.java b/camel-core/src/main/java/org/apache/camel/model/DynamicToDefinition.java
index fc1a2f7..cd264a2 100644
--- a/camel-core/src/main/java/org/apache/camel/model/DynamicToDefinition.java
+++ b/camel-core/src/main/java/org/apache/camel/model/DynamicToDefinition.java
@@ -65,6 +65,8 @@ public class DynamicToDefinition extends NoOutputDefinition<DynamicToDefinition>
 
     @Override
     public Processor createProcessor(RouteContext routeContext) throws Exception {
+        ObjectHelper.notEmpty(uri, "uri", this);
+
         List<Expression> list = new ArrayList<Expression>();
         String[] parts = uri.split("\\+");
         for (String part : parts) {
@@ -95,7 +97,7 @@ public class DynamicToDefinition extends NoOutputDefinition<DynamicToDefinition>
             exp = ExpressionBuilder.concatExpression(list);
         }
 
-        DynamicSendProcessor processor = new DynamicSendProcessor(exp);
+        DynamicSendProcessor processor = new DynamicSendProcessor(uri, exp);
         processor.setPattern(pattern);
         if (cacheSize != null) {
             processor.setCacheSize(cacheSize);
@@ -123,8 +125,7 @@ public class DynamicToDefinition extends NoOutputDefinition<DynamicToDefinition>
     }
 
     /**
-     * Sets the maximum size used by the {@link org.apache.camel.impl.ConsumerCache} which is used
-     * to cache and reuse consumers when using this pollEnrich, when uris are reused.
+     * Sets the maximum size used by the {@link org.apache.camel.impl.ConsumerCache} which is used to cache and reuse producers.
      *
      * @param cacheSize  the cache size, use <tt>0</tt> for default cache size, or <tt>-1</tt> to turn cache off.
      * @return the builder

http://git-wip-us.apache.org/repos/asf/camel/blob/90f7feca/camel-core/src/main/java/org/apache/camel/processor/DynamicSendProcessor.java
----------------------------------------------------------------------
diff --git a/camel-core/src/main/java/org/apache/camel/processor/DynamicSendProcessor.java b/camel-core/src/main/java/org/apache/camel/processor/DynamicSendProcessor.java
index 523ed9e..a8d5994 100644
--- a/camel-core/src/main/java/org/apache/camel/processor/DynamicSendProcessor.java
+++ b/camel-core/src/main/java/org/apache/camel/processor/DynamicSendProcessor.java
@@ -46,6 +46,7 @@ import org.slf4j.LoggerFactory;
 public class DynamicSendProcessor extends ServiceSupport implements AsyncProcessor, IdAware, CamelContextAware {
     protected static final Logger LOG = LoggerFactory.getLogger(DynamicSendProcessor.class);
     protected CamelContext camelContext;
+    protected final String uri;
     protected final Expression expression;
     protected ExchangePattern pattern;
     protected ProducerCache producerCache;
@@ -53,7 +54,8 @@ public class DynamicSendProcessor extends ServiceSupport implements AsyncProcess
     protected boolean ignoreInvalidEndpoint;
     protected int cacheSize;
 
-    public DynamicSendProcessor(Expression expression) {
+    public DynamicSendProcessor(String uri, Expression expression) {
+        this.uri = uri;
         this.expression = expression;
     }
 
@@ -178,6 +180,10 @@ public class DynamicSendProcessor extends ServiceSupport implements AsyncProcess
         this.camelContext = camelContext;
     }
 
+    public String getUri() {
+        return uri;
+    }
+
     public Expression getExpression() {
         return expression;
     }

http://git-wip-us.apache.org/repos/asf/camel/blob/90f7feca/camel-core/src/test/java/org/apache/camel/management/ManagedDynamicSendProcessorTest.java
----------------------------------------------------------------------
diff --git a/camel-core/src/test/java/org/apache/camel/management/ManagedDynamicSendProcessorTest.java b/camel-core/src/test/java/org/apache/camel/management/ManagedDynamicSendProcessorTest.java
new file mode 100644
index 0000000..6e17a46
--- /dev/null
+++ b/camel-core/src/test/java/org/apache/camel/management/ManagedDynamicSendProcessorTest.java
@@ -0,0 +1,95 @@
+/**
+ * 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.management;
+
+import javax.management.MBeanServer;
+import javax.management.ObjectName;
+import javax.management.openmbean.TabularData;
+
+import org.apache.camel.ServiceStatus;
+import org.apache.camel.builder.RouteBuilder;
+import org.apache.camel.component.mock.MockEndpoint;
+
+/**
+ * @version 
+ */
+public class ManagedDynamicSendProcessorTest extends ManagementTestSupport {
+
+    public void testManageDynamicSendProcessor() throws Exception {
+        // JMX tests dont work well on AIX CI servers (hangs them)
+        if (isPlatform("aix")) {
+            return;
+        }
+
+        MockEndpoint foo = getMockEndpoint("mock:foo");
+        foo.expectedMessageCount(1);
+
+        template.sendBodyAndHeader("direct:start", "Hello World", "whereto", "foo");
+
+        assertMockEndpointsSatisfied();
+
+        // get the stats for the route
+        MBeanServer mbeanServer = getMBeanServer();
+
+        // get the object name for the delayer
+        ObjectName on = ObjectName.getInstance("org.apache.camel:context=camel-1,type=processors,name=\"mysend\"");
+
+        // should be on route1
+        String routeId = (String) mbeanServer.getAttribute(on, "RouteId");
+        assertEquals("route1", routeId);
+
+        String camelId = (String) mbeanServer.getAttribute(on, "CamelId");
+        assertEquals("camel-1", camelId);
+
+        String state = (String) mbeanServer.getAttribute(on, "State");
+        assertEquals(ServiceStatus.Started.name(), state);
+
+        String uri = (String) mbeanServer.getAttribute(on, "Uri");
+        assertEquals("direct:${header.whereto}", uri);
+
+        String pattern = (String) mbeanServer.getAttribute(on, "MessageExchangePattern");
+        assertNull(pattern);
+
+        TabularData data = (TabularData) mbeanServer.invoke(on, "explain", new Object[]{false}, new String[]{"boolean"});
+        assertNotNull(data);
+        assertEquals(2, data.size());
+
+        data = (TabularData) mbeanServer.invoke(on, "explain", new Object[]{true}, new String[]{"boolean"});
+        assertNotNull(data);
+        assertEquals(6, data.size());
+
+        String json = (String) mbeanServer.invoke(on, "informationJson", null, null);
+        assertNotNull(json);
+        assertTrue(json.contains("\"description\": \"Sends the message to a dynamic endpoint (uri supports languages)"));
+        assertTrue(json.contains(" \"uri\": { \"kind\": \"attribute\", \"required\": \"true\", \"type\": \"string\", \"javaType\": \"java.lang.String\","
+                + " \"deprecated\": \"false\", \"value\": \"direct:${header.whereto}\""));
+    }
+
+    @Override
+    protected RouteBuilder createRouteBuilder() throws Exception {
+        return new RouteBuilder() {
+            @Override
+            public void configure() throws Exception {
+                from("direct:start")
+                    .toD("direct:${header.whereto}").id("mysend");
+
+                from("direct:foo").to("mock:foo");
+            }
+        };
+    }
+
+}


[3/4] camel git commit: CAMEL-8966: Add toD to scala-dsl

Posted by da...@apache.org.
CAMEL-8966: Add toD to scala-dsl


Project: http://git-wip-us.apache.org/repos/asf/camel/repo
Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/bfd3ff0f
Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/bfd3ff0f
Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/bfd3ff0f

Branch: refs/heads/master
Commit: bfd3ff0f8b12dfedbe8ab2572c983730bbc31bc1
Parents: 90f7fec
Author: Claus Ibsen <da...@apache.org>
Authored: Mon Jul 20 13:07:21 2015 +0200
Committer: Claus Ibsen <da...@apache.org>
Committed: Mon Jul 20 13:07:21 2015 +0200

----------------------------------------------------------------------
 .../scala/org/apache/camel/scala/dsl/DSL.scala  |  2 +
 .../camel/scala/dsl/SAbstractDefinition.scala   |  2 +
 .../camel/scala/dsl/builder/RouteBuilder.scala  |  2 +
 .../apache/camel/scala/dsl/ToDynamicTest.scala  | 47 ++++++++++++++++++++
 4 files changed, 53 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/camel/blob/bfd3ff0f/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/DSL.scala
----------------------------------------------------------------------
diff --git a/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/DSL.scala b/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/DSL.scala
index cfce461..2e48581 100644
--- a/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/DSL.scala
+++ b/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/DSL.scala
@@ -105,6 +105,8 @@ trait DSL {
   def throwException(exception: Exception) : DSL
   def throwException(exceptionType: Class[_ <: Exception], message: String) : DSL
   def to(uris: String*) : DSL
+  def toD(uri: String) : DSL
+  def toD(uri: String, ignoreInvalidEndpoint: Boolean) : DSL
   def transacted : DSL
   def transacted(ref: String) : DSL
   def transform(expression: Exchange => Any) : DSL

http://git-wip-us.apache.org/repos/asf/camel/blob/bfd3ff0f/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/SAbstractDefinition.scala
----------------------------------------------------------------------
diff --git a/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/SAbstractDefinition.scala b/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/SAbstractDefinition.scala
index 23914dd..7530227 100644
--- a/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/SAbstractDefinition.scala
+++ b/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/SAbstractDefinition.scala
@@ -174,5 +174,7 @@ abstract class SAbstractDefinition[P <: ProcessorDefinition[_]] extends DSL with
     }
     this
   }
+  def toD(uri: String) = wrap(target.toD(uri))
+  def toD(uri: String, ignoreInvalidEndpoint: Boolean) = wrap(target.toD(uri, ignoreInvalidEndpoint))
 
 }

http://git-wip-us.apache.org/repos/asf/camel/blob/bfd3ff0f/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/builder/RouteBuilder.scala
----------------------------------------------------------------------
diff --git a/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/builder/RouteBuilder.scala b/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/builder/RouteBuilder.scala
index 9faf2a4..cbaa426 100644
--- a/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/builder/RouteBuilder.scala
+++ b/components/camel-scala/src/main/scala/org/apache/camel/scala/dsl/builder/RouteBuilder.scala
@@ -212,6 +212,8 @@ class RouteBuilder extends Preamble with DSL with RoutesBuilder with Languages w
   def wireTap(uri: String, expression: Exchange => Any) = stack.top.wireTap(uri, expression)
 
   def to(uris: String*) = stack.top.to(uris: _*)
+  def toD(uri: String) = stack.top.toD(uri)
+  def toD(uri: String, ignoreInvalidEndpoint: Boolean) = stack.top.toD(uri, ignoreInvalidEndpoint)
   def -->(uris: String*) = stack.top.to(uris: _*)
 
 }

http://git-wip-us.apache.org/repos/asf/camel/blob/bfd3ff0f/components/camel-scala/src/test/scala/org/apache/camel/scala/dsl/ToDynamicTest.scala
----------------------------------------------------------------------
diff --git a/components/camel-scala/src/test/scala/org/apache/camel/scala/dsl/ToDynamicTest.scala b/components/camel-scala/src/test/scala/org/apache/camel/scala/dsl/ToDynamicTest.scala
new file mode 100644
index 0000000..ec3e8ba
--- /dev/null
+++ b/components/camel-scala/src/test/scala/org/apache/camel/scala/dsl/ToDynamicTest.scala
@@ -0,0 +1,47 @@
+/**
+ * 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.scala.dsl
+
+import org.apache.camel.scala.dsl.builder.RouteBuilder
+import org.junit.Test
+
+/**
+ * Test case for dynamic to
+ */
+class ToDynamicTest extends ScalaTestSupport {
+
+  @Test
+  def testToD() {
+    val mock = getMockEndpoint("mock:b")
+    mock.expectedMessageCount(1)
+
+    // send a string
+    template.sendBodyAndHeader("direct:b", "74", "foo", "b")
+
+    assertMockEndpointsSatisfied()
+  }
+  
+  val builder =
+    //START SNIPPET: e1
+    new RouteBuilder {
+       "direct:b" ==> {
+         toD("mock:${header.foo}")
+       }
+    }
+    //END SNIPPET: e1
+
+}


[4/4] camel git commit: CAMEL-8966: Add test to groovy dsl

Posted by da...@apache.org.
CAMEL-8966: Add test to groovy dsl


Project: http://git-wip-us.apache.org/repos/asf/camel/repo
Commit: http://git-wip-us.apache.org/repos/asf/camel/commit/56a06b01
Tree: http://git-wip-us.apache.org/repos/asf/camel/tree/56a06b01
Diff: http://git-wip-us.apache.org/repos/asf/camel/diff/56a06b01

Branch: refs/heads/master
Commit: 56a06b014332ca556827915a73c993b3d0c6b937
Parents: bfd3ff0
Author: Claus Ibsen <da...@apache.org>
Authored: Mon Jul 20 13:59:43 2015 +0200
Committer: Claus Ibsen <da...@apache.org>
Committed: Mon Jul 20 13:59:43 2015 +0200

----------------------------------------------------------------------
 .../camel/groovy/extend/CamelGroovyMethodsTest.groovy  | 13 +++++++++++--
 1 file changed, 11 insertions(+), 2 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/camel/blob/56a06b01/components/camel-groovy/src/test/groovy/org/apache/camel/groovy/extend/CamelGroovyMethodsTest.groovy
----------------------------------------------------------------------
diff --git a/components/camel-groovy/src/test/groovy/org/apache/camel/groovy/extend/CamelGroovyMethodsTest.groovy b/components/camel-groovy/src/test/groovy/org/apache/camel/groovy/extend/CamelGroovyMethodsTest.groovy
index 76db6db..2766892 100644
--- a/components/camel-groovy/src/test/groovy/org/apache/camel/groovy/extend/CamelGroovyMethodsTest.groovy
+++ b/components/camel-groovy/src/test/groovy/org/apache/camel/groovy/extend/CamelGroovyMethodsTest.groovy
@@ -18,13 +18,11 @@ package org.apache.camel.groovy.extend
 
 import org.apache.camel.EndpointInject
 import org.apache.camel.Exchange
-import org.apache.camel.ProducerTemplate
 import org.apache.camel.builder.RouteBuilder
 import org.apache.camel.component.mock.MockEndpoint
 import org.apache.camel.test.junit4.CamelTestSupport
 import org.junit.Test
 
-
 /**
  * Test a few DSL extensions. 
  */
@@ -126,6 +124,9 @@ class CamelGroovyMethodsTest extends CamelTestSupport {
                     }
                     .to('mock:test1')
 
+                from('direct:toD')
+                    .toD('mock:${header.foo}')
+
             }
             
         }
@@ -232,4 +233,12 @@ class CamelGroovyMethodsTest extends CamelTestSupport {
         // The created XML differs in terms of white spaces and line feeds.
         assertEquals(text.replaceAll('\\s+', ''), resultEndpoint.exchanges[0].in.body.replaceAll('\\s+', ''))
     }
+
+    @Test
+    void testToD() {
+        resultEndpoint.expectedMessageCount(1)
+        template.sendBodyAndHeader('direct:toD', WORLD, "foo", "test1")
+        resultEndpoint.assertIsSatisfied()
+    }
+
 }