理解性能

    etcd 提供稳定的,持续的高性能。两个定义性能的因素:延迟(latency)和吞吐量(throughput)。延迟是完成操作的时间。吞吐量是在某个时间期间之内完成操作的总数量。当 etcd 接收并发客户端请求时,通常平均延迟随着总体吞吐量增加而增加。在通常的云环境,比如 Google Compute Engine (GCE) 标准的 n-4 或者 AWS 上相当的机器类型,一个三成员 etcd 集群在轻负载下可以在低于1毫秒内完成一个请求,并在重负载下可以每秒完成超过 30000 个请求。

    etcd 使用 Raft 一致性算法来在成员之间复制请求并达成一致。一致性性能,特别是提交延迟,受限于两个物理约束:网络IO延迟和磁盘IO延迟。完成一个etcd请求的最小时间是成员之间的网络往返时延(Round Trip Time / RTT),加需要提交数据到持久化存储的 fdatasync 时间。在一个数据中心内的 RTT 可能有数百毫秒。在美国典型的 RTT 是大概 50ms, 而在大陆之间可以慢到400ms. 旋转硬盘(注:指传统机械硬盘)的典型 fdatasync 延迟是大概 10ms。对于 SSD 硬盘, 延迟通常低于 1ms. 为了提高吞吐量, etcd 将多个请求打包在一起并提交给 Raft。这个批量策略让 etcd 在重负载试获得高吞吐量.

    有其他子系统影响到 etcd 的整体性能。每个序列化的 etcd 请求必须通过 etcd 的 boltdb支持的(boltdb-backed) MVCC 存储引擎,它通常需要10微秒来完成。etcd 定期递增快照它最近实施的请求,将他们和之前在磁盘上的快照合并。这个过程可能导致延迟尖峰(latency spike)。虽然在SSD上这通常不是问题,在HDD上它可能加倍可观察到的延迟。而且,进行中的压缩可以影响 etcd 的性能。幸运的是,压缩通常无足轻重,因为压缩是错开的,因此它不和常规请求竞争资源。RPC 系统,gRPC,为 etcd 提供定义良好,可扩展的 API,但是它也引入了额外的延迟,尤其是本地读取。

评测

    可以通过 etcd 自带的 benchmark CLI 工具来评测 etcd 的性能.

3节点硬件配置

  • Google Cloud Compute Engine

  • 3 machines of 8 vCPUs + 16GB Memory + 50GB SSD

  • 1 machine(client) of 16 vCPUs + 30GB Memory + 50GB SSD

  • Ubuntu 17.04

  • etcd 3.2.0, go 1.8.3

使用这些配置,etcd 能近似的写入:

key的数量

Key的大小

Value的大小

连接数量

客户端数量

目标 etcd 服务器

平均写入 QPS

每请求平均延迟

内存

10,000

8

256

1

1

leader only

583

1.6ms

48 MB

100,000

8

256

100

1000

leader only

44,341

22ms

124MB

100,000

8

256

100

1000

all members

50,104

20ms

126MB

示例命令:

# 写向leader

benchmark --endpoints=${HOST_1} --target-leader --conns=1 --clients=1 \

    put --key-size=8 --sequential-keys --total=10000 --val-size=256 

benchmark --endpoints=${HOST_1} --target-leader  --conns=100 --clients=1000 \

    put --key-size=8 --sequential-keys --total=100000 --val-size=256

# 写向所有成员

benchmark --endpoints=${HOST_1},${HOST_2},${HOST_3} --conns=100 --clients=1000 \

    put --key-size=8 --sequential-keys --total=100000 --val-size=256

    为了一致性,线性化(Linearizable)读取请求要通过集群成员的法定人数来获取最新的数据。串行化(Serializable)读取请求比线性化读取要廉价一些,因为他们是通过任意单台 etcd 服务器来提供服务,而不是成员的法定人数,代价是可能提供过期数据。etcd 可以读取:

请求数量

Key 大小

Value 大小

连接数量

客户端数量

一致性

每请求平均延迟

平均读取 QPS

10,000

8

256

1

1

Linearizable

1,353

0.7ms

10,000

8

256

1

1

Serializable

2,909

0.3ms

100,000

8

256

100

1000

Linearizable

141,578

5.5ms

100,000

8

256

100

1000

Serializable

185,758

2.2ms

示例命令:

# 单客户端读benchmark --endpoints=${HOST_1},${HOST_2},${HOST_3} --conns=1 --clients=1 \

    range YOUR_KEY --consistency=l --total=10000 

benchmark --endpoints=${HOST_1},${HOST_2},${HOST_3} --conns=1 --clients=1 \

    range YOUR_KEY --consistency=s --total=10000

# 多客户端并发读

benchmark --endpoints=${HOST_1},${HOST_2},${HOST_3} --conns=100 --clients=1000 \

    range YOUR_KEY --consistency=l --total=100000 

benchmark --endpoints=${HOST_1},${HOST_2},${HOST_3} --conns=100 --clients=1000 \

    range YOUR_KEY --consistency=s --total=100000

当在新的环境中第一次搭建 etcd 集群时,我们鼓励运行评测测试来保证集群达到足够的性能;集群延迟和吞吐量对微小的环境差异会很敏感。


官网原文地址:https://github.com/etcd-io/etcd/blob/master/Documentation/op-guide/performance.md

参考翻译文章:https://skyao.gitbooks.io/learning-etcd3/content/documentation/op-guide/performance.html