grpc学习笔记

Posted 还是那个徐东强

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了grpc学习笔记相关的知识,希望对你有一定的参考价值。

rpc框架的调用原理如下:


http+json+hystrix

grpc+protobuf+hystrix

性能压测结果比较;

1. 相同请求数,吞吐量有明显上升

2. 错误率降低,(该错误率是由于hystrix的线程池无空闲线程,且等待队列已满,则fallback的异常),grpc说明线程的利用率更高。


随便贴两组数据:


之所以性能会提升如此,大概有如下原因

1.协议采用的http2,头部压缩,多路复用的特性。

在http1.1的协议中,传输的request和response都是基于文本的,所有的数据必须按顺序传输,http2是基于二级制数据帧和流的,帧对数据进行顺序标识,可以并行传输,最后合并数据。并且同一个域名只需要建立一个连接。

2.序列化方式采用的protobuf

3.netty io线程异步非阻塞


服务端创建

监听端口,创建NettyServer实例,等待基于HTTP2协议的请求消息接入

服务启动的时候,将实现类实例注册到grpc内部的服务注册中心。


服务端service调用流程

由grpc服务将PB消息反序列化为POJO对象,然后通过服务定义查询该消息对应的接口实例,发起本地java调用,调用完成之后,将相应消息反序列化为PB,通过HTTP2 发送给客户端。

 

服务调用和发送响应,详细如下: 

  1. SocketChannel读状态就绪,读取消息bytebuf,解码为httpHeader和Body

  2. 从Http2 header中提取需要调用的接口和方法名,转换为grpc内部的metadata对象

  3. 将Http2 消息体中的pb消息反序列化为 java的POJO对象,即protobuf文件中接口的请求参数对象

  4. 根据请求消息头中的方法名到注册中心查询对应的service实现类实例

  5. 通过本地java调用,调用服务端启动时注册的service实例,执行

  6. 根据请求消息,构造应答消息的http header 和 http body,将其接入到writeQueue队列中调用netty channel的write方法,将消息发送到channelPipeline


客户端调用和响应流程,详细如下:

  1. 客户端Stub(动态代理)调用,发起rpc调用

  2. 根据负载均衡,选择一个服务端实例

  3. 对请求消息pb序列化,通过http2 stream发送给grpc服务端

  4. 接收到服务端响应之后,使用PB做反序列化

  5. 回调GrpcFuture的setResponse方法,唤醒阻塞的业务调用线程,返回grpc响应

※ 客户端同步阻塞RPC调用阻塞的是调用方业务线程,底层(Netty客户端)仍然是非阻塞。


grpc线程模型

服务端线程模型

  1. 网络通信相关的线程模型,基于Netty 4.1的线程模型实现

  2.  服务接口调用模型,基于JDK线程池实现

具体点就是 HTTP2请求消息的接入和响应发送都有Netty负责, grpc消息的序列化和反序列化,服务接口调用都由grpc的线程池负责。


b服务调用线程模型:

  1. 请求消息的反序列化,主要包括了Http/2 header的反序列化,以及body反序列化为请求service实现类的请求参数

  2. 服务接口的调用

  3. 将响应消息封装成WriteQueue.QueuedCommand,写入一个Netty Channel,同时对响应Header和Body对象序列化


客户端线程模型

  • 业务调用线程

  • 客户端连接和IO读写线程

  • 请求消息业务处理和响应回调 


Netty4的线程模型---使劲了解一下



TCP/IP 四层模型

应用层  ---->  HTTP头

传输层  ---->  TCP头

网络层  ---->  IP头

传输层  ---->  MAC头


HTTP协议

当一个请求发出去,从上往下走,当经过应用层包装数据,加上应用层,http头; 当经过传输层,加上传输层 tcp头。。。

最终的数据包如下:

MAC头 | IP头 | TCP头 | HTTP头 | HTTP正文


当请求到达目标服务器,则从下往上 摘到 数据头,拿到最终的数据。


TCP协议

当一个请求发出去

最终的数据包如下

MAC头 | IP头 | TCP头 | TCP正文


所有网络上跑的包都是完整的,可以有下层没有上层(比如TCP协议发出的数据包就没有http头),绝对不可能有上层没有下层(看下面,如果没有下层,没有ip和MAC信息,则无法定位到具体的网上具体的机器)。


来看看 各数据头中包含的信息:

IP头    ---> 客户端电脑IP, 服务端IP

TCP头   ---> 浏览器端口,应用服务端口 (决定了送给目标机器的哪个进程)

HTTP头  ---> post or get, http1.1? 正文格式:json, 正文长度


"grpc是在http2之上实现的rpc框架,http2是在第7层(应用层)协议,它运行在tcp第四层(传输层)协议之上。" ---> 这个还好理解

"直接在tcp上构建http2"

"http2在tcp连接之初通过协商的方式进行通信"

一下子就不理解 http2和tcp到底啥关系了???



以上是关于grpc学习笔记的主要内容,如果未能解决你的问题,请参考以下文章

《Go-micro微服务框架入门教程》学习笔记 | gRPC

2021-07-22学习笔记总结(grpc和client接口调用)

学习笔记TF041:分布式并行

fabric1.0学习笔记

C语言基础学习笔记+ C语言进阶学习笔记总结篇(坚持才有收获!)

学习笔记TF061:分布式TensorFlow,分布式原理最佳实践