dubbogo 在云原生时代


written by Alex Stocks on 2021/04/11,版权所有,无授权不得转载

周六【20210410】正在和社区同学忙着 dubbogo 3.0 发版,某互联网教育公司的曾同学报来一个问题,随后和相关同学展开了多轮讨论。因为个人觉得这是一次比较有意义的讨论,觉得有必要花费时间记录下来,算是 dubbogo 在云原生进化途中的一个见证。

后面如果有更多有意义的讨论,个人将继续补加此文。

1 新服务上线后 consumer 无法调用


2021-04-07T19:39+08:00 pm 曾同学报出来一个 dubbo-go pr 1137 ,当时囿于工作繁忙,没有分析其背景,且代码改动不甚合理,就没理会让其自己继续追踪下根因。

2021-04-10T17:51+08:00 pm,曾同学发来如下消息:

这次预感其分析过程比较靠谱,遂组织社区五个同学对其问题进行分析。

1.1 问题描述

根据与曾同学的沟通,其整体环境是在一个 k8s 环境下,使用注册中心 zk,其出问题的过程如下:

如下图:

分析其过程,根因是其 devops 部署的问题,但是用户希望能在 dubbo/dubbogo 层把这个问题吃掉。使用方希望能根据通知下线中一些可靠字段【譬如 timestamp?】确认下线服务的准确性。

1.2 解决方案

曾同学给出了一个解决方案,对 consumer 端的本地 service map 缓存进行改造,由于 provider 启动时上报注册中心的 metadata 中使用了服务启动的时间戳 timestamp,可以在原来的 key 维度中加入 timestamp 这个维度。但被社区否决了:加入时间戳维度并不能解决问题,因为时间戳精度只能达到 秒 级别,并不能从根本上解决问题。

dubbogo 有一个 health check 机制:consumer 对注册中心下发的 provider 列表定时发送心跳 check 逻辑,进行 alive 二次验证。结合 health check 机制,社区给出的解决方案是:

最终下线与否取决于 healthCheck 的结果。最终方案通过这个 timestamp 和 health check 这两个双保险把误下线的概率降到最低。

详细内容已经整理到 dubbo-go issue 1141,欢迎关注后续讨论。

1.3 隐含前提

社区方案,有个前提是:注册中心通知事件的有序性。

梳理下我们支持的所有注册中心对这个特性的支持特点:

2 多余的话

有人说 dubbogo 的架子太过于庞大,维护成本和学习成本很高,不如微内核框架的可插拔机制优雅,其实任何框架都是有历史的,都是有现实意义的。诚所谓存在即合理,无意义的口水争论是无法推动产品进步的。

诚如 linus 与其老师 Andrew Tanenbaum 就 linux 的宏内核与 minix 的微内核的争论,并不能因此就动摇 linux 是第一大 OS 的地位。dubbogo 重构前的版本直接借鉴了 go-micro,是可插拔的,但后来经鄙人和一些 Javaer 借鉴 dubbogo v1 、getty rpc 以及 dubbo 重构后,彻底变成了 Dubbo 的翻版,被人戏称为一个类似于宏内核的 “怪物”。另外,重构过程中鄙人的代码提交被彻底打乱,所以可能有些人觉得鄙人没写多少代码。

站在事后的角度来看,这也铸就了 dubbogo 强大的功能,对各种注册中心的支持正是基于它有可插拔的灵魂,否则也不可能支持这么多第三方组件和如此多的通信协议与序列化协议。目前 dubbogo 的各项功能几乎都被生产环境验证过,譬如 芒果TV 使用了基于 nacos 注册中心的 HTTP + JSONRPC、TCP + hessian2 通信协议,而 得物 则 使用了基于 nacos 注册中心的 gRPC 通信方式。况且 dubbogo 并不是如一些喷子所谓的没有代码生成工具,其 v1.5 中 gRPC 和 dubbogo 3.0 都提供了各种工具,并不比竞品差太多。或者说, dubbogo 的任何一角都很强大,足以覆盖竞品的功能。

在云原生时代,dubbogo 未来会继续秉承 “bridging the gap between Java and Go”,在 多语言和多框架【gRPC 和 Spring Cloud】之间架起桥梁,继续进化。

dubbogo 不仅仅是一个 RPC 微服务治理框架,而应该成为云原生时代的微服务基础设施!

Payment

Timeline