Consistent use of LinkedHashSet for interfaces (since interface order may matter in subtle cases)
(cherry picked from commit 6f9d7da)
This commit is contained in:
@@ -34,6 +34,6 @@ public interface IntroductionInfo {
|
|||||||
* Return the additional interfaces introduced by this Advisor or Advice.
|
* Return the additional interfaces introduced by this Advisor or Advice.
|
||||||
* @return the introduced interfaces
|
* @return the introduced interfaces
|
||||||
*/
|
*/
|
||||||
Class[] getInterfaces();
|
Class<?>[] getInterfaces();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -34,7 +34,7 @@ import org.springframework.aop.support.DelegatingIntroductionInterceptor;
|
|||||||
*/
|
*/
|
||||||
public class DeclareParentsAdvisor implements IntroductionAdvisor {
|
public class DeclareParentsAdvisor implements IntroductionAdvisor {
|
||||||
|
|
||||||
private final Class introducedInterface;
|
private final Class<?> introducedInterface;
|
||||||
|
|
||||||
private final ClassFilter typePatternClassFilter;
|
private final ClassFilter typePatternClassFilter;
|
||||||
|
|
||||||
@@ -47,7 +47,7 @@ public class DeclareParentsAdvisor implements IntroductionAdvisor {
|
|||||||
* @param typePattern type pattern the introduction is restricted to
|
* @param typePattern type pattern the introduction is restricted to
|
||||||
* @param defaultImpl the default implementation class
|
* @param defaultImpl the default implementation class
|
||||||
*/
|
*/
|
||||||
public DeclareParentsAdvisor(Class interfaceType, String typePattern, Class defaultImpl) {
|
public DeclareParentsAdvisor(Class<?> interfaceType, String typePattern, Class<?> defaultImpl) {
|
||||||
this(interfaceType, typePattern, defaultImpl,
|
this(interfaceType, typePattern, defaultImpl,
|
||||||
new DelegatePerTargetObjectIntroductionInterceptor(defaultImpl, interfaceType));
|
new DelegatePerTargetObjectIntroductionInterceptor(defaultImpl, interfaceType));
|
||||||
}
|
}
|
||||||
@@ -58,7 +58,7 @@ public class DeclareParentsAdvisor implements IntroductionAdvisor {
|
|||||||
* @param typePattern type pattern the introduction is restricted to
|
* @param typePattern type pattern the introduction is restricted to
|
||||||
* @param delegateRef the delegate implementation object
|
* @param delegateRef the delegate implementation object
|
||||||
*/
|
*/
|
||||||
public DeclareParentsAdvisor(Class interfaceType, String typePattern, Object delegateRef) {
|
public DeclareParentsAdvisor(Class<?> interfaceType, String typePattern, Object delegateRef) {
|
||||||
this(interfaceType, typePattern, delegateRef.getClass(),
|
this(interfaceType, typePattern, delegateRef.getClass(),
|
||||||
new DelegatingIntroductionInterceptor(delegateRef));
|
new DelegatingIntroductionInterceptor(delegateRef));
|
||||||
}
|
}
|
||||||
@@ -71,13 +71,13 @@ public class DeclareParentsAdvisor implements IntroductionAdvisor {
|
|||||||
* @param implementationClass implementation class
|
* @param implementationClass implementation class
|
||||||
* @param advice delegation advice
|
* @param advice delegation advice
|
||||||
*/
|
*/
|
||||||
private DeclareParentsAdvisor(Class interfaceType, String typePattern, Class implementationClass, Advice advice) {
|
private DeclareParentsAdvisor(Class<?> interfaceType, String typePattern, Class<?> implementationClass, Advice advice) {
|
||||||
this.introducedInterface = interfaceType;
|
this.introducedInterface = interfaceType;
|
||||||
ClassFilter typePatternFilter = new TypePatternClassFilter(typePattern);
|
ClassFilter typePatternFilter = new TypePatternClassFilter(typePattern);
|
||||||
|
|
||||||
// Excludes methods implemented.
|
// Excludes methods implemented.
|
||||||
ClassFilter exclusion = new ClassFilter() {
|
ClassFilter exclusion = new ClassFilter() {
|
||||||
public boolean matches(Class clazz) {
|
public boolean matches(Class<?> clazz) {
|
||||||
return !(introducedInterface.isAssignableFrom(clazz));
|
return !(introducedInterface.isAssignableFrom(clazz));
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
@@ -103,8 +103,8 @@ public class DeclareParentsAdvisor implements IntroductionAdvisor {
|
|||||||
return this.advice;
|
return this.advice;
|
||||||
}
|
}
|
||||||
|
|
||||||
public Class[] getInterfaces() {
|
public Class<?>[] getInterfaces() {
|
||||||
return new Class[] {this.introducedInterface};
|
return new Class<?>[] {this.introducedInterface};
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2012 the original author or authors.
|
* Copyright 2002-2014 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -19,7 +19,7 @@ package org.springframework.aop.support;
|
|||||||
import java.lang.reflect.InvocationTargetException;
|
import java.lang.reflect.InvocationTargetException;
|
||||||
import java.lang.reflect.Method;
|
import java.lang.reflect.Method;
|
||||||
import java.lang.reflect.Proxy;
|
import java.lang.reflect.Proxy;
|
||||||
import java.util.HashSet;
|
import java.util.LinkedHashSet;
|
||||||
import java.util.LinkedList;
|
import java.util.LinkedList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
@@ -215,7 +215,7 @@ public abstract class AopUtils {
|
|||||||
introductionAwareMethodMatcher = (IntroductionAwareMethodMatcher) methodMatcher;
|
introductionAwareMethodMatcher = (IntroductionAwareMethodMatcher) methodMatcher;
|
||||||
}
|
}
|
||||||
|
|
||||||
Set<Class> classes = new HashSet<Class>(ClassUtils.getAllInterfacesForClassAsSet(targetClass));
|
Set<Class> classes = new LinkedHashSet<Class>(ClassUtils.getAllInterfacesForClassAsSet(targetClass));
|
||||||
classes.add(targetClass);
|
classes.add(targetClass);
|
||||||
for (Class<?> clazz : classes) {
|
for (Class<?> clazz : classes) {
|
||||||
Method[] methods = clazz.getMethods();
|
Method[] methods = clazz.getMethods();
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2012 the original author or authors.
|
* Copyright 2002-2014 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -17,7 +17,7 @@
|
|||||||
package org.springframework.aop.support;
|
package org.springframework.aop.support;
|
||||||
|
|
||||||
import java.io.Serializable;
|
import java.io.Serializable;
|
||||||
import java.util.HashSet;
|
import java.util.LinkedHashSet;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
|
|
||||||
import org.aopalliance.aop.Advice;
|
import org.aopalliance.aop.Advice;
|
||||||
@@ -43,7 +43,7 @@ public class DefaultIntroductionAdvisor implements IntroductionAdvisor, ClassFil
|
|||||||
|
|
||||||
private final Advice advice;
|
private final Advice advice;
|
||||||
|
|
||||||
private final Set<Class> interfaces = new HashSet<Class>();
|
private final Set<Class> interfaces = new LinkedHashSet<Class>();
|
||||||
|
|
||||||
private int order = Integer.MAX_VALUE;
|
private int order = Integer.MAX_VALUE;
|
||||||
|
|
||||||
@@ -68,11 +68,11 @@ public class DefaultIntroductionAdvisor implements IntroductionAdvisor, ClassFil
|
|||||||
Assert.notNull(advice, "Advice must not be null");
|
Assert.notNull(advice, "Advice must not be null");
|
||||||
this.advice = advice;
|
this.advice = advice;
|
||||||
if (introductionInfo != null) {
|
if (introductionInfo != null) {
|
||||||
Class[] introducedInterfaces = introductionInfo.getInterfaces();
|
Class<?>[] introducedInterfaces = introductionInfo.getInterfaces();
|
||||||
if (introducedInterfaces.length == 0) {
|
if (introducedInterfaces.length == 0) {
|
||||||
throw new IllegalArgumentException("IntroductionAdviceSupport implements no interfaces");
|
throw new IllegalArgumentException("IntroductionAdviceSupport implements no interfaces");
|
||||||
}
|
}
|
||||||
for (Class ifc : introducedInterfaces) {
|
for (Class<?> ifc : introducedInterfaces) {
|
||||||
addInterface(ifc);
|
addInterface(ifc);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -83,7 +83,7 @@ public class DefaultIntroductionAdvisor implements IntroductionAdvisor, ClassFil
|
|||||||
* @param advice the Advice to apply
|
* @param advice the Advice to apply
|
||||||
* @param intf the interface to introduce
|
* @param intf the interface to introduce
|
||||||
*/
|
*/
|
||||||
public DefaultIntroductionAdvisor(DynamicIntroductionAdvice advice, Class intf) {
|
public DefaultIntroductionAdvisor(DynamicIntroductionAdvice advice, Class<?> intf) {
|
||||||
Assert.notNull(advice, "Advice must not be null");
|
Assert.notNull(advice, "Advice must not be null");
|
||||||
this.advice = advice;
|
this.advice = advice;
|
||||||
addInterface(intf);
|
addInterface(intf);
|
||||||
@@ -94,7 +94,7 @@ public class DefaultIntroductionAdvisor implements IntroductionAdvisor, ClassFil
|
|||||||
* Add the specified interface to the list of interfaces to introduce.
|
* Add the specified interface to the list of interfaces to introduce.
|
||||||
* @param intf the interface to introduce
|
* @param intf the interface to introduce
|
||||||
*/
|
*/
|
||||||
public void addInterface(Class intf) {
|
public void addInterface(Class<?> intf) {
|
||||||
Assert.notNull(intf, "Interface must not be null");
|
Assert.notNull(intf, "Interface must not be null");
|
||||||
if (!intf.isInterface()) {
|
if (!intf.isInterface()) {
|
||||||
throw new IllegalArgumentException("Specified class [" + intf.getName() + "] must be an interface");
|
throw new IllegalArgumentException("Specified class [" + intf.getName() + "] must be an interface");
|
||||||
@@ -102,12 +102,13 @@ public class DefaultIntroductionAdvisor implements IntroductionAdvisor, ClassFil
|
|||||||
this.interfaces.add(intf);
|
this.interfaces.add(intf);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Class[] getInterfaces() {
|
public Class<?>[] getInterfaces() {
|
||||||
return this.interfaces.toArray(new Class[this.interfaces.size()]);
|
return this.interfaces.toArray(new Class<?>[this.interfaces.size()]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void validateInterfaces() throws IllegalArgumentException {
|
public void validateInterfaces() throws IllegalArgumentException {
|
||||||
for (Class ifc : this.interfaces) {
|
for (Class<?> ifc : this.interfaces) {
|
||||||
if (this.advice instanceof DynamicIntroductionAdvice &&
|
if (this.advice instanceof DynamicIntroductionAdvice &&
|
||||||
!((DynamicIntroductionAdvice) this.advice).implementsInterface(ifc)) {
|
!((DynamicIntroductionAdvice) this.advice).implementsInterface(ifc)) {
|
||||||
throw new IllegalArgumentException("DynamicIntroductionAdvice [" + this.advice + "] " +
|
throw new IllegalArgumentException("DynamicIntroductionAdvice [" + this.advice + "] " +
|
||||||
@@ -138,7 +139,7 @@ public class DefaultIntroductionAdvisor implements IntroductionAdvisor, ClassFil
|
|||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean matches(Class clazz) {
|
public boolean matches(Class<?> clazz) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
/*
|
/*
|
||||||
* Copyright 2002-2012 the original author or authors.
|
* Copyright 2002-2014 the original author or authors.
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
@@ -20,7 +20,7 @@ import java.io.IOException;
|
|||||||
import java.io.ObjectInputStream;
|
import java.io.ObjectInputStream;
|
||||||
import java.io.Serializable;
|
import java.io.Serializable;
|
||||||
import java.lang.reflect.Method;
|
import java.lang.reflect.Method;
|
||||||
import java.util.HashSet;
|
import java.util.LinkedHashSet;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
import java.util.Set;
|
import java.util.Set;
|
||||||
import java.util.concurrent.ConcurrentHashMap;
|
import java.util.concurrent.ConcurrentHashMap;
|
||||||
@@ -43,7 +43,7 @@ import org.springframework.util.ClassUtils;
|
|||||||
@SuppressWarnings("serial")
|
@SuppressWarnings("serial")
|
||||||
public class IntroductionInfoSupport implements IntroductionInfo, Serializable {
|
public class IntroductionInfoSupport implements IntroductionInfo, Serializable {
|
||||||
|
|
||||||
protected final Set<Class> publishedInterfaces = new HashSet<Class>();
|
protected final Set<Class> publishedInterfaces = new LinkedHashSet<Class>();
|
||||||
|
|
||||||
private transient Map<Method, Boolean> rememberedMethods = new ConcurrentHashMap<Method, Boolean>(32);
|
private transient Map<Method, Boolean> rememberedMethods = new ConcurrentHashMap<Method, Boolean>(32);
|
||||||
|
|
||||||
@@ -55,12 +55,12 @@ public class IntroductionInfoSupport implements IntroductionInfo, Serializable {
|
|||||||
* <p>Does nothing if the interface is not implemented by the delegate.
|
* <p>Does nothing if the interface is not implemented by the delegate.
|
||||||
* @param intf the interface to suppress
|
* @param intf the interface to suppress
|
||||||
*/
|
*/
|
||||||
public void suppressInterface(Class intf) {
|
public void suppressInterface(Class<?> intf) {
|
||||||
this.publishedInterfaces.remove(intf);
|
this.publishedInterfaces.remove(intf);
|
||||||
}
|
}
|
||||||
|
|
||||||
public Class[] getInterfaces() {
|
public Class<?>[] getInterfaces() {
|
||||||
return this.publishedInterfaces.toArray(new Class[this.publishedInterfaces.size()]);
|
return this.publishedInterfaces.toArray(new Class<?>[this.publishedInterfaces.size()]);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -68,8 +68,8 @@ public class IntroductionInfoSupport implements IntroductionInfo, Serializable {
|
|||||||
* @param ifc the interface to check
|
* @param ifc the interface to check
|
||||||
* @return whether the interface is part of this introduction
|
* @return whether the interface is part of this introduction
|
||||||
*/
|
*/
|
||||||
public boolean implementsInterface(Class ifc) {
|
public boolean implementsInterface(Class<?> ifc) {
|
||||||
for (Class pubIfc : this.publishedInterfaces) {
|
for (Class<?> pubIfc : this.publishedInterfaces) {
|
||||||
if (ifc.isInterface() && ifc.isAssignableFrom(pubIfc)) {
|
if (ifc.isInterface() && ifc.isAssignableFrom(pubIfc)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user