How to get the pointcut details in the aspect constructor

295 views Asked by At

I have a an annotation style aspect which is something like that:

//....
//somewhere in another class
//
@MyAnnotation 
public void foo(){ \* does stuff *\}
/////////////////////

// in the aspect file
@Aspect("percflow(execution(@com.bla.MyAnnotation * *(..)))")
public class MyAspect {
    public MyAspect(){
         /* Here I'd like to access the name of the annotated function e.g: foo*/ 
    }
    /* more pointcuts and advice*/
}

I've tried capturing the object with this(Object) but this didn't do any good. I've also tried introducing a parameter to the constructor but that just caused an error.

1

There are 1 answers

0
kriegaex On

Well, it is actually not necessary to do anything in the constructor. You can just declare the pointcut within percflow() as a stand-alone object and use it within percflow() as well as in a @Before advice which, as the instantiation model implies, will only be executed once and gives you all necessary information via the corresponding JoinPoint object. You can now log or store the information as you fancy.

BTW, idea of using a constructor is not so nice because within the constructor the aspect instance is not initialised yet (hen vs. egg problem) and will cause exceptions when trying to access it.

package de.scrum_master.app;

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface MyAnnotation {}
package de.scrum_master.app;

public class Application {
    public void doSomething() {}

    @MyAnnotation
    public String repeatText(int times, String text) {
        String result = "";
        for (int i = 0; i < times; i++)
            result += text;
        return result;
    }

    public static void main(String[] args) {
        Application application = new Application();
        application.doSomething();
        application.repeatText(3, "andale ");
    }
}
package de.scrum_master.aspect;

import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;

@Aspect("percflow(myPointcut())")
public class MyAspect {
    @Pointcut("execution(@de.scrum_master.app.MyAnnotation * *(..))")
    private static void myPointcut() {}

    @Before("myPointcut()")
    public void myAdvice(JoinPoint thisJoinPoint) {
        System.out.println(thisJoinPoint);
        System.out.println("  " + thisJoinPoint.getSignature().getName());
        for (Object arg : thisJoinPoint.getArgs())
            System.out.println("    " + arg);
    }
}

Console output:

execution(String de.scrum_master.app.Application.repeatText(int, String))
  repeatText
    3
    andale