Reputation: 4504
I have some troubles with aspectj and its syntax. I have something written on a java file and I want to translate it to an .aj file because I think that is easier, but I can't find a tutorial to follow.
This is my code:
@Aspect
public class Aspect{
@Pointcut("@annotation(annotationVariableName)")
public void annotationPointCutDefinition(Annotation annotationVariableName){
}
@Pointcut("execution(* *(..))")
public void atExecution(){}
@Around("annotationPointCutDefinition(withTransactionVariableName) && atExecution()")
public Object aroundAdvice(ProceedingJoinPoint joinPoint, Annotation annotationVariableName) throws Throwable {
boolean parameter= annotationVariableName.parameter();
Object returnObject = null;
try {
returnObject = joinPoint.proceed();
} catch (Throwable throwable) {
throw throwable;
}
return returnObject;
}
}
Can anyone help me with this? Thank you!
Upvotes: 0
Views: 693
Reputation: 67297
I have made up a little example MCVE relating to your comment about transaction management, so as to make the code and its log output a little clearer:
Annotation:
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 Transaction {
boolean myFlag();
}
Driver application:
Please note that two methods bear the annotation, one does not.
package de.scrum_master.app;
public class Application {
public static void main(String[] args) {
Application application = new Application();
application.doSomething();
application.doSomethingElse();
application.doSomethingWeird();
}
@Transaction(myFlag = true)
public void doSomething() {
System.out.println("Doing something");
}
public void doSomethingElse() {
System.out.println("Doing something else\n");
}
@Transaction(myFlag = false)
public void doSomethingWeird() {
System.out.println("Doing something weird");
throw new RuntimeException("oops");
}
}
Aspect:
package de.scrum_master.aspect;
import org.aspectj.lang.SoftException;
import de.scrum_master.app.Transaction;
public aspect TransactionAspect {
pointcut hasAnnotation(Transaction myAnnotation) : @annotation(myAnnotation);
pointcut methodExecution() : execution(* *(..));
Object around(Transaction myAnnotation) : methodExecution() && hasAnnotation(myAnnotation) {
System.out.println(thisJoinPoint + " -> " + myAnnotation);
boolean parameter = myAnnotation.myFlag();
System.out.println("Transaction start");
try {
Object result = proceed(myAnnotation);
System.out.println("Transaction commit\n");
return result;
} catch (Exception e) {
System.out.println("Transaction roll-back\n");
// Native AspectJ advices must not return checked exceptions, only runtime exceptions.
// So we soften the caught exception, just in case.
throw new SoftException(e);
}
}
}
Console log:
execution(void de.scrum_master.app.Application.doSomething()) -> @de.scrum_master.app.Transaction(myFlag=true)
Transaction start
Doing something
Transaction commit
Doing something else
execution(void de.scrum_master.app.Application.doSomethingWeird()) -> @de.scrum_master.app.Transaction(myFlag=false)
Transaction start
Doing something weird
Transaction roll-back
Exception in thread "main" org.aspectj.lang.SoftException
at de.scrum_master.app.Application.doSomethingWeird_aroundBody3$advice(Application.java:22)
at de.scrum_master.app.Application.doSomethingWeird(Application.java:1)
at de.scrum_master.app.Application.main(Application.java:8)
Caused by: java.lang.RuntimeException: oops
at de.scrum_master.app.Application.doSomethingWeird_aroundBody2(Application.java:23)
at de.scrum_master.app.Application.doSomethingWeird_aroundBody3$advice(Application.java:17)
... 2 more
By the way, if you are fine with anonymous pointcuts, there is no need to declare them separately. You can just do it this way:
Aspect variant with anonymous pointcut:
package de.scrum_master.aspect;
import org.aspectj.lang.SoftException;
import de.scrum_master.app.Transaction;
public aspect TransactionAspect {
Object around(Transaction myAnnotation) : execution(* *(..)) && @annotation(myAnnotation) {
System.out.println(thisJoinPoint + " -> " + myAnnotation);
boolean parameter = myAnnotation.myFlag();
System.out.println("Transaction start");
try {
Object result = proceed(myAnnotation);
System.out.println("Transaction commit\n");
return result;
} catch (Exception e) {
System.out.println("Transaction roll-back\n");
// Native AspectJ advices must not return checked exceptions, only runtime exceptions.
// So we soften the caught exception, just in case.
throw new SoftException(e);
}
}
}
Upvotes: 1
Reputation: 131
Personally I found the following programmer guide useful myself although it's not really a tutorial : https://eclipse.org/aspectj/doc/next/progguide/index.html. Click on Pointcuts to get the basics of converting your pointcuts, advice is also covered on that page although it doesn't detail "around" advice but there is an example of that under production aspects
A quick search for a tutorial throws up the following (I haven't used this) : http://o7planning.org/en/10257/java-aspect-oriented-programming-tutorial-with-aspectj
Upvotes: 0