4.Spring AOP理解

男娘i 2022-03-22 10:20 328阅读 0赞
  1. AOP原理
    AOP将应用系统分为两部分,核心业务逻辑(Core business concerns)及横向的通用逻辑,也就是所谓的方面Crosscutting enterprise concerns,例如,所有大中型应用都要涉及到的持久化管理(Persistent)、事务管理(Transaction Management)、安全管理(Security)、日志管理(Logging)、Authentication (权限)、Caching(缓存)和调试管理(Debugging)等。

从Spring的角度看,AOP最大的用途就在于提供了事务管理的能力。事务管理就是一个关注点,你的正事就是去访问数据库,而你不想管事务(太烦),所以,Spring在你访问数据库之前,自动帮你开启事务,当你访问数据库结束之后,自动帮你提交/回滚事务!

  1. AOP概念术语

    • 切面(aspect):用来切插业务方法的类。
    • 连接点(joinpoint):是切面类和业务类的连接点,其实就是封装了业务方法的一些基本属性,作为通知的参数来解析,如方法的调用或特定的异常被抛出。
    • 通知(Advice):在特定的连接点,AOP框架执行的动作。各种类型的通知包括“around”、“before”和“throws”通知。通知类型将在下面讨论。许多AOP框架包括Spring都是以拦截器做通知模型,维护一个“围绕”连接点的拦截器链。
    • 切入点(Pointcut):指定一个通知将被引发的一系列连接点的集合。AOP框架必须允许开发者指定切入点,例如,使用正则表达式。
    • 引入(Introduction):添加方法或字段到被通知的类。Spring允许引入新的接口到任何被通知的对象。例如,你可以使用一个引入使任何对象实现IsModified接口,来简化缓存。
    • 目标对象(Target Object):包含连接点的对象,也被称作被通知或被代理对象。
    • AOP代理(AOP Proxy):AOP框架创建的对象,包含通知。在Spring中,AOP代理可以是JDK动态代理或CGLIB代理。
  2. AOP通知类型

    • 前置通知(before advice):在切入点之前执行。
    • 后置通知(after returning advice):在切入点执行完成后,执行通知。
    • 环绕通知(around advice):包围切入点,调用方法前后完成自定义行为。
    • 异常通知(after throwing advice):在切入点抛出异常后,执行通知。
  3. AspectJ相关Jar包

aspectjrt.jar:主要是提供运行时的一些注解,静态方法等等东西,通常我们要使用aspectJ的时候都要使用这个包。
aspectjtools.jar:主要是提供赫赫有名的ajc编译器,可以在编译期将将java文件或者class文件或者aspect文件定义的切面织入到业务代码中。通常这个东西会被封装进各种IDE插件或者自动化插件中。
aspectjweaverjar:主要是提供了一个java agent用于在类加载期间织入切面(Load time weaving)。并且提供了对切面语法的相关处理等基础方法,供ajc使用或者供第三方开发使用。这个包一般我们不需要显式引用,除非需要使用LTW。

5.切面示例

  1. @Aspect
  2. @Component
  3. public class ServiceLogAspect {
  4. // 设置 Service层切点
  5. @Pointcut("execution(* com.uaf.nlp.*.service.*.*.*(..))")
  6. public void serviceAspect() {
  7. }
  8. /** * 异常通知 用于拦截service层记录异常日志 * @param joinPoint * @param e * 作者:will * 日期:2016年8月11日下午3:44:45 */
  9. @AfterThrowing(pointcut = "serviceAspect()", throwing = "e")
  10. public void doAfterThrowing(JoinPoint joinPoint, Throwable e) {
  11. try {
  12. String packageName = joinPoint.getTarget().getClass().getPackage().getName();
  13. String className = joinPoint.getTarget().getClass().getName().substring(packageName.length() + 1) + ".java";
  14. String methodName = joinPoint.getSignature().getName();
  15. StringWriter sw = new StringWriter();
  16. PrintWriter pw = new PrintWriter(sw);
  17. e.printStackTrace(pw);
  18. Map<String, Object> map = new HashMap<String, Object>();
  19. map.put("包名", packageName);
  20. map.put("类名", className);
  21. map.put("方法", methodName);
  22. map.put("参数", joinPoint.getArgs());
  23. map.put("异常信息", sw.toString());
  24. MyLog4j.textError("[ASPECT]评分模型切面异常日志:{0}", JsonUtil.toJson(map));
  25. } catch (Exception ex) {
  26. // 记录本地异常日志
  27. MyLog4j.textError("切面日志处理异常{0}", LogUtil.ExceptionToString(ex));
  28. }
  29. }
  30. /** * 记录Service层请求参数及返回值 * @param joinPoint * @param result * 作者:will * 日期:2016年8月11日下午3:44:53 */
  31. @AfterReturning(pointcut = "serviceAspect()", returning = "result")
  32. public void afterReturning(JoinPoint joinPoint, Object result) {
  33. try {
  34. String packageName = joinPoint.getTarget().getClass().getPackage().getName();
  35. String className = joinPoint.getTarget().getClass().getName().substring(packageName.length() + 1) + ".java";
  36. String methodName = joinPoint.getSignature().getName();
  37. Map<String, Object> map = new HashMap<String, Object>();
  38. map.put("包名", packageName);
  39. map.put("类名", className);
  40. map.put("方法", methodName);
  41. map.put("参数", joinPoint.getArgs());
  42. map.put("返回值", result);
  43. MyLog4j.textInfo("[ASPECT]评分模型切面请求及返回参数日志:{0}", JsonUtil.toJson(map));
  44. } catch (Exception e) {
  45. // 记录本地异常日志
  46. MyLog4j.textError("切面日志处理异常{0}", LogUtil.ExceptionToString(e));
  47. }
  48. }
  49. }

发表评论

表情:
评论列表 (有 0 条评论,328人围观)

还没有评论,来说两句吧...

相关阅读

    相关 4.Spring AOP理解

    1. AOP原理 AOP将应用系统分为两部分,核心业务逻辑(Core business concerns)及横向的通用逻辑,也就是所谓的方面Crosscuttin

    相关 spring aop 理解

    最近一直在面试,aop这个还是永远的热点,看不了不少大佬的关于aop的文章,感觉还是下面不错 常问的点 :  两种动态代理 区别 , 怎么强制使用CGLIB代理  切点和切面