我正在创建用于记录目的的Java库,因此,如果任何应用程序都使用我的库,那么spring AOP的建议将应用于该应用程序的每种方法。但是在我的库中,我不知道将要使用它的应用程序的基本软件包。因此,应用程序应该在application.properties文件中指定其基本包,我的库将使用它并将其作为变量放入我的切入点中。但是似乎切入点表达式仅在其中接受常量。
我不想采用基于注释的方法。
@Component
@Aspect
@Slf4j
public class LoggingAop {
@Value("${base.package}")
String basePackage;
@Pointcut("within("+basePackage+"..*)") //error
public void logAllMethods()
{
}
}
以下问题的答案说明了为什么基于注释的Spring AOP配置无法做到这一点
Spring boot支持基于xml的配置,并且可以通过以下方式实现要求。
假设我们必须拦截基本包com.app.service
中的所有方法调用,>
在resources / application.properties中有一个条目。
base.package=com.app.service
基本程序包中记录方法调用的方面如下
package com.app.aspect; import org.aspectj.lang.ProceedingJoinPoint; import org.slf4j.Logger; import org.slf4j.LoggerFactory; public class LogAspect { Logger log = LoggerFactory.getLogger(LogAspect.class); public Object logAllMethods(ProceedingJoinPoint pjp) throws Throwable { log.info("Log before method call"); try { return pjp.proceed(); }finally { log.info("Log after method call"); } } }
aop配置可以定义如下。
文件:resources / aop-application-context.xml
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:aop="http://www.springframework.org/schema/aop" xsi:schemaLocation="http://www.springframework.org/schema/beans https://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/aop https://www.springframework.org/schema/aop/spring-aop.xsd"> <bean id="logAspect" class="com.app.aspect.LogAspect"></bean> <aop:config> <aop:aspect id="logallaspect" ref="logAspect" > <!-- @Around --> <aop:pointcut id="logAllMethodsAround" expression="within(${base.package}..*)" /> <aop:around method="logAllMethods" pointcut-ref="logAllMethodsAround" /> </aop:aspect> </aop:config> </beans>
请注意,切入点表达式是使用application.properties条目构造的。
请记住按如下方式加载aop-application-context.xml
@SpringBootApplication @ImportResource("classpath:aop-application-context.xml") public class Application { public static void main(String[] args) { SpringApplication.run(Application.class, args); } }
以上代码将建议已定义的基本包中的所有可拦截Spring bean方法调用并记录它们。
希望这会有所帮助。