前言

nacos 2.0.0 已经发布了 alpha1, alpha2 和 beta 三个版本了,部分测试报告也已经出来了。

还是比较值得期待的。

前段时间也一直在完善 nacos-sdk-csharp 这个项目。

主要就是对接 Nacos 2.0.0 这一块,也考虑到之前主要是针对Open API封装,同时参考JAVA的SDK进行功能叠加。

这一次就索性全部重新来过了,也对齐 JAVA SDK 提供的方法。

这其中最为重要的应该是底层协议由 HTTP 换成 gRPC,也是长轮询到长连接的一个跨越。

现在就和大家简单梳理一下老黄在对接中认为要注意的地方。

这里以 nacos 2.0.0 beta 版本为准,后续版本可能会有变化。

端口

nacos 的默认端口是 8848,也是之前 HTTP 协议对接时的请求端口,那么我们是不是通过 8848 这个端口进行 gRPC 的交互呢?

答案是否定的!

nacos 里面做了一个约定,把 gRPC 的服务端口设置成 nacos 启动的端口加 1000。

也就是说,nacos 的端口是 8848 的话,那么 gRPC 服务端口就是 9848

所以这里是第一个注意的点。

proto 文件

下面是 nacos 提供的 proto 文件,这个是SDK和Server交互的基础。

syntax = "proto3";

import "google/protobuf/any.proto";
import "google/protobuf/timestamp.proto"; option java_multiple_files = true;
option java_package = "com.alibaba.nacos.api.grpc.auto"; message Metadata {
string type = 3;
map<string, string> headers = 7;
} message Payload {
Metadata metadata = 2;
google.protobuf.Any body = 3;
} service RequestStream {
// build a streamRequest
rpc requestStream (Payload) returns (stream Payload) {
}
} service Request {
// Sends a commonRequest
rpc request (Payload) returns (Payload) {
}
} service BiRequestStream {
// Sends a commonRequest
rpc requestBiStream (stream Payload) returns (stream Payload) {
}
}

这里有 3 个 service,其中 RequestStream 这个在实际对接中是没有使用到的。 所以只介绍其他两个。

Request 这个是通用请求,发布配置,注册服务之类的请求都是通过这个方法来交互的。

BiRequestStream 这个是双向流,主要是用来注册连接,和一些监听回调。

Nacos 1.x 里面, 配置的监听回调是基于长轮询机制,服务的监听回调是基于udp机制。

再来看看 service 的参数和响应。

Payload 的设计是有两个部分, 一个是自定义类型的 metadata, 一个是 Any 类型的 body

metadata 里面有一个 type 字段,这个字段代表的是客户端和服务端交互的 RPC 语义。好比说,我要发布配置,就是通过这个 type 告诉服务端,当前请求是要做什么。

body 这个在交互时需要做一下转换,拿到一个 object 对象,序列化成一个 JSON 字符串,最后在转化成 Any 类型的 value。

下面是一个简单的示例:

var body = new Google.Protobuf.WellKnownTypes.Any
{
// convert the request paramter to a json string, as the body
Value = Google.Protobuf.ByteString.CopyFromUtf8(request.ToJsonString())
};

这里有一个要注意的地方,在生成 C# 代码后,会因为参数名和方法名一样造成编译不过,所以这里要修改一下生成代码的参数名。

对接

知道了服务端的端口, proto 文件也有了,接下来就可以和服务端对接了。

想要和服务端对接上,成功获取到正确的数据,其实还有不少内容的。

下面老黄拆成 3 个小节来说。

建立连接

Step 1:

与 gRPC 服务端进行交互,首先就是要创建一个 Channel ,这里用的是 Insecure 的方式,不需要提供额外的证书信息。

Step 2:

创建 Request 请求客户端,并发起 ServerCheckRequest 请求,检查服务是否可用,不可用就直接关闭这个 Channel 了。

Step 3:

创建 BiRequestStream 请求客户端,注册处理服务端推送的相关操作,主要是配置和服务的变更。

注册完成后,还要发送 ConnectionSetupRequest 请求和 server 端建立真正意义上的连接。

这一步至关重要,因为这一步过后,服务端会把这个连接维护到客户端的连接管理里面,后续的请求会通过这个来判断是不是合法的请求。可以理解成拿到了大门的钥匙。

这一步完成之后,就可以通过 Request 发送请求了。

请求与响应

这里的请求,指的是通过 Request 发起的。

前面有提到,body 参数这一块,是对一个 JSON 字符串进行转化后的值。

这个 JSON 字符串大概成下面这样。

{
"headers": {
"h1": "v1",
"h2": "v2"
},
"requestId": "xxxx",
"biz-prop-1": "value-1",
"biz-prop-2": "value-2",
"biz-prop-n": "value-n",
}

其中, headers 和 requestId 这两个是通用参数,每个接口都应该带上,其他的就是各个接口需要什么就加什么。

响应的话会有正常和异常。

正常的话,返回的 type 是和请求的 type 相对应的。

好比 ConfigPublishRequest 就会对应 ConfigPublishResponse

如果服务端处理异常了,就会返 ErrorResponse

这里的异常可以分为两类。

  1. 请求没有注册
{"resultCode":500,"errorCode":301,"message":"Connection is unregistered.","success":false}

出现这种情况后,客户端这边是要重新和服务端进行连接,不然所有的请求都会是这个返回。

可能的原因有:

  • 在请求之前没有提前在双向流里面发起建立连接的请求。
  • 客户端与服务端断开过连接
  1. 请求处理失败

这个一般就是服务端处理出现了异常。

重新连接

如果响应告诉客户端请求没有注册,这个时候要及时触发重新连接,这样才不会让业务受到影响。

触发重连操作后,会有一个 SwitchServer 的操作,可以简单理解成换了一个服务地址,然后重复连接里面的几个步骤。

到这里其实对接相关的内容基本差不多了,剩下的就是对接具体的请求和其他操作了。

也附上一张老黄之前画的粗糙的图。

写在最后

老黄参与的 nacos-sdk-csharp 目前已经基本适配好了 nacos 2.0.0 beta 版本,但是还有许多细节需要慢慢的调整和改进。

希望有感兴趣的大佬一起参与到这个项目来。

nacos-sdk-csharp 的地址 :https://github.com/nacos-group/nacos-sdk-csharp

聊一聊和Nacos 2.0.0对接那些事的更多相关文章

  1. Nacos v0.7.0:对接CMDB,实现基于标签的服务发现能力

    Nacos近期发布了0.7.0版本,该版本支持对接第三方CMDB获取CMDB数据.使用Selector机制来配置服务的路由类型.支持单机模式使用MySQL数据库.上线Node.js客户端,并修复了一些 ...

  2. Nacos 1.1.0发布,支持灰度配置和地址服务器模式

    https://nacos.io/zh-cn/blog/nacos%201.1.0.html

  3. Nacos 发布 1.0.0 GA 版本,可大规模投入到生产环境

    经过 3 个 RC 版本的社区体验之后,Nacos 正式发布 1.0.0 GA 版本,在架构.功能和 API 设计上进行了全方位的重构和升级. 1.0.0 版本的发布标志着 Nacos 已经可以大规模 ...

  4. Nacos 配置MySQL8.0持久化

    问题描述 官网下载的Nacos mysql由于驱动过低只支持5.X版本,使用8.X版本的mysql时无法正常启动 解决办法 克隆nacos源码(branch 1.0.0-RC3) master等分支也 ...

  5. Spring Cloud Alibaba(6)---Nacos持久化Mysql8.0版本

    Nacos持久化Mysql8.0版本 有关Nacos之前写过三篇文章. Spring Cloud Alibaba(3)---Nacos概述 Spring Cloud Alibaba(4)---Naco ...

  6. 全网最新的nacos 2.1.0集群多节点部署教程

    原文链接:全网最新的nacos 2.1.0集群多节点部署教程-语雀 基本信息 进度整理中 版本 2.1.0 版本发布日期 2022-04-29 git revision number b5845313 ...

  7. springboot2.0.4对接redis3.2.12版本哨兵模式

    redis 哨兵模式的创建 1. 下载redis3.2.12版本.https://codeload.github.com/antirez/redis/zip/3.2.12 2.  解压后放到/usr/ ...

  8. Nacos:Nacos与OpenFeign的对接使用

    Nacos(三):Nacos与OpenFeign的对接使用   上篇文章中,简单介绍了如何在SpringCloud项目中接入Nacos作为注册中心,其中服务消费者是通过RestTemplate+Rib ...

  9. 关于端口冲突的解决方式Error: listen EACCES 0.0.0.80

    笔者昨天下午临走前安装了vs 2017想要运行一下项目的NET后端来让本机的前端直接对接后端,但是没注意到运行vs后IIS直接占用了本机的80端口.第二天跑nodeJS的时候直接Error: list ...

随机推荐

  1. Codeforces Round #666 (Div. 2) B. Power Sequence (枚举)

    题意:有一个长度为\(n\)的序列,你每次可以对序列重新排序,然后花费\(1\)使某个元素加减\(1\),多次操作后使得新序列满足\(a_{i}=c^i\),\(c\)是某个正整数,求最小花费. 题解 ...

  2. Codeforces Round #529 (Div. 3) E. Almost Regular Bracket Sequence (思维,模拟栈)

    题意:给你一串括号,每次仅可以修改一个位置,问有多少位置仅修改一次后所有括号合法. 题解:我们用栈来将这串括号进行匹配,每成功匹配一对就将它们消去,因为题目要求仅修改一处使得所有括号合法,所以栈中最后 ...

  3. log4net GetLogger(source).IsInfoEnabled = false

    GetLogger(source).IsInfoEnabled = false解决办法 在.net core中需要把log4net.config放到 ITCP.Web\ITCP.Web\obj\Rel ...

  4. Nestjs入门学习教程

    初次接触Nest,有问题欢迎指出: 简介 NestJS是一个用于构建高效.可扩展的Node.js服务器端应用程序的开发框架.简单来说是一款Node.js的后端框架. 它利用JavaScript的渐进增 ...

  5. 二进制方式安装docker(非root用户启动docker)

    二进制方式安装docker(非root用户启动docker) 一.下载安装包: 地址:https://download.docker.com/linux/static/stable/x86_64/ 这 ...

  6. C++含有无符号类型的表达式的计算

    unsigned u=10; int i=-42; cout<<i+i<<endl; cout<<u+i<<endl; 在第二个输出表达式中,相加前首先 ...

  7. C# 数据类型(2)

    String char的集合 string name = "John Doe"; 双引号,char是单引号string是不可变的,一旦初始化后就不能变了,每次对已存在的string ...

  8. xss 之herf输出

    首先查看下漏洞页面,发现输入的1111,  直接传参到herf 中, 查阅资料得知: 输出出现在a标签的href属性里面,可以使用javascript协议来执行js 查看源代码: if(isset($ ...

  9. 修改jupyter-notebook的python3版本

    将默认的kernel修改为对应的python即可: /home/a/.virtualenvs/YOUR_VENV/bin/python -m pip install ipykernel /home/a ...

  10. 2015 - 2020 最新 Linux 命令大全

    # 2015 - 2020 最新 Linux 命令大全 ## VIM 命令模式(Command mode):vi 插入模式(Insert mode):i底线命令模式(Last line mode):e ...