etcd心跳超时处理过程

发布时间 2023-04-03 15:12:47作者: K&

正文不废话

 

背景原因

 

日常巡检发现etcd报了心跳超时(大二层,所以可能不在同一交换机下,怀疑网络质量问题)

 

failed to send out heartbeat on time (exceeded the 100ms timeout for .*ms.)

 

解决方案

 

调整etcd心跳

 

排查过程

 

先了解一下etcd心跳工作原理:

 

 

etcd是一个分布式键值存储系统,用于可靠的数据存储和服务发现。etcd集群中的每个节点都会向其他节点发送心跳信号以保持连接状态,并且如果一个节点在一段时间内没有收到来自其他节点的心跳信号,则会将该节点标记为“unhealthy”。

 

 

底层的分布式共识协议依赖于两个独立的时间参数,以确保节点在一个停滞或离线时可以交接领导权。

 

第一个参数称为心跳间隔。这是领导者通知追随者它仍然是领导者的频率。对于最佳实践,该参数应围绕成员之间的往返时间进行设置。默认情况下,etcd 使用100ms心跳间隔。

 

第二个参数是选举超时。这个超时是跟随者节点在尝试成为领导者之前没有听到心跳的时间。默认情况下,etcd 使用1000ms选举超时。

 

 

 

 

--heartbeat-interval参数是指follower节点每隔多久发送一次心跳信号给leader节点。这个参数的目的是确保follower节点与leader节点之间的连接正常。


--election-timeout参数是指follower节点在多长时间内没有收到leader节点的心跳信号就会发起一次选举。这个参数的目的是确保在leader节点宕机后,follower节点能够及时地发起选举并选出新的leader节点。

 


当心跳信号无法在--election-timeout时间内到达follower节点时,etcd会将leader节点视为不可用,并且follower节点会发起一次新的选举。

 

 

 

在实际生产环境中,可以根据集群规模、网络环境等因素来调整这两个参数的值。如果集群规模较小且网络环境较好,则可以适当缩短心跳间隔和选举超时时间,以减少节点宕机后的恢复时间。如果集群规模较大或者网络环境较差,则可以适当延长心跳间隔和选举超时时间,以避免因网络延迟而频繁发起选举。

 

 

 

在进行调整时,还需要注意避免设置过小的值,因为这可能会导致网络拥塞和CPU过载等问题。一般来说,合理的心跳间隔和选举超时时间可以提高etcd集群的稳定性和性能。

 

 

疑问是不是心跳超时就选举leader:

 

答案:并不是

 

在 etcd 中,心跳超时是一种用于检测节点健康状态的机制。当节点未能及时响应心跳时,其它节点将认为该节点出现了故障,这可能会触发一些自动化的机制,如leader选举和节点重连等。
但是,仅仅是心跳超时并不一定会导致 leader 切换。这取决于 etcd 的具体配置以及节点的状态。如果该节点是 leader 节点,那么心跳超时可能会导致其它节点发起新一轮的 leader 选举,从而导致 leader 切换。如果该节点是 follower 节点,那么心跳超时通常不会导致 leader 切换,因为 follower 节点并不具备成为 leader 节点的资格。
另外,即使一个节点的心跳超时被检测到,它也不一定是故障的原因。在某些情况下,如节点资源紧张或网络延迟等,节点可能会在短时间内无法及时响应心跳。因此,etcd 在进行故障检测和节点状态转移时,通常会综合考虑多种因素,而不是仅仅依赖于心跳超时这一个指标。

 

 

以下是一些可能导致etcd心跳超时的常见原因以及解决方法

 

 

网络问题:etcd集群中的节点需要通过网络通信来发送心跳信号。如果网络不稳定,节点可能无法及时收到其他节点的心跳信号,从而导致心跳超时。解决方法是检查网络连接并确保网络稳定。

 

资源不足:如果etcd集群节点的资源(如内存、CPU等)不足,则可能导致节点无法及时处理心跳信号,从而导致心跳超时。解决方法是检查每个节点的资源使用情况,并根据需要增加节点的资源。

 

节点负载过高:如果某个节点的负载过高,可能会导致节点无法及时处理心跳信号,从而导致心跳超时。解决方法是检查节点的负载情况,并根据需要增加节点数量或优化负载。

 

防火墙问题:如果节点之间的网络连接受到防火墙限制,则可能会导致节点无法及时发送或接收心跳信号,从而导致心跳超时。解决方法是检查防火墙配置并确保允许etcd节点之间的通信。

 

etcd配置问题:如果etcd节点的配置存在问题,则可能会导致节点无法及时发送或接收心跳信号,从而导致心跳超时。解决方法是检查etcd节点的配置并确保其正确。

 

etcd版本不兼容:如果etcd集群中的节点运行不同版本的etcd,则可能会导致心跳超时。解决方法是确保所有节点运行相同版本的etcd。

 

总结:

 

总之,定位etcd心跳超时问题需要综合考虑多种因素。通过检查网络连接、资源使用情况、节点负载、防火墙配置、etcd配置和版本兼容性等方面,可以帮助诊断和解决etcd心跳超时问题。

 

 

那么心跳时间怎么衡量需要改那个参数,为什么?

 

调整这些值是一种权衡。心跳间隔的值建议在成员之间平均往返时间(RTT)的最大值,通常为往返时间的0.5-1.5倍左右。如果心跳间隔太低,etcd 会发送不必要的消息,增加 CPU 和网络资源的使用。另一方面,太高的心跳间隔会导致高选举超时。更高的选举超时需要更长的时间来检测领导者故障。测量往返时间 (RTT) 的最简单方法是使用PING 实用程序

 

就是ping命令最大时间那个值取0.5到1.5倍之间即可

 

选举超时应该根据成员之间的心跳间隔和平均往返时间来设置。选举超时必须至少是往返时间的 10 倍(实际你会发现etcd集群告知为5倍的心跳时间即可),以便它可以解决网络中的差异。例如,如果成员之间的往返时间为 10 毫秒,则选举超时应至少为 100 毫秒。

选举超时的上限为 50000 毫秒(50 秒),仅应在部署全球分布式 etcd 集群时使用。美国大陆的合理往返时间为 130ms,美国和日本之间的时间约为 350-400ms。如果网络性能不均匀或有规律的数据包延迟/丢失,则可能需要重试几次才能成功发送数据包。所以5s是全局往返时间的安全上限。由于选举超时应该比广播时间大一个数量级,对于全球分布式集群大约 5 秒的情况,50 秒成为一个合理的最大值。

一个集群中的所有成员的心跳间隔和选举超时值应该相同。为 etcd 成员设置不同的值可能会破坏集群的稳定性。

 

配置文件如下

[root@host0-1 ~]# cat /etc/etcd/etcd.conf 
ETCD_NAME="etcd_1"
ETCD_DATA_DIR="/opt/etcd_data/etcd"

ETCD_CIPHER_SUITES=TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256,TLS_ECDHE_ECDSA_WITH_CHACHA20_POLY1305,TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384,TLS_ECDHE_RSA_WITH_CHACHA20_POLY1305,TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384,TLS_RSA_WITH_AES_256_GCM_SHA384,TLS_RSA_WITH_AES_128_GCM_SHA256
ETCD_CERT_FILE=/etc/kubernetes/ssl/etcd_server.crt
ETCD_KEY_FILE=/etc/kubernetes/ssl/etcd_server.key
ETCD_TRUSTED_CA_FILE=/etc/kubernetes/ssl/ca.crt
ETCD_CLIENT_CERT_AUTH=true

ETCD_LISTEN_CLIENT_URLS="https://IP:2379,https://127.0.0.1:2379"
ETCD_ADVERTISE_CLIENT_URLS="https://IP:2379,https://127.0.0.1:2379"

ETCD_PEER_CERT_FILE=/etc/kubernetes/ssl/etcd_server.crt
ETCD_PEER_KEY_FILE=/etc/kubernetes/ssl/etcd_server.key
ETCD_PEER_TRUSTED_CA_FILE=/etc/kubernetes/ssl/ca.crt

ETCD_INITIAL_CLUSTER="etcd_1=https://IP:2380,etcd_2=https://IP:2380,etcd_3=https://IP:2380"
ETCD_INITIAL_CLUSTER_STATE="new"
ETCD_INITIAL_CLUSTER_TOKEN="cc34c326-4694-48c6-afdf-c317f40c1847"
ETCD_LISTEN_PEER_URLS="https://IP:2380"
ETCD_INITIAL_ADVERTISE_PEER_URLS="https://IP:2380"
ETCD_HEARTBEAT_INTERVAL=600
ETCD_ELECTION_TIMEOUT=3000