IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 网络协议 -> Dubbo -> 正文阅读

[网络协议]Dubbo

一、dubbo的处理流程

  1. Provider:暴露服务的服务提供方
  2. Consumer:调用远程服务的服务消费方
  3. Registry:服务注册与发现的注册中心
  4. Monitor:统计服务的调用次数和调用时间的监控中心
  5. Container:服务运行容器 负责启动 加载 运行服务提供者

二、服务注册

注册中心是Dubbo的重要组成部分,主要用于服务的注册与发现,我们可以选择Redis、Nacos、
Zookeeper作为Dubbo的注册中心,Dubbo推荐用户使用Zookeeper作为注册中心。单选择zookeeper作为注册中心的时候,服务注册之后,zookeeper的目录结构为:

+- dubbo
| +- com.lagou.service.HelloService
| | +- consumers
| | | +- consumer://192.168.1.102/com.lagou.service.HelloService?
application=dubbo-demo-annotationconsumer&
category=consumers&check=false&dubbo=2.0.2&init=false&interface=com.lag
ou.service.HelloService&methods=sayHello,sayHelloWithPrint,sayHelloWithTransmiss
ion,sayHelloWithException&pid=25923&release=2.7.5&side=consumer&sticky=false&tim
estamp=1583896043650
| | +- providers
| | | +- dubbo://192.168.1.102:20880/com.lagou.service.HelloService?
anyhost=true&application=dubbo-demo-annotationprovider&
deprecated=false&dubbo=2.0.2&dynamic=true&generic=false&interface=com.l
agou.service.HelloService&methods=sayHello,sayHelloWithPrint,sayHelloWithTransmi
ssion,sayHelloWithException&pid=25917&release=2.7.5&side=provider&telnet=clear,e
xit,help,status,log,ls,ps,cd,pwd,invoke,trace,count,select,shutdown&timestamp=15
83896023597
| | +- configuration
| | +- routers

  • consumers: 当前服务下面所有的消费者列表(URL)
  • providers: 当前服务下面所有的提供者列表(URL)
  • configuration: 当前服务下面的配置信息信息,provider或者consumer会通过读取这里的配
    置信息来获取配置
  • routers: 当消费者在进行获取提供者的时,会通过这里配置好的路由来进行适配匹配规则?

生产者注册过程?

?dubbo配置生产者,通过在接口上添加@Service注解或者<dubbo:service/>标签,相当于配置类的ServiceConfig,现在就以ServiceConfig为入口,分析服务注册的流程。

服务注册过程

? 首先 ServiceConfig 类拿到对外提供服务的实际类 ref,然后通过ProxyFactory 接口实现类中的 getInvoker 方法使用 ref 生成一个 AbstractProxyInvoker 实例,到这一步就完成具体服务到 Invoker 的转化。接下来就是 Invoker 转换到 Exporter 的过程。?

? 我们可以看到,最终会调用Protocol的export方法生成Exporter并且注册到注册中心。先来看一下Protocol的export方法。通过断点我们可以看到最终调用的是RegistryProtocol.export方法。进入源码。

这里的override协议是一个动态更改配置的协议,服务提供者配置更改之后?可以按照最新的配置,重新建立invoker并销毁原来的invoker(了解overrider可以查看博客源码分析Dubbo配置规则机制(override协议) - JavaShuo)。进入register方法

根据断点,可以看到使用的registry是ZookeeperRegistry, 查看具体的ZookeeperRegistry的注册方法。这里可以看到继承了FailbackRegistry

?FailbackRegistry是一个注册失败只有会有稍后重试机制的注册。

里面的两个方法分别是注册和重试注册。看一下注册的方法doRegister,这是方法通过ZookeeperRegister具体实现的。

?到这里就完成了服务的注册。?

三、服务的消费

首先 ReferenceConfig 类的 init 方法调用 createProxy() ,期间 使用Protocol 调用 refer 方法生
成 Invoker 实例(如上图中的红色部分),这是服务消费的关键。接下来使用ProxyFactory把 Invoker
转换为客户端需要的接口。?

?集群工作过程可分为两个阶段,第一个阶段是在服务消费者初始化期间,集群 Cluster 实现类为服务消费者创建 Cluster Invoker 实例,即上图中的 merge 操作。第二个阶段是在服务消费者进行远程调用时。以 FailoverClusterInvoker 为例,该类型 Cluster Invoker 首先会调用 Directory 的 list 方法列举Invoker 列表(可将 Invoker 简单理解为服务提供者)。Directory 的用途是保存 Invoker列表,可简单类比为 List。其实现类 RegistryDirectory 是一个动态服务目录,可感知注册中心配置的变化,它所持有的 Invoker 列表会随着注册中心内容的变化而变化。每次变化后,RegistryDirectory 会动态增删Invoker,并调用 Router 的 route 方法进行路由,过滤掉不符合路由规则的 Invoker。当FailoverClusterInvoker 拿到 Directory 返回的 Invoker 列表后,它会通过 LoadBalance 从 Invoker 列表中选择一个 Invoker。最后 FailoverClusterInvoker 会将参数传给 LoadBalance 选择出的 Invoker实例的 invoke 方法,进行真正的远程调用。

Dubbo 主要提供了这样几种容错方式:

  • Failover Cluster - 失败自动切换 失败时会重试其它服务器
  • Failfast Cluster - 快速失败 请求失败后快速返回异常结果 不重试
  • Failsafe Cluster - 失败安全 出现异常 直接忽略 会对请求做负载均衡
  • Failback Cluster - 失败自动恢复 请求失败后 会自动记录请求到失败队列中
  • Forking Cluster - 并行调用多个服务提供者 其中有一个返回 则立即返回结果

根据上面的分析,我们知道消费者通过Cluster为调用的起点进行服务的调用。Cluster主要用于代理真正的invoker执行时做处理。而Invoker消费者服务会使用Protocol 调用 refer 方法生成 Invoker 实例。

?这里主要调用的是doRefer方法,这里面就是最主要产生Directory并且注册和监听的主要代
码逻辑。

这里生成了RegistryDirectory,通过上面的流程图我们可以知道,RegistryDirectory缓存了所有的Invoker,Cluster会从RegistryDirectory中获取invoker列表。这里还有一步时buildRouterChain,这一步生成了路由过滤规则,在获取invoker列表的时候会通过路由规则对服务列表进行过滤。RegistryDirectory可以根据注册中心的服务提供者的变化而动态变化的。这里主要看一下里面的doList方法,也是选择服务列表的方法。

?这里面有一个关键的步骤就是routerChain的route方法,这里就不展开去看了。主要是遍历所有的路由规则,选择满足条件的invoker。

?回到刚开是说的服务的调用那快,我们说过服务调用依赖的是FailoverCluster,而FailoverCluster刚才上面已经分析过了通过doRefer方法已经生成了,现在我们就看一下FailoverCluster是怎么调用的。回到刚才的doJoin方法产生invoke的那里,我们进入方法。

最终生成了FailbackClusterInvoker。而?FailbackClusterInvoker最关键的是invoke方法,进入方法。这里是继承了一个抽象类AbstractClusterInvoker调用的invoke方法进入AbstractClusterInvoker的invoke方法。

这里有几个关键的步骤,list方会从RegistryDirectory中经过过滤获取到所有的invoker列表,然后获取负载均衡器,最后调用doInvoke方法,负载均衡是在doInvoke方法中执行的。?

?这里面实现了负载均衡和服务的调用。

我们可以看到,负载均衡策略都在select方发中。最后我们看最关键的一步,就是调用远程服务的方法。进入AbstractInvoker的invoke方法,这里调用了子类的doInvoke方法。invoke方法里面具体的细节这里就不讨论了,现在进入子了dubboIvoker查看doInvoke方法?

?

这里面判断是否是同步还是异步,同步则调用currentClient的request方法并且同步等待结果,异步的情况则调用send方法。查看request方法

?这里交给真正的渠道进行处理,这里的nettyChannel也是这里创建的。具体的细节这里就不讨论了。

到此dubbo的服务注册和消费以及信息缓存、路由、容错(Cluster组件)、负载均衡都粗略的说了一下。还有一个重要的内容就是dubbo的SPI,留到下一篇专门的讲述。?

  网络协议 最新文章
使用Easyswoole 搭建简单的Websoket服务
常见的数据通信方式有哪些?
Openssl 1024bit RSA算法---公私钥获取和处
HTTPS协议的密钥交换流程
《小白WEB安全入门》03. 漏洞篇
HttpRunner4.x 安装与使用
2021-07-04
手写RPC学习笔记
K8S高可用版本部署
mySQL计算IP地址范围
上一篇文章      下一篇文章      查看所有文章
加:2022-04-18 18:20:11  更:2022-04-18 18:22:42 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2024年11日历 -2024/11/26 4:42:22-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码