0

I'm trying to intercept a method test() using annotation @Myfinder and return value Result.

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface Myfinder {}

@Aspect
@Component
public class MyAspect {

    @AfterReturning(value="@annotation(com.<MypackageHide>.MyFinder)",returning="result")
    public void after(JoinPoint joinPoint, Result result) {
        //something
    }

But it is intercepted only if I call it through rest api /test. I want to intercept even if this method is called from repair() method.

@RequestMapping(path = "/repair")
@RestController
@Configurable
public class MyController {

    @PostMapping("")
    public ResponseEntity<String> repair() {

        //some code
        test(); // <=============== not intercepted if i call /repair
        return ResponseEntity.ok("dummy");
    }

@MyFinder
    @PostMapping("/test") // <===== intercepted if i call this independently
    public Result test() {
        System.out.println("^^^^^^^");
        return (Result) null;
    }
    }

I want this to be called even if I call /repair

I'm fairly new to AOP

Ajeetkumar
  • 1,271
  • 7
  • 16
  • 34
  • Spring AOP cannot advise self-invocation (internal method calls) .To understand this concept in detail , do refer the official spring reference documentation : [Understanding AOP Proxies](https://docs.spring.io/spring-framework/docs/current/reference/html/core.html#aop-understanding-aop-proxies) . Read through the section starting with - The key thing to understand here is that the client code inside the main(..) – R.G Jun 30 '21 at 11:42
  • You can achieve your requirement by autowiring a self reference to `MyController` and calling `self.test()` so that the call goes through proxy and gets intercepted – R.G Jun 30 '21 at 11:44
  • Can you put bit of sample code :( – Ajeetkumar Jun 30 '21 at 11:58
  • `@Autowired MyController self` within class `MyController` . Now within `repair()` method , call `self.test()`. – R.G Jun 30 '21 at 12:00

1 Answers1

1

Spring AOP works on proxies. Calling test() from repair() is called a self-invocation. Spring AOP will not be able to advice the method call to test() from repair() , as it will not go through the proxy.

Spring reference documentation : Understanding AOP Proxies . Read through the section starting with The key thing to understand here is that the client code inside the main(..)

If you still wants to intercept and advice such a method call , you can autowire the controller instance to the same class as follows. I would recommended you to refactor the code , but to demonstrate the possibility , following code would work.

@RequestMapping(path = "/repair")
@RestController
@Configurable
public class MyController {
    @Autowired
    MyController self;

    @PostMapping("")
    public ResponseEntity<String> repair() {

        //some code
        self.test(); // <=============== self reference
        return ResponseEntity.ok("dummy");
    }

@MyFinder
    @PostMapping("/test") // <===== intercepted if i call this independently
    public Result test() {
        System.out.println("^^^^^^^");
        return (Result) null;
    }
    }
dreamcrash
  • 47,137
  • 25
  • 94
  • 117
R.G
  • 6,436
  • 3
  • 19
  • 28
  • One small question, if it is reference to self, why this.test() isn;t working – Ajeetkumar Jun 30 '21 at 15:42
  • Apparently you didn’t go through the reference documentation. Once the call reaches the target object any call to another method in the same class will not go through the proxy . ‘this’ is the target object and not the proxy – R.G Jun 30 '21 at 17:54
  • I waited for your good answer to be accepted before I closed the question as a duplicate,because you do deserve the recognition and reputation. – kriegaex Jul 01 '21 at 04:10