想要熟悉流程的时候,一定要多多打断点
-
jdkproxy的优点
动态的产生代理对象,只需要一个拦截器就可以了
-
jdkproxy的缺点
如果在invoke方法中做事务的判断, 是很复杂的事情
程序员还需要对invoke方法进行修改,写拦截器
新的事物是对老事物的改进及完善
AOP(针对的是大量的重复性的工作)
AOP的意义
AOP的各个概念
检验切入点表达式配置是否成功,可以查看一下代理对象是否正确
AOP的原理
1 启动spring容器
2 实例化PersonDao和Transaction
3 spring容器解析aop:config配置
当spring容器解析到切入点表达式的时候,将切入点表达式中的解析出来
-
将切入点表达式的类与spring容器中的类进行匹配
成功,为该对象创建代理对象
失败, 则报错
代理对象方法的形成 = 通知 + 目标方法
4 在客户端context.getbean()中, 有代理对象则返回代理对象。没有则返回原对象
5 在spring内部,需要判断目标类是否实现了接口
如果实现了, 有jdkproxy来产生代理对象
如果没有实现, 由cglibproxy来产生代理对象
aop xml文件
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-2.5.xsd">
<!--
导入目标类
导入切面
进行aop的配置
-->
<bean id="personDao" class="com.itheima11.spring.aop.xml.transaction.PersonDaoImpl"></bean>
<bean id="transaction" class="com.itheima11.spring.aop.xml.transaction.Transaction"></bean>
<aop:config>
<!--
pointcut切入点表达式
符合切入点表达式的类要产生代理对象
expression就是切入点表达式
id 标示符
-->
<aop:pointcut
expression="execution(* com.itheima11.spring.aop.xml.transaction.PersonDaoImpl.*(..))"
id="perform"/>
<!--
ref属性指向切面
-->
<aop:aspect ref="transaction">
<!--
前置通知
在目标方法执行之前
-->
<aop:before method="beginTransaction" pointcut-ref="perform"/>
<!--
后置通知
-->
<aop:after-returning method="commit" pointcut-ref="perform"/>
</aop:aspect>
</aop:config>
</beans>
AOP各种通知
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:aop="http://www.springframework.org/schema/aop"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-2.5.xsd
http://www.springframework.org/schema/aop
http://www.springframework.org/schema/aop/spring-aop-2.5.xsd">
<bean id="personDao" class="aop.xml.transaction.PersonDaoImpl"></bean>
<bean id="transaction" class="aop.xml.transaction.Transaction"></bean>
<aop:config>
<aop:pointcut
expression="execution(* aop.xml.transaction.PersonDaoImpl.*(..))"
id="perform"/>
<aop:aspect ref="transaction">
<!--
前置通知
1、在目标方法执行之前
2、前置通知中,方法有一个参数JoinPoint
-->
<!--
<aop:before method="beginTransaction" pointcut-ref="perform"/>
-->
<!--
后置通知
1、在目标方法执行之后
2、能够获取目标方法的返回值
returning="val"
3、如果目标方法产生异常,则后置通知不再执行
-->
<!--
<aop:after-returning method="commit" pointcut-ref="perform" returning="val"/>
-->
<!--
异常通知
获取目标方法抛出的异常信息
throwing="ex"
-->
<aop:after-throwing method="throwingMethod" pointcut-ref="perform" throwing="ex"/>
<!--
最终通知
-->
<aop:after method="finallyMethod" pointcut-ref="perform"/>
<!--
环绕通知
能够控制目标方法的执行
环绕通知可以有返回值,这个返回值就是代理对象的方法的返回值
前置通知和后置通知只能在目标方法执行之前和之后加代码,但是不能控制目标方法的执行
-->
<aop:around method="aroundMethod" pointcut-ref="perform"/>
</aop:aspect>
</aop:config>
</beans>
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。