解析动态代理模式与跟自定义注解配合使用以及事务注解原理
来源:互联网 发布:中国小镇 知乎 编辑:程序博客网 时间:2024/06/05 10:15
动态代理:用来修改已经具有的对象的方法,控制方法是否执行,或在方法执行之前和执行之后做一些额外的操作
Proxy.newProxyInstance(ClassLoader loader, Class<?>[] interfaces, InvocationHandler h);
loader -- 类加载器
interfaces -- 指定代理对象实现哪些接口,通常代理对象要和被代理对象实现相同的接口,从而保证和被代理者具有相同的方法
InvocationHandler
-- 处理器对象,当调用代理对象的任何方法时,都会导致此对象中的invoke方法执行,在这个方法中可以编写是否允许方法执行,以及在方法执行之前和之后做那些额外的操作
{
Object invoke(Object proxy, Method method, Object[] args)
proxy -- 代理者对象
method -- 当前调用到的方法
args -- 方法的参数
返回值 -- 就是这个方法要返回什么
}
1.加载配置文件,用于程序解耦
config.properties 配置文件如下几行:
UserDao=com.itheima.dao.UserDaoImpl
UserService=com.itheima.service.UserServiceImpl
ProdDao=com.itheima.dao.ProdDaoImpl
ProdService=com.itheima.service.ProdServiceImpl
OrderService=com.itheima.service.OrderServiceImpl
OrderDao=com.itheima.dao.OrderDaoImpl
private static BasicFactory factory = new BasicFactory();
private static Properties prop = null;
private BasicFactory(){}
static{
try {
prop = new Properties();
prop.load(new FileReader(BasicFactory.class.getClassLoader().getResource("config.properties").getPath())); // 读取配置文件
} catch (Exception e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
2.解析,模仿注解事务原理
/**
* 获取Service的方法
*/
public <T extends Service> T getService(Class<T> clazz){
try{
//--根据配置文件创建具体的Service
String infName = clazz.getSimpleName(); //获取简单类名 单单是名称
String implName = prop.getProperty(infName); // 获取类名对应的实现类 从配置文件中读取
final T service = (T) Class.forName(implName).newInstance();
//--为了实现AOP,生成service代理,根据注解确定在Service方法执行之前和之后做一些操作,比如:事务管理/记录日志/细粒度权限控制....
T proxyService = (T) Proxy.newProxyInstance(service.getClass().getClassLoader(), service.getClass().getInterfaces()
, new InvocationHandler(){
//根据注解控制事务
public Object invoke(Object proxy, Method method,Object[] args) throws Throwable {
if(method.isAnnotationPresent(Tran.class)){//如果有注解,则管理事务:
try{
TransactionManager.startTran();//--开启事务
Object obj = method.invoke(service, args);//--真正执行方法
TransactionManager.commit();//--提交事务
return obj;
}catch (InvocationTargetException e) {
TransactionManager.rollback();//--回滚事务
throw new RuntimeException(e.getTargetException());
} catch (Exception e) {
TransactionManager.rollback();//--回滚事务
throw new RuntimeException(e);
}finally{
TransactionManager.release();//--释放资源
}
}else{//如果没有注解,则不管理事务,直接执行方法
return method.invoke(service, args);
}
}
});
return proxyService;
}catch (Exception e) {
e.printStackTrace();
throw new RuntimeException(e);
}
}
- 解析动态代理模式与跟自定义注解配合使用以及事务注解原理
- 使用DBUtils、动态代理以及注解实现事务控制
- 使用动态代理+自定义注解控制数据库事务
- 如何创建、使用以及解析自定义注解
- JDK注解以及自定义注解的使用和解析
- Java 自定义注解以及注解解析器
- java自定义注解以及原理
- 切面和自定义注解的配合使用
- java 注解与动态代理
- 代理模式-----进行事务的注解
- 自定义注解与使用
- JAVAWEB开发之Servlet3.0新特性的使用以及注解的详细使用和自定义注解的方法、动态代理的使用、利用动态代理实现细粒度的权限控制以及类加载和泛型反射
- 【注解】动态代理模式的好伙伴
- 自定义注解与设计模式
- Spring事务传播特性实例解析(以及如何使用注解形式事务)
- 自定义注解与spring事务的问题
- 通过使用反射+动态代理+注解来实现对事务的控制
- java自定义注解原理深度解析
- stm32成长记之滴答时钟
- 开始多线程
- centos 安装mysql 5.5.44
- 一起来点React Native——你必须要会点FlexBox布局
- 20170803~20170804
- 解析动态代理模式与跟自定义注解配合使用以及事务注解原理
- java Logger类和Apache slf4j
- 如何在阿里云安装和调用R程序
- python 列表分片
- JavaScript中arguments关键字
- Linux 虚拟机:Network error: Connection refused 排查
- 实现ViewPager懒加载的三种方法
- 第四天 在嵩天老师的教授进度中查缺补漏
- java编程思想读书笔记一(面向对象)