struts-issues mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From "ASF GitHub Bot (JIRA)" <j...@apache.org>
Subject [jira] [Commented] (WW-4912) Allowed methods inheritance
Date Tue, 30 Jan 2018 09:48:00 GMT

    [ https://issues.apache.org/jira/browse/WW-4912?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=16344760#comment-16344760
] 

ASF GitHub Bot commented on WW-4912:
------------------------------------

yasserzamani closed pull request #206: WW-4912: scan package-info and class at the same time
URL: https://github.com/apache/struts/pull/206
 
 
   

This is a PR merged from a forked repository.
As GitHub hides the original diff on merge, it is displayed below for
the sake of provenance:

As this is a foreign pull request (from a fork), the diff is supplied
below (as it won't show otherwise due to GitHub magic):

diff --git a/core/src/main/java/com/opensymphony/xwork2/util/AnnotationUtils.java b/core/src/main/java/com/opensymphony/xwork2/util/AnnotationUtils.java
index 42c113f34..cbebc8003 100644
--- a/core/src/main/java/com/opensymphony/xwork2/util/AnnotationUtils.java
+++ b/core/src/main/java/com/opensymphony/xwork2/util/AnnotationUtils.java
@@ -18,9 +18,12 @@
  */
 package com.opensymphony.xwork2.util;
 
+import org.apache.commons.lang3.ClassUtils;
+
 import java.lang.annotation.Annotation;
 import java.lang.reflect.Field;
 import java.lang.reflect.Method;
+import java.util.ArrayList;
 import java.util.Arrays;
 import java.util.List;
 import java.util.regex.Matcher;
@@ -129,7 +132,7 @@ public static String resolvePropertyName(Method method) {
     }
 
     /**
-     * Returns the annotation on the given class or the package of the class. This searchs
up the
+     * Returns the annotation on the given class or the package of the class. This searches
up the
      * class hierarchy and the package hierarchy for the closest match.
      *
      * @param <T>             class type
@@ -154,4 +157,36 @@ public static String resolvePropertyName(Method method) {
 
         return ann;
     }
+
+    /**
+     * Returns a list of the annotation on the given class or the package of the class.
+     * This searches up the class hierarchy and the package hierarchy.
+     *
+     * @param <T>             class type
+     * @param clazz           The class to search for the annotation.
+     * @param annotationClass The Class of the annotation.
+     * @return List of the annotations or an empty list.
+     */
+    public static <T extends Annotation> List<T> findAnnotations(Class<?>
clazz, Class<T> annotationClass) {
+        List<T> anns = new ArrayList<>();
+
+        List<Class<?>> classes = new ArrayList<>();
+        classes.add(clazz);
+
+        classes.addAll(ClassUtils.getAllSuperclasses(clazz));
+        classes.addAll(ClassUtils.getAllInterfaces(clazz));
+        for (Class<?> aClass : classes) {
+            T ann = aClass.getAnnotation(annotationClass);
+            if (ann != null) {
+                anns.add(ann);
+            }
+
+            ann = aClass.getPackage().getAnnotation(annotationClass);
+            if (ann != null) {
+                anns.add(ann);
+            }
+        }
+
+        return anns;
+    }
 }
diff --git a/core/src/test/java/com/opensymphony/xwork2/util/AnnotationUtilsTest.java b/core/src/test/java/com/opensymphony/xwork2/util/AnnotationUtilsTest.java
index c1d7ecafa..16fbab4fe 100644
--- a/core/src/test/java/com/opensymphony/xwork2/util/AnnotationUtilsTest.java
+++ b/core/src/test/java/com/opensymphony/xwork2/util/AnnotationUtilsTest.java
@@ -19,14 +19,19 @@
 package com.opensymphony.xwork2.util;
 
 import com.opensymphony.xwork2.util.annotation.Dummy2Class;
+import com.opensymphony.xwork2.util.annotation.Dummy3Class;
 import com.opensymphony.xwork2.util.annotation.DummyClass;
+import com.opensymphony.xwork2.util.annotation.DummyClassExt;
 import com.opensymphony.xwork2.util.annotation.MyAnnotation;
-
+import com.opensymphony.xwork2.util.annotation.MyAnnotation2;
 import junit.framework.TestCase;
 
-/**
- * @author Dan Oxlade, dan d0t oxlade at gmail d0t c0m
- */
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+
+import static org.fest.assertions.Assertions.assertThat;
+
 public class AnnotationUtilsTest extends TestCase {
 
     public void testFindAnnotationOnClass() {
@@ -41,4 +46,25 @@ public void testFindAnnotationOnPackage() {
         assertEquals("package-test", ns.value());
     }
 
+    public void testFindAnnotationOnParents() {
+        MyAnnotation2 ns = AnnotationUtils.findAnnotation(Dummy3Class.class, MyAnnotation2.class);
+        assertNotNull(ns);
+        assertEquals("abstract-abstract", ns.value());
+    }
+
+    public void testFindAnnotationsOnAll() {
+        List<MyAnnotation> annotations = AnnotationUtils.findAnnotations(DummyClassExt.class,
MyAnnotation.class);
+
+        assertThat(annotations)
+                .isNotNull()
+                .isNotEmpty()
+                .hasSize(5);
+
+        Set<String> values = new HashSet<>();
+        for (MyAnnotation annotation : annotations) {
+            values.add(annotation.value());
+        }
+        assertThat(values).contains("class-test", "package-test", "interface-test", "package2-test");
+    }
+
 }
diff --git a/core/src/test/java/com/opensymphony/xwork2/util/annotation/Dummy3Class.java b/core/src/test/java/com/opensymphony/xwork2/util/annotation/Dummy3Class.java
new file mode 100644
index 000000000..f25c852c7
--- /dev/null
+++ b/core/src/test/java/com/opensymphony/xwork2/util/annotation/Dummy3Class.java
@@ -0,0 +1,25 @@
+/*
+ * 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 com.opensymphony.xwork2.util.annotation;
+
+import com.opensymphony.xwork2.util.annotation.pkg1.AbstractDummyAction;
+
+public class Dummy3Class extends AbstractDummyAction{
+
+}
diff --git a/core/src/test/java/com/opensymphony/xwork2/util/annotation/DummyClass.java b/core/src/test/java/com/opensymphony/xwork2/util/annotation/DummyClass.java
index 707b73592..bb65b5c6e 100644
--- a/core/src/test/java/com/opensymphony/xwork2/util/annotation/DummyClass.java
+++ b/core/src/test/java/com/opensymphony/xwork2/util/annotation/DummyClass.java
@@ -18,8 +18,10 @@
  */
 package com.opensymphony.xwork2.util.annotation;
 
+import com.opensymphony.xwork2.util.annotation.pkg2.Package2DummyInterface;
+
 @MyAnnotation("class-test")
-public class DummyClass {
+public class DummyClass implements Package2DummyInterface {
 
     public DummyClass() {
     }
diff --git a/core/src/test/java/com/opensymphony/xwork2/util/annotation/MyAnnotation2.java
b/core/src/test/java/com/opensymphony/xwork2/util/annotation/MyAnnotation2.java
index baeef0da8..c3700551b 100644
--- a/core/src/test/java/com/opensymphony/xwork2/util/annotation/MyAnnotation2.java
+++ b/core/src/test/java/com/opensymphony/xwork2/util/annotation/MyAnnotation2.java
@@ -23,4 +23,6 @@
 
 @Retention(RetentionPolicy.RUNTIME)
 public @interface MyAnnotation2 {
+
+    String value() default "";
 }
diff --git a/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg1/AbstractAbstractDummyAction.java
b/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg1/AbstractAbstractDummyAction.java
new file mode 100644
index 000000000..8221b98f8
--- /dev/null
+++ b/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg1/AbstractAbstractDummyAction.java
@@ -0,0 +1,25 @@
+/*
+ * 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 com.opensymphony.xwork2.util.annotation.pkg1;
+
+import com.opensymphony.xwork2.util.annotation.MyAnnotation2;
+
+@MyAnnotation2("abstract-abstract")
+public class AbstractAbstractDummyAction {
+}
diff --git a/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg1/AbstractDummyAction.java
b/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg1/AbstractDummyAction.java
new file mode 100644
index 000000000..88f20a293
--- /dev/null
+++ b/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg1/AbstractDummyAction.java
@@ -0,0 +1,22 @@
+/*
+ * 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 com.opensymphony.xwork2.util.annotation.pkg1;
+
+public class AbstractDummyAction extends AbstractAbstractDummyAction {
+}
diff --git a/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg2/Package2DummyInterface.java
b/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg2/Package2DummyInterface.java
new file mode 100644
index 000000000..ea1aa1279
--- /dev/null
+++ b/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg2/Package2DummyInterface.java
@@ -0,0 +1,25 @@
+/*
+ * 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 com.opensymphony.xwork2.util.annotation.pkg2;
+
+import com.opensymphony.xwork2.util.annotation.MyAnnotation;
+
+@MyAnnotation("interface-test")
+public interface Package2DummyInterface {
+}
diff --git a/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg2/package-info.java
b/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg2/package-info.java
new file mode 100644
index 000000000..2eee0a823
--- /dev/null
+++ b/core/src/test/java/com/opensymphony/xwork2/util/annotation/pkg2/package-info.java
@@ -0,0 +1,23 @@
+/*
+ * 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.
+ */
+
+@MyAnnotation("package2-test")
+package com.opensymphony.xwork2.util.annotation.pkg2;
+
+import com.opensymphony.xwork2.util.annotation.MyAnnotation;
\ No newline at end of file
diff --git a/plugins/convention/src/main/java/org/apache/struts2/convention/PackageBasedActionConfigBuilder.java
b/plugins/convention/src/main/java/org/apache/struts2/convention/PackageBasedActionConfigBuilder.java
index a4e7eceb8..bc586d4ac 100644
--- a/plugins/convention/src/main/java/org/apache/struts2/convention/PackageBasedActionConfigBuilder.java
+++ b/plugins/convention/src/main/java/org/apache/struts2/convention/PackageBasedActionConfigBuilder.java
@@ -749,13 +749,13 @@ protected void buildConfiguration(Set<Class> classes) {
     }
 
     private Set<String> getAllowedMethods(Class<?> actionClass) {
-        AllowedMethods annotation = AnnotationUtils.findAnnotation(actionClass, AllowedMethods.class);
-        if (annotation == null) {
+        List<AllowedMethods> annotations = AnnotationUtils.findAnnotations(actionClass,
AllowedMethods.class);
+        if (annotations == null || annotations.isEmpty()) {
             return Collections.emptySet();
         } else {
             Set<String> methods = new HashSet<>();
-            for (String method : annotation.value()) {
-                methods.add(method);
+            for (AllowedMethods allowedMethods : annotations) {
+                methods.addAll(Arrays.asList(allowedMethods.value()));
             }
             return methods;
         }
@@ -924,7 +924,7 @@ protected void createActionConfig(PackageConfig.Builder pkgCfg, Class<?>
actionC
                                       String actionMethod, Action annotation, Set<String>
allowedMethods) {
     	String className = actionClass.getName();
         if (annotation != null) {
-            actionName = annotation.value() != null && annotation.value().equals(Action.DEFAULT_VALUE)
? actionName : annotation.value();
+            actionName = annotation.value().equals(Action.DEFAULT_VALUE) ? actionName : annotation.value();
             actionName = StringUtils.contains(actionName, "/") && !slashesInActionNames
? StringUtils.substringAfterLast(actionName, "/") : actionName;
             if(!Action.DEFAULT_VALUE.equals(annotation.className())){
             	className = annotation.className();
@@ -960,7 +960,7 @@ protected void createActionConfig(PackageConfig.Builder pkgCfg, Class<?>
actionC
             actionConfig.addParams(StringTools.createParameterMap(annotation.params()));
 
         //add exception mappings from annotation
-        if (annotation != null && annotation.exceptionMappings() != null)
+        if (annotation != null)
             actionConfig.addExceptionMappings(buildExceptionMappings(annotation.exceptionMappings(),
actionName));
 
         //add exception mapping from class
@@ -997,8 +997,7 @@ protected void createActionConfig(PackageConfig.Builder pkgCfg, Class<?>
actionC
                         exceptionMapping.result(), actionName);
             ExceptionMappingConfig.Builder builder = new ExceptionMappingConfig.Builder(null,
exceptionMapping
                     .exception(), exceptionMapping.result());
-            if (exceptionMapping.params() != null)
-                builder.addParams(StringTools.createParameterMap(exceptionMapping.params()));
+            builder.addParams(StringTools.createParameterMap(exceptionMapping.params()));
             exceptionMappings.add(builder.build());
         }
 
diff --git a/plugins/convention/src/test/java/org/apache/struts2/convention/PackageBasedActionConfigBuilderTest.java
b/plugins/convention/src/test/java/org/apache/struts2/convention/PackageBasedActionConfigBuilderTest.java
index 6c97dec38..d9e60f63b 100644
--- a/plugins/convention/src/test/java/org/apache/struts2/convention/PackageBasedActionConfigBuilderTest.java
+++ b/plugins/convention/src/test/java/org/apache/struts2/convention/PackageBasedActionConfigBuilderTest.java
@@ -544,10 +544,14 @@ public Container getContainer() {
         assertEquals("struts-default", pkgConfig.getParents().get(0).getName());
 
         ActionConfig actionConfig = pkgConfig.getActionConfigs().get("class-level-allowed-methods");
-        assertEquals(actionConfig.getAllowedMethods().size(), 5);
+        assertEquals(7, actionConfig.getAllowedMethods().size());
         assertTrue(actionConfig.getAllowedMethods().contains("execute"));
         assertTrue(actionConfig.getAllowedMethods().contains("end"));
         assertTrue(actionConfig.getAllowedMethods().contains("input"));
+        assertTrue(actionConfig.getAllowedMethods().contains("cancel"));
+        assertTrue(actionConfig.getAllowedMethods().contains("start"));
+        assertTrue(actionConfig.getAllowedMethods().contains("home"));
+        assertTrue(actionConfig.getAllowedMethods().contains("browse"));
 
         /* org.apache.struts2.convention.actions.allowedmethods.sub package level */
         pkgConfig = configuration.getPackageConfig("org.apache.struts2.convention.actions.allowedmethods.sub#struts-default#/allowedmethods/sub");


 

----------------------------------------------------------------
This is an automated message from the Apache Git Service.
To respond to the message, please log on GitHub and use the
URL above to go to the specific comment.
 
For queries about this service, please contact Infrastructure at:
users@infra.apache.org


> Allowed methods inheritance
> ---------------------------
>
>                 Key: WW-4912
>                 URL: https://issues.apache.org/jira/browse/WW-4912
>             Project: Struts 2
>          Issue Type: Improvement
>    Affects Versions: 2.5.14.1
>            Reporter: Britta Katzenbach
>            Assignee: Lukasz Lenart
>            Priority: Minor
>             Fix For: 2.5.15
>
>
> As we use a lot of inheritance on action classes we would appreciate, if the allowed
methods would be inherited as well.
> For example:
> We do not declare actions in struts.xml and just use the Convention.
> struts.xml:
> {code:xml}
> <package name="default" extends="tiles-default"  namespace="/„ >
>     ...
>     <global-allowed-methods> abort,execute,search,reset,download,refresh,delegate,forward,release,saveComments
</global-allowed-methods>
> </package>
> {code}
> Java:
> {code:java}
> @AllowedMethods(value = \{"changeLanguage", "deleteAttachment", "uploadMailAttachment"})
> public class SpecifyMailTask extends AbstractTask {
> @AllowedMethods(value = \{"saveInputAndSuccess"})
> public abstract class AbstractTask extends AbstractBasicJbpmTask implements ModelDriven<TaskModel>,
Preparable \{...}
> @AllowedMethods(value = { "abort", "cancel", "claim", "claimAndStart", "claimAndSkip",
"complete", "delegate", "forward",
>         "incomplete", "release", "skipAndComplete", "start", "suspend", "uploadTaskAttachment"})
> public abstract class AbstractBasicJbpmTask extends AbstractCrmAction implements ModelDriven<TaskModel>,
Preparable \{...}
> {code}
> I tried to add the allowed methods in the package-info.java. It worked as long as I did
not add an additional method to a certain action, i.e. SpecifyMailTask. If I add here the
annotation to allow the methods "changeLanguage", "deleteAttachment", "uploadMailAttachment"
additionally, the other methods, which are allowed via the package-info.java, are not allowed
anymore.
>  



--
This message was sent by Atlassian JIRA
(v7.6.3#76005)

Mime
View raw message