SpringAop中的Advice通知实例

 更新时间:2023年09月25日 11:06:53   作者:至学者  
这篇文章主要介绍了SpringAop中的Advice通知详解,Spring的AOP功能中一个关键概念是通知Advice与切点Pointcut表达式相关联在特定节点织入一些逻辑,Spring提供了五种类型的通知,需要的朋友可以参考下

一 概述

  • @Before:前置通知
  • @After :后置通知,方法执行完之后
  • @AfterReturning:返回通知,完成执行之后
  • @AfterThrowing:异常通知,抛出异常之后
  • @Around:环绕通知

二 Advice应用实例

通过环绕通知获取方法执行时间

@Component
@Aspect
public class RepositoryAspect {
    @Pointcut("execution(* com.repository..*(..))")
    private void crud() {
    }
    //环绕通知
    @Around("crud()")
    public Object logPerformance(ProceedingJoinPoint joinPoint) throws Throwable {
        long startTimes = System.currentTimeMillis();
        Object result = null;
        String name = "-";
        try {
            name = joinPoint.getSignature().toShortString();
            result = joinPoint.proceed();
            return result;
        } catch (Throwable t) {
            throw t;
        } finally {
            long duration = System.currentTimeMillis() - startTimes;
            StringBuilder stringBuilder = new StringBuilder();
            stringBuilder.append(name);
            System.out.println(stringBuilder+"执行时间为"+duration)
        }
    }
}
public class AbstractAspect {
	protected ThreadLocal<Map<String, Object>> threadLocal = new ThreadLocal<>();
	protected ThreadLocal<Map<String, Object>> getThreadLocal(){
		if (threadLocal.get() == null){
			threadLocal.set(new HashMap<>());
		}
		return threadLocal;
	}
}
@Component
@Aspect
public class ControllerAspect extends AbstractAspect {
    //对于controller包下所有类和方法进行获取,除被注解NoHealth标注的类除外。
    @Pointcut("execution(* com.controller..*(..))&&!@annotation(NoHealth)")
    private void controllerPointCut() {
    }
    //在方法执行之前对参数进行处理 
    @Before(value = "controllerPointCut()")
    public void doBefore(JoinPoint joinPoint) {
        try {
            getThreadLocal().get().put(joinPoint.getSignature().toString(), System.currentTimeMillis());
            Object[] args = joinPoint.getArgs();
            MethodSignature methodSignature = (MethodSignature) joinPoint.getSignature();
            String[] parameterNamesArray = methodSignature.getParameterNames();
            int i = 0;
            List<String> argsList = new ArrayList<>();
            if (!ObjectUtils.isEmpty(args)) {
                for (Object object : args) {
                    if (ObjectUtils.isEmpty(object)
                            || (object instanceof BeanPropertyBindingResult)
                            || (object instanceof HttpServletResponse)
                            || (object instanceof Boolean)
                            || (object instanceof String)
                            || (object instanceof Integer)) {
                        if ((object instanceof Boolean) || (object instanceof String) || (object instanceof Integer)) {
                            StringBuilder stringBuilder = new StringBuilder();
                            stringBuilder.append("{\"");
                            stringBuilder.append(parameterNamesArray[i]);
                            stringBuilder.append("\":\"");
                            stringBuilder.append(object);
                            stringBuilder.append("\"}");
                            argsList.add(JSONObject.fromObject(String.valueOf(stringBuilder)).toString());
                        }
                        i++;
                        continue;//跳出当前循环,且不执行此语句后面的语句!
                    }
                    if (!(object instanceof HttpServletRequest)) {
                        argsList.add(JSONObject.fromObject(object).toString());
                    } else {
                        HttpServletRequest request = (HttpServletRequest) object;
                        Enumeration<String> parameterNames = request.getParameterNames();
                        Map<String, String> argsMap = new HashMap<>();
                        while (parameterNames.hasMoreElements()) {
                            String elementName = parameterNames.nextElement();
                            argsMap.put(elementName, request.getAttribute(elementName).toString());
                        }
                        if (!ObjectUtils.isEmpty(argsMap)) {
                            argsList.add(JSONObject.fromObject(argsMap).toString());
                        }
                    }
                    i++;
                }
            }
            StringBuilder stringBuilder = new StringBuilder();
            stringBuilder.append(JSONArray.fromObject(argsList));
        } catch (Exception e) {
        }
    }
    //对方法执行之后的返回值进行某种操作
    @AfterReturning(value = "controllerPointCut()", returning = "response")
    public void responseLog(JoinPoint joinPoint, Object response) {
        try {
            if (response == null) {
                response = new Object();
            }
            long duration = System.currentTimeMillis() - (Long) threadLocal.get().get(joinPoint.getSignature().toString());
            StringBuilder stringB uilder = new StringBuilder();
            stringBuilder.append(JSONObject.fromObject(response));
        } catch (Exception e) {
        }
    }
    //对方法抛出的异常进行操作
    @AfterThrowing(value = "controllerPointCut()", throwing = "e")
    public void exceptionLog(Exception e) {
    }
}

根据这些实例就可以参照写一些简单的SpringAOP实例了!

到此这篇关于SpringAop中的Advice通知详解的文章就介绍到这了,更多相关Advice通知内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • 浅析SpringCloud Alibaba-Nacos 作为注册中心示例代码

    浅析SpringCloud Alibaba-Nacos 作为注册中心示例代码

    这篇文章主要介绍了SpringCloud Alibaba-Nacos 作为注册中心示例代码,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2020-10-10
  • SpringBoot+mybatis+Vue实现前后端分离项目的示例

    SpringBoot+mybatis+Vue实现前后端分离项目的示例

    本文主要介绍了SpringBoot+mybatis+Vue实现前后端分离项目的示例,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2021-12-12
  • Java9版本新特性同一个Jar支持多JDK版本运行

    Java9版本新特性同一个Jar支持多JDK版本运行

    这篇文章主要为大家介绍了Java9新版本的特性之同一个Jar支持多JDK版本运行的示例详解,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步
    2022-03-03
  • Spring boot 处理大文件上传完整代码

    Spring boot 处理大文件上传完整代码

    这篇文章主要介绍了Spring boot 处理大文件上传,本文通过实例代码给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2023-07-07
  • Java实现PDF在线预览功能(四种方式)

    Java实现PDF在线预览功能(四种方式)

    这篇文章主要介绍了Java实现PDF在线预览功能的四种方式,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2021-10-10
  • Java中批处理框架spring batch详细介绍

    Java中批处理框架spring batch详细介绍

    这篇文章主要介绍了Java中批处理框架spring batch详细介绍,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2020-07-07
  • Java环境配置与编译运行详解

    Java环境配置与编译运行详解

    这篇文章主要为大家详细介绍了Java环境配置与编译运行的相关资料,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2017-03-03
  • IDEA调试源码小技巧之辨别抽象类或接口多种实现类的正确路径

    IDEA调试源码小技巧之辨别抽象类或接口多种实现类的正确路径

    这篇文章主要介绍了IDEA调试源码小技巧之辨别抽象类或接口多种实现类的正确路径,本文给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2021-01-01
  • 初步认识JVM的体系结构

    初步认识JVM的体系结构

    大家都知道,Java中JVM的重要性,学习了JVM你对Java的运行机制、编译过程和如何对Java程序进行调优相信都会有一个很好的认知.在面试中JVM也是非常重要的一部分,比如JVM调优,JVM对象分配规则,内存模型、方法区,还有种要GC等,需要的朋友可以参考下
    2021-06-06
  • MyEclipse 2016 CI 4新增BootStrap模板

    MyEclipse 2016 CI 4新增BootStrap模板

    MyEclipse2016是一款全球使用最为广泛的企业级开发环境程序,这篇文章主要介绍了MyEclipse 2016 CI 4新增BootStrap模板的相关资料,非常不错,具有参考借鉴价值,需要的朋友可以参考下
    2016-06-06

最新评论