This is an automated email from the ASF dual-hosted git repository. davsclaus pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/camel.git
commit 4f1bdac7f3a758859175749dd2b2c4fc97a5c44f Author: Claus Ibsen <claus.ib...@gmail.com> AuthorDate: Fri Jun 21 09:21:18 2019 +0200 CAMEL-13663: camel-main-maven-plugin to generte spring-boot tooling metadata to fool Java editors to have code completions for Camel Main application.properties files. --- .../org/apache/camel/maven/AbstractMainMojo.java | 33 ++++++- .../java/org/apache/camel/maven/AutowireMojo.java | 108 ++++++++------------- .../apache/camel/maven/SpringBootToolingMojo.java | 49 +++------- 3 files changed, 89 insertions(+), 101 deletions(-) diff --git a/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/AbstractMainMojo.java b/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/AbstractMainMojo.java index 7e14948..44a8891 100644 --- a/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/AbstractMainMojo.java +++ b/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/AbstractMainMojo.java @@ -28,13 +28,18 @@ import java.util.Enumeration; import java.util.Iterator; import java.util.LinkedHashSet; import java.util.List; +import java.util.Map; import java.util.Properties; import java.util.Set; import java.util.TreeSet; +import java.util.function.Function; import org.apache.camel.catalog.CamelCatalog; import org.apache.camel.catalog.DefaultCamelCatalog; +import org.apache.camel.catalog.JSonSchemaHelper; import org.apache.camel.catalog.maven.MavenVersionManager; +import org.apache.camel.maven.model.AutowireData; +import org.apache.camel.maven.model.SpringBootData; import org.apache.camel.util.IOHelper; import org.apache.maven.artifact.Artifact; import org.apache.maven.artifact.repository.ArtifactRepository; @@ -91,8 +96,12 @@ public abstract class AbstractMainMojo extends AbstractExecMojo { @Parameter(property = "project.remoteArtifactRepositories") private List remoteRepositories; - @Override - public void execute() throws MojoExecutionException, MojoFailureException { + @FunctionalInterface + protected interface ComponentCallback { + void onOption(String componentName, String name, String type, String javaType, String description, String defaultValue); + } + + protected void doExecute(ComponentCallback callback) throws MojoExecutionException, MojoFailureException { catalog = new DefaultCamelCatalog(); // add activemq as known component catalog.addComponent("activemq", "org.apache.activemq.camel.component.ActiveMQComponent"); @@ -145,6 +154,26 @@ public abstract class AbstractMainMojo extends AbstractExecMojo { .addUrls(ClasspathHelper.forClassLoader(classLoader)) .addClassLoader(classLoader) .setScanners(new SubTypesScanner())); + + for (String componentName : camelComponentsOnClasspath) { + String json = catalog.componentJSonSchema(componentName); + if (json == null) { + getLog().debug("Cannot find component JSon metadata for component: " + componentName); + continue; + } + + List<Map<String, String>> rows = JSonSchemaHelper.parseJsonSchema("componentProperties", json, true); + Set<String> names = JSonSchemaHelper.getNames(rows); + for (String name : names) { + Map<String, String> row = JSonSchemaHelper.getRow(rows, name); + String type = row.get("type"); + String javaType = safeJavaType(row.get("javaType")); + String desc = row.get("description"); + String defaultValue = row.get("defaultValue"); + + callback.onOption(componentName, name, type, javaType, desc, defaultValue); + } + } } protected static String findCamelVersion(MavenProject project) { diff --git a/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/AutowireMojo.java b/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/AutowireMojo.java index 50a7190..d46b653 100644 --- a/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/AutowireMojo.java +++ b/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/AutowireMojo.java @@ -92,9 +92,6 @@ public class AutowireMojo extends AbstractMainMojo { @Override public void execute() throws MojoExecutionException, MojoFailureException { - // perform common tasks - super.execute(); - // load default mappings Properties mappingProperties = loadDefaultMappings(); getLog().debug("Loaded default-mappings: " + mappingProperties); @@ -115,8 +112,48 @@ public class AutowireMojo extends AbstractMainMojo { mappingProperties.putAll(mappingFileProperties); } - // find the autowire via classpath scanning - List<AutowireData> autowires = findAutowireComponentOptionsByClasspath(catalog, camelComponentsOnClasspath, reflections, mappingProperties); + final List<AutowireData> autowires = new ArrayList<>(); + ComponentCallback callback = (componentName, name, type, javaType, description, defaultValue) -> { + if ("object".equals(type)) { + if (!isValidPropertyName(componentName, name)) { + getLog().debug("Skipping property name: " + name); + return; + } + try { + Class clazz = classLoader.loadClass(javaType); + if (clazz.isInterface() && isComplexUserType(clazz)) { + Set<Class<?>> classes = reflections.getSubTypesOf(clazz); + // filter classes (must not be interfaces, must be public, must not be abstract, must be top level) and also a valid autowire class + classes = classes.stream().filter( + c -> !c.isInterface() + && Modifier.isPublic(c.getModifiers()) + && !Modifier.isAbstract(c.getModifiers()) + && c.getEnclosingClass() == null + && isValidAutowireClass(c)) + .collect(Collectors.toSet()); + Class best = chooseBestKnownType(componentName, name, clazz, classes, mappingProperties); + if (best != null) { + String key = "camel.component." + componentName + "." + name; + String value = "#class:" + best.getName(); + getLog().debug(key + "=" + value); + autowires.add(new AutowireData(key, value)); + + // TODO: get options from best class (getter/setter pairs) + // we dont have documentation + // add as spring boot options + + } + } + + } catch (Exception e) { + // ignore + getLog().debug("Cannot load class: " + name, e); + } + } + }; + + // perform the work with this callback + doExecute(callback); if (!autowires.isEmpty()) { outFolder.mkdirs(); @@ -164,67 +201,6 @@ public class AutowireMojo extends AbstractMainMojo { return mappings; } - protected List<AutowireData> findAutowireComponentOptionsByClasspath(CamelCatalog catalog, Set<String> components, - Reflections reflections, Properties mappingProperties) { - List<AutowireData> autowires = new ArrayList<>(); - - for (String componentName : components) { - getLog().debug("Autowiring Camel component: " + componentName); - - String json = catalog.componentJSonSchema(componentName); - if (json == null) { - getLog().debug("Cannot find component JSon metadata for component: " + componentName); - continue; - } - - List<Map<String, String>> rows = JSonSchemaHelper.parseJsonSchema("componentProperties", json, true); - Set<String> names = JSonSchemaHelper.getNames(rows); - for (String name : names) { - Map<String, String> row = JSonSchemaHelper.getRow(rows, name); - String type = row.get("type"); - String javaType = safeJavaType(row.get("javaType")); - if ("object".equals(type)) { - if (!isValidPropertyName(componentName, name)) { - getLog().debug("Skipping property name: " + name); - continue; - } - try { - Class clazz = classLoader.loadClass(javaType); - if (clazz.isInterface() && isComplexUserType(clazz)) { - Set<Class<?>> classes = reflections.getSubTypesOf(clazz); - // filter classes (must not be interfaces, must be public, must not be abstract, must be top level) and also a valid autowire class - classes = classes.stream().filter( - c -> !c.isInterface() - && Modifier.isPublic(c.getModifiers()) - && !Modifier.isAbstract(c.getModifiers()) - && c.getEnclosingClass() == null - && isValidAutowireClass(c)) - .collect(Collectors.toSet()); - Class best = chooseBestKnownType(componentName, name, clazz, classes, mappingProperties); - if (best != null) { - String key = "camel.component." + componentName + "." + name; - String value = "#class:" + best.getName(); - getLog().debug(key + "=" + value); - autowires.add(new AutowireData(key, value)); - - // TODO: get options from best class (getter/setter pairs) - // we dont have documentation - // add as spring boot options - - } - } - - } catch (Exception e) { - // ignore - getLog().debug("Cannot load class: " + name, e); - } - } - } - } - - return autowires; - } - protected Class chooseBestKnownType(String componentName, String optionName, Class type, Set<Class<?>> candidates, Properties knownTypes) { String known = knownTypes.getProperty(type.getName()); if (known != null) { diff --git a/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/SpringBootToolingMojo.java b/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/SpringBootToolingMojo.java index d331108..dc56282 100644 --- a/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/SpringBootToolingMojo.java +++ b/catalog/camel-main-maven-plugin/src/main/java/org/apache/camel/maven/SpringBootToolingMojo.java @@ -21,10 +21,7 @@ import java.io.FileOutputStream; import java.io.InputStream; import java.util.ArrayList; import java.util.List; -import java.util.Map; -import java.util.Set; -import org.apache.camel.catalog.JSonSchemaHelper; import org.apache.camel.maven.model.SpringBootData; import org.apache.camel.util.IOHelper; import org.apache.maven.plugin.MojoExecutionException; @@ -51,38 +48,17 @@ public class SpringBootToolingMojo extends AbstractMainMojo { @Override public void execute() throws MojoExecutionException, MojoFailureException { - // perform common tasks - super.execute(); - // load camel-main metadata - String mainJson = loadCamelMainConfigurationMetadata(); - if (mainJson == null) { - getLog().warn("Cannot load camel-main-configuration-metadata.json from within the camel-main JAR from the classpath." - + " Not possible to build spring boot configuration file for this project"); - return; - } - - List<SpringBootData> componentData = new ArrayList<>(); - for (String componentName : camelComponentsOnClasspath) { - String json = catalog.componentJSonSchema(componentName); - if (json == null) { - getLog().debug("Cannot find component JSon metadata for component: " + componentName); - continue; - } + final List<SpringBootData> componentData = new ArrayList<>(); + ComponentCallback callback = (componentName, name, type, javaType, description, defaultValue) -> { + // we want to use dash in the name + String dash = camelCaseToDash(name); + String key = "camel.component." + componentName + "." + dash; + componentData.add(new SpringBootData(key, springBootJavaType(javaType), description, defaultValue)); + }; - List<Map<String, String>> rows = JSonSchemaHelper.parseJsonSchema("componentProperties", json, true); - Set<String> names = JSonSchemaHelper.getNames(rows); - for (String name : names) { - Map<String, String> row = JSonSchemaHelper.getRow(rows, name); - String javaType = springBootJavaType(safeJavaType(row.get("javaType"))); - String desc = row.get("description"); - String defaultValue = row.get("defaultValue"); - // we want to use dash in the name - String dash = camelCaseToDash(name); - String key = "camel.component." + componentName + "." + dash; - componentData.add(new SpringBootData(key, javaType, desc, defaultValue)); - } - } + // perform the work with this callback + doExecute(callback); if (!componentData.isEmpty()) { StringBuilder sb = new StringBuilder(); @@ -113,6 +89,13 @@ public class SpringBootToolingMojo extends AbstractMainMojo { sb.append("}\n"); // okay then add the components into the main json at the end so they get merged together + // load camel-main metadata + String mainJson = loadCamelMainConfigurationMetadata(); + if (mainJson == null) { + getLog().warn("Cannot load camel-main-configuration-metadata.json from within the camel-main JAR from the classpath." + + " Not possible to build spring boot configuration file for this project"); + return; + } int pos = mainJson.lastIndexOf(" }"); String newJson = mainJson.substring(0, pos); newJson = newJson + " },\n";