基于注解的AOP实现

xiaoxiao2021-02-28  138

  在web项目中有很多的AOP是基于路径来拦截的,但是有些情况下项目的API路径是多种多样的,而且需要被拦截做AOP的API也是杂七乱八的,那这种情况下,我们基于包路径的AOP的能力就会觉着很无力。曾经我使用的是黑白名单的功能支持。但是后来发现这种方案代价也挺高的。下面我简单介绍下基于配置注解的AOP拦截,这中实现方案,对我上文讲述的问题的支持能力个人感觉真是太好了。 首先创建一个注解

package org.demo.annotations; 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 DemoPermission { String[] demo() default {}; }

基于当前注解实现AOP

package org.demo; import java.lang.annotation.Annotation; import java.util.HashMap; import java.util.Map; import org.aspectj.lang.JoinPoint; import org.aspectj.lang.ProceedingJoinPoint; import org.aspectj.lang.annotation.After; import org.aspectj.lang.annotation.Around; import org.aspectj.lang.annotation.Aspect; import org.aspectj.lang.annotation.Before; import org.aspectj.lang.reflect.MethodSignature; import org.demo.annotations.DemoPermission; import org.demo.controller.DemoFactory; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; @Aspect @Component public class CopyOfPermissionAspect { @Autowired(required = false) DemoFactory demoFactory; @Before("@annotation(org.demo.annotations.DemoPermission)") public void before(JoinPoint caller) { Map<String, Object> functionParamValueMap = getFunctionParamValueMap(caller); DemoPermission annotation = getAnnotation(caller, DemoPermission.class); System.out.println("before-->" + annotation); } @After("@annotation(org.demo.annotations.DemoPermission)") public void after(JoinPoint caller) { DemoPermission annotation = getAnnotation(caller, DemoPermission.class); System.out.println("after-->" + annotation); } @Around("@annotation(org.demo.annotations.DemoPermission)") public Object around(ProceedingJoinPoint pjp) { DemoPermission annotation = getAnnotation(pjp, DemoPermission.class); System.out.println("around-->" + annotation); Object proceed = null; try { proceed = pjp.proceed(); } catch (Throwable e) { } return proceed; } private <T extends Annotation> T getAnnotation(JoinPoint caller, Class<T> annotationClass) { if (caller.getSignature() instanceof MethodSignature) { MethodSignature methodSignature = (MethodSignature) caller .getSignature(); return methodSignature.getMethod().getAnnotation(annotationClass); } return null; } private Map<String, Object> getFunctionParamValueMap(JoinPoint caller) { Map<String, Object> result = new HashMap<>(); if (caller.getSignature() instanceof MethodSignature) { Object[] paramsValues = caller.getArgs(); MethodSignature methodSignature = (MethodSignature) caller .getSignature(); String[] paramNames = methodSignature.getParameterNames(); for (int i = 0, len = paramNames.length; i < len; i++) { String paramName = paramNames[i]; Object paramValue = paramsValues[i]; result.put(paramName, paramValue); } } return result; } }

然后使用注解测试下功能

package org.demo.controller; import org.demo.annotations.DemoAspect; import org.demo.annotations.DemoPermission; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; @RestController public class DemoController { @DemoPermission @RequestMapping("/demo") public String demo(String name) { System.out.println("demo--->" + name); return "demo"; } }

  这个是一个最简单是实现demo,在此基础上我们可以做更多的扩展和支持。详细的扩展代码就不在此一一列出了。   更多代码请访问GitHub

转载请注明原文地址: https://www.6miu.com/read-33397.html

最新回复(0)