聊聊dubbo的MetadataReportService
时间:2022-06-25
本文章向大家介绍聊聊dubbo的MetadataReportService,主要内容包括其使用实例、应用技巧、基本知识点总结和需要注意事项,具有一定的参考价值,需要的朋友可以参考一下。
序
本文主要研究一下dubbo的MetadataReportService
MetadataReportService
dubbo-2.7.2/dubbo-metadata-report/dubbo-metadata-report-api/src/main/java/org/apache/dubbo/metadata/integration/MetadataReportService.java
public class MetadataReportService {
protected final Logger logger = LoggerFactory.getLogger(getClass());
private static volatile MetadataReportService metadataReportService;
private static Object lock = new Object();
private MetadataReportFactory metadataReportFactory = ExtensionLoader.getExtensionLoader(MetadataReportFactory.class).getAdaptiveExtension();
MetadataReport metadataReport;
URL metadataReportUrl;
MetadataReportService(URL metadataReportURL) {
if (METADATA_REPORT_KEY.equals(metadataReportURL.getProtocol())) {
String protocol = metadataReportURL.getParameter(METADATA_REPORT_KEY, DEFAULT_DIRECTORY);
metadataReportURL = URLBuilder.from(metadataReportURL)
.setProtocol(protocol)
.removeParameter(METADATA_REPORT_KEY)
.build();
}
this.metadataReportUrl = metadataReportURL;
metadataReport = metadataReportFactory.getMetadataReport(this.metadataReportUrl);
}
public static MetadataReportService instance(Supplier<URL> metadataReportUrl) {
if (metadataReportService == null) {
synchronized (lock) {
if (metadataReportService == null) {
URL metadataReportURLTmp = metadataReportUrl.get();
if (metadataReportURLTmp == null) {
return null;
}
metadataReportService = new MetadataReportService(metadataReportURLTmp);
}
}
}
return metadataReportService;
}
public void publishProvider(URL providerUrl) throws RpcException {
//first add into the list
// remove the individul param
providerUrl = providerUrl.removeParameters(PID_KEY, TIMESTAMP_KEY, Constants.BIND_IP_KEY, Constants.BIND_PORT_KEY, TIMESTAMP_KEY);
try {
String interfaceName = providerUrl.getParameter(INTERFACE_KEY);
if (StringUtils.isNotEmpty(interfaceName)) {
Class interfaceClass = Class.forName(interfaceName);
FullServiceDefinition fullServiceDefinition = ServiceDefinitionBuilder.buildFullDefinition(interfaceClass, providerUrl.getParameters());
metadataReport.storeProviderMetadata(new MetadataIdentifier(providerUrl.getServiceInterface(),
providerUrl.getParameter(VERSION_KEY), providerUrl.getParameter(GROUP_KEY),
PROVIDER_SIDE, providerUrl.getParameter(APPLICATION_KEY)), fullServiceDefinition);
return;
}
logger.error("publishProvider interfaceName is empty . providerUrl: " + providerUrl.toFullString());
} catch (ClassNotFoundException e) {
//ignore error
logger.error("publishProvider getServiceDescriptor error. providerUrl: " + providerUrl.toFullString(), e);
}
}
public void publishConsumer(URL consumerURL) throws RpcException {
consumerURL = consumerURL.removeParameters(PID_KEY, TIMESTAMP_KEY, Constants.BIND_IP_KEY, Constants.BIND_PORT_KEY, TIMESTAMP_KEY);
metadataReport.storeConsumerMetadata(new MetadataIdentifier(consumerURL.getServiceInterface(),
consumerURL.getParameter(VERSION_KEY), consumerURL.getParameter(GROUP_KEY), CONSUMER_SIDE,
consumerURL.getParameter(APPLICATION_KEY)), consumerURL.getParameters());
}
}
- MetadataReportService的构造器通过metadataReportURL来获取对应的MetadataReport;它定义了publishProvider方法主要是执行metadataReport.storeProviderMetadata方法;还定义了publishConsumer方法主要是执行metadataReport.storeConsumerMetadata方法;同时还提供了一个静态方法使用双重检锁的单例模式创建MetadataReportService
实例
dubbo-2.7.2/dubbo-metadata-report/dubbo-metadata-report-api/src/test/java/org/apache/dubbo/metadata/integration/MetadataReportServiceTest.java
public class MetadataReportServiceTest {
URL url = URL.valueOf("JTest://" + NetUtils.getLocalAddress().getHostName() + ":4444/org.apache.dubbo.TestService?version=1.0.0&application=vic");
MetadataReportService metadataReportService1;
@BeforeEach
public void before() {
metadataReportService1 = MetadataReportService.instance(() -> url);
}
@Test
public void testInstance() {
MetadataReportService metadataReportService2 = MetadataReportService.instance(new Supplier<URL>() {
@Override
public URL get() {
return url;
}
});
Assertions.assertSame(metadataReportService1, metadataReportService2);
Assertions.assertEquals(metadataReportService1.metadataReportUrl, url);
}
@Test
public void testPublishProviderNoInterfaceName() {
URL publishUrl = URL.valueOf("dubbo://" + NetUtils.getLocalAddress().getHostName() + ":4444/org.apache.dubbo.TestService?version=1.0.0&application=vicpubprovder&side=provider");
metadataReportService1.publishProvider(publishUrl);
Assertions.assertTrue(metadataReportService1.metadataReport instanceof JTestMetadataReport4Test);
JTestMetadataReport4Test jTestMetadataReport4Test = (JTestMetadataReport4Test) metadataReportService1.metadataReport;
Assertions.assertTrue(!jTestMetadataReport4Test.store.containsKey(JTestMetadataReport4Test.getProviderKey(publishUrl)));
}
@Test
public void testPublishProviderWrongInterface() {
URL publishUrl = URL.valueOf("dubbo://" + NetUtils.getLocalAddress().getHostName() + ":4444/org.apache.dubbo.TestService?version=1.0.0&application=vicpu&interface=ccc&side=provider");
metadataReportService1.publishProvider(publishUrl);
Assertions.assertTrue(metadataReportService1.metadataReport instanceof JTestMetadataReport4Test);
JTestMetadataReport4Test jTestMetadataReport4Test = (JTestMetadataReport4Test) metadataReportService1.metadataReport;
Assertions.assertTrue(!jTestMetadataReport4Test.store.containsKey(JTestMetadataReport4Test.getProviderKey(publishUrl)));
}
@Test
public void testPublishProviderContainInterface() throws InterruptedException {
URL publishUrl = URL.valueOf("dubbo://" + NetUtils.getLocalAddress().getHostName() + ":4444/org.apache.dubbo.TestService?version=1.0.3&application=vicpubp&interface=org.apache.dubbo.metadata.integration.InterfaceNameTestService&side=provider");
metadataReportService1.publishProvider(publishUrl);
Thread.sleep(300);
Assertions.assertTrue(metadataReportService1.metadataReport instanceof JTestMetadataReport4Test);
JTestMetadataReport4Test jTestMetadataReport4Test = (JTestMetadataReport4Test) metadataReportService1.metadataReport;
Assertions.assertTrue(jTestMetadataReport4Test.store.containsKey(JTestMetadataReport4Test.getProviderKey(publishUrl)));
String value = jTestMetadataReport4Test.store.get(JTestMetadataReport4Test.getProviderKey(publishUrl));
FullServiceDefinition fullServiceDefinition = toServiceDefinition(value);
Map<String,String> map = fullServiceDefinition.getParameters();
Assertions.assertEquals(map.get("application"), "vicpubp");
Assertions.assertEquals(map.get("version"), "1.0.3");
Assertions.assertEquals(map.get("interface"), "org.apache.dubbo.metadata.integration.InterfaceNameTestService");
}
@Test
public void testPublishConsumer() throws InterruptedException {
URL publishUrl = URL.valueOf("dubbo://" + NetUtils.getLocalAddress().getHostName() + ":4444/org.apache.dubbo.TestService?version=1.0.x&application=vicpubconsumer&side=consumer");
metadataReportService1.publishConsumer(publishUrl);
Thread.sleep(300);
Assertions.assertTrue(metadataReportService1.metadataReport instanceof JTestMetadataReport4Test);
JTestMetadataReport4Test jTestMetadataReport4Test = (JTestMetadataReport4Test) metadataReportService1.metadataReport;
Assertions.assertTrue(jTestMetadataReport4Test.store.containsKey(JTestMetadataReport4Test.getConsumerKey(publishUrl)));
String value = jTestMetadataReport4Test.store.get(JTestMetadataReport4Test.getConsumerKey(publishUrl));
Gson gson = new Gson();
Map<String, String> map = gson.fromJson(value, Map.class);
Assertions.assertEquals(map.get("application"), "vicpubconsumer");
Assertions.assertEquals(map.get("version"), "1.0.x");
}
private FullServiceDefinition toServiceDefinition(String urlQuery) {
Gson gson = new Gson();
return gson.fromJson(urlQuery, FullServiceDefinition.class);
}
}
- 这里的testInstance方法验证了单例模式;之后对publishProvider验证了noInterfaceName、wrongInterface、containInterface的场景;最后验证了publishConsumer
小结
MetadataReportService的构造器通过metadataReportURL来获取对应的MetadataReport;它定义了publishProvider方法主要是执行metadataReport.storeProviderMetadata方法;还定义了publishConsumer方法主要是执行metadataReport.storeConsumerMetadata方法;同时还提供了一个静态方法使用双重检锁的单例模式创建MetadataReportService
doc
- dedecms怎样调用指定id文章?
- c++ list, vector, map, set 区别与用法比较
- 前台开发从头说起:谈谈CSS选择符
- dedecms无法登录提示本页面禁止返回
- 前台开发从头说起:理解css盒模型
- 两个js冲突怎么解决?试试这四个方法
- dedecms如何去除后台登陆验证码
- DEDECMS自定义表单unix时间戳转换成常规时间方法及增加表单添加时间方法
- dedecms自定义表单发布成功后返回当前页面
- 前端构建工具 Gulp.js 上手实例
- dedecms数据库内容替换安全确认码不显示怎么解决
- 利用宏避免发送确认邮件时忘记添加附件
- dateDiff在Objective-C中的实现
- 禁用Firefox自带的元素查看工具
- JavaScript 教程
- JavaScript 编辑工具
- JavaScript 与HTML
- JavaScript 与Java
- JavaScript 数据结构
- JavaScript 基本数据类型
- JavaScript 特殊数据类型
- JavaScript 运算符
- JavaScript typeof 运算符
- JavaScript 表达式
- JavaScript 类型转换
- JavaScript 基本语法
- JavaScript 注释
- Javascript 基本处理流程
- Javascript 选择结构
- Javascript if 语句
- Javascript if 语句的嵌套
- Javascript switch 语句
- Javascript 循环结构
- Javascript 循环结构实例
- Javascript 跳转语句
- Javascript 控制语句总结
- Javascript 函数介绍
- Javascript 函数的定义
- Javascript 函数调用
- Javascript 几种特殊的函数
- JavaScript 内置函数简介
- Javascript eval() 函数
- Javascript isFinite() 函数
- Javascript isNaN() 函数
- parseInt() 与 parseFloat()
- escape() 与 unescape()
- Javascript 字符串介绍
- Javascript length属性
- javascript 字符串函数
- Javascript 日期对象简介
- Javascript 日期对象用途
- Date 对象属性和方法
- Javascript 数组是什么
- Javascript 创建数组
- Javascript 数组赋值与取值
- Javascript 数组属性和方法
- 开机报错/dev/vda1 contains a file system with errors,check forced.
- centos内核的删除或修改
- chkconfig学习笔记
- 3分钟短文:说说Laravel通用缓存Cache的使用技巧
- 【技术创作101训练营】想用代码改变世界?先用好Git和Github!
- 绘制散点图(克利夫兰系列)
- 绘制分组散点图(克里夫兰点图)
- ggplot2绘制玫瑰图
- 绘制极坐标系条形图
- 四步重新认识冗余机器人的控制器设计
- 人脸识别接入常见问题汇总
- TKE上关于postStart 和preStop使用
- 文字识别接入常见问题
- 从 1 到 0 构建博客项目(2) -- 操作系统篇(2)--定制Centos
- 使用Angular依赖注入自定义SAP Spartacus的ProductAdapter