WW-4744: Remove copied Spring's code (also from PR#117)

This commit is contained in:
Yasser Zamani
2017-03-26 18:07:58 +04:30
parent e1bb1a70c0
commit 2d5f0aaa66
7 changed files with 97 additions and 480 deletions
@@ -18,8 +18,8 @@ package com.opensymphony.xwork2.interceptor;
import com.opensymphony.xwork2.Action;
import com.opensymphony.xwork2.ActionInvocation;
import com.opensymphony.xwork2.interceptor.annotations.InputConfig;
import com.opensymphony.xwork2.util.ReflectionUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.reflect.MethodUtils;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import com.opensymphony.xwork2.util.AnnotationUtils;
@@ -211,9 +211,7 @@ public class DefaultWorkflowInterceptor extends MethodFilterInterceptor {
InputConfig annotation = AnnotationUtils.findAnnotation(action.getClass().getMethod(method, EMPTY_CLASS_ARRAY), InputConfig.class);
if (annotation != null) {
if (StringUtils.isNotEmpty(annotation.methodName())) {
Method m = ReflectionUtils.findMethod(action.getClass(), annotation.methodName());
ReflectionUtils.makeAccessible(m);
resultName = (String) ReflectionUtils.invokeMethod(m, action);
resultName = (String) MethodUtils.invokeMethod(action, true, annotation.methodName());
} else {
resultName = annotation.resultName();
}
@@ -20,7 +20,7 @@ import com.opensymphony.xwork2.XWorkException;
import com.opensymphony.xwork2.interceptor.AbstractInterceptor;
import com.opensymphony.xwork2.interceptor.PreResultListener;
import com.opensymphony.xwork2.util.AnnotationUtils;
import com.opensymphony.xwork2.util.ReflectionUtils;
import org.apache.commons.lang3.reflect.MethodUtils;
import java.lang.reflect.Method;
import java.util.ArrayList;
@@ -123,8 +123,7 @@ public class AnnotationWorkflowInterceptor extends AbstractInterceptor implement
}
});
for (Method m : methods) {
ReflectionUtils.makeAccessible(m);
final String resultCode = (String) ReflectionUtils.invokeMethod(m, action);
final String resultCode = (String) MethodUtils.invokeMethod(action, true, m.getName());
if (resultCode != null) {
// shortcircuit execution
return resultCode;
@@ -146,8 +145,7 @@ public class AnnotationWorkflowInterceptor extends AbstractInterceptor implement
}
});
for (Method m : methods) {
ReflectionUtils.makeAccessible(m);
ReflectionUtils.invokeMethod(m, action);
MethodUtils.invokeMethod(action, true, m.getName());
}
}
@@ -183,8 +181,7 @@ public class AnnotationWorkflowInterceptor extends AbstractInterceptor implement
});
for (Method m : methods) {
try {
ReflectionUtils.makeAccessible(m);
ReflectionUtils.invokeMethod(m, action);
MethodUtils.invokeMethod(action, true, m.getName());
} catch (Exception e) {
throw new XWorkException(e);
}
@@ -1,6 +1,5 @@
/*
* Copyright 2002-2006,2009 The Apache Software Foundation.
* Copyright 2002-2014 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -17,17 +16,16 @@
package com.opensymphony.xwork2.util;
import org.apache.commons.lang3.ArrayUtils;
import org.apache.commons.lang3.ClassUtils;
import java.lang.annotation.Annotation;
import java.lang.reflect.AnnotatedElement;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
@@ -40,12 +38,6 @@ import java.util.regex.Pattern;
* @author Rainer Hermanns
* @author Zsolt Szasz, zsolt at lorecraft dot com
* @author Dan Oxlade, dan d0t oxlade at gmail d0t c0m
* @author Rob Harrop
* @author Juergen Hoeller
* @author Sam Brannen
* @author Mark Fisher
* @author Chris Beams
* @author Phillip Webb
* @version $Id$
*/
public class AnnotationUtils {
@@ -53,12 +45,6 @@ public class AnnotationUtils {
private static final Pattern SETTER_PATTERN = Pattern.compile("set([A-Z][A-Za-z0-9]*)$");
private static final Pattern GETTER_PATTERN = Pattern.compile("(get|is|has)([A-Z][A-Za-z0-9]*)$");
private static final Map<AnnotationCacheKey, Annotation> findAnnotationCache =
new ConcurrentHashMap<AnnotationCacheKey, Annotation>(256);
private static final Map<Class<?>, Boolean> annotatedInterfaceCache =
new ConcurrentHashMap<Class<?>, Boolean>(256);
/**
* Adds all fields with the specified Annotation of class clazz and its superclasses to allFields
*
@@ -131,136 +117,101 @@ public class AnnotationUtils {
* @param annotation the {@link Annotation}s to find
* @return A {@link Collection}&lt;{@link AnnotatedElement}&gt; containing all of the
* method {@link AnnotatedElement}s matching the specified {@link Annotation}s
* @deprecated Will be removed after release of <a href="https://github.com/apache/commons-lang/pull/261">LANG-1317</a>
*/
public static Collection<Method> getAnnotatedMethods(Class clazz, final Class<? extends Annotation>... annotation) {
final Collection<Method> toReturn = new HashSet<>();
ReflectionUtils.doWithMethods(clazz, new ReflectionUtils.MethodCallback() {
@Override
public void doWith(Method method) throws IllegalArgumentException {
public static Collection<Method> getAnnotatedMethods(Class clazz, Class<? extends Annotation>... annotation) {
List<Class<?>> allSuperclasses = ClassUtils.getAllSuperclasses(clazz);
allSuperclasses.add(0, clazz);
int sci = 0;
List<Class<?>> allInterfaces = ClassUtils.getAllInterfaces(clazz);
int ifi = 0;
final List<Method> annotatedMethods = new ArrayList<>();
while (ifi < allInterfaces.size() ||
sci < allSuperclasses.size()) {
Class<?> acls;
if (ifi >= allInterfaces.size()) {
acls = allSuperclasses.get(sci++);
}
else if (sci >= allSuperclasses.size()) {
acls = allInterfaces.get(ifi++);
}
else if (sci <= ifi) {
acls = allSuperclasses.get(sci++);
}
else {
acls = allInterfaces.get(ifi++);
}
final Method[] allMethods = acls.getDeclaredMethods();
for (final Method method : allMethods) {
if (ArrayUtils.isEmpty(annotation) && ArrayUtils.isNotEmpty(method.getAnnotations())) {
toReturn.add(method);
return;
annotatedMethods.add(method);
continue;
}
for (Class<? extends Annotation> c : annotation) {
if (null != findAnnotation(method, c)) {
toReturn.add(method);
break;
if (method.getAnnotation(c) != null) {
annotatedMethods.add(method);
}
}
}
});
return toReturn;
}
/**
* Find a single {@link Annotation} of {@code annotationType} from the supplied
* {@link Method}, traversing its super methods (i.e., from superclasses and
* interfaces) if no annotation can be found on the given method itself.
* <p>Annotations on methods are not inherited by default, so we need to handle
* this explicitly.
*
* @param method the method to look for annotations on
* @param annotationType the annotation type to look for
* @return the annotation found, or {@code null} if none
*/
public static <A extends Annotation> A findAnnotation(Method method, Class<A> annotationType) {
AnnotationCacheKey cacheKey = new AnnotationCacheKey(method, annotationType);
A result = (A) findAnnotationCache.get(cacheKey);
if (result == null) {
result = getAnnotation(method, annotationType);
Class<?> clazz = method.getDeclaringClass();
if (result == null) {
result = searchOnInterfaces(method, annotationType, clazz.getInterfaces());
}
while (result == null) {
clazz = clazz.getSuperclass();
if (clazz == null || clazz.equals(Object.class)) {
break;
}
try {
Method equivalentMethod = clazz.getDeclaredMethod(method.getName(), method.getParameterTypes());
result = getAnnotation(equivalentMethod, annotationType);
} catch (NoSuchMethodException ex) {
// No equivalent method found
}
if (result == null) {
result = searchOnInterfaces(method, annotationType, clazz.getInterfaces());
}
}
if (result != null) {
findAnnotationCache.put(cacheKey, result);
}
}
return result;
return annotatedMethods;
}
/**
* Get a single {@link Annotation} of {@code annotationType} from the supplied
* Method, Constructor or Field. Meta-annotations will be searched if the annotation
* is not declared locally on the supplied element.
*
* @param annotatedElement the Method, Constructor or Field from which to get the annotation
* @param annotationType the annotation type to look for, both locally and as a meta-annotation
* @return the matching annotation, or {@code null} if none found
* <p>BFS to find the annotation object that is present on the given method or any equivalent method in
* super classes and interfaces, with the given annotation type. Returns null if the annotation type was not present
* on any of them.</p>
* @param <A>
* the annotation type
* @param method
* the {@link Method} to query
* @param annotationCls
* the {@link Annotation} to check if is present on the method
* @return an Annotation (possibly null).
* @deprecated Will be removed after release of <a href="https://github.com/apache/commons-lang/pull/261">LANG-1317</a>
*/
public static <T extends Annotation> T getAnnotation(AnnotatedElement annotatedElement, Class<T> annotationType) {
try {
T ann = annotatedElement.getAnnotation(annotationType);
if (ann == null) {
for (Annotation metaAnn : annotatedElement.getAnnotations()) {
ann = metaAnn.annotationType().getAnnotation(annotationType);
if (ann != null) {
public static <A extends Annotation> A findAnnotation(final Method method, final Class<A> annotationCls) {
A annotation = method.getAnnotation(annotationCls);
if(annotation == null) {
Class<?> mcls = method.getDeclaringClass();
List<Class<?>> allSuperclasses = ClassUtils.getAllSuperclasses(mcls);
int sci = 0;
List<Class<?>> allInterfaces = ClassUtils.getAllInterfaces(mcls);
int ifi = 0;
while (ifi < allInterfaces.size() ||
sci < allSuperclasses.size()) {
Class<?> acls;
if(ifi >= allInterfaces.size()) {
acls = allSuperclasses.get(sci++);
}
else if(sci >= allSuperclasses.size()) {
acls = allInterfaces.get(ifi++);
}
else if(ifi <= sci) {
acls = allInterfaces.get(ifi++);
}
else {
acls = allSuperclasses.get(sci++);
}
Method equivalentMethod = null;
try {
equivalentMethod = acls.getDeclaredMethod(method.getName(), method.getParameterTypes());
} catch (NoSuchMethodException e) {
// If not found, just keep on breadth first search
}
if(equivalentMethod != null) {
annotation = equivalentMethod.getAnnotation(annotationCls);
if(annotation != null) {
break;
}
}
}
return ann;
} catch (Exception ex) {
// Assuming nested Class values not resolvable within annotation attributes...
return null;
}
}
private static <A extends Annotation> A searchOnInterfaces(Method method, Class<A> annotationType, Class<?>... ifcs) {
A annotation = null;
for (Class<?> iface : ifcs) {
if (isInterfaceWithAnnotatedMethods(iface)) {
try {
Method equivalentMethod = iface.getMethod(method.getName(), method.getParameterTypes());
annotation = getAnnotation(equivalentMethod, annotationType);
} catch (NoSuchMethodException ex) {
// Skip this interface - it doesn't have the method...
}
if (annotation != null) {
break;
}
}
}
return annotation;
}
private static boolean isInterfaceWithAnnotatedMethods(Class<?> iface) {
Boolean flag = annotatedInterfaceCache.get(iface);
if (flag != null) {
return flag;
}
boolean found = false;
for (Method ifcMethod : iface.getMethods()) {
try {
if (ifcMethod.getAnnotations().length > 0) {
found = true;
break;
}
} catch (Exception ex) {
// Assuming nested Class values not resolvable within annotation attributes...
}
}
annotatedInterfaceCache.put(iface, found);
return found;
}
/**
* Returns the property name for a method.
* This method is independent from property fields.
@@ -295,61 +246,20 @@ public class AnnotationUtils {
* @return The annotation or null.
*/
public static <T extends Annotation> T findAnnotation(Class<?> clazz, Class<T> annotationClass) {
AnnotationCacheKey cacheKey = new AnnotationCacheKey(clazz, annotationClass);
T ann = (T) findAnnotationCache.get(cacheKey);
if (ann == null) {
T ann = clazz.getAnnotation(annotationClass);
while (ann == null && clazz != null) {
ann = clazz.getAnnotation(annotationClass);
while (ann == null && clazz != null) {
ann = clazz.getAnnotation(annotationClass);
if (ann == null) {
ann = clazz.getPackage().getAnnotation(annotationClass);
}
if (ann == null) {
clazz = clazz.getSuperclass();
if (clazz != null) {
ann = clazz.getAnnotation(annotationClass);
}
}
if (ann == null) {
ann = clazz.getPackage().getAnnotation(annotationClass);
}
if (ann != null) {
findAnnotationCache.put(cacheKey, ann);
if (ann == null) {
clazz = clazz.getSuperclass();
if (clazz != null) {
ann = clazz.getAnnotation(annotationClass);
}
}
}
return ann;
}
/**
* Cache key for the AnnotatedElement cache.
*/
private static class AnnotationCacheKey {
private final AnnotatedElement element;
private final Class<? extends Annotation> annotationType;
public AnnotationCacheKey(AnnotatedElement element, Class<? extends Annotation> annotationType) {
this.element = element;
this.annotationType = annotationType;
}
@Override
public boolean equals(Object other) {
if (this == other) {
return true;
}
if (!(other instanceof AnnotationCacheKey)) {
return false;
}
AnnotationCacheKey otherKey = (AnnotationCacheKey) other;
return (this.element.equals(otherKey.element) &&
this.annotationType.equals(otherKey.annotationType));
}
@Override
public int hashCode() {
return (this.element.hashCode() * 29 + this.annotationType.hashCode());
}
}
}
@@ -1,274 +0,0 @@
/*
* Copyright 2002-2015 The Apache Software Foundation.
* Copyright 2002-2015 the original author or authors.
*
* Licensed 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;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;
import java.lang.reflect.UndeclaredThrowableException;
import java.util.Arrays;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
/**
* Simple utility class for working with the reflection API and handling
* reflection exceptions.
*
* <p>Only intended for internal use.
*
* @author Juergen Hoeller
* @author Rob Harrop
* @author Rod Johnson
* @author Costin Leau
* @author Sam Brannen
* @author Chris Beams
*/
public abstract class ReflectionUtils {
/**
* Cache for {@link Class#getDeclaredMethods()}, allowing for fast iteration.
*/
private static final Map<Class<?>, Method[]> declaredMethodsCache =
new ConcurrentHashMap<Class<?>, Method[]>(256);
/**
* Perform the given callback operation on all matching methods of the given
* class and superclasses.
* <p>The same named method occurring on subclass and superclass will appear
* twice, unless excluded by a {@link MethodFilter}.
* @param clazz the class to introspect
* @param mc the callback to invoke for each method
* @see #doWithMethods(Class, MethodCallback, MethodFilter)
*/
public static void doWithMethods(Class<?> clazz, MethodCallback mc) {
doWithMethods(clazz, mc, null);
}
/**
* Perform the given callback operation on all matching methods of the given
* class and superclasses (or given interface and super-interfaces).
* <p>The same named method occurring on subclass and superclass will appear
* twice, unless excluded by the specified {@link MethodFilter}.
* @param clazz the class to introspect
* @param mc the callback to invoke for each method
* @param mf the filter that determines the methods to apply the callback to
*/
public static void doWithMethods(Class<?> clazz, MethodCallback mc, MethodFilter mf) {
// Keep backing up the inheritance hierarchy.
Method[] methods = getDeclaredMethods(clazz);
for (Method method : methods) {
if (mf != null && !mf.matches(method)) {
continue;
}
try {
mc.doWith(method);
}
catch (IllegalAccessException ex) {
throw new IllegalStateException("Not allowed to access method '" + method.getName() + "': " + ex);
}
}
if (clazz.getSuperclass() != null) {
doWithMethods(clazz.getSuperclass(), mc, mf);
}
else if (clazz.isInterface()) {
for (Class<?> superIfc : clazz.getInterfaces()) {
doWithMethods(superIfc, mc, mf);
}
}
}
/**
* Make the given method accessible, explicitly setting it accessible if
* necessary. The {@code setAccessible(true)} method is only called
* when actually necessary, to avoid unnecessary conflicts with a JVM
* SecurityManager (if active).
* @param method the method to make accessible
* @see java.lang.reflect.Method#setAccessible
*/
public static void makeAccessible(Method method) {
if ((!Modifier.isPublic(method.getModifiers()) ||
!Modifier.isPublic(method.getDeclaringClass().getModifiers())) && !method.isAccessible()) {
method.setAccessible(true);
}
}
/**
* Attempt to find a {@link Method} on the supplied class with the supplied name
* and no parameters. Searches all superclasses up to {@code Object}.
* <p>Returns {@code null} if no {@link Method} can be found.
* @param clazz the class to introspect
* @param name the name of the method
* @return the Method object, or {@code null} if none found
*/
public static Method findMethod(Class<?> clazz, String name) {
return findMethod(clazz, name, new Class<?>[0]);
}
/**
* Attempt to find a {@link Method} on the supplied class with the supplied name
* and parameter types. Searches all superclasses up to {@code Object}.
* <p>Returns {@code null} if no {@link Method} can be found.
* @param clazz the class to introspect
* @param name the name of the method
* @param paramTypes the parameter types of the method
* (may be {@code null} to indicate any signature)
* @return the Method object, or {@code null} if none found
*/
public static Method findMethod(Class<?> clazz, String name, Class<?>... paramTypes) {
Class<?> searchType = clazz;
while (searchType != null) {
Method[] methods = (searchType.isInterface() ? searchType.getMethods() : getDeclaredMethods(searchType));
for (Method method : methods) {
if (name.equals(method.getName()) &&
(paramTypes == null || Arrays.equals(paramTypes, method.getParameterTypes()))) {
return method;
}
}
searchType = searchType.getSuperclass();
}
return null;
}
/**
* Invoke the specified {@link Method} against the supplied target object with no arguments.
* The target object can be {@code null} when invoking a static {@link Method}.
* <p>Thrown exceptions are handled via a call to {@link #handleReflectionException}.
* @param method the method to invoke
* @param target the target object to invoke the method on
* @return the invocation result, if any
* @see #invokeMethod(java.lang.reflect.Method, Object, Object[])
*/
public static Object invokeMethod(Method method, Object target) {
return invokeMethod(method, target, new Object[0]);
}
/**
* Invoke the specified {@link Method} against the supplied target object with the
* supplied arguments. The target object can be {@code null} when invoking a
* static {@link Method}.
* <p>Thrown exceptions are handled via a call to {@link #handleReflectionException}.
* @param method the method to invoke
* @param target the target object to invoke the method on
* @param args the invocation arguments (may be {@code null})
* @return the invocation result, if any
*/
public static Object invokeMethod(Method method, Object target, Object... args) {
try {
return method.invoke(target, args);
}
catch (Exception ex) {
handleReflectionException(ex);
}
throw new IllegalStateException("Should never get here");
}
/**
* Handle the given reflection exception. Should only be called if no
* checked exception is expected to be thrown by the target method.
* <p>Throws the underlying RuntimeException or Error in case of an
* InvocationTargetException with such a root cause. Throws an
* IllegalStateException with an appropriate message else.
* @param ex the reflection exception to handle
*/
public static void handleReflectionException(Exception ex) {
if (ex instanceof NoSuchMethodException) {
throw new IllegalStateException("Method not found: " + ex.getMessage());
}
if (ex instanceof IllegalAccessException) {
throw new IllegalStateException("Could not access method: " + ex.getMessage());
}
if (ex instanceof InvocationTargetException) {
handleInvocationTargetException((InvocationTargetException) ex);
}
if (ex instanceof RuntimeException) {
throw (RuntimeException) ex;
}
throw new UndeclaredThrowableException(ex);
}
/**
* Handle the given invocation target exception. Should only be called if no
* checked exception is expected to be thrown by the target method.
* <p>Throws the underlying RuntimeException or Error in case of such a root
* cause. Throws an IllegalStateException else.
* @param ex the invocation target exception to handle
*/
public static void handleInvocationTargetException(InvocationTargetException ex) {
rethrowRuntimeException(ex.getTargetException());
}
/**
* Rethrow the given {@link Throwable exception}, which is presumably the
* <em>target exception</em> of an {@link InvocationTargetException}. Should
* only be called if no checked exception is expected to be thrown by the
* target method.
* <p>Rethrows the underlying exception cast to an {@link RuntimeException} or
* {@link Error} if appropriate; otherwise, throws an
* {@link IllegalStateException}.
* @param ex the exception to rethrow
* @throws RuntimeException the rethrown exception
*/
public static void rethrowRuntimeException(Throwable ex) {
if (ex instanceof RuntimeException) {
throw (RuntimeException) ex;
}
if (ex instanceof Error) {
throw (Error) ex;
}
throw new UndeclaredThrowableException(ex);
}
/**
* This variant retrieves {@link Class#getDeclaredMethods()} from a local cache
* in order to avoid the JVM's SecurityManager check and defensive array copying.
*/
private static Method[] getDeclaredMethods(Class<?> clazz) {
Method[] result = declaredMethodsCache.get(clazz);
if (result == null) {
result = clazz.getDeclaredMethods();
declaredMethodsCache.put(clazz, result);
}
return result;
}
/**
* Action to take on each method.
*/
public interface MethodCallback {
/**
* Perform an operation using the given method.
* @param method the method to operate on
*/
void doWith(Method method) throws IllegalArgumentException, IllegalAccessException;
}
/**
* Callback optionally used to filter methods to be operated on by a method callback.
*/
public interface MethodFilter {
/**
* Determine whether the given method matches.
* @param method the method to check
*/
boolean matches(Method method);
}
}
@@ -23,17 +23,12 @@ package org.apache.struts2.interceptor.validation;
import com.opensymphony.xwork2.ActionInvocation;
import com.opensymphony.xwork2.config.ConfigurationException;
import com.opensymphony.xwork2.inject.Inject;
import com.opensymphony.xwork2.util.AnnotationUtils;
import com.opensymphony.xwork2.validator.ValidationInterceptor;
import org.apache.commons.lang3.BooleanUtils;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.apache.struts2.StrutsConstants;
import java.lang.reflect.Method;
import java.util.Arrays;
import java.util.Collection;
/**
* Extends the xwork validation interceptor to also check for a @SkipValidation
@@ -3,13 +3,13 @@ package com.opensymphony.xwork2.util;
import com.opensymphony.xwork2.util.annotation.Dummy2Class;
import com.opensymphony.xwork2.util.annotation.DummyClass;
import com.opensymphony.xwork2.util.annotation.DummyClassExt;
import com.opensymphony.xwork2.util.annotation.DummyInterface;
import com.opensymphony.xwork2.util.annotation.MyAnnotation;
import com.opensymphony.xwork2.util.annotation.MyAnnotation2;
import com.opensymphony.xwork2.util.annotation.MyAnnotationI;
import junit.framework.TestCase;
import java.lang.annotation.Retention;
import java.lang.reflect.AnnotatedElement;
import java.util.Collection;
@@ -18,15 +18,6 @@ import java.util.Collection;
*/
public class AnnotationUtilsTest extends TestCase {
public void testGetAnnotationMeta() throws Exception {
assertNotNull(AnnotationUtils.getAnnotation(DummyClass.class.getMethod("methodWithAnnotation"), Retention.class));
}
public void testGetAnnotation() throws Exception {
assertNull(AnnotationUtils.getAnnotation(DummyClass.class.getMethod("methodWithAnnotation"), Deprecated.class));
assertNotNull(AnnotationUtils.getAnnotation(DummyClass.class.getMethod("methodWithAnnotation"), MyAnnotation.class));
}
public void testFindAnnotationFromSuperclass() throws Exception {
assertNotNull(AnnotationUtils.findAnnotation(DummyClassExt.class.getMethod("methodWithAnnotation"), MyAnnotation.class));
}
@@ -43,15 +34,16 @@ public class AnnotationUtilsTest extends TestCase {
public void testGetAnnotatedMethodsIncludingSuperclassAndInterface() throws Exception {
Collection<? extends AnnotatedElement> ans = AnnotationUtils.getAnnotatedMethods(DummyClassExt.class, Deprecated.class, MyAnnotation.class, MyAnnotation2.class, MyAnnotationI.class);
assertEquals(5, ans.size());
assertEquals(4, ans.size());
}
@SuppressWarnings("unchecked")
public void testGetAnnotatedMethodsWithoutAnnotationArgs() throws Exception {
Collection<? extends AnnotatedElement> ans = AnnotationUtils.getAnnotatedMethods(DummyClass.class);
assertTrue(ans.size() == 2);
assertEquals(3, ans.size());
assertTrue(ans.contains(DummyClass.class.getMethod("methodWithAnnotation")));
assertTrue(ans.contains(DummyClass.class.getDeclaredMethod("privateMethodWithAnnotation")));
assertTrue(ans.contains(DummyInterface.class.getDeclaredMethod("interfaceMethodWithAnnotation")));
}
@SuppressWarnings("unchecked")
@@ -69,7 +61,7 @@ public class AnnotationUtilsTest extends TestCase {
assertEquals(2, ans.size());
ans = AnnotationUtils.getAnnotatedMethods(DummyClassExt.class, MyAnnotation.class, MyAnnotation2.class);
assertEquals(4, ans.size());
assertEquals(3, ans.size());
}
public void testFindAnnotationOnClass() {
@@ -39,7 +39,6 @@ import org.apache.struts2.interceptor.validation.SkipValidation;
import javax.validation.ConstraintViolation;
import javax.validation.Validator;
import java.lang.reflect.Method;
import java.util.Collection;
import java.util.Set;
/**