Logging and Security are the common examples for cross cutting concerns. For example in authorisation we need to check permission for the user when the user try to execute some method that need to be secured. If there are many this type of method that checks security, it will be duplicated every where and code will be tangle and scattered. In AOP it has their own terminology which explain those points.
1. Join Point
A join point is a execution point that has cross cutting concern. This might be a method or some exceptional case.
2.Point Cut
Point cut is the expression that explain about Joint points. So one point cut may represent many join points. For example below point cut represent all methods in com.xyz.service or sub package.
@Pointcut(value = "execution(* com.xyz.service.*.*(..))")
private void anyMethod() {
}
3.Advice
Advice is a code fragment that need to be implemented at defined point cut. For example think we need to have a log every time before executing above mentioned point cut. That means before calling any method in com.xyz.service or sub package we need to have a log message. we can define that advice below.
@Before("anyMethod()")
public void logMessage() throws Throwable {
logger.debug("Going to execute com.xyz.service method");
}
We can see different type of advice as below.
* Before advice
* After returning advice
* After throwing advice
* After (finally) advice
* Around advice
4. Aspect
Aspect modularise similar concerns spread every where into one place. In spring Aspect is a class which has @Aspect annotation.
Let's try to implement this using AOP.
public class MyService implements IMyService{
private static final Logger logger = LoggerFactory.getLogger(MyService.class);
public void someSecuredMethod(String userName) {
logger.debug("Hi " + userName + ". I have a secret to tell you");
}
}
@Aspect
public class MyAopAspect {
private static Logger logger = LoggerFactory.getLogger(MyAopAspect.class);
@Pointcut(value = "execution(public * someSecuredMethod(..))")
private void anyPublicOperation() {
}
@Around("anyPublicOperation() && args(userName)")
public void checkPermission(ProceedingJoinPoint pj, String userName) throws Throwable {
if (userName.equals("che guevara")) {
pj.proceed();
} else {
logger.error("User {} doesn't have permission", userName);
}
}
}
In above example I have used around advice. With around advice aspect can decide whether it need to execute doSomething() method or not. If you don't call ProceedingJoinPoint.proced(), doSomeThing() will never be invoked.
get working example with test cases here.

No comments:
Post a Comment