Spring AOP: @AfterThrowing execution pointcut never matches

I'm completely new to AOP. I need advice to write the correct pointcut. I have a service package that contains all service classes. All the classes implement the Service interface. This interface has a method save(entity) . My advice should be executed every time the service.save(entity) method throws a DataIntegrityViolationException .

Here the aspect:

@Component
@Aspect
public class DIVExceptionHandler {
    @AfterThrowing(pointcut = "execution(* myPackage.service.Service.save(*))", throwing = "ex")
        public void handleException(JoinPoint joinPoint, DataIntegrityViolationException ex) {
        //snipped
    }
}

I have both aspectj jars in the CP as explained in Spring AOP documentation and I have added <aop:aspectj-autoproxy/> to Spring configuration and I'm using component scanning. In the log of the test I can see that the aspect is detected as aspetcj aspect:

DEBUG o.s.a.a.a.ReflectiveAspectJAdvisorFactory - Found AspectJ method...

So I believe this is not a configuartion issue and my pointcut expression is wrong. I also tried

@AfterThrowing(pointcut = "execution(* myPackage.service.*.save(*))", throwing = "ex")

But that did also not work.

So what is the correct pointcut expression?


it in fact was a configuration issue.

@AfterThrowing(pointcut = "execution(* myPackage.service.Service.save(*))", throwing = "ex")

Works fine.

The actual problem was that DataIntegrityViolationException is only thrown after the proxy for @Transactional completes the transaction. In my case this happened after my advice can be called.

The solution is to add an order attribute to transaction configuration:

<tx:annotation-driven transaction-manager="transactionManager" order="2000"/>

And then add an @Order annotation to your aspect that is smaller than the one for the transaction:

@Component
@Order(1500) // must be less than order of <tx:annotation-driven />
@Aspect
public class DIVExceptionHandler {
    @AfterThrowing(pointcut = "execution(* myPackage.service.Service.save(*))", throwing = "ex")
        public void handleException(JoinPoint joinPoint, DataIntegrityViolationException ex) {
        //snipped
    }
}

See:

Spring AOP ordering - Transactions before Advise

链接地址: http://www.djcxy.com/p/77252.html

上一篇: AspectJ方面不使用@RequestMapping注释编织Spring MVC方法

下一篇: Spring AOP:@AfterThrowing执行切入点永远不会匹配