第 29 章 - ES 源码篇 - 网络 IO 模型及其实现概述

前言

本文介绍了 ES 使用的网络模型,并介绍 transport,http 接收、响应请求的代码入口。

网络 IO 模型

Node 在初始化的时候,会创建网络模块。网络模块会加载 Netty4Plugin plugin。

而后由 Netty4Plugin 创建对应的 transports,以及 http server。

代码分别入口为:Netty4Plugin#getTransports,Netty4Plugin#getHttpTransports

众所周知,Netty 中使用的网络 IO 模型是 主从 Reactor。

接下来带大家一起看创建的细节。

Transport

代码入口为构造函数 Netty4Transport。

因为 transport 主要用于内部,因此既有 ServerBootstrap,又有 Bootstrap。
ServerBootstrap 是 Netty 中表示 Server 的类。
Bootstrap 是 Netty 中表示 Client 的类。

ES 使用的是 NioEventLoopGroup,其底层实现基于 Java NIO。

而 JAVA NIO 在不同的平台上,会执行不同的系统调用。例如,在 Linux(2.6之后) 会使用 epoll。

创建 NioEventLoopGroup 的代码入口为:SharedGroupFactory#getGenericGroup(),默认会创建 Runtime.availableProcessors() 个 EventLoop(工作线程),可通过 transport.netty.worker_count 修改创建的个数。

其中,Server 和 Client 会共用同一个 NioEventLoopGroup。代码入口 Netty4Transport#doStart()

接收请求代码入口:
Netty4MessageChannelHandler#channelRead(ChannelHandlerContext ctx, Object msg)

响应请求代码入口:
Netty4MessageChannelHandler#write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise)

http server

创建

代码入口为构造函数 Netty4HttpServerTransport。在 doStart() 函数中描述了 ServerBootstrap 的创建过程。

默认情况下 http server 和 transport 共用同一个 NioEventLoopGroup。如果想改变这个行为,需要设置 http.netty.worker_count 的值大于 0。描述这段逻辑的代码入口为:SharedGroupFactory#getHttpGroup()

接收 http 请求

接收请求的入口为:Netty4HttpRequestHandler#channelRead0(ChannelHandlerContext ctx, HttpPipelinedRequest httpRequest)

与我们所熟知的 MVC 框架类似,请求进来后,都会交由某个类去做请求的分发。在 ES 中,负责分发请求的类为:RestController#dispatchRequest(RestRequest request, RestChannel channel, ThreadContext threadContext)

不同的请求可能会运行在不同的业务线程上。

响应 http 请求

响应 http 请求的入口为: Netty4HttpResponseCreator#encode
Netty4HttpResponseCreator 继承的是 Netty 的 MessageToMessageEncoder 类。该类在可以写就绪时,会自动调用 write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise) 方法,而 write 方法中则会调用 encode 方法,因此这里说,入口是 encode 方法。

本文由mdnice多平台发布

相关推荐
喵个咪几秒前
GoWind CMS 拆解:给 NL2SQL 上四把锁——智能问数的安全边界
后端
喵个咪7 分钟前
GoWind CMS 拆解:在 Go 里给 TipTap 搭一套 Yjs 协同后端
后端·go·cms
不像程序员的程序媛14 分钟前
springboot支持的web容器
前端·spring boot·后端
喵个咪14 分钟前
GoWind Admin 拆解:一个 Sender 接口接 39 个通知渠道
后端·架构·go
用户693717500138428 分钟前
当你向领导申请 AI 编程工具预算时,如果领导追问“能提效多少,有量化数据吗”,你该怎么回答?
android·后端·ios
喵个咪30 分钟前
GoWind CMS 拆解:社交分发引擎——10 平台适配器、状态闸门与自愈定时任务
后端·go·cms
lichenyang45338 分钟前
技术穿刺怎么做?以企业知识库问答为例,验证风险、方案和投入
前端·后端
喵个咪43 分钟前
GoWind UBA 拆解:把 Doris UNIQUE KEY 翻译成 ClickHouse——读数正确性对齐实录
大数据·后端·go
Elastic 中国社区官方博客1 小时前
控制告警如何触发、恢复和发送通知:Elastic 可观测性中的 Kibana 通用告警
大数据·数据库·安全·elasticsearch·搜索引擎·全文检索·es
武子康1 小时前
把调用移进同一个类之后:一次 Spring 事务回滚反例
人工智能·后端·agent