dubbo-源码阅读之javaspi&javasist简单使用
dubbo可扩展的点的类的对象创建 都是用类似javaspi和javasist的思想来做的。所以看后面代码 先熟悉一下java的SPI和javasist的使用
如ServicesConfig的代码
private static final Protocol protocol = (Protocol)ExtensionLoader.getExtensionLoader(Protocol.class).getAdaptiveExtension();
JAVASPI的作用
服务(接口实现类)的自动发现。我们定义好一组接口标准。而具体实现调用者根据自身需求自己实现
JavaSPI简单使用
我们模拟我们做了一个框架(jar) 框架的正常运行需要相关配置。配置加载方式由使用者来实现
1.定义接口
/**
* 加载配置文件的句柄
*/
public interface LoadConfigHandle {
public String load();
}
2.定义实现类
public class HttpLoadConfigHandle implements LoadConfigHandle {
public String load() {
System.out.println("正在用http请求加载配置文件数据");
return "";
}
}
public class XmlLoadConfigHandle implements LoadConfigHandle {
public String load() {
System.out.println("正在加载配置文件xml");
return "";
}
}
在resource创建META-INF文件夹,再创建一个与接口全名称同名的文件。将实现类配置进去

com.liqiang.spi.XmlLoadConfigHandle com.liqiang.spi.HttpLoadConfigHandle
3测试
public static void main(String[] str) throws InterruptedException {
ServiceLoader<LoadConfigHandle> serviceLoader = ServiceLoader.load(LoadConfigHandle.class);
Iterator<LoadConfigHandle> iterator = serviceLoader.iterator();
while (iterator.hasNext()) {//next时候查缓存有没有加载过。如果没有加载才去加载
LoadConfigHandle loadConfigHandle = iterator.next();//next时候查缓存有没有加载过。如果没有加载采取加载
loadConfigHandle.load(); } }

javasist使用
假设我们在运行时要动态的创建和编译类这样一个类
package com.liqiang.ssist;
public class Person {
private String name;
private int age;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public int getAge() {
return age;
}
public void setAge(int age) {
this.age = age;
}
public Person(String name, int age){
this.name=name;
this.age=age;
}
public void show(String ... date){
System.out.println(this.name+"|"+this.age);
}
}
public static void main(String[]str) throws Exception{
//ClassPool:CtClass对象的容器
ClassPool pool = ClassPool.getDefault();
//通过ClassPool生成一个public新类Emp.java
CtClass ctClass = pool.makeClass("com.liqiang.ssist.Person");
/**
* 创建字段
*/
//创建字段private String name;
CtField nameField = new CtField(pool.getCtClass("java.lang.String"),"name",ctClass);
nameField.setModifiers(Modifier.PRIVATE);//私有字段
ctClass.addField(nameField);
//创建字段private int age;
CtField ageField = new CtField(pool.getCtClass("java.lang.Integer"),"age",ctClass);
ageField.setModifiers(Modifier.PRIVATE);//私有字段
ctClass.addField(ageField);
/**
* 为他们添加添加get set个访问器
*/
ctClass.addMethod(CtNewMethod.getter("getName", nameField));
ctClass.addMethod(CtNewMethod.setter("setName", nameField));
ctClass.addMethod(CtNewMethod.getter("getAge", ageField));
ctClass.addMethod(CtNewMethod.setter("setAge", ageField));
/**
* 添加构造函数
*/
CtConstructor ctConstructor = new CtConstructor(new CtClass[]{pool.getCtClass("java.lang.String"),
pool.getCtClass("java.lang.Integer")}, ctClass);
//为构造函数设置函数体$1表示第一个参数 $2表示第二个参数
StringBuffer buffer = new StringBuffer();
buffer.append("{\n")
.append("name=$1;\n")
.append("age=$2;\n}");
ctConstructor.setBody(buffer.toString());
//把构造函数添加到新的类中
ctClass.addConstructor(ctConstructor);
/**
* 定义方法
*/
CtMethod ctMethod = new CtMethod(CtClass.voidType,"show",new CtClass[]{},ctClass);
//为自定义方法设置修饰符
ctMethod.setModifiers(Modifier.PUBLIC);
//为自定义方法设置函数体
StringBuffer buffer2 = new StringBuffer();
buffer2.append("{\nSystem.out.println(this.name+\"|\"+this.age);\n")
.append("}");
ctMethod.setBody(buffer2.toString());
ctClass.addMethod(ctMethod);
/**
* 反射生成实体
*/
Class<?> clazz = ctClass.toClass();
Constructor cla = clazz.getDeclaredConstructor(String.class,Integer.class);//获取构造函数的构造器
Object obj=cla.newInstance("小明",12);//调用构造器生成对象
obj.getClass().getMethod("show", new Class[]{}).invoke(obj, new Object[]{});
}
输出

还有更多的使用方法 动态继承实现类。动态改变类方法 增加方法等。
dubbo-源码阅读之javaspi&javasist简单使用的更多相关文章
- 【Dubbo源码阅读系列】之远程服务调用(上)
今天打算来讲一讲 Dubbo 服务远程调用.笔者在开始看 Dubbo 远程服务相关源码的时候,看的有点迷糊.后来慢慢明白 Dubbo 远程服务的调用的本质就是动态代理模式的一种实现.本地消费者无须知道 ...
- 【Dubbo源码阅读系列】服务暴露之远程暴露
引言 什么叫 远程暴露 ?试着想象着这么一种场景:假设我们新增了一台服务器 A,专门用于发送短信提示给指定用户.那么问题来了,我们的 Message 服务上线之后,应该如何告知调用方服务器,服务器 A ...
- 【Dubbo源码阅读系列】服务暴露之本地暴露
在上一篇文章中我们介绍 Dubbo 自定义标签解析相关内容,其中我们自定义的 XML 标签 <dubbo:service /> 会被解析为 ServiceBean 对象(传送门:Dubbo ...
- 【Dubbo源码阅读系列】之 Dubbo SPI 机制
最近抽空开始了 Dubbo 源码的阅读之旅,希望可以通过写文章的方式记录和分享自己对 Dubbo 的理解.如果在本文出现一些纰漏或者错误之处,也希望大家不吝指出. Dubbo SPI 介绍 Java ...
- Dubbo源码阅读顺序
转载: https://blog.csdn.net/heroqiang/article/details/85340958 Dubbo源码解析之配置解析篇,主要内容是<dubbo:service/ ...
- Dubbo源码阅读-服务导出
Dubbo服务导出过程始于Spring容器发布刷新事件,Dubbo在接收到事件后,会立即执行服务导出逻辑.整个逻辑大致可分为三个部分,第一部分是前置工作,主要用于检查参数,组装URL.第二部分是导出服 ...
- dubbo源码阅读之SPI
dubbo SPI SPI,全程Service Provider interface, java中的一种借口扩展机制,将借口的实现类注明在配置文件中,程序在运行时通过扫描这些配置文件从而获取全部的实现 ...
- dubbo源码阅读之自适应扩展
自适应扩展机制 刚开始看代码,其实并不能很好地理解dubbo的自适应扩展机制的作用,我们不妨先把代码的主要逻辑过一遍,梳理一下,在了解了代码细节之后,回过头再来思考自适应扩展的作用,dubbo为什么要 ...
- 【Dubbo源码阅读系列】之 Dubbo XML 配置加载
今天我们来谈谈 Dubbo XML 配置相关内容.关于这部分内容我打算分为以下几个部分进行介绍: Dubbo XML Spring 自定义 XML 标签解析 Dubbo 自定义 XML 标签解析 Du ...
随机推荐
- Codeforces Round #330 (Div. 2) D. Max and Bike 二分
D. Max and Bike For months Maxim has been coming to work on his favorite bicycle. And quite recently ...
- 摄像头ov2685中关于sensor id 设置的相关的寄存器地址【转】
本文转载自:http://blog.csdn.net/morixinguan/article/details/51220992 OV2685 : CHIP_ID address : 0x300A ...
- Getting Installation aborted (Status 7) ApplyParsePerms: lsetfilecon of /syst...【转】
OTA升级失败:原文http://en.miui.com/thread-112197-1-1.html Do you get this "Status 7" error in Re ...
- What is the difference between task and thread?
http://stackoverflow.com/questions/4130194/what-is-the-difference-between-task-and-thread 回答一: A tas ...
- Android WiFi开发教程(二)——WiFi的搜索和连接
在上一篇中我们介绍了WiFi热点的创建和关闭,如果你还没阅读过,建议先阅读上一篇文章Android WiFi开发教程(一)——WiFi热点的创建与关闭. 本章节主要继续介绍WiFi的搜索和连接. Wi ...
- 查看tensorflow pb模型文件的节点信息
查看tensorflow pb模型文件的节点信息: import tensorflow as tf with tf.Session() as sess: with open('./quantized_ ...
- poj3041——最小点覆盖
Bessie wants to navigate her spaceship through a dangerous asteroid field in the shape of an N x N g ...
- PCB 后台自动系统集成与邮件推送实现
在PCB行业中,工程系统是主要数据生产者,而这些数据不仅仅给自己系统使用呀,我们需要将数据传递到各系统,才达到各系统共同协作的目的. 这里以问答方式对实现方式进行讲解.呵呵呵! 后台自动集成问题解答: ...
- PCB 3D PCB 后续改进与扩展功能一些想法
再次感受到WelGl实现3D效果的震撼, 一.目前功能: Gerber与钻孔 解析 并转为3D实景图,用户360度操控 二.后续改进扩展功能: 1.增加ODB++解析 2. 3D 尺寸标注(外形尺寸, ...
- jquery.validate验证text,checkbox,radio,selected
index.cshtml <form id="formLogin" method="post"> <div> <label for ...