You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@camel.apache.org by dh...@apache.org on 2014/06/10 21:51:30 UTC

[02/35] git commit: Initial version of component util maven plugin

Initial version of component util maven plugin


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

Branch: refs/heads/master
Commit: 7c1a35fcaf0ead8da52b333136647a47e7dd24e8
Parents: 7431e7e
Author: Dhiraj Bokde <dh...@yahoo.com>
Authored: Fri May 23 18:35:56 2014 -0700
Committer: Dhiraj Bokde <dh...@yahoo.com>
Committed: Tue Jun 10 12:48:29 2014 -0700

----------------------------------------------------------------------
 .../camel-component-util-maven-plugin/pom.xml   | 111 +++++++++++
 .../camel/maven/ApiMethodGeneratorMojo.java     | 197 +++++++++++++++++++
 .../camel/maven/FileApiMethodGeneratorMojo.java |  82 ++++++++
 .../org/apache/camel/maven/Substitution.java    |  67 +++++++
 .../src/main/resources/api-method-enum.vm       |  62 ++++++
 .../apache/camel/maven/ApiMethodEnumTest.java   |  71 +++++++
 .../java/org/apache/camel/maven/TestProxy.java  |  64 ++++++
 .../src/test/resources/log4j.properties         |  36 ++++
 tooling/maven/pom.xml                           |   1 +
 9 files changed, 691 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/camel/blob/7c1a35fc/tooling/maven/camel-component-util-maven-plugin/pom.xml
----------------------------------------------------------------------
diff --git a/tooling/maven/camel-component-util-maven-plugin/pom.xml b/tooling/maven/camel-component-util-maven-plugin/pom.xml
new file mode 100644
index 0000000..d6159f1
--- /dev/null
+++ b/tooling/maven/camel-component-util-maven-plugin/pom.xml
@@ -0,0 +1,111 @@
+<?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.
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
+  <modelVersion>4.0.0</modelVersion>
+
+  <parent>
+    <groupId>org.apache.camel</groupId>
+    <artifactId>maven-plugins</artifactId>
+    <version>2.14-SNAPSHOT</version>
+  </parent>
+
+  <artifactId>camel-component-util-maven-plugin</artifactId>
+  <packaging>maven-plugin</packaging>
+  <name>Camel :: Maven Plugins :: Camel Component Utilities</name>
+  <description>Maven plugin to generate Camel Components for APIs</description>
+
+  <dependencies>
+    <dependency>
+      <groupId>org.apache.camel</groupId>
+      <artifactId>camel-core</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>org.apache.maven</groupId>
+      <artifactId>maven-plugin-api</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.apache.maven.plugin-tools</groupId>
+      <artifactId>maven-plugin-annotations</artifactId>
+      <version>3.3</version>
+      <scope>provided</scope>
+    </dependency>
+    <dependency>
+      <groupId>org.apache.maven</groupId>
+      <artifactId>maven-plugin-descriptor</artifactId>
+      <version>2.2.1</version>
+    </dependency>
+    <dependency>
+      <groupId>org.apache.maven</groupId>
+      <artifactId>maven-artifact</artifactId>
+      <version>2.2.1</version>
+    </dependency>
+    <dependency>
+      <groupId>org.apache.velocity</groupId>
+      <artifactId>velocity</artifactId>
+      <version>${velocity-version}</version>
+    </dependency>
+
+    <!-- add some logging to the classpath -->
+    <dependency>
+      <groupId>log4j</groupId>
+      <artifactId>log4j</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.slf4j</groupId>
+      <artifactId>slf4j-log4j12</artifactId>
+    </dependency>
+
+    <dependency>
+      <groupId>junit</groupId>
+      <artifactId>junit</artifactId>
+      <scope>test</scope>
+    </dependency>
+  </dependencies>
+
+  <build>
+    <pluginManagement>
+      <plugins>
+        <plugin>
+          <groupId>org.apache.maven.plugins</groupId>
+          <artifactId>maven-plugin-plugin</artifactId>
+          <version>3.3</version>
+          <configuration>
+            <!-- see http://jira.codehaus.org/browse/MNG-5346 -->
+            <skipErrorNoDescriptorsFound>true</skipErrorNoDescriptorsFound>
+          </configuration>
+          <executions>
+            <execution>
+              <id>mojo-descriptor</id>
+              <goals>
+                  <goal>descriptor</goal>
+              </goals>
+            </execution>
+            <execution>
+              <id>help-goal</id>
+              <goals>
+                  <goal>helpmojo</goal>
+              </goals>
+            </execution>
+          </executions>
+          </plugin>
+      </plugins>
+    </pluginManagement>
+  </build>
+
+</project>

http://git-wip-us.apache.org/repos/asf/camel/blob/7c1a35fc/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/ApiMethodGeneratorMojo.java
----------------------------------------------------------------------
diff --git a/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/ApiMethodGeneratorMojo.java b/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/ApiMethodGeneratorMojo.java
new file mode 100644
index 0000000..ff0d7f9
--- /dev/null
+++ b/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/ApiMethodGeneratorMojo.java
@@ -0,0 +1,197 @@
+/**
+ * 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.maven;
+
+import java.io.BufferedWriter;
+import java.io.File;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.net.MalformedURLException;
+import java.net.URL;
+import java.net.URLClassLoader;
+import java.util.Date;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Properties;
+
+import org.apache.camel.util.component.ApiMethodParser;
+import org.apache.log4j.Logger;
+import org.apache.maven.plugin.AbstractMojo;
+import org.apache.maven.plugin.MojoExecutionException;
+import org.apache.maven.plugin.MojoFailureException;
+import org.apache.maven.plugins.annotations.Parameter;
+import org.apache.maven.project.MavenProject;
+import org.apache.velocity.Template;
+import org.apache.velocity.VelocityContext;
+import org.apache.velocity.app.VelocityEngine;
+import org.apache.velocity.runtime.RuntimeConstants;
+import org.apache.velocity.runtime.log.Log4JLogChute;
+import org.apache.velocity.runtime.resource.loader.ClasspathResourceLoader;
+
+/**
+ * Base Mojo class for ApiMethod generators.
+ */
+public abstract class ApiMethodGeneratorMojo extends AbstractMojo {
+
+    protected static final String PREFIX = "camel.component.util.";
+
+    // used for velocity logging, to avoid creating velocity.log
+    private final Logger LOG = Logger.getLogger(this.getClass());
+
+    @Parameter(defaultValue = "${project}", readonly = true)
+    MavenProject project;
+
+    @Parameter(defaultValue = "${project.build.directory}/generated-sources/camelComponent")
+    protected File outDir;
+
+    @Parameter(defaultValue = "org.apache.camel.util.component")
+    protected String outPackage;
+
+    @Parameter(required = true, property = PREFIX + "proxyClass")
+    protected String proxyClass;
+
+    // cached fields
+    private Class<?> proxyType;
+    private ClassLoader projectClassLoader;
+    private VelocityEngine engine;
+
+    @Override
+    public void execute() throws MojoExecutionException, MojoFailureException {
+
+        // initialize velocity
+        initVelocityEngine();
+
+        // load proxy class and get enumeration file to generate
+        final Class proxyType = getProxyType();
+
+        // create parser
+        ApiMethodParser parser = createAdapterParser(proxyType);
+        parser.setSignatures(getSignatureList());
+        parser.setClassLoader(getProjectClassLoader());
+
+        // parse signatures
+        final List<ApiMethodParser.ApiMethodModel> models = parser.parse();
+
+        // generate enumeration from model
+        generateEnum(models);
+    }
+
+    protected ApiMethodParser createAdapterParser(Class proxyType) {
+        return new ApiMethodParser(proxyType){};
+    }
+
+    private void initVelocityEngine() {
+        // initialize velocity to load resources from class loader and use Log4J
+        Properties velocityProperties = new Properties();
+        velocityProperties.setProperty(RuntimeConstants.RESOURCE_LOADER, "cloader");
+        velocityProperties.setProperty("cloader.resource.loader.class", ClasspathResourceLoader.class.getName());
+        velocityProperties.setProperty(RuntimeConstants.RUNTIME_LOG_LOGSYSTEM_CLASS, Log4JLogChute.class.getName());
+        velocityProperties.setProperty(RuntimeConstants.RUNTIME_LOG_LOGSYSTEM + ".log4j.logger", LOG.getName());
+        engine = new VelocityEngine(velocityProperties);
+        engine.init();
+    }
+
+    private void generateEnum(List<ApiMethodParser.ApiMethodModel> models) throws MojoExecutionException {
+        final File apiMethodFile = getApiMethodFile();
+        // ensure parent directories exist
+        apiMethodFile.getParentFile().mkdirs();
+
+        // set template parameters
+        VelocityContext context = new VelocityContext();
+        context.put("generatedDate", new Date().toString());
+        context.put("packageName", outPackage);
+        context.put("enumName", getEnumName());
+        context.put("models", models);
+        context.put("proxyType", getProxyType());
+        context.put("helper", getClass());
+
+        // load velocity template
+        final Template template = engine.getTemplate("/api-method-enum.vm", "UTF-8");
+
+        // generate Enumeration
+        BufferedWriter writer = null;
+        try {
+            writer = new BufferedWriter(new FileWriter(apiMethodFile));
+            template.merge(context, writer);
+        } catch (IOException e) {
+            throw new MojoExecutionException(e.getMessage(), e);
+        } finally {
+            if (writer != null) {
+                try {
+                    writer.close();
+                } catch (IOException ignore) {}
+            }
+        }
+    }
+
+    public abstract List<String> getSignatureList() throws MojoExecutionException;
+
+    public Class getProxyType() throws MojoExecutionException {
+        if (proxyType == null) {
+            // load proxy class from Project runtime dependencies
+            try {
+                proxyType = getProjectClassLoader().loadClass(proxyClass);
+            } catch (ClassNotFoundException e) {
+                throw new MojoExecutionException(e.getMessage(), e);
+            }
+        }
+        return proxyType;
+    }
+
+    private ClassLoader getProjectClassLoader() throws MojoExecutionException {
+        if (projectClassLoader == null)  {
+            final List classpathElements;
+            try {
+                classpathElements = project.getRuntimeClasspathElements();
+            } catch (org.apache.maven.artifact.DependencyResolutionRequiredException e) {
+                throw new MojoExecutionException(e.getMessage(), e);
+            }
+            final URL[] urls = new URL[classpathElements.size()];
+            int i = 0;
+            for (Iterator it = classpathElements.iterator(); it.hasNext(); i++) {
+                try {
+                    urls[i] = new File((String) it.next()).toURI().toURL();
+                } catch (MalformedURLException e) {
+                    throw new MojoExecutionException(e.getMessage(), e);
+                }
+            }
+            projectClassLoader = new URLClassLoader(urls, Thread.currentThread().getContextClassLoader());
+        }
+        return projectClassLoader;
+    }
+
+    public File getApiMethodFile() throws MojoExecutionException {
+        final StringBuilder fileName = new StringBuilder();
+        fileName.append(outPackage.replaceAll("\\.", File.separator)).append(File.separator);
+        fileName.append(getEnumName()).append(".java");
+        return new File(outDir, fileName.toString());
+    }
+
+    private String getEnumName() throws MojoExecutionException {
+        return getProxyType().getSimpleName() + "ApiMethod";
+    }
+
+    public static String getType(Class<?> clazz) {
+        if (clazz.isArray()) {
+            // create a zero length array and get the class from the instance
+            return "new " + clazz.getCanonicalName().replaceAll("\\[\\]", "[0]") + ".getClass()";
+        } else {
+            return clazz.getCanonicalName() + ".class";
+        }
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/7c1a35fc/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/FileApiMethodGeneratorMojo.java
----------------------------------------------------------------------
diff --git a/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/FileApiMethodGeneratorMojo.java b/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/FileApiMethodGeneratorMojo.java
new file mode 100644
index 0000000..8ce2cf2
--- /dev/null
+++ b/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/FileApiMethodGeneratorMojo.java
@@ -0,0 +1,82 @@
+/**
+ * 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.maven;
+
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileNotFoundException;
+import java.io.FileReader;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+
+import org.apache.camel.util.component.ApiMethodParser;
+import org.apache.camel.util.component.ArgumentSubstitutionParser;
+import org.apache.maven.plugin.MojoExecutionException;
+import org.apache.maven.plugins.annotations.LifecyclePhase;
+import org.apache.maven.plugins.annotations.Mojo;
+import org.apache.maven.plugins.annotations.Parameter;
+import org.apache.maven.plugins.annotations.ResolutionScope;
+
+/**
+ * Parses ApiMethod signatures from a File.
+ */
+@Mojo(name = "fromFile", requiresDependencyResolution = ResolutionScope.RUNTIME, requiresProject = true,
+        defaultPhase = LifecyclePhase.GENERATE_SOURCES)
+public class FileApiMethodGeneratorMojo extends ApiMethodGeneratorMojo {
+
+    @Parameter(required = true, property = "camel.component.util.signatures")
+    protected File signatures;
+
+    @Parameter(property = "camel.component.util.substitutions")
+    protected Substitution[] substitutions;
+
+    @Override
+    protected ApiMethodParser createAdapterParser(Class proxyType) {
+        return new ArgumentSubstitutionParser(proxyType, getArgumentSubstitutions());
+    }
+
+    @Override
+    public List<String> getSignatureList() throws MojoExecutionException {
+        // get signatures as a list of Strings
+        List<String> result = new ArrayList<String>();
+        try {
+            BufferedReader reader = new BufferedReader(new FileReader(this.signatures));
+            String line = reader.readLine();
+            while (line != null) {
+                result.add(line);
+            }
+        } catch (FileNotFoundException e) {
+            throw new MojoExecutionException(e.getMessage(), e);
+        } catch (IOException e) {
+            throw new MojoExecutionException(e.getMessage(), e);
+        }
+        if (result.isEmpty()) {
+            throw new MojoExecutionException("Signature file " + signatures.getPath() + " is empty");
+        }
+        return result;
+    }
+
+    public ArgumentSubstitutionParser.Substitution[] getArgumentSubstitutions() {
+        ArgumentSubstitutionParser.Substitution[] subs = new ArgumentSubstitutionParser.Substitution[substitutions.length];
+        for (int i = 0; i < substitutions.length; i++) {
+            subs[i] = new ArgumentSubstitutionParser.Substitution(substitutions[i].getMethod(),
+                    substitutions[i].getArgName(), substitutions[i].getArgType(), substitutions[i].getReplacement());
+        }
+        return subs;
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/7c1a35fc/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/Substitution.java
----------------------------------------------------------------------
diff --git a/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/Substitution.java b/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/Substitution.java
new file mode 100644
index 0000000..c0772a7
--- /dev/null
+++ b/tooling/maven/camel-component-util-maven-plugin/src/main/java/org/apache/camel/maven/Substitution.java
@@ -0,0 +1,67 @@
+/**
+ * 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.maven;
+
+/**
+ * Argument name substitution for {@link FileApiMethodGeneratorMojo}.
+ */
+public class Substitution {
+
+    public String method;
+    private String argName;
+    private String argType;
+    private String replacement;
+
+    public Substitution(String method, String argName, String argType, String replacement) {
+        this.method = method;
+        this.argName = argName;
+        this.argType = argType;
+        this.replacement = replacement;
+    }
+
+    public String getMethod() {
+        return method;
+    }
+
+    public void setMethod(String method) {
+        this.method = method;
+    }
+
+    public String getArgName() {
+        return argName;
+    }
+
+    public void setArgName(String argName) {
+        this.argName = argName;
+    }
+
+    public String getArgType() {
+        return argType;
+    }
+
+    public void setArgType(String argType) {
+        this.argType = argType;
+    }
+
+    public String getReplacement() {
+        return replacement;
+    }
+
+    public void setReplacement(String replacement) {
+        this.replacement = replacement;
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/7c1a35fc/tooling/maven/camel-component-util-maven-plugin/src/main/resources/api-method-enum.vm
----------------------------------------------------------------------
diff --git a/tooling/maven/camel-component-util-maven-plugin/src/main/resources/api-method-enum.vm b/tooling/maven/camel-component-util-maven-plugin/src/main/resources/api-method-enum.vm
new file mode 100644
index 0000000..9dab27c
--- /dev/null
+++ b/tooling/maven/camel-component-util-maven-plugin/src/main/resources/api-method-enum.vm
@@ -0,0 +1,62 @@
+## ------------------------------------------------------------------------
+## 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.
+## ------------------------------------------------------------------------
+## api-method-enum.vm
+/*
+ * Camel ApiMethod Enumeration generated by camel-component-util-maven-plugin
+ * Generated on: $generatedDate
+ */
+package $packageName;
+
+import java.lang.reflect.Method;
+import java.util.List;
+
+import $proxyType.Name;
+
+import org.apache.camel.util.component.ApiMethod;
+import org.apache.camel.util.component.ApiMethodImpl;
+
+/**
+ * Camel {@link ApiMethod} Enumeration for $proxyType.Name
+ */
+public enum $enumName implements ApiMethod {
+
+#foreach ( $model in $models )
+    ${model.UniqueName}($helper.getType($model.ResultType), "$model.Name"#foreach ( $arg in $model.Arguments ), $helper.getType($arg.Type), "$arg.Name"#end)#if ( $foreach.hasNext ),#else;#end
+
+#end
+
+    private final ApiMethod apiMethod;
+
+    private ${enumName}(Class<?> resultType, String name, Object... args) {
+        this.apiMethod = new ApiMethodImpl(${proxyType.SimpleName}.class, resultType, name, args);
+    }
+
+    @Override
+    public String getName() { return apiMethod.getName(); }
+
+    @Override
+    public Class<?> getResultType() { return apiMethod.getResultType(); }
+
+    @Override
+    public List<String> getArgNames() { return apiMethod.getArgNames(); }
+
+    @Override
+    public List<Class<?>> getArgTypes() { return apiMethod.getArgTypes(); }
+
+    @Override
+    public Method getMethod() { return apiMethod.getMethod(); }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/7c1a35fc/tooling/maven/camel-component-util-maven-plugin/src/test/java/org/apache/camel/maven/ApiMethodEnumTest.java
----------------------------------------------------------------------
diff --git a/tooling/maven/camel-component-util-maven-plugin/src/test/java/org/apache/camel/maven/ApiMethodEnumTest.java b/tooling/maven/camel-component-util-maven-plugin/src/test/java/org/apache/camel/maven/ApiMethodEnumTest.java
new file mode 100644
index 0000000..b224a6e
--- /dev/null
+++ b/tooling/maven/camel-component-util-maven-plugin/src/test/java/org/apache/camel/maven/ApiMethodEnumTest.java
@@ -0,0 +1,71 @@
+/**
+ * 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.maven;
+
+import java.io.File;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.List;
+
+import org.apache.maven.artifact.DependencyResolutionRequiredException;
+import org.apache.maven.model.Model;
+import org.apache.maven.plugin.MojoExecutionException;
+import org.apache.maven.plugin.MojoFailureException;
+import org.apache.maven.project.MavenProject;
+import org.junit.Test;
+
+/**
+ * Tests api-method-enum.vm
+ */
+public class ApiMethodEnumTest {
+
+    @Test
+    public void testTemplate() throws IOException, MojoFailureException, MojoExecutionException {
+
+        final FileApiMethodGeneratorMojo mojo = new FileApiMethodGeneratorMojo() {
+
+            @Override
+            public List<String> getSignatureList() throws MojoExecutionException {
+                final ArrayList<String> signatures = new ArrayList<String>();
+                signatures.add("public String sayHi();");
+                signatures.add("public String sayHi(final String name);");
+                signatures.add("public final String greetMe(final String name);");
+                signatures.add("public final String greetUs(final String name1, String name2);");
+                signatures.add("public final String greetAll(String[] names);");
+                signatures.add("public final String greetAll(java.util.List<String> names);");
+                signatures.add("public final String[] greetTimes(String name, int times);");
+                return signatures;
+            }
+        };
+        mojo.substitutions = new Substitution[1];
+        mojo.substitutions[0] = new Substitution(".+", "(.+)", "java.util.List", "$1List");
+
+        mojo.outDir = new File("target/generated-test-sources/camelComponent");
+        mojo.outPackage = "org.apache.camel.component.util";
+        mojo.proxyClass = TestProxy.class.getCanonicalName();
+        mojo.project = new MavenProject((Model) null) {
+            @Override
+            public List getRuntimeClasspathElements() throws DependencyResolutionRequiredException {
+                return Collections.EMPTY_LIST;
+            }
+        };
+
+        mojo.execute();
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/7c1a35fc/tooling/maven/camel-component-util-maven-plugin/src/test/java/org/apache/camel/maven/TestProxy.java
----------------------------------------------------------------------
diff --git a/tooling/maven/camel-component-util-maven-plugin/src/test/java/org/apache/camel/maven/TestProxy.java b/tooling/maven/camel-component-util-maven-plugin/src/test/java/org/apache/camel/maven/TestProxy.java
new file mode 100644
index 0000000..ced2058
--- /dev/null
+++ b/tooling/maven/camel-component-util-maven-plugin/src/test/java/org/apache/camel/maven/TestProxy.java
@@ -0,0 +1,64 @@
+/**
+ * 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.maven;
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class TestProxy {
+    public String sayHi() {
+        return "Hello!";
+    }
+
+    public String sayHi(final String name) {
+        return "Hello " + name;
+    }
+
+    public final String greetMe(final String name) {
+        return "Greetings " + name;
+    }
+
+    public final String greetUs(final String name1, String name2) {
+        return "Greetings " + name1 + ", " + name2;
+    }
+
+    public final String greetAll(final String[] names) {
+        StringBuilder builder = new StringBuilder("Greetings ");
+        for (String name : names) {
+            builder.append(name).append(", ");
+        }
+        builder.delete(builder.length() - 2, builder.length());
+        return builder.toString();
+    }
+
+    public final String greetAll(List<String> names) {
+        StringBuilder builder = new StringBuilder("Greetings ");
+        for (String name : names) {
+            builder.append(name).append(", ");
+        }
+        builder.delete(builder.length() - 2, builder.length());
+        return builder.toString();
+    }
+
+    public final String[] greetTimes(String name, int times) {
+        final List<String> result = new ArrayList<String>();
+        for (int i = 0; i < times; i++) {
+            result.add("Greetings " + name);
+        }
+        return result.toArray(new String[result.size()]);
+    }
+}

http://git-wip-us.apache.org/repos/asf/camel/blob/7c1a35fc/tooling/maven/camel-component-util-maven-plugin/src/test/resources/log4j.properties
----------------------------------------------------------------------
diff --git a/tooling/maven/camel-component-util-maven-plugin/src/test/resources/log4j.properties b/tooling/maven/camel-component-util-maven-plugin/src/test/resources/log4j.properties
new file mode 100644
index 0000000..3d544fc
--- /dev/null
+++ b/tooling/maven/camel-component-util-maven-plugin/src/test/resources/log4j.properties
@@ -0,0 +1,36 @@
+#
+# 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.
+#
+
+#
+# The logging properties used
+#
+log4j.rootLogger=INFO, out
+
+# uncomment the following line to turn on Camel debugging
+#log4j.logger.org.apache.camel=DEBUG
+
+# CONSOLE appender not used by default
+log4j.appender.out=org.apache.log4j.ConsoleAppender
+log4j.appender.out.layout=org.apache.log4j.PatternLayout
+log4j.appender.out.layout.ConversionPattern=[%30.30t] %-30.30c{1} %-5p %m%n
+#log4j.appender.out.layout.ConversionPattern=%d [%-15.15t] %-5p %-30.30c{1} - %m%n
+
+log4j.throwableRenderer=org.apache.log4j.EnhancedThrowableRenderer
+
+#log4j.logger.org.apache.camel.maven=DEBUG
+#log4j.logger.org.apache.http=DEBUG
+#log4j.logger.org.apache.camel.util.component=TRACE

http://git-wip-us.apache.org/repos/asf/camel/blob/7c1a35fc/tooling/maven/pom.xml
----------------------------------------------------------------------
diff --git a/tooling/maven/pom.xml b/tooling/maven/pom.xml
index de5078a..fbd883e 100644
--- a/tooling/maven/pom.xml
+++ b/tooling/maven/pom.xml
@@ -33,6 +33,7 @@
     <module>camel-package-maven-plugin</module>
     <module>camel-maven-plugin</module>
     <module>guice-maven-plugin</module>
+    <module>camel-component-util-maven-plugin</module>
   </modules>
 
   <dependencies>