SpringAOP-动态代理,日志注入
SpringAOP
前言:
1.AOP定义? 用来干啥的? 怎么用?(怎么跑通它的思路)
代理模式
为啥要学代理模式? -- 因为是SpringAop的底层
原有的代码不敢动,一动就是Bug,。所以使用代理可以做很多事,
- 在原有的基础上,进行封装一层,客户使用的就我们这一层封装后的功能
代理模式的分类:
- 静态代理
角色分析:
- 抽象角色:一般用接口或者抽象类来解决,
- 真实角色:被代理的角色
- 代理角色:代理真实角色,代理真实角色后,我们一般做一些附属操作
- 客户:访问代理角色的人
代理模式的好处:1.可以使真实角色的操作更加纯粹!不用去关注一些公共的业务
- 2.公共的业务交给了代理角色--实现了业务的分工
- 3.业务发送扩展的时候,方便集中管理
缺点:
- 一个真实角色就会产生一个代理角色,代码量翻倍---开发效率bian低
操作步骤---1,接口-->真实角色--》代理角色--》客户端访问代理
静态代理这么麻烦,每次重写人家的很多方法???---怎么解决代码多---动态代理
个人理解代理:无非是在原有的基础上,进行一层封装,这样既能使用被代理人的方法,也能实现自我的灵活安排!
动态代理
- 动态代理和静态代理角色一样
- 动态代理类是动态生成的,不是我们直接写好的,,,想想直接将被代理人的很多方法都再次复述
- 动态代理分了两大类---1.基于接口的动态代理---2.基于类的动态代理
- 基于接口---JDK动态代理 --- 注意,,,基于接口的!!!
- 基于类:cglib
- java字节码:javasist
- 需要了解两个类:Proxy,代理--InvocationHandler 调用处理程序 ----使用时:
- Proxy提供了创建动态代理类和实例的静态方法,它也是由这些方法创建的所有动态代理类的超类。
- InvocationHandler接口提供的-newProxyInstance返回指定接口的代理类的实例,该接口将方法调用分派给指定的调用处理程序。
Proxy.newProxyInstance因为与IlegalArgumentException相同的原因而Proxy.getProxyClass.
它两结合返回的proxyInstance---Proxy.newProxyInstance
至于被代理人方法,使用invoke操作
目的:生成一个代理对象,并执行被代理人方法
交互--被代理人方法,以及生成代理对象,提供一个调用代理人对象的方法
1.被代理人的方法的获取,必须要获取到被代理人的对象
2.生成代理对象,必须要依托于代理人的方法(接口)以及它的加载器(要不jvm处理不了)
建立一个动态代理
目的:生成一个代理对象,并执行被代理人方法
交互--被代理人方法,以及生成代理对象,提供一个调用代理人对象的方法
- 1.被代理人的方法的获取,必须要获取到被代理人的对象
- 2.生成代理对象,必须要依托于代理人的方法(接口)以及它的加载器(要不jvm处理不了)
package com.zjz.ProxyMethod; /*
* 目的:生成一个代理对象,并执行被代理人方法
* 交互--被代理人方法,以及生成代理对象,提供一个调用代理人对象的方法
* 1.被代理人的方法的获取,必须要获取到被代理人的对象
* 2.生成代理对象,必须要依托于代理人的方法(接口)以及它的加载器(要不jvm处理不了)
*
* */ import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy; public class ProxyInvocationHandler implements InvocationHandler { private Object target; // 被代理的人-对象 public void setTarget(Object target) {
this.target = target;
} // 调用代理人对象的方法,以及生成代理对象
public Object getProxy(){ Object proxyInstance = Proxy.newProxyInstance(target.getClass().getClassLoader(), target.getClass().getInterfaces(), this);
return proxyInstance;
} // 被代理人方法
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println("执行"+method.getName()+"方法---");
Object result = method.invoke(target, args); // 此时执行被代理人的方法 return result;
}
}
关于代理中为啥自动运行invoke,而且不可缺少
Proxy.newProxyInstance 执行时会生成一个创建出一个类$Proxy0,此类中调用invoke
如果少了还会执行,但是咱们的代理对象没有方法了。。
Object result = method.invoke(被代理对象的接口, args); // 执行 被代理对象的接口方法,,invoke
AOP
每走一步,对照代理模式
介绍
- AOP(Aspect Oriented Programming)意为:面向切面编程,通过预编译方式和运行期动态代理实现
程序功能的统一维护的一种技术。AOP是OOP的延续,是软件开发中的一个热点,也是Spring框架中的
一个重要内容,是函数式编程的一种衍生范型。利用AOP可以对业务逻辑的各个部分进行隔离,从而使
得业务逻辑各部分之间的耦合度降低,提高程序的可重用性,同时提高了开发的效率。
Aop在Spring中的作用
提供声明式事务;允许用户自定义切面
- 横切关注点:跨越应用程序多个模块的方法或功能。即是,与我们业务逻辑无关的,
但是我们需要关注的部分,就是横切关注点。如日志 , 安全 , 缓存 , 事务等等 .... - 切面(ASPECT):横切关注点 被模块化 的特殊对象。即,它是一个类。
- 通知(Advice):切面必须要完成的工作。即,它是类中的一个方法。
- 目标(Target):被通知对象。
- 代理(Proxy):向目标对象应用通知之后创建的对象。
- 切入点(PointCut):切面通知 执行的 “地点”的定义。
- 连接点(JointPoint):与切入点匹配的执行点。
- SpringAOP中,通过Advice定义横切逻辑,Spring中支持5种类型的Advice:
使用Spring实现Aop
1.导包
【重点】使用AOP织入,需要导入一个依赖包!
<!-- https://mvnrepository.com/artifact/org.aspectj/aspectjweaver -->
<dependency>
<groupId>org.aspectj</groupId>
<artifactId>aspectjweaver</artifactId>
<version>1.9.4</version>
</dependency>2.目的
- 1.切入的配置
- 切入的位置
- 注意:execution(* com.zjz.serivce.UserServiceImpl.*(..))
- 第一个表示所有...第二个切入的类,然后.之后应该是方法(..)表示所有方法..
- 注意:execution(* com.zjz.serivce.UserServiceImpl.*(..))
- 切入方法的加入
- 切入的位置
- 2.切入的编写
- 三种方法...
- 1.切入的配置
使用Spring的API接口
目的:将日志,或者其它玩意,,切入到要执行的接口中
使用代理模式:怎么用? 你依据API写好你要切的东西,然后交给ApplicationContext去做(定位!配置你写的)
为啥交给间接管理员,服务者。。。你要在大的生态里整东西就是靠它。。
关键:ApplicationContext怎么做,,,,要切的东西怎么写
要切的东西怎么写;
- 1.要实现org.springframework.aop.下的接口 ---对应的Xml中要加对应的资源
- 2.直接使用它的方法(like-a) 扩展点就好了
配置:关键!!
- 1.约束,资源导入 aop的
2.aop配置
<aop:config>
中- 1.切入的位置 aop:pointcut
- 2.将我们的东西配进去 aop:advisor
<!--方式1,使用Spring API接口-->
<!--配置AOP,需要导入AOP的约束-->
<aop:config>
<!--切入点 expression:表达式 execution(要执行的位置!* * * * *)-->
<aop:pointcut id="pointcut" expression="execution(* com.zjz.serivce.UserServiceImpl.*(..))"/> <!-- 执行环绕增强!-->
<aop:advisor advice-ref="log" pointcut-ref="pointcut"/> <aop:advisor advice-ref="afterLog" pointcut-ref="pointcut"/>
</aop:config>
自定义类来实现Aop
目的:将日志,或者其它玩意,,切入到要执行的接口中
使用代理模式:怎么用? 你写好你要切的东西(自己编的),然后交给ApplicationContext去做(定位!配置你写的)
为啥交给间接管理员,服务者。。。你要在大的生态里整东西就是靠它。。
关键:ApplicationContext怎么做,,,,要切的东西怎么写
要切的东西怎么写;
- 1.自己写一个类,里面自己定义几个方法---
public class DiyPointCut {
public void before(){
System.out.println("=======方法执行前=======");
}
public void after(){
System.out.println("=======方法执行后=======");
}
}
配置
1.约束,资源导入 aop的
2.我们自己编写bean导入,
3.aop配置
<aop:config>
中- 导入我们的配置,让我们的写的东西进行赋予方法
<aop:aspect ref="diy">
- 1.切入的位置 aop:pointcut
- 2.将我们的东西配进去 aop:before aop:after
<!--方式2:自定义类-->
<bean id="diy" class="com.zjz.diy.DiyPointCut"/>
<aop:config>
<aop:aspect ref="diy">
<!--切入点-->
<aop:pointcut id="point" expression="execution(* com.zjz.serivce.UserServiceImpl.*(..))"/>
<!--通知-->
<aop:before method="before" pointcut-ref="point"/>
<aop:after method="after" pointcut-ref="point"/>
</aop:aspect>
</aop:config>- 导入我们的配置,让我们的写的东西进行赋予方法
注解实现Aop
1.自己写一个加注解的类
// 使用注解方式实现AOP
@Aspect // 标注这个类是一个切面
public class AnnotationPointCut { @Before("execution(* com.zjz.serivce.UserServiceImpl.*(..))")
public void before(){
System.out.println("======方法执行前=====");
} @After("execution(* com.zjz.serivce.UserServiceImpl.*(..))")
public void after(){
System.out.println("=====方法执行后=====");
} // 在环绕增强中,我们可以给定一个参数,代表我们要处理切入的点
@Around("execution(* com.zjz.serivce.UserServiceImpl.*(..))")
public void around(ProceedingJoinPoint pj) throws Throwable {
System.out.println("环绕前---"); // 获得签名
Signature signature = pj.getSignature();
System.out.println(signature); // 执行方法
Object proceed = pj.proceed(); System.out.println(proceed);
System.out.println("环绕后---"); }配置
1.约束,资源导入 aop的
2.我们自己编写bean导入,
3.开启注解支持
<!--方式3 注解配置-->
<bean id="annotationPointCut" class="com.zjz.diy.AnnotationPointCut"/>
<!--开启注解支持-->
<aop:aspectj-autoproxy/>
SpringAOP-动态代理,日志注入的更多相关文章
- spring-AOP动态代理,以及aspectJ的xml配置或注解配置方法,各个拦截器的使用顺序
package com.itheima.aspect; public class MyAspect { public void check_Permissions(){ System.out.prin ...
- Spring-AOP动态代理技术(底层代码)
1.JDK代理:基于接口的动态代理技术 目标对象必须有接口,目标对象有什么方法,目标接口就有什么方法, 运行期间基于接口动态生成代理对象,所以代理对象也就有目标对象同样的方法. 注意:以下代码只是底层 ...
- java使用动态代理来实现AOP(日志记录)
以下内容为原创,转载时请注明链接地址:http://www.cnblogs.com/tiantianbyconan/p/3336627.html AOP(面向方面)的思想,就是把项目共同的那部分功能分 ...
- xml文件的方式实现动态代理基于SpringAOP
1.配置spring容器 导入jar包 com.springsource.net.sf.cglib-2.2.0.jar com.springsource.org.aopalliance-1.0.0.j ...
- spring---aop(4)---Spring AOP的CGLIB动态代理
写在前面 前面介绍了Spring AOP的JDK动态代理的过程,这一篇文章就要介绍下Spring AOP的Cglib代理过程. CGLib全称为Code Generation Library,是一个强 ...
- spring---aop(2)---Spring AOP的JDK动态代理
写在前面 spring 事务是springAOP 的一个实现.我们以分析spring的事务,来分析spring的AOP实现. 基本知识 如果目标方法被spring的事务声明,则执行该目标方法的对象就会 ...
- Mybaits 源码解析 (十一)----- 设计模式精妙使用:静态代理和动态代理结合使用:@MapperScan将Mapper接口生成代理注入到Spring
上一篇文章我们讲了SqlSessionFactoryBean,通过这个FactoryBean创建SqlSessionFactory并注册进Spring容器,这篇文章我们就讲剩下的部分,通过Mapper ...
- SpringAOP ApectJ 动态代理
参考链接:https://docs.spring.io/spring/docs/4.3.13.RELEASE/spring-framework-reference/htmlsingle/#aop ht ...
- SpringAOP之动态代理
一.动态代理: 1.在原有的静态代理的基础上进一步的完善,由于静态代理中,重复写了相同的代码使得代码的整体结构显得冗余,而且还不同的核心类还需要有不用的代理类,是写死了的具体的类.所以需要使用动态代理 ...
随机推荐
- 热血动漫番太好看了!用Python爬取了1T的动漫,内存都爆了
最近被室友安利热血动漫番<终末的女武神>和<拳愿阿修罗>,太上头了周末休息熬夜看完了.不过资源不太好找,辣条一怒爬取了资源,这下可以看个够了.室友崇拜连连,想起了我的班 ...
- 启动或重启Oracle数据以及监听
(以下均为命令行形式) 1.切换到oracle数据库用户: su - oracle 2.查看数据库的监听状态: lsnrctl status 3.停止监听: lsnrctl stop 4.登陆到ora ...
- 跟我一起写 Makefile(十四)
使用make更新函数库文件 ----------- 函数库文件也就是对Object文件(程序编译的中间文件)的打包文件.在Unix下,一般是由命令"ar"来完成打包工作. 一.函数 ...
- Android Hello World程序开发过程
按照Building Your First App,详细过程如下: 安装SDK(如果网速慢,需要用离线安装的方法,见笔记 离线安装Android SDK的方法 ): 采用命令行开发方法(不用装Ecli ...
- 将vim打造成Java IDE
需要的插件列表: Taglist Conque Shell FuzzyFinder NERDTree javaComplete 其他选项: JavaKit exVim winmanager (Depr ...
- (转)Python爬虫--通用框架
转自https://blog.csdn.net/m0_37903789/article/details/74935906 前言: 相信不少写过Python爬虫的小伙伴,都应该有和笔者一样的经历吧只要确 ...
- DDD领域驱动理解
在理解领域驱动的时候,网上很多大谈理论的文章,这种对于初学者不是太容易接受.根据我自己的学习经历,建议按照如下几个步骤学习: 粗略的看一遍领域驱动的理论,做到心中有形,知道领域驱动是什么,解决什么问题 ...
- 通俗易懂理解——dijkstra算法求最短路径
迪杰斯特拉(Dijkstra)算法是典型最短路径算法,用于计算一个节点到其他节点的最短路径.它的主要特点是以起始点为中心向外层层扩展(广度优先搜索思想),直到扩展到终点为止 ###基本思想 通过Dij ...
- springCloud-Hystrix服务监控Dashboard
1.Hystrix服务监控Dashboard 介绍 Hystrix服务监控Dashboard仪表盘 在实际生产中,成千上万的服务,我们怎么知道提供服务的高可用情况,即服务的成功失败超时等相关情况; H ...
- [C#]c#中数据的同步加锁机制 的几种方法
一,锁定机制最简单的做法就是使用锁定关键字Lock.Lock关键字英文中就是锁的意思,顾名思义就是为操作加上一把锁.它的语法如下: lock(lockObj){//加锁的代码段,一般是操作共同资源的代 ...