七叶笔记 » java编程 » 如何通过memberlist库实现gossip管理集群及集群数据交互问题

如何通过memberlist库实现gossip管理集群及集群数据交互问题

通过memberlist库实现gossip管理集群以及集群数据交互

概述

memberlist库的简单用法如下,注意下面使用for循环来执行 list.Join ,原因是一开始各节点都没有runing,直接执行 Join 会出现连接拒绝的错误。

memberlist的两个主要接口如下:

Create:根据入参配置创建一个 Memberlist ,初始化阶段 Memberlist 仅包含本节点状态。注意此时并不会连接到其他节点,执行成功之后就可以允许其他节点加入该memberlist。

Join:使用已有的 Memberlist 来尝试连接给定的主机,并与之同步状态,以此来加入某个cluster。执行该操作可以让其他节点了解到本节点的存在。最后返回成功建立连接的节点数以及错误信息,如果没有与任何节点建立连接,则返回错误。

注意当join一个cluster时,至少需要指定集群中的一个已知成员,后续会通过gossip同步整个集群的成员信息。

memberlist提供的功能主要分为两块:维护成员状态(gossip)以及数据同步(boardcast、SendReliable)。下面看几个相关接口。

接口

memberlist.Create 的入参要求给出相应的 配置 信息, DefaultLocalConfig() 给出了通用的配置信息,但还需要实现相关接口来实现成员状态的同步以及用户数据的收发。注意下面有些接口是必选的,有些则可选:

memberlist使用如下 类型 的消息来同步集群状态和处理用户消息:

Delegate

如果要使用memberlist的gossip协议,则必须实现该接口。所有这些方法都必须是线程安全的。

主要方法如下:

NotifyMsg:用于接收用户消息( userMsg )。注意不能阻塞该方法,否则会阻塞整个UDP/TCP报文接收循环。此外由于数据可能在方法调用时被修改,因此应该事先拷贝数据。

该方法用于接收通过UDP/TCP方式发送的用户消息( userMsg ):

注意UDP方式并不是立即发送的,它会随gossip周期性发送或在处理 pingMsg 等消息时发送从GetBroadcasts获取到的用户消息。

GetBroadcasts:用于在gossip周期性调度或处理处理 pingMsg 等消息时携带用户消息,因此并不是即时的。通常会把需要发送的消息通过 TransmitLimitedQueue.QueueBroadcast 保存起来,然后在发送时通过 TransmitLimitedQueue.GetBroadcasts 获取需要发送的消息。见下面 TransmitLimitedQueue 的描述。

LocalState:用于TCP Push/Pull,用于向远端发送除成员之外的信息(可以发送任意数据),用于定期同步成员状态。参数 join 用于表示将该方法用于join阶段,而非push/pull。

MergeRemoteState:TCP Push/Pull之后调用,接收到远端的状态(即远端调用LocalState的结果)。参数 join 用于表示将该方法用于join阶段,而非push/pull。

定期(PushPullInterval)调用pushPull来随机执行一次完整的状态交互。但由于pushPull会与其他节点同步本节点的所有状态,因此代价也比较大。

EventDelegate

仅用于接收成员的joining 和leaving通知,可以用于更新本地的成员状态信息。

ChannelEventDelegate 实现了简单的 EventDelegate 接口:

ConflictDelegate

用于通知某个client在执行join时产生了命名冲突。通常是因为两个client配置了相同的名称,但使用了不同的地址。可以用于统计错误信息。

MergeDelegate

在集群执行merge操作时调用。 NotifyMerge 方法的参数 peers 提供了对端成员信息。 可以不实现该接口。

PingDelegate

用于通知观察者完成一个ping消息( pingMsg )要花费多长时间。可以在 NotifyPingComplete 中(使用histogram)统计ping的执行时间。

AliveDelegate

当接收到 aliveMsg 消息时调用的接口,可以用于添加日志和指标等信息。

Broadcast

可以随gossip将数据广播到memberlist集群。

Broadcast 接口通常作为 TransmitLimitedQueue.QueueBroadcast 的入参:

alertmanager中的实现如下:

TransmitLimitedQueue

TransmitLimitedQueue主要用于处理广播消息。有两个主要的方法: QueueBroadcast 和 GetBroadcasts ,前者用于保存广播消息,后者用于在发送的时候获取需要广播的消息。随gossip周期性调度或在处理 pingMsg 等消息时调用 GetBroadcasts 方法。

小结

memberlist中的消息分为两种,一种是内部用于同步集群状态的消息,另一种是用户消息。

GossipInterval 周期性调度的有两个方法:

gossip :用于同步 aliveMsg 、 deadMsg 、 suspectMsg 消息probe :用于使用 pingMsg 消息探测节点状态

用户消息又分为两种:

周期性同步:以 PushPullInterval 为周期,使用 Delegate.LocalState 和 Delegate.MergeRemoteState 以TCP方式同步用户信息;使用 Delegate.GetBroadcasts 随gossip发送用户信息。主动发送:使用 SendReliable 等方法实现主动发送用户消息。

alertmanager的处理

alertmanager通过两种方式发送用户消息,即UDP方式和TCP方式。在alertmanager中,当要发送的数据大于 MaxGossipPacketSize/2 将采用TCP方式( SendReliable 方法),否则使用UDP方式( Broadcast 接口)。

demo

这里 实现了一个简单的基于gossip管理集群信息,并通过TCP给集群成员发送信息的例子。

到此这篇关于通过memberlist库实现gossip管理集群以及集群数据交互的文章就介绍到这了,更多相关memberlist库gossip集群内容请搜索七叶笔记以前的文章或继续浏览下面的相关文章希望大家以后多多支持七叶笔记!

相关文章