Socket.D 基于消息的响应式应用层网络协议

首先根据 Socket.D 官网的副标题,Socket.D 的自我定义是:

基于事件和语义消息流的网络应用协议。

官网定义的特点是:

  • 基于事件,每个消息都可事件路由
  • 所谓语义,通过元信息进行语义描述
  • 流关联性,有相关的消息会串成一个流
  • 语言无关,使用二进制输传数据(支持 tcp, ws, udp)。支持多语言、多平台
  • 断线重连,自动连接恢复
  • 多路复用,一个连接便可允许多个请求和响应消息同时运行
  • 双向通讯,单链接双向互听互发
  • 自动分片,数据超出 16Mb,会自动分片、自动重组(udp 除外)
  • 接口简单,是响应式但用的是监听与回调风格(经典易用)

Socket.D 是基于这些特性需求诞生的一种新型响应式网络协议。Socket.D 借鉴了很多其他协议发展过程中遇到的问题,然后总结归纳进自己的实践当中。

基于 Socket.D 的一些主要特性分别做一下介绍,并和 HTTP 之类的常见协议进行比较:

  • Destination (URL) 显示连接地址
  • Event 事件
  • Multiplexed, Binary Protocol 多路复用的二进制协议
  • Bidirectional Streaming 双向流
  • Socket Resumption 连接恢复
  • Message passing 消息传递模型
  • Transport independent 与传输层解耦的应用层协议

一、两层路由能力

  • path 路由能力

Socket.D 是基于显示连接地址的,可以实现像 http 或 websocket 一样的“频道”路由的效果。地址例:

//模拟聊天场景的用户地址
sd:tcp://127.0.0.1:8602//模拟聊天场景的管理员地址
sd:tcp://127.0.0.1:8602/admin?u=admin&p=1234
  • event 路由能力

Socket.D 每个消息都有事件描述,可以起到 path 或 topic 或 cmd 类似的路由效果。示例:

//模拟消息中间件的发布指令
client.send("event.mq.publish", new StringEvent("{userId:1}").metaSet("topic","demo"));//模拟消息中间件的订阅指令
client.send("event.mq.subscribe", new StringEvent("").metaSet("topic","demo"));

二、多路复用的二进制协议

现在 Multiplexing,Asynchronous,Non-blocking I/O 已经被说烂了,基本上就是标配。这些特性意味着什么?拿HTTP的发展史感受一下:

从 HTTP1.0 到 HTTP3.0 在传输性能上的进步
  • 在 HTTP1.0 时代,每个 HTTP request 都要新建一个网络连接。网络连接不能复用
  • HTTP1.1 时代,一个网络连接仍然在一个时候只能负责一个 request,但是整个 request/response 结束后连接可以得到复用。
  • 会有文章讲到 HTTP1.1 的核心是pipeline功能,是也不是。pipelining 支持一个 TCP 连接上按照顺序连续发送多个 HTTP 请求而不需要等待前一个请求的响应,但是它同时要求HTTP response也要按照请求的顺序逐个发送,这对服务器提出了很多要求,而且如果第一个响应很慢会拖累所有的后续响应(pipeling的队头阻塞),所以事实上并没有得到多少运用。即使到今天大部分浏览器仍然是默认关闭HTTP pipelining功能的,所以说HTTP1.1的主要突破还只是连接复用。
  • HTTP2.0 是个飞跃,开始支持 multiplexing,一个TCP连接上可以同时承载多个request/response,用这种方式替代1.1的pipelining提升HTTP的并行效果,也自然不存在什么队头阻塞了。每一个request/response的信息流,我们把它称作一个HTTP stream。这个时候一个HTTP client对于一个origin,只需要建立一个TCP就够了。(但是multiplexing带来了新的问题)
  • 现在HTTP3.0也差不多了。2.0解决了1.1pipelining的队头阻塞问题,但是却无法解决TCP本身的队头阻塞。而因为TCP/IP在内核协议栈中,简直无法升级,于是HTTP选择了QUIC作为新的传输层协议。 QUIC基于UDP,在用户模式中实现了类似TCP的connection oriented的功能同时解决TCP的队头阻塞,自带multiplexing等等。

所以,HTTP/2具有的优点,Socket.D 都有。另外,Socket.D 是一个二进制协议,也就是说在一个 Socket.D 连接上传输的消息体对数据格式没有任何要求,应用程序可以为所欲为的压缩数据量的大小。

这样的二进制协议通常来说能给性能带来极大的提升,但是产生的代价是,网络中间件也会因为无法解读消息体中的数据,丧失了在对具体应用流量进行监控,日志和路由的能力。所以 Socket.D 通过把每个消息体分成 sid, event, data 和 metaString 的方式,在保证高效传输的前提下,也提供了暴露元数据给网络中间件的能力(方便做语义处理),同时还能路由消息。

frame: {flag, message: {sid, event, entity: { metaString, data}}}

对于每个 data,应用可以采用不同的序列化方法。metaString 则采用标准的 url queryString 的通用格式(所有网络中间件通用)。

  • data 一般作为应用本身需要传递的业务数据,采取自定义的高效序列化方式,且对网络基础设施不可见
  • metaString 采用标准的 url queryString 的通用格式。在分布式传输的过程中,这些中间件可以按需求对 metaString 进行读写,然后调整路由。

三、双向流

上面提到,HTTP这几年在传输性能上进步了很多。但说到底在应用层仍然仅支持client request/server response的交互模型。

这里一些同学可能有疑问,比如:

那HTTP/2推出的Server Push是什么

HTTP2.0推出了一个新的Server Push功能,但这个功能通常只是用来提前将一些静态资源返还给用户而已。举个例子:一个简单的网站有三个静态资源组成: index.html, index.css, index.js。 我们打开浏览器打开index.html,就会发起一个HTTP request拿到index.html。在不使用server push的情况下,我们要等浏览器解析出index.css 和 index.js之后才会再次向服务器发起请求。而运用server push,服务器可以根据一些规则预知到浏览器也需要index.css和index.js,并在客户端发送新的请求之前直接推送给该客户端。

所以,这个功能的使用场景非常有限,而且也不是一个真正双向的交互模式。

结论:仅仅使用HTTP/2协议,不在其基础之上再加一层其他协议的情况下是无法在应用层实现双向流的(比如,gRPC)。

回到交互模式,Socket.D 的几种模式:

  • Send
  • SendAndRequest -> Reply
  • SendAndSubscribe -> Stream Reply
  • Reply
  • ReplyEnd
  • Session(双向使用上面的发送与答复)

通常来说,越复杂的交互模式,为了保存交互状态,就需要占用更多的内存和计算资源。这也是为什么 Socket.D 会提供多种不同的 API。另外,当 Socket.D 的 client 和 server 建立了长连接之后,任何一方都可以是 Requester 或是 Responder。服务器也可以扮演 Requester 的角色,首先发起 Request。

四、异步消息传递

Socket.D 还有另外一个非常重要的概念使之完全区分于类HTTP协议,那就是异步消息传递。

不同于HTTP当中存在Request,Response。Socket.D在网络传输上只有Frame这一个消息格式。有一个相同点是,类HTTP协议通常拥有一个显式的destination (URL),使用起来会非常有亲切感和简单。

如果Requester的 Socket.D 消息R首先通过了一个网络中间件(Broker),那么请求者(Requester)并不关心该消息的最终目的地在哪里,网络中间件可以全权负责路由模块的实现。该架构可以支持微服务,也可以支持IOT场景,等等。

在这里插入图片描述

这种架构很有意思,不仅能在微服务中加入streaming支持,还有如下特点:

1.客户端也可以暴露服务

由于 Socket.D 的双向流特性,和Broker建立连接的客户端即可以做Requester也可以做Responder,比如图中的Device 1和Device 2虽然是移动终端或者IOT设备,但仍然可以向其他设备或数据中心的主机提供服务

2.自动服务注册/发现

Socket.D 在成功建立连接时。如果该client想要暴露一个服务,则在连接地址上给自己取个名字(就像加入一个社交群,让别人能At到你)。连接成功建立之后,Socket.D Broker可以直接通过记录网络连接状况来达到服务注册和发现的效果。通过’@'参数取名示例:

sd:tcp://127.0.0.1:8602?@=demoapp
3.基于消息 metaString 实现请求路由

前面说过,Socket.D 是一个二进制协议,但仍然可以在消息体中通过 metaString 来暴露信息给网络中间件。每个消息实体的 metaString 会带有‘@’参数, 告诉 Socket.D Broker 消息应该转发给谁,从而实现路由效果。示例:

client.send("/demo", new StringEntity("").at("demoapp"));

与连接时给自己取名的 ‘@’ 参数相乎应。取了名,就能被“别人” at 到!

4.暴露服务不需要Ip和Port

整个架构当中,所有节点都只需要知道Broker的地址和服务端口即可。只要成功连接信息流就是双向的。Borker可以直接通过建立的Connection寻址服务节点,所有的服务调用者都不需要知道服务暴露方的地址

而Broker又可以通过连接的 url 地址,进行签权控制。

5.天生的中心化管理

管理微服务集群往往需要有一个中心化的控制中心,在这个架构中 Socket.D Broker 就是自然而然的中心,知道整个集群中所有的情况。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/236746.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Android Studio设置android:background 属性背景颜色

除了默认的颜色之外都要自己添加。 添加颜色的操作步骤: 打开res文件夹,找values,里面有个colors.xml的文件。然后在里面定义一些颜色。 完成

21、Web攻防——JavaWeb项目JWT身份攻击组件安全访问控制

文章目录 一、JavaWeb二、JWT攻击 一、JavaWeb webgoat 1.java web的配置文件,配置文件一般在META-INF目录下,文件名常为pom.xml或web.xml 2.如何通过请求,查看运行的java代码。 地址信息PathTraversal/profile-upload 直接找到以该字符P…

网络安全知识图谱 图数据库介绍及语法

本体构建: 资产: 系统,软件 威胁: 攻击: 建模: 3个本体 5个实体类型 CWE漏洞库 http://cwe.mitre.org/data/downloads.html CPECP攻击模式分类库 http://capec.mitre.org/data/downloads.html CPE通用组件库 http:…

Modbus RTU协议与S7 200 PLC通讯

一、Modbus RTU功能码 二、功能码使用与解析实例 01功能码 –读线圈状态 主机发送:01 01 00 01 00 08 6C 0C 从机回复: 01 01 01 2F 10 54 主机解析:01 地址(设备ID); 01 功能码;00 01 代表查询的起始线圈地址,即…

二叉树题目:输出二叉树

文章目录 题目标题和出处难度题目描述要求示例数据范围 前言解法一思路和算法代码复杂度分析 解法二思路和算法代码复杂度分析 题目 标题和出处 标题:输出二叉树 出处:655. 输出二叉树 难度 6 级 题目描述 要求 给定二叉树的根结点 root \textt…

链接未来:深入理解链表数据结构(一.c语言实现无头单向非循环链表)

在上一篇文章中,我们探索了顺序表这一基础的数据结构,它提供了一种有序存储数据的方法,使得数据的访 问和操作变得更加高效。想要进一步了解,大家可以移步于上一篇文章:探索顺序表:数据结构中的秩序之美 今…

06.仿简道云公式函数实战-前瞻

1.前言 在上篇文章中,我们介绍了QLExpress的进阶知识,扩展操作符,自定义操作符和自定义函数等内容。学了上面的内容后,目前对于QLExpress使用已经问题不大,从这篇文章,我们就进入我们的主题仿简道云公式函…

CentOS:Docker容器中安装vim

在使用docker容器时,里边没有安装vim时,敲vim命令时提示说:vim: command not found 这个时候就须要安装vim,安装命令: apt-get install vim 出现以下错误: 解决方法: apt-get update 这个命令的…

Spark中使用scala完成数据抽取任务 -- 总结

如题 任务二:离线数据处理,校赛题目需要使用spark框架将mysql数据库中ds_db01数据库的user_info表的内容抽取到Hive库的user_info表中,并且添加一个字段设置字段的格式 第二个任务和第一个的内容几乎一样。 在该任务中主要需要完成以下几个阶…

刷题记录第五十一天-去除重复字母

题目要求的是字典序最小的结果。只需要理解一点就是按大小顺序排列的字符串的字典序就是最小的,如“abcd”这种。 解题思路如下: 首先明确要使用栈结构,并且是从栈底到栈顶递增,要尽可能保证递增,这样就能保证字典序最…

前端项目常用函数封装(二)

文章目录 前端项目常用函数封装(一)判断两个数组是否有相同元素 返回相同元素(数组)判断hex颜色值是深色还是浅色随机生成深浅样色 js判断是手机端还是移动端使用UA判断使用媒体查询判断 fetch直接读文件内容,解决乱码问题下载文件将字符串下…

ansibe的脚本---playbook剧本(1)

playbook剧本组成部分: 1、task 任务: 主要是包含要在目标主机上的操作,使用模块定义操作。每个任务都是模块的调用。 2、variables变量:存储和传递数据。变量可自定义,可以在playbook中定义为全局变量,可…

深入理解 Spring Boot:核心知识与约定大于配置原则

深入理解 Spring Boot:核心知识与约定大于配置原则 简单说一下为什么要有 Spring Boot? 因为 Spring 的缺点。 虽然 Spring 的组件代码是轻量级的,但它的配置却是重量级的(需要大量 XML 配置) 为了减少配置文件,简化开发 Spri…

HarmonyOS应用事件打点开发指导

简介 传统的日志系统里汇聚了整个设备上所有程序运行的过程流水日志,难以识别其中的关键信息。因此,应用开发者需要一种数据打点机制,用来评估如访问数、日活、用户操作习惯以及影响用户使用的关键因素等关键信息。 HiAppEvent 是在系统层面…

手机数码品牌网站建设的作用是什么

手机数码产品几乎已经成为成年人必备的,包括手机、电脑、摄像机、键盘配件等,同时市场中相关企业也非常多,消费者可供选择的商品类型也很多样,而对企业来讲,只有不断提升品牌形象、获客拉新等才能不断提升企业地位&…

istio工作负载

目录 文章目录 目录本节实战前言1、WorkloadEntry多实例不同端口权重位置 2、WorkloadGroup关于我最后 本节实战 实战名称🚩 实战:WorkloadEntry测试-2023.12.21(测试成功) 前言 在之前的章节中我们已经多次提到了工作负载,在 Istio 中工作…

持续集成交付CICD:HELM 手动完成前端项目应用发布与回滚

目录 一、实验 1.环境 2.K8S master节点部署HELM3 3.K8S master节点安装git 4. Harbor镜像确认 5. HELM 手动完成前端项目应用发布与回滚 6.代码上传到GitLab 二、问题 1.Ingress中 path 的类型有何区别 2. HELM创建项目报错 一、实验 1.环境 (1&#x…

智能优化算法应用:基于野狗算法3D无线传感器网络(WSN)覆盖优化 - 附代码

智能优化算法应用:基于野狗算法3D无线传感器网络(WSN)覆盖优化 - 附代码 文章目录 智能优化算法应用:基于野狗算法3D无线传感器网络(WSN)覆盖优化 - 附代码1.无线传感网络节点模型2.覆盖数学模型及分析3.野狗算法4.实验参数设定5.算法结果6.参考文献7.MA…

APP测试要点有哪些?本文已经给你梳理好了!

我们日常购物、旅游、支付等活动都离不开手机,由此衍生了很多APP。 比如每天使用频率非常高的微信、支付宝、微博、抖音、王者荣耀等等。 APP测试主要进行功能测试、性能测试、自动化测试、安全性测试、兼容性测试、专项测试。 01 APP测试流程 APP测试流程与web…

NLP论文阅读记录 - AAAI-23 | 01 Cogito Ergo Summ:通过语义解析图和一致性奖励对生物医学论文进行抽象总结

文章目录 前言0、论文摘要一、Introduction1.1目标问题1.2相关的尝试1.3本文贡献 二.相关工作2.1抽象概括2.2图增强摘要2.3 抽象概括的强化学习 三.本文方法COGITOERGOSUMM 框架3.1 问题陈述3.2 图表构建**事件图****AMR 图****图合并和重新连接**Model文本编码器图编码器解码器…