I want to conditionally enable aspect like this:
import org.aspectj.lang.ProceedingJoinPoint;
import org.aspectj.lang.annotation.Around;
import org.aspectj.lang.annotation.Aspect;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.Bean;
@SpringBootApplication
public class DemoApplication {
public static void main(String[] args) {
ApplicationContext ctx = SpringApplication.run(DemoApplication.class, args);
TestService testService = ctx.getBean(TestService.class);
testService.test();
}
@Bean
TestService testService() {
return new TestService();
}
@Bean
TestAspect testAspect() {
boolean enabled = false; // TODO
return enabled ? new TestAspect() : null;
}
@Aspect
public static class TestAspect {
@Around("execution(public * test(..))")
public Object test(ProceedingJoinPoint pjp) throws Throwable {
return pjp.proceed();
}
}
public static class TestService {
public void test() {
}
}
}
It will raise exception when proxied method invoked:
Exception in thread "main" org.springframework.aop.AopInvocationException: Mismatch on arguments to advice method [public java.lang.Object com.example.demo.DemoApplication$TestAspect.test(org.aspectj.lang.ProceedingJoinPoint) throws java.lang.Throwable]; pointcut expression [org.aspectj.weaver.internal.tools.PointcutExpressionImpl@51e1e058]
at org.springframework.aop.aspectj.AbstractAspectJAdvice.invokeAdviceMethodWithGivenArgs(AbstractAspectJAdvice.java:647)
at org.springframework.aop.aspectj.AbstractAspectJAdvice.invokeAdviceMethod(AbstractAspectJAdvice.java:632)
at org.springframework.aop.aspectj.AspectJAroundAdvice.invoke(AspectJAroundAdvice.java:71)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:184)
at org.springframework.aop.interceptor.ExposeInvocationInterceptor.invoke(ExposeInvocationInterceptor.java:97)
at org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:184)
at org.springframework.aop.framework.CglibAopProxy$DynamicAdvisedInterceptor.intercept(CglibAopProxy.java:728)
at com.example.demo.DemoApplication$TestService$$SpringCGLIB$$0.test(<generated>)
at com.example.demo.DemoApplication.main(DemoApplication.java:18)
Caused by: java.lang.IllegalArgumentException: object is not an instance of declaring class
at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.checkReceiver(DirectMethodHandleAccessor.java:197)
at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:99)
at java.base/java.lang.reflect.Method.invoke(Method.java:580)
at org.springframework.aop.aspectj.AbstractAspectJAdvice.invokeAdviceMethodWithGivenArgs(AbstractAspectJAdvice.java:642)
... 8 more
If the proposal is accepted, please note that application context failed to initialize if the aspect implements Ordered
:
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'testService' defined in com.example.demo.DemoApplication: class org.springframework.beans.factory.support.NullBean cannot be cast to class org.springframework.core.Ordered (org.springframework.beans.factory.support.NullBean and org.springframework.core.Ordered are in unnamed module of loader 'app')
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:614) ~[spring-beans-6.2.7.jar:6.2.7]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:529) ~[spring-beans-6.2.7.jar:6.2.7]
at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:339) ~[spring-beans-6.2.7.jar:6.2.7]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:373) ~[spring-beans-6.2.7.jar:6.2.7]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:337) ~[spring-beans-6.2.7.jar:6.2.7]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:202) ~[spring-beans-6.2.7.jar:6.2.7]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.instantiateSingleton(DefaultListableBeanFactory.java:1222) ~[spring-beans-6.2.7.jar:6.2.7]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingleton(DefaultListableBeanFactory.java:1188) ~[spring-beans-6.2.7.jar:6.2.7]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:1123) ~[spring-beans-6.2.7.jar:6.2.7]
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:987) ~[spring-context-6.2.7.jar:6.2.7]
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:627) ~[spring-context-6.2.7.jar:6.2.7]
at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:146) ~[spring-boot-3.5.0.jar:3.5.0]
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:753) ~[spring-boot-3.5.0.jar:3.5.0]
at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:439) ~[spring-boot-3.5.0.jar:3.5.0]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:318) ~[spring-boot-3.5.0.jar:3.5.0]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1362) ~[spring-boot-3.5.0.jar:3.5.0]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1351) ~[spring-boot-3.5.0.jar:3.5.0]
at com.example.demo.DemoApplication.main(DemoApplication.java:16) ~[main/:na]
Caused by: java.lang.ClassCastException: class org.springframework.beans.factory.support.NullBean cannot be cast to class org.springframework.core.Ordered (org.springframework.beans.factory.support.NullBean and org.springframework.core.Ordered are in unnamed module of loader 'app')
at org.springframework.aop.aspectj.annotation.BeanFactoryAspectInstanceFactory.getOrder(BeanFactoryAspectInstanceFactory.java:133) ~[spring-aop-6.2.7.jar:6.2.7]
at org.springframework.aop.aspectj.annotation.LazySingletonAspectInstanceFactoryDecorator.getOrder(LazySingletonAspectInstanceFactoryDecorator.java:95) ~[spring-aop-6.2.7.jar:6.2.7]
at org.springframework.aop.aspectj.annotation.InstantiationModelAwarePointcutAdvisorImpl.getOrder(InstantiationModelAwarePointcutAdvisorImpl.java:184) ~[spring-aop-6.2.7.jar:6.2.7]
at org.springframework.core.OrderComparator.findOrder(OrderComparator.java:145) ~[spring-core-6.2.7.jar:6.2.7]
at org.springframework.core.annotation.AnnotationAwareOrderComparator.findOrder(AnnotationAwareOrderComparator.java:64) ~[spring-core-6.2.7.jar:6.2.7]
at org.springframework.core.OrderComparator.getOrder(OrderComparator.java:128) ~[spring-core-6.2.7.jar:6.2.7]
at org.springframework.core.OrderComparator.getOrder(OrderComparator.java:116) ~[spring-core-6.2.7.jar:6.2.7]
at org.springframework.core.OrderComparator.doCompare(OrderComparator.java:86) ~[spring-core-6.2.7.jar:6.2.7]
at org.springframework.core.OrderComparator.compare(OrderComparator.java:73) ~[spring-core-6.2.7.jar:6.2.7]
at org.springframework.aop.aspectj.autoproxy.AspectJPrecedenceComparator.compare(AspectJPrecedenceComparator.java:83) ~[spring-aop-6.2.7.jar:6.2.7]
at org.springframework.aop.aspectj.autoproxy.AspectJPrecedenceComparator.compare(AspectJPrecedenceComparator.java:51) ~[spring-aop-6.2.7.jar:6.2.7]
at org.springframework.aop.aspectj.autoproxy.AspectJAwareAdvisorAutoProxyCreator$PartiallyComparableAdvisorHolder.compareTo(AspectJAwareAdvisorAutoProxyCreator.java:143) ~[spring-aop-6.2.7.jar:6.2.7]
at org.aspectj.util.PartialOrder$SortObject.addDirectedLinks(PartialOrder.java:71) ~[aspectjweaver-1.9.24.jar:na]
at org.aspectj.util.PartialOrder.addNewPartialComparable(PartialOrder.java:92) ~[aspectjweaver-1.9.24.jar:na]
at org.aspectj.util.PartialOrder.sort(PartialOrder.java:128) ~[aspectjweaver-1.9.24.jar:na]
at org.springframework.aop.aspectj.autoproxy.AspectJAwareAdvisorAutoProxyCreator.sortAdvisors(AspectJAwareAdvisorAutoProxyCreator.java:79) ~[spring-aop-6.2.7.jar:6.2.7]
at org.springframework.aop.framework.autoproxy.AbstractAdvisorAutoProxyCreator.findEligibleAdvisors(AbstractAdvisorAutoProxyCreator.java:103) ~[spring-aop-6.2.7.jar:6.2.7]
at org.springframework.aop.framework.autoproxy.AbstractAdvisorAutoProxyCreator.getAdvicesAndAdvisorsForBean(AbstractAdvisorAutoProxyCreator.java:80) ~[spring-aop-6.2.7.jar:6.2.7]
at org.springframework.aop.framework.autoproxy.AbstractAutoProxyCreator.wrapIfNecessary(AbstractAutoProxyCreator.java:367) ~[spring-aop-6.2.7.jar:6.2.7]
at org.springframework.aop.framework.autoproxy.AbstractAutoProxyCreator.postProcessAfterInitialization(AbstractAutoProxyCreator.java:319) ~[spring-aop-6.2.7.jar:6.2.7]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.applyBeanPostProcessorsAfterInitialization(AbstractAutowireCapableBeanFactory.java:445) ~[spring-beans-6.2.7.jar:6.2.7]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1829) ~[spring-beans-6.2.7.jar:6.2.7]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:607) ~[spring-beans-6.2.7.jar:6.2.7]
... 17 common frames omitted