提交 296aa96d 编写于 作者: J Juergen Hoeller

AopUtils.getTargetClass(...) never returns null (SPR-7011)

上级 a2c3274b
/* /*
* Copyright 2002-2009 the original author or authors. * Copyright 2002-2010 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.
...@@ -85,7 +85,7 @@ public abstract class AopUtils { ...@@ -85,7 +85,7 @@ public abstract class AopUtils {
* Check whether the specified class is a CGLIB-generated class. * Check whether the specified class is a CGLIB-generated class.
* @param clazz the class to check * @param clazz the class to check
*/ */
public static boolean isCglibProxyClass(Class clazz) { public static boolean isCglibProxyClass(Class<?> clazz) {
return (clazz != null && isCglibProxyClassName(clazz.getName())); return (clazz != null && isCglibProxyClassName(clazz.getName()));
} }
...@@ -102,18 +102,20 @@ public abstract class AopUtils { ...@@ -102,18 +102,20 @@ public abstract class AopUtils {
* which might be an AOP proxy. * which might be an AOP proxy.
* <p>Returns the target class for an AOP proxy and the plain class else. * <p>Returns the target class for an AOP proxy and the plain class else.
* @param candidate the instance to check (might be an AOP proxy) * @param candidate the instance to check (might be an AOP proxy)
* @return the target class (or the plain class of the given object as fallback) * @return the target class (or the plain class of the given object as fallback;
* never <code>null</code>)
* @see org.springframework.aop.TargetClassAware#getTargetClass() * @see org.springframework.aop.TargetClassAware#getTargetClass()
*/ */
public static Class getTargetClass(Object candidate) { public static Class<?> getTargetClass(Object candidate) {
Assert.notNull(candidate, "Candidate object must not be null"); Assert.notNull(candidate, "Candidate object must not be null");
Class<?> result = null;
if (candidate instanceof TargetClassAware) { if (candidate instanceof TargetClassAware) {
return ((TargetClassAware) candidate).getTargetClass(); result = ((TargetClassAware) candidate).getTargetClass();
} }
if (isCglibProxy(candidate)) { if (result == null) {
return candidate.getClass().getSuperclass(); result = (isCglibProxy(candidate) ? candidate.getClass().getSuperclass() : candidate.getClass());
} }
return candidate.getClass(); return result;
} }
/** /**
...@@ -165,7 +167,7 @@ public abstract class AopUtils { ...@@ -165,7 +167,7 @@ public abstract class AopUtils {
* <code>targetClass</code> doesn't implement it or is <code>null</code> * <code>targetClass</code> doesn't implement it or is <code>null</code>
* @see org.springframework.util.ClassUtils#getMostSpecificMethod * @see org.springframework.util.ClassUtils#getMostSpecificMethod
*/ */
public static Method getMostSpecificMethod(Method method, Class targetClass) { public static Method getMostSpecificMethod(Method method, Class<?> targetClass) {
Method resolvedMethod = ClassUtils.getMostSpecificMethod(method, targetClass); Method resolvedMethod = ClassUtils.getMostSpecificMethod(method, targetClass);
// If we are dealing with method with generic parameters, find the original method. // If we are dealing with method with generic parameters, find the original method.
return BridgeMethodResolver.findBridgedMethod(resolvedMethod); return BridgeMethodResolver.findBridgedMethod(resolvedMethod);
...@@ -180,7 +182,7 @@ public abstract class AopUtils { ...@@ -180,7 +182,7 @@ public abstract class AopUtils {
* @param targetClass the class to test * @param targetClass the class to test
* @return whether the pointcut can apply on any method * @return whether the pointcut can apply on any method
*/ */
public static boolean canApply(Pointcut pc, Class targetClass) { public static boolean canApply(Pointcut pc, Class<?> targetClass) {
return canApply(pc, targetClass, false); return canApply(pc, targetClass, false);
} }
...@@ -194,7 +196,7 @@ public abstract class AopUtils { ...@@ -194,7 +196,7 @@ public abstract class AopUtils {
* for this bean includes any introductions * for this bean includes any introductions
* @return whether the pointcut can apply on any method * @return whether the pointcut can apply on any method
*/ */
public static boolean canApply(Pointcut pc, Class targetClass, boolean hasIntroductions) { public static boolean canApply(Pointcut pc, Class<?> targetClass, boolean hasIntroductions) {
if (!pc.getClassFilter().matches(targetClass)) { if (!pc.getClassFilter().matches(targetClass)) {
return false; return false;
} }
...@@ -207,7 +209,7 @@ public abstract class AopUtils { ...@@ -207,7 +209,7 @@ public abstract class AopUtils {
Set<Class> classes = new HashSet<Class>(ClassUtils.getAllInterfacesForClassAsSet(targetClass)); Set<Class> classes = new HashSet<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();
for (Method method : methods) { for (Method method : methods) {
if ((introductionAwareMethodMatcher != null && if ((introductionAwareMethodMatcher != null &&
...@@ -229,7 +231,7 @@ public abstract class AopUtils { ...@@ -229,7 +231,7 @@ public abstract class AopUtils {
* @param targetClass class we're testing * @param targetClass class we're testing
* @return whether the pointcut can apply on any method * @return whether the pointcut can apply on any method
*/ */
public static boolean canApply(Advisor advisor, Class targetClass) { public static boolean canApply(Advisor advisor, Class<?> targetClass) {
return canApply(advisor, targetClass, false); return canApply(advisor, targetClass, false);
} }
...@@ -243,7 +245,7 @@ public abstract class AopUtils { ...@@ -243,7 +245,7 @@ public abstract class AopUtils {
* any introductions * any introductions
* @return whether the pointcut can apply on any method * @return whether the pointcut can apply on any method
*/ */
public static boolean canApply(Advisor advisor, Class targetClass, boolean hasIntroductions) { public static boolean canApply(Advisor advisor, Class<?> targetClass, boolean hasIntroductions) {
if (advisor instanceof IntroductionAdvisor) { if (advisor instanceof IntroductionAdvisor) {
return ((IntroductionAdvisor) advisor).getClassFilter().matches(targetClass); return ((IntroductionAdvisor) advisor).getClassFilter().matches(targetClass);
} }
...@@ -265,7 +267,7 @@ public abstract class AopUtils { ...@@ -265,7 +267,7 @@ public abstract class AopUtils {
* @return sublist of Advisors that can apply to an object of the given class * @return sublist of Advisors that can apply to an object of the given class
* (may be the incoming List as-is) * (may be the incoming List as-is)
*/ */
public static List<Advisor> findAdvisorsThatCanApply(List<Advisor> candidateAdvisors, Class clazz) { public static List<Advisor> findAdvisorsThatCanApply(List<Advisor> candidateAdvisors, Class<?> clazz) {
if (candidateAdvisors.isEmpty()) { if (candidateAdvisors.isEmpty()) {
return candidateAdvisors; return candidateAdvisors;
} }
......
...@@ -237,7 +237,7 @@ public abstract class JmxUtils { ...@@ -237,7 +237,7 @@ public abstract class JmxUtils {
* @return the bean class to expose * @return the bean class to expose
* @see org.springframework.util.ClassUtils#getUserClass(Object) * @see org.springframework.util.ClassUtils#getUserClass(Object)
*/ */
public static Class getClassToExpose(Object managedBean) { public static Class<?> getClassToExpose(Object managedBean) {
return ClassUtils.getUserClass(managedBean); return ClassUtils.getUserClass(managedBean);
} }
...@@ -247,12 +247,12 @@ public abstract class JmxUtils { ...@@ -247,12 +247,12 @@ public abstract class JmxUtils {
* (for example, checked for annotations). * (for example, checked for annotations).
* <p>This implementation returns the superclass for a CGLIB proxy and * <p>This implementation returns the superclass for a CGLIB proxy and
* the class of the given bean else (for a JDK proxy or a plain bean class). * the class of the given bean else (for a JDK proxy or a plain bean class).
* @param beanClass the bean class (might be an AOP proxy class) * @param clazz the bean class (might be an AOP proxy class)
* @return the bean class to expose * @return the bean class to expose
* @see org.springframework.util.ClassUtils#getUserClass(Class) * @see org.springframework.util.ClassUtils#getUserClass(Class)
*/ */
public static Class getClassToExpose(Class beanClass) { public static Class<?> getClassToExpose(Class<?> clazz) {
return ClassUtils.getUserClass(beanClass); return ClassUtils.getUserClass(clazz);
} }
/** /**
...@@ -260,14 +260,14 @@ public abstract class JmxUtils { ...@@ -260,14 +260,14 @@ public abstract class JmxUtils {
* <p>This implementation checks for {@link javax.management.DynamicMBean} * <p>This implementation checks for {@link javax.management.DynamicMBean}
* classes as well as classes with corresponding "*MBean" interface * classes as well as classes with corresponding "*MBean" interface
* (Standard MBeans) or corresponding "*MXBean" interface (Java 6 MXBeans). * (Standard MBeans) or corresponding "*MXBean" interface (Java 6 MXBeans).
* @param beanClass the bean class to analyze * @param clazz the bean class to analyze
* @return whether the class qualifies as an MBean * @return whether the class qualifies as an MBean
* @see org.springframework.jmx.export.MBeanExporter#isMBean(Class) * @see org.springframework.jmx.export.MBeanExporter#isMBean(Class)
*/ */
public static boolean isMBean(Class beanClass) { public static boolean isMBean(Class<?> clazz) {
return (beanClass != null && return (clazz != null &&
(DynamicMBean.class.isAssignableFrom(beanClass) || (DynamicMBean.class.isAssignableFrom(clazz) ||
(getMBeanInterface(beanClass) != null || getMXBeanInterface(beanClass) != null))); (getMBeanInterface(clazz) != null || getMXBeanInterface(clazz) != null)));
} }
/** /**
...@@ -277,13 +277,13 @@ public abstract class JmxUtils { ...@@ -277,13 +277,13 @@ public abstract class JmxUtils {
* @param clazz the class to check * @param clazz the class to check
* @return the Standard MBean interface for the given class * @return the Standard MBean interface for the given class
*/ */
public static Class getMBeanInterface(Class clazz) { public static Class<?> getMBeanInterface(Class<?> clazz) {
if (clazz.getSuperclass() == null) { if (clazz == null || clazz.getSuperclass() == null) {
return null; return null;
} }
String mbeanInterfaceName = clazz.getName() + MBEAN_SUFFIX; String mbeanInterfaceName = clazz.getName() + MBEAN_SUFFIX;
Class[] implementedInterfaces = clazz.getInterfaces(); Class[] implementedInterfaces = clazz.getInterfaces();
for (Class iface : implementedInterfaces) { for (Class<?> iface : implementedInterfaces) {
if (iface.getName().equals(mbeanInterfaceName)) { if (iface.getName().equals(mbeanInterfaceName)) {
return iface; return iface;
} }
...@@ -298,12 +298,12 @@ public abstract class JmxUtils { ...@@ -298,12 +298,12 @@ public abstract class JmxUtils {
* @param clazz the class to check * @param clazz the class to check
* @return whether there is an MXBean interface for the given class * @return whether there is an MXBean interface for the given class
*/ */
public static Class getMXBeanInterface(Class clazz) { public static Class<?> getMXBeanInterface(Class<?> clazz) {
if (clazz.getSuperclass() == null) { if (clazz == null || clazz.getSuperclass() == null) {
return null; return null;
} }
Class[] implementedInterfaces = clazz.getInterfaces(); Class[] implementedInterfaces = clazz.getInterfaces();
for (Class iface : implementedInterfaces) { for (Class<?> iface : implementedInterfaces) {
boolean isMxBean = iface.getName().endsWith(MXBEAN_SUFFIX); boolean isMxBean = iface.getName().endsWith(MXBEAN_SUFFIX);
if (mxBeanAnnotationAvailable) { if (mxBeanAnnotationAvailable) {
Boolean checkResult = MXBeanChecker.evaluateMXBeanAnnotation(iface); Boolean checkResult = MXBeanChecker.evaluateMXBeanAnnotation(iface);
......
/* /*
* Copyright 2002-2009 the original author or authors. * Copyright 2002-2010 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,13 +17,13 @@ ...@@ -17,13 +17,13 @@
package org.springframework.scheduling.annotation; package org.springframework.scheduling.annotation;
import java.lang.annotation.Annotation; import java.lang.annotation.Annotation;
import java.util.concurrent.Executor;
import org.springframework.aop.framework.Advised; import org.springframework.aop.framework.Advised;
import org.springframework.aop.framework.AopInfrastructureBean; import org.springframework.aop.framework.AopInfrastructureBean;
import org.springframework.aop.framework.ProxyConfig; import org.springframework.aop.framework.ProxyConfig;
import org.springframework.aop.framework.ProxyFactory; import org.springframework.aop.framework.ProxyFactory;
import org.springframework.aop.support.AopUtils; import org.springframework.aop.support.AopUtils;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.BeanClassLoaderAware; import org.springframework.beans.factory.BeanClassLoaderAware;
import org.springframework.beans.factory.InitializingBean; import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.config.BeanPostProcessor; import org.springframework.beans.factory.config.BeanPostProcessor;
...@@ -32,8 +32,6 @@ import org.springframework.core.task.TaskExecutor; ...@@ -32,8 +32,6 @@ import org.springframework.core.task.TaskExecutor;
import org.springframework.util.Assert; import org.springframework.util.Assert;
import org.springframework.util.ClassUtils; import org.springframework.util.ClassUtils;
import java.util.concurrent.Executor;
/** /**
* Bean post-processor that automatically applies asynchronous invocation * Bean post-processor that automatically applies asynchronous invocation
* behavior to any bean that carries the {@link Async} annotation at class or * behavior to any bean that carries the {@link Async} annotation at class or
...@@ -105,22 +103,16 @@ public class AsyncAnnotationBeanPostProcessor extends ProxyConfig ...@@ -105,22 +103,16 @@ public class AsyncAnnotationBeanPostProcessor extends ProxyConfig
} }
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException { public Object postProcessBeforeInitialization(Object bean, String beanName) {
return bean; return bean;
} }
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException { public Object postProcessAfterInitialization(Object bean, String beanName) {
if (bean instanceof AopInfrastructureBean) { if (bean instanceof AopInfrastructureBean) {
// Ignore AOP infrastructure such as scoped proxies. // Ignore AOP infrastructure such as scoped proxies.
return bean; return bean;
} }
Class<?> targetClass = AopUtils.getTargetClass(bean); Class<?> targetClass = AopUtils.getTargetClass(bean);
if (targetClass == null) {
// Can't do much here.
return bean;
}
if (AopUtils.canApply(this.asyncAnnotationAdvisor, targetClass)) { if (AopUtils.canApply(this.asyncAnnotationAdvisor, targetClass)) {
if (bean instanceof Advised) { if (bean instanceof Advised) {
((Advised) bean).addAdvisor(this.asyncAnnotationAdvisor); ((Advised) bean).addAdvisor(this.asyncAnnotationAdvisor);
......
...@@ -21,7 +21,6 @@ import java.util.HashMap; ...@@ -21,7 +21,6 @@ import java.util.HashMap;
import java.util.Map; import java.util.Map;
import org.springframework.aop.support.AopUtils; import org.springframework.aop.support.AopUtils;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.DisposableBean; import org.springframework.beans.factory.DisposableBean;
import org.springframework.beans.factory.config.BeanPostProcessor; import org.springframework.beans.factory.config.BeanPostProcessor;
import org.springframework.context.ApplicationContext; import org.springframework.context.ApplicationContext;
...@@ -82,15 +81,12 @@ public class ScheduledAnnotationBeanPostProcessor implements BeanPostProcessor, ...@@ -82,15 +81,12 @@ public class ScheduledAnnotationBeanPostProcessor implements BeanPostProcessor,
} }
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException { public Object postProcessBeforeInitialization(Object bean, String beanName) {
return bean; return bean;
} }
public Object postProcessAfterInitialization(final Object bean, String beanName) throws BeansException { public Object postProcessAfterInitialization(final Object bean, String beanName) {
Class<?> targetClass = AopUtils.getTargetClass(bean); Class<?> targetClass = AopUtils.getTargetClass(bean);
if (targetClass == null) {
return bean;
}
ReflectionUtils.doWithMethods(targetClass, new MethodCallback() { ReflectionUtils.doWithMethods(targetClass, new MethodCallback() {
public void doWith(Method method) throws IllegalArgumentException, IllegalAccessException { public void doWith(Method method) throws IllegalArgumentException, IllegalAccessException {
Scheduled annotation = AnnotationUtils.getAnnotation(method, Scheduled.class); Scheduled annotation = AnnotationUtils.getAnnotation(method, Scheduled.class);
......
/* /*
* Copyright 2002-2009 the original author or authors. * Copyright 2002-2010 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.
...@@ -106,22 +106,16 @@ public class PersistenceExceptionTranslationPostProcessor extends ProxyConfig ...@@ -106,22 +106,16 @@ public class PersistenceExceptionTranslationPostProcessor extends ProxyConfig
} }
public Object postProcessBeforeInitialization(Object bean, String beanName) throws BeansException { public Object postProcessBeforeInitialization(Object bean, String beanName) {
return bean; return bean;
} }
public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException { public Object postProcessAfterInitialization(Object bean, String beanName) {
if (bean instanceof AopInfrastructureBean) { if (bean instanceof AopInfrastructureBean) {
// Ignore AOP infrastructure such as scoped proxies. // Ignore AOP infrastructure such as scoped proxies.
return bean; return bean;
} }
Class targetClass = AopUtils.getTargetClass(bean); Class targetClass = AopUtils.getTargetClass(bean);
if (targetClass == null) {
// Can't do much here.
return bean;
}
if (AopUtils.canApply(this.persistenceExceptionTranslationAdvisor, targetClass)) { if (AopUtils.canApply(this.persistenceExceptionTranslationAdvisor, targetClass)) {
if (bean instanceof Advised) { if (bean instanceof Advised) {
((Advised) bean).addAdvisor(this.persistenceExceptionTranslationAdvisor); ((Advised) bean).addAdvisor(this.persistenceExceptionTranslationAdvisor);
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册