SpringAOP(三)

简介: SpringAOP(三)

二、AOP案例


1. 案例-测量业务层接口万次执行效率


问题导入


能不能描述一下环绕通知里面的实现步骤?


1.1 需求和分析


需求:任意业务层接口执行均可显示其执行效率(执行时长)


分析:


①:业务功能:业务层接口执行前后分别记录时间,求差值得到执行效率

②:通知类型选择前后均可以增强的类型——环绕通知


1.2 代码实现


【前置工作】环境准备

Spring整合mybatis对spring_db数据库中的Account进行CRUD操作


Spring整合Junit测试CRUD是否OK。


在pom.xml中添加aspectjweaver切入点表达式依赖


… …


【第一步】编写通知类


@Component
@Aspect
public class ProjectAdvice {
    //匹配业务层的所有方法
    @Pointcut("execution(* com.itheima.service.*Service.*(..))")
    private void servicePt(){}
    //设置环绕通知,在原始操作的运行前后记录执行时间
    @Around("ProjectAdvice.servicePt()") //本类类名可以省略不写
    public void runSpeed(ProceedingJoinPoint pjp) throws Throwable {
        //获取执行的签名对象
        Signature signature = pjp.getSignature();
        //获取接口/类全限定名
        String className = signature.getDeclaringTypeName();
        //获取方法名
        String methodName = signature.getName();
        //记录开始时间
        long start = System.currentTimeMillis();
        //执行万次操作
        for (int i = 0; i < 10000; i++) {
           pjp.proceed();
        }
        //记录结束时间
        long end = System.currentTimeMillis();
        //打印执行结果
        System.out.println("万次执行:"+ className+"."+methodName+"---->" +(end-start) + "ms");
    }
}



【第二步】在SpringConfig配置类上开启AOP注解功能


@Configuration
@ComponentScan("com.itheima")
@PropertySource("classpath:jdbc.properties")
@Import({JdbcConfig.class,MybatisConfig.class})
@EnableAspectJAutoProxy //开启AOP注解功能
public class SpringConfig {
}


【第三步】运行测试类,查看结果


@RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(classes = SpringConfig.class)
public class AccountServiceTestCase {
    @Autowired
    private AccountService accountService;
    @Test
    public void testFindById(){
        Account account = accountService.findById(2);
    }
    @Test
    public void testFindAll(){
        List<Account> list = accountService.findAll();
    }
}


2e99b1521bb67c24b990a3e16af453a8_d30d97977e72dc4a1954b7cea53beac4.png


2. AOP切入点数据获取


问题导入


在环绕通知中可以获取到哪些数据?


2.1 获取参数


说明:在前置通知和环绕通知中都可以获取到连接点方法的参数们


JoinPoint对象描述了连接点方法的运行状态,可以获取到原始方法的调用参数
@Before("pt()")
public void before(JoinPoint jp) {
    Object[] args = jp.getArgs(); //获取连接点方法的参数们
    System.out.println(Arrays.toString(args));
}


ProccedJointPoint是JoinPoint的子类
@Around("pt()")
public Object around(ProceedingJoinPoint pjp) throws Throwable {
    Object[] args = pjp.getArgs(); //获取连接点方法的参数们
    System.out.println(Arrays.toString(args));
    Object ret = pjp.proceed();
    return ret;
}


2.2 获取返回值


说明:在返回后通知和环绕通知中都可以获取到连接点方法的返回值


抛出异常后通知可以获取切入点方法中出现的异常信息,使用形参可以接收对应的异常对象


@AfterReturning(value = "pt()",returning = "ret")
public void afterReturning(String ret) { //变量名要和returning="ret"的属性值一致
    System.out.println("afterReturning advice ..."+ret);
}


环绕通知中可以手工书写对原始方法的调用,得到的结果即为原始方法的返回值



         


2.3 获取异常


说明:在抛出异常后通知和环绕通知中都可以获取到连接点方法中出现的异常


抛出异常后通知可以获取切入点方法中出现的异常信息,使用形参可以接收对应的异常对象


@AfterThrowing(value = "pt()",throwing = "t")
public void afterThrowing(Throwable t) {//变量名要和throwing = "t"的属性值一致
    System.out.println("afterThrowing advice ..."+ t);
}


抛出异常后通知可以获取切入点方法运行的异常信息,使用形参可以接收运行时抛出的异常对象


@Around("pt()")
public Object around(ProceedingJoinPoint pjp)  {
    Object ret = null;
    //此处需要try...catch处理,catch中捕获到的异常就是连接点方法中抛出的异常
    try {
        ret = pjp.proceed();
    } catch (Throwable t) {
        t.printStackTrace();
    }
    return ret;
}


相关文章
|
8月前
|
存储 关系型数据库 MySQL
Openldap集成Kerberos
Openldap集成Kerberos
137 21
|
10月前
|
算法 定位技术 Python
震惊!Python 图结构竟然可以这样玩?DFS&BFS 遍历技巧大公开
在 Python 编程中,图是一种重要的数据结构,而深度优先搜索(DFS)和广度优先搜索(BFS)是遍历图的两种关键算法。本文将通过定义图的数据结构、实现 DFS 和 BFS 算法,并通过具体示例展示其应用,帮助读者深入理解这两种算法。DFS 适用于寻找路径和检查图连通性,而 BFS 适用于寻找最短路径。掌握这些技巧,可以更高效地解决与图相关的复杂问题。
142 2
|
8月前
|
机器学习/深度学习 人工智能 算法
具身智能与大模型融合创新技术实训研讨会成功举办
2025年1月16日-19日武汉,TsingtaoAI联合北京博创鑫鑫教育科技,举行“具身智能与大模型融合创新技术”实训研讨会,本次会议面向高校AI教师和企业AI工程师群体,通过3天的技术研修和实操教学,通过将 AI 大模型与具备3D视觉的机器人相结合,为学员实践演示,带领学员深入理解通用具身智能的原理和应用。
292 53
|
8月前
|
数据挖掘 数据库
服务器数据恢复—Zfs文件系统下误删除数据的恢复案例
服务器数据恢复环境&故障: 一台zfs文件系统的服务器,管理员误操作删除了服务器上的数据。
|
机器学习/深度学习 数据采集 人工智能
探索AI在软件测试中的应用和优势
【2月更文挑战第22天】 随着科技的不断发展,人工智能(AI)在各个领域的应用越来越广泛。本文主要探讨了AI在软件测试领域的应用及其带来的优势。文章首先介绍了AI技术的基本概念,然后详细分析了AI在软件测试中的具体应用,包括自动化测试、智能缺陷检测和预测等方面。最后,文章总结了AI在软件测试领域的优势,如提高测试效率、降低人力成本、提高测试质量等,并展望了AI在软件测试领域的未来发展趋势。
|
Java Spring
Spring的@Retryable实现方法重试
`@Retryable`注解用于配置异常重试,参数包括:指定异常类型`value`,额外包含异常`include`,排除异常`exclude`,最大尝试次数`maxAttempts`和回退策略`backoff`。可选地,可以用`retryExceptions`列表替换`value`。当重试失败,可使用`@Recover`注解定义恢复逻辑。
234 1
|
开发者
【Qt 学习笔记】Qt系统相关 | Qt事件 | 事件的介绍及基本概念
【Qt 学习笔记】Qt系统相关 | Qt事件 | 事件的介绍及基本概念
505 4
|
开发框架 并行计算 算法
揭秘Python并发神器:IO密集型与CPU密集型任务的异步革命,你竟还傻傻分不清?
【7月更文挑战第18天】Python并发编程中,异步IO适合IO密集型任务,如异步HTTP请求,利用`asyncio`和`aiohttp`实现并发抓取,避免等待延迟。而对于CPU密集型任务,如并行计算斐波那契数列,多进程通过`multiprocessing`库能绕过GIL限制实现并行计算。选择正确的并发模型能显著提升性能。
217 2
|
敏捷开发 测试技术 API
阿里云云效产品使用合集之调用API次数过多导致限流,该怎么办
云效作为一款全面覆盖研发全生命周期管理的云端效能平台,致力于帮助企业实现高效协同、敏捷研发和持续交付。本合集收集整理了用户在使用云效过程中遇到的常见问题,问题涉及项目创建与管理、需求规划与迭代、代码托管与版本控制、自动化测试、持续集成与发布等方面。
|
监控 API 计算机视觉
OpenCV这么简单为啥不学——1.5、解决putText中文乱码问题
OpenCV这么简单为啥不学——1.5、解决putText中文乱码问题
592 0
OpenCV这么简单为啥不学——1.5、解决putText中文乱码问题