写点什么

大画 Spark :: 网络 (4)-Endpoint 与的注册使用与网络环境的构建

作者:dclar
  • 2022 年 2 月 21 日
  • 本文字数:2358 字

    阅读完需:约 8 分钟

大画 Spark :: 网络(4)-Endpoint与的注册使用与网络环境的构建

回顾

回顾之前的网络(1)~(3)的部分,可以清晰的得出以下的结论


  • Spark 的服务之间的通信是通过 Netty 的 RPC 方式联通

  • Endpoint是处理网络请求服务的一个端点处理单元,给Endpoint发送请求,需要在发送方端构建起这个EndpointEndpointRef,通过EndpointRefsend或者ask来进行操作

  • send方法是不需要 response 的OneWayMessage类型

  • ask方法是需要 response 的RpcRequest类型

  • 接收方接收到请求后,是通过TransportRequestHandlerNettyRpcHandlerDispatcherRpcEndpoint的调用流来访问到相应的Endpoint的,这个过程可以参看

  • 大画 Spark :: 网络(3)-回复消息机制OneWayMessageRpcRequest对比

本篇主旨

稍稍描述一下 Driver 和 Executor

如果说到网络,还是需要简单描述一下 Spark 在作业中的执行原理,也需要简单描述一下其内部的逻辑单元。其中最重要的就是 Driver 和 Executor,Driver 和 Executor 也是在作业过程中会不断进行网络通信的组件之一

Endpoint 与 EndpointRef 的注册

前文中一直提及的RpcEndpoint是如何注册到 spark 的环境当中的,能够被Dispatcher调用起来?而RpcEndpoint的影子RpcEndpointRef又是如何被如何注册到系统中的呢

回顾之前的架构



在上图中,可以看到我们把 spark 的服务分成了 client 端和 Server 端,这个会在后续继续介绍,这里我们先关注 Server 端的部分。


在 Server 端中,有无数个RpcEndpoint,这些RpcEndpoint是在系统启动的时候,注册到Dispatcher中的,先介绍一下这个注册的过程。

RpcEndpoint 的注册

所有的 Endpoint 的注册都是从Dispatcher中的registerRpcEndpoint方法中来的。


如下图所示,RpcEndpoint是通过调用registerRpcEndpoint的方法,注册到了Dispatcher的 endpoints 中,当需要使用到Endpoint的时候,从 endpoints 按照 key 取出 value 的EndpointData即可。而EndpointRef的过程同理,


利用 NettyRpcEnv 调用 Dispatcher

Dispatcher 中的方法registerRpcEndpoint,在 spark 中,很多场景是由 NettyRpcEnv 通过setupEndpoint的方法调用起来的


这个 NettyRpcEnv,顾名思义,就是 spark 的 RPC 环境的实现。它是对抽象类 RpcEnv 的实现。在前面的章节中,有过这么一个图来表示 NettyRpcEnv 的作用



逻辑上NettyRpcEnv是 Rpc 的环境,承接了消息的发送与接收。而从整体构建结构上,NettyRpcEnv也承担了去设置Dispatcher中的Endpoint的职责,其重要工作为


  • 设置Endpoint

  • 进行sendreceive的操作


SparkEnv → NettyRpcEnv →Dispatcher

整个构建的结构如图所示,SparkEnvNettyRpcEnvDispatcher的过程


需要简单描述一下 Driver 和 Executor

说了半天的网络过程,必须要简单描述一下 Driver 和 Executor 的概念,否则无法后续推进网络间通信和 client 与 server 的关系了。之前一直画图在说 client 与 server 的关系,但是在 spark 集群中,什么样的节点是 client 什么样的又是 server 呢?这里简单描述一下,主要是讲网络环境的前置知识,后续讲解调度的时候会深入来聊这块。

Spark 的背景

没有 spark 的年代,mapreduce 是分布式计算的王者,记得 2015 年,我在某互联网公司时,还是写 MR 在 yarn 排队。但 MR 的问题在于,速度慢不用说,更大的问题是无法进行 pipeline 的操作,需要一个任务接着一个任务的去人为的调度,如果一个处理复杂一些,中间过程也需要考虑存储为后续再使用做准备。


Spark 的出现,颠覆了这个过程。很多人都对 spark 有误解,一说到 spark 的快,都会说因为利用了内存,但真正的原因并非如此。虽然 spark 可以使用内存缓存数据,但是只要遇到 shuffle,一定会落盘进行文件的读写,一定会进行磁盘 IO,和 MR 没有区别(spark 的数据的预聚合过程也借鉴了 MR)。但 spark 之所以能高效处理,最重要的是,可以形成一个不用反复重新启动 JVM 的 pipeline 的过程,让整个处理流程即使出现了 shuffle IO 也可以一气到底的执行完成,或者说是迭代器模式的非常经典的使用案例,正是因为这个原因才是 spark 最大的性能优势。

Driver 和 Executor 的职责

spark 的代码一般是这样的,借助 scala 的特点,函数式的书写过程,时不时的还会在中间传递几个函数,对于 java 出身的很多程序员会觉得不太友好,阅读和学习起来也需要一些成本。不过当你深入研究后,会发现 scala 和 spark 的结合真的是行云流水,无所不能,减少了很多 java 的冗长,多了很多优雅。

val line: RDD[String] = sc.textFile(args(0)).flatMap(_.split(" ")).map((_,1)).reduceByKey(_+_).saveAsTextFile("path")
复制代码


这段代码的意思非常简单,就是根据传入的文件地址,进行 wordcount 的计算,并把结果存储到一个 path 中。即使没有接触过 spark 的同学,看到这段代码应该也很容易能懂。


如果是普通的 java 程序,那么这段代码就按照一行的过程直接处理了,而 spark 则会对其进行“翻译”,变成 map 的过程和 reduce 的代码过程,把这些代码过程序列化后发送到集群的不同的节点上,进行并行的执行,也就是说,我们看到的是一个串行的过程,spark 可以把它变成几个并行处理的过程,后续我会细化这个过程,这里借一幅图来描述。



一行代码,执行进去后,发现是上图的两个过程,一个是 Transform 的过程,类似于 MR 中的 map,后面的 Action 的过程,类似于 MR 中的 reduce 的过程。


spark 会切分我们的代码,并且按照顺序去提交,还要考虑依赖关系,所以就会出现两个概念,一个是类似于 Director 的协调者,另一个就是执行者,这个协调者就是 Driver,执行者就是 Executor


Driver 和 Executor 的构建

无论是 Driver 还是 Executor,都是下面的这个构建的结构



构建后,双方通过 RPC 进行通信,最终接收消息执行的单元都是双方各自的 endpoints 中的 RpcEndpoint

总结

本篇描述了 Endpoint 的注册到 spark 内的过程,简单介绍了 Driver 和 Executor

Next

下一篇,围绕 Driver 和 Executor 的角色,聊一下 Driver 作为 server 端和 Executor 作为 client 端的异同,双方启动的过程以及发送消息的过程是如何处理的,后续会利用一个 Executor 启动后向 Drvier 进行反向注册的过程来整体描述一遍网络处理的过程

发布于: 刚刚阅读数: 2
用户头像

dclar

关注

有技术 有智慧 有胸怀 有眼界 2020.05.29 加入

I am an Artist

评论

发布
暂无评论
大画 Spark :: 网络(4)-Endpoint与的注册使用与网络环境的构建