This is an automated email from the ASF dual-hosted git repository.

nfilotto pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/camel.git


The following commit(s) were added to refs/heads/main by this push:
     new 96226cb  CAMEL-16628: Add applicableFor to Metadata to filter header 
by scheme (#7224)
96226cb is described below

commit 96226cb3548e14fdf242f38590180811b1d25f42
Author: Nicolas Filotto <essob...@users.noreply.github.com>
AuthorDate: Fri Mar 18 12:10:51 2022 +0100

    CAMEL-16628: Add applicableFor to Metadata to filter header by scheme 
(#7224)
    
    ## Motivation
    
    Some Constants class are shared with several endpoints, we need a mechanism 
allowing to filter the message headers by endpoint's scheme.
    
    ## Modifications
    
    * Add the new element `applicableFor` to `@Metadata` to provide the list of 
schemes for which the metadata is applicable.
    * Enable the IT as the plugin updates have been published (not related to 
this need)
---
 .../java/org/apache/camel/spi/Metadata.java        | 17 +++++++++++
 tooling/maven/camel-package-maven-plugin/pom.xml   |  4 ---
 .../packaging/EndpointSchemaGeneratorMojo.java     | 35 +++++++++++++++-------
 .../packaging/EndpointSchemaGeneratorMojoTest.java | 19 ++++++++++--
 .../packaging/endpoint/SomeEndpointWithFilter.java | 34 +++++++++++++++++++++
 .../main/java/org/apache/camel/spi/Metadata.java   | 17 +++++++++++
 6 files changed, 109 insertions(+), 17 deletions(-)

diff --git 
a/core/camel-api/src/generated/java/org/apache/camel/spi/Metadata.java 
b/core/camel-api/src/generated/java/org/apache/camel/spi/Metadata.java
index f37ea43..57f5a47 100644
--- a/core/camel-api/src/generated/java/org/apache/camel/spi/Metadata.java
+++ b/core/camel-api/src/generated/java/org/apache/camel/spi/Metadata.java
@@ -132,4 +132,21 @@ public @interface Metadata {
      * specify which options each implementation only supports.
      */
     String includeProperties() default "";
+
+    /**
+     * Indicates the list of schemes for which this metadata is applicable. 
This is used to filter out message headers
+     * that are shared with several endpoints but only applicable for some of 
them.
+     * <p/>
+     * In the next example, the header {@code SOME_HEADER} is only applicable 
for endpoints whose scheme is "foo" or
+     * "bar".
+     *
+     * <pre>
+     * <code>
+     *
+     * &#64;Metadata(description = "some description", javaType = "String", 
applicableFor = {"foo", "bar"})
+     * public static final String SOME_HEADER = "someHeaderName";
+     * </code>
+     * </pre>
+     */
+    String[] applicableFor() default {};
 }
diff --git a/tooling/maven/camel-package-maven-plugin/pom.xml 
b/tooling/maven/camel-package-maven-plugin/pom.xml
index 82041b4..39c6839 100644
--- a/tooling/maven/camel-package-maven-plugin/pom.xml
+++ b/tooling/maven/camel-package-maven-plugin/pom.xml
@@ -188,8 +188,6 @@
                     </mojoDependencies>
                 </configuration>
             </plugin>
-
-<!--
             <plugin>
                 <groupId>org.apache.maven.plugins</groupId>
                 <artifactId>maven-invoker-plugin</artifactId>
@@ -230,8 +228,6 @@
                     </dependency>
                 </dependencies>
             </plugin>
--->
-
         </plugins>
     </build>
 
diff --git 
a/tooling/maven/camel-package-maven-plugin/src/main/java/org/apache/camel/maven/packaging/EndpointSchemaGeneratorMojo.java
 
b/tooling/maven/camel-package-maven-plugin/src/main/java/org/apache/camel/maven/packaging/EndpointSchemaGeneratorMojo.java
index 1bc68d8..58b3ddf 100644
--- 
a/tooling/maven/camel-package-maven-plugin/src/main/java/org/apache/camel/maven/packaging/EndpointSchemaGeneratorMojo.java
+++ 
b/tooling/maven/camel-package-maven-plugin/src/main/java/org/apache/camel/maven/packaging/EndpointSchemaGeneratorMojo.java
@@ -261,7 +261,7 @@ public class EndpointSchemaGeneratorMojo extends 
AbstractGeneratorMojo {
         }
 
         // component headers
-        addEndpointHeaders(componentModel, uriEndpoint);
+        addEndpointHeaders(componentModel, uriEndpoint, scheme);
 
         // endpoint options
         findClassProperties(componentModel, classElement, new HashSet<>(), "", 
null, null, false);
@@ -301,11 +301,14 @@ public class EndpointSchemaGeneratorMojo extends 
AbstractGeneratorMojo {
      * {@code headersClass} of the annotation {@code UriEndpoint}, convert the 
metadata found into instances of
      * {@link EndpointHeaderModel} and finally add the instances of {@link 
EndpointHeaderModel} to the given component
      * model.
-     * 
+     * <p/>
+     * Only headers applicable for the given scheme are added.
+     *
      * @param componentModel the component model to which the headers should 
be added.
      * @param uriEndpoint    the annotation from which the headers class is 
retrieved.
+     * @param scheme         the scheme for which we want to add the headers.
      */
-    void addEndpointHeaders(ComponentModel componentModel, UriEndpoint 
uriEndpoint) {
+    void addEndpointHeaders(ComponentModel componentModel, UriEndpoint 
uriEndpoint, String scheme) {
         final Class<?> headersClass = uriEndpoint.headersClass();
         if (headersClass == void.class) {
             getLog().debug(String.format("The endpoint %s has not defined any 
headers class", uriEndpoint.scheme()));
@@ -319,9 +322,10 @@ public class EndpointSchemaGeneratorMojo extends 
AbstractGeneratorMojo {
                 getLog().debug(
                         String.format("Trying to add the constant %s in the 
class %s as header.", field.getName(),
                                 headersClass.getName()));
-                addEndpointHeader(componentModel, field);
-                foundHeader = true;
-                continue;
+                if (addEndpointHeader(componentModel, field, scheme)) {
+                    foundHeader = true;
+                    continue;
+                }
             }
             getLog().debug(
                     String.format("The field %s of the class %s is not 
considered as a name of a header, thus it is skipped",
@@ -336,16 +340,26 @@ public class EndpointSchemaGeneratorMojo extends 
AbstractGeneratorMojo {
      * Retrieve the metadata added to the given field, convert the metadata 
found into an instance of
      * {@link EndpointHeaderModel} and finally add the instance of {@link 
EndpointHeaderModel} to the given component
      * model.
+     * <p/>
+     * The header is only added if it is applicable for the given scheme.
      * 
-     * @param componentModel the component to which the header should be added.
-     * @param field          the field corresponding to the constant from 
which the metadata should be extracted.
+     * @param  componentModel the component to which the header should be 
added.
+     * @param  field          the field corresponding to the constant from 
which the metadata should be extracted.
+     * @param  scheme         the scheme for which we want to add the header.
+     * @return                {@code true} if the header has been added, 
{@code false} otherwise.
      */
-    private void addEndpointHeader(ComponentModel componentModel, Field field) 
{
+    private boolean addEndpointHeader(ComponentModel componentModel, Field 
field, String scheme) {
         final Metadata metadata = field.getAnnotation(Metadata.class);
         if (metadata == null) {
             getLog().debug(String.format("The field %s in class %s has no 
Metadata", field.getName(),
                     field.getDeclaringClass().getName()));
-            return;
+            return false;
+        }
+        final String[] applicableFor = metadata.applicableFor();
+        if (applicableFor.length > 0 && 
!Arrays.stream(applicableFor).anyMatch(s -> s.equals(scheme))) {
+            getLog().debug(String.format("The field %s in class %s is not 
applicable for %s", field.getName(),
+                    field.getDeclaringClass().getName(), scheme));
+            return false;
         }
         final EndpointHeaderModel header = new EndpointHeaderModel();
         header.setDescription(metadata.description().trim());
@@ -373,6 +387,7 @@ public class EndpointSchemaGeneratorMojo extends 
AbstractGeneratorMojo {
             getLog().debug(String.format("The field %s in class %s cannot be 
accessed", field.getName(),
                     field.getDeclaringClass().getName()));
         }
+        return true;
     }
 
     private String getExcludedEnd(Metadata classElement) {
diff --git 
a/tooling/maven/camel-package-maven-plugin/src/test/java/org/apache/camel/maven/packaging/EndpointSchemaGeneratorMojoTest.java
 
b/tooling/maven/camel-package-maven-plugin/src/test/java/org/apache/camel/maven/packaging/EndpointSchemaGeneratorMojoTest.java
index 8e65a7d..d64649b 100644
--- 
a/tooling/maven/camel-package-maven-plugin/src/test/java/org/apache/camel/maven/packaging/EndpointSchemaGeneratorMojoTest.java
+++ 
b/tooling/maven/camel-package-maven-plugin/src/test/java/org/apache/camel/maven/packaging/EndpointSchemaGeneratorMojoTest.java
@@ -21,6 +21,7 @@ import java.util.List;
 
 import org.apache.camel.maven.packaging.endpoint.SomeEndpoint;
 import org.apache.camel.maven.packaging.endpoint.SomeEndpointWithBadHeaders;
+import org.apache.camel.maven.packaging.endpoint.SomeEndpointWithFilter;
 import org.apache.camel.maven.packaging.endpoint.SomeEndpointWithoutHeaders;
 import org.apache.camel.spi.UriEndpoint;
 import org.apache.camel.tooling.model.ComponentModel;
@@ -53,7 +54,7 @@ class EndpointSchemaGeneratorMojoTest {
 
     @Test
     void testCanRetrieveMetadataOfHeaders() {
-        mojo.addEndpointHeaders(model, 
SomeEndpoint.class.getAnnotation(UriEndpoint.class));
+        mojo.addEndpointHeaders(model, 
SomeEndpoint.class.getAnnotation(UriEndpoint.class), "some");
         List<EndpointHeaderModel> endpointHeaders = model.getEndpointHeaders();
         assertEquals(2, endpointHeaders.size());
         // Full
@@ -91,13 +92,25 @@ class EndpointSchemaGeneratorMojoTest {
 
     @Test
     void testHeadersNotProperlyDefinedAreIgnored() {
-        mojo.addEndpointHeaders(model, 
SomeEndpointWithBadHeaders.class.getAnnotation(UriEndpoint.class));
+        mojo.addEndpointHeaders(model, 
SomeEndpointWithBadHeaders.class.getAnnotation(UriEndpoint.class), "some");
         assertEquals(0, model.getEndpointHeaders().size());
     }
 
     @Test
     void testEndpointWithoutHeadersAreIgnored() {
-        mojo.addEndpointHeaders(model, 
SomeEndpointWithoutHeaders.class.getAnnotation(UriEndpoint.class));
+        mojo.addEndpointHeaders(model, 
SomeEndpointWithoutHeaders.class.getAnnotation(UriEndpoint.class), "some");
         assertEquals(0, model.getEndpointHeaders().size());
     }
+
+    @Test
+    void testEndpointWithFilterKeepOnlyApplicableHeaders() {
+        mojo.addEndpointHeaders(model, 
SomeEndpointWithFilter.class.getAnnotation(UriEndpoint.class), "some");
+        List<EndpointHeaderModel> endpointHeaders = model.getEndpointHeaders();
+        assertEquals(2, endpointHeaders.size());
+        for (int i = 0; i < endpointHeaders.size(); i++) {
+            EndpointHeaderModel headerEmpty = endpointHeaders.get(i);
+            assertEquals("header", headerEmpty.getKind());
+            assertEquals(String.format("keep-%d", i + 1), 
headerEmpty.getName());
+        }
+    }
 }
diff --git 
a/tooling/maven/camel-package-maven-plugin/src/test/java/org/apache/camel/maven/packaging/endpoint/SomeEndpointWithFilter.java
 
b/tooling/maven/camel-package-maven-plugin/src/test/java/org/apache/camel/maven/packaging/endpoint/SomeEndpointWithFilter.java
new file mode 100644
index 0000000..e406eb3
--- /dev/null
+++ 
b/tooling/maven/camel-package-maven-plugin/src/test/java/org/apache/camel/maven/packaging/endpoint/SomeEndpointWithFilter.java
@@ -0,0 +1,34 @@
+/*
+ * 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.packaging.endpoint;
+
+import org.apache.camel.spi.Metadata;
+import org.apache.camel.spi.UriEndpoint;
+
+@UriEndpoint(scheme = "some", syntax = "some", title = "some", headersClass = 
SomeEndpointWithFilter.class)
+public final class SomeEndpointWithFilter {
+
+    @Metadata(description = "some description")
+    static final String KEEP_1 = "keep-1";
+    @Metadata(description = "some description", applicableFor = "some")
+    static final String KEEP_2 = "keep-2";
+    @Metadata(description = "some description", applicableFor = "other")
+    static final String IGNORE = "ignore";
+
+    private SomeEndpointWithFilter() {
+    }
+}
diff --git 
a/tooling/spi-annotations/src/main/java/org/apache/camel/spi/Metadata.java 
b/tooling/spi-annotations/src/main/java/org/apache/camel/spi/Metadata.java
index f37ea43..57f5a47 100644
--- a/tooling/spi-annotations/src/main/java/org/apache/camel/spi/Metadata.java
+++ b/tooling/spi-annotations/src/main/java/org/apache/camel/spi/Metadata.java
@@ -132,4 +132,21 @@ public @interface Metadata {
      * specify which options each implementation only supports.
      */
     String includeProperties() default "";
+
+    /**
+     * Indicates the list of schemes for which this metadata is applicable. 
This is used to filter out message headers
+     * that are shared with several endpoints but only applicable for some of 
them.
+     * <p/>
+     * In the next example, the header {@code SOME_HEADER} is only applicable 
for endpoints whose scheme is "foo" or
+     * "bar".
+     *
+     * <pre>
+     * <code>
+     *
+     * &#64;Metadata(description = "some description", javaType = "String", 
applicableFor = {"foo", "bar"})
+     * public static final String SOME_HEADER = "someHeaderName";
+     * </code>
+     * </pre>
+     */
+    String[] applicableFor() default {};
 }

Reply via email to