From cdac5459ea223df39a51195c4743cb88e07ec31f Mon Sep 17 00:00:00 2001 From: lvxiao Date: Tue, 28 Feb 2023 15:54:40 +0800 Subject: [PATCH] fix: Custom CGLIB classes cannot be registered Add `ClassUtils.getUserClass` to get the target class of a custom CGLIB class --- ...ketMQMessageListenerBeanPostProcessor.java | 8 ++++-- ...QMessageListenerBeanPostProcessorTest.java | 27 +++++++++++++++++++ 2 files changed, 33 insertions(+), 2 deletions(-) diff --git a/rocketmq-spring-boot/src/main/java/org/apache/rocketmq/spring/annotation/RocketMQMessageListenerBeanPostProcessor.java b/rocketmq-spring-boot/src/main/java/org/apache/rocketmq/spring/annotation/RocketMQMessageListenerBeanPostProcessor.java index 82269835..119d83a8 100644 --- a/rocketmq-spring-boot/src/main/java/org/apache/rocketmq/spring/annotation/RocketMQMessageListenerBeanPostProcessor.java +++ b/rocketmq-spring-boot/src/main/java/org/apache/rocketmq/spring/annotation/RocketMQMessageListenerBeanPostProcessor.java @@ -17,7 +17,7 @@ package org.apache.rocketmq.spring.annotation; import org.apache.rocketmq.spring.autoconfigure.ListenerContainerConfiguration; -import org.springframework.aop.support.AopUtils; +import org.springframework.aop.framework.AopProxyUtils; import org.springframework.beans.BeansException; import org.springframework.beans.factory.InitializingBean; import org.springframework.beans.factory.config.BeanPostProcessor; @@ -25,6 +25,7 @@ import org.springframework.context.ApplicationContextAware; import org.springframework.core.OrderComparator; import org.springframework.core.annotation.AnnotationUtils; +import org.springframework.util.ClassUtils; import java.lang.reflect.AnnotatedElement; import java.util.List; @@ -47,7 +48,10 @@ public Object postProcessBeforeInitialization(Object bean, String beanName) thro @Override public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException { - Class targetClass = AopUtils.getTargetClass(bean); + Class targetClass = AopProxyUtils.ultimateTargetClass(bean); + if (targetClass.getName().contains(ClassUtils.CGLIB_CLASS_SEPARATOR)) { + targetClass = ClassUtils.getUserClass(bean); + } RocketMQMessageListener ann = targetClass.getAnnotation(RocketMQMessageListener.class); if (ann != null) { RocketMQMessageListener enhance = enhance(targetClass, ann); diff --git a/rocketmq-spring-boot/src/test/java/org/apache/rocketmq/spring/annotation/RocketMQMessageListenerBeanPostProcessorTest.java b/rocketmq-spring-boot/src/test/java/org/apache/rocketmq/spring/annotation/RocketMQMessageListenerBeanPostProcessorTest.java index 4bddd578..af5a568f 100644 --- a/rocketmq-spring-boot/src/test/java/org/apache/rocketmq/spring/annotation/RocketMQMessageListenerBeanPostProcessorTest.java +++ b/rocketmq-spring-boot/src/test/java/org/apache/rocketmq/spring/annotation/RocketMQMessageListenerBeanPostProcessorTest.java @@ -19,13 +19,20 @@ import org.apache.rocketmq.spring.autoconfigure.RocketMQAutoConfiguration; import org.apache.rocketmq.spring.core.RocketMQListener; +import org.apache.rocketmq.spring.support.DefaultRocketMQListenerContainer; import org.junit.Test; import org.springframework.boot.autoconfigure.AutoConfigurations; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.boot.test.context.runner.ApplicationContextRunner; +import org.springframework.cglib.proxy.Callback; +import org.springframework.cglib.proxy.Enhancer; +import org.springframework.cglib.proxy.MethodInterceptor; +import org.springframework.cglib.proxy.MethodProxy; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; +import java.lang.reflect.Method; + import static org.assertj.core.api.Assertions.assertThat; @SpringBootTest @@ -47,6 +54,15 @@ public void testAnnotationEnhancer() { } + @Test + public void testGetTargetClass() { + runner.withPropertyValues("rocketmq.name-server=127.0.0.1:9876"). + withUserConfiguration(TestAnnotationEnhancerConfig.class, TestGetTargetClassConfig.class). + run((context) -> { + assertThat(context).getFailure().hasMessageContaining("connect to null failed"); + }); + } + @Configuration static class TestAnnotationEnhancerConfig { @Bean @@ -65,6 +81,17 @@ public RocketMQMessageListenerBeanPostProcessor.AnnotationEnhancer consumeContai } } + @Configuration + static class TestGetTargetClassConfig { + @Bean + public Receiver customEnhancer() { + Enhancer enhancer = new Enhancer(); + enhancer.setSuperclass(Receiver.class); + enhancer.setCallback((MethodInterceptor) (o, method, objects, methodProxy) -> null); + return (Receiver) enhancer.create(); + } + } + @Configuration static class TestReceiverConfig { @Bean