方法与工具 / INTERACTIVE EDITION · ETCD 3.6.6
真实网络分区实验
进程还活着,客户端端口也能连上,但共识节点之间断开了。它还能告诉你什么?
新增可执行实验:真实节点连接分区
首版实验 A 暂停进程;本扩展让三个 etcd 进程始终运行,在每个 Peer 监听端口前放一个自己创建的回环 TCP 代理。分区时关闭跨组既有连接,并拒绝重连。客户端端口始终直接可达。代理从 etcd 3.6.6 首个 HTTP/1 请求头中的 X-Server-From 识别来源,不解释或模拟 Raft 消息。
这是受控的连接分区,不是任意数据包丢失、TLS 代理或生产网络混沌矩阵。不改防火墙、网卡或路由表;每个代理最多 64 条并发连接,并限制缓冲区。
执行前先预测
- 写入基线值,在全部副本上观察到它。
- 把当前 Leader 与另外两个投票者双向隔离。
- 让多数派分区写一个新值。
- 分别以本地
serializable模式和默认线性一致模式读取孤立节点,结果会相同吗? - 恢复连接,比较全部副本。
- 作为对照,把三个投票者分别隔离,同时保持全部进程存活。
预期差异:两个投票者的分区仍可推进;孤立节点本地读可能陈旧;默认读成功需要更强协议。三个进程存活,并不等于存在可达多数派。
运行原创练习
python3 scripts/install_etcd.py
python3 scripts/run_network.py --repeats 3 --out build/my-network.json
python3 scripts/learning_exercises.py recovery
python3 -m unittest discover -s tests -v恢复练习读取已提交的基线报告;自己的新结果写在 build/my-network.json,与基线分离。可在私人工作副本中调整分区组,探索其他调度。基线独立断言返回值和客户端结果;代理 cut 计数仅辅助证明故障范围,不能单凭它证明共识行为。
实际观测及边界
保存的三次重复均保留:所有进程存活;多数派写成功;孤立本地读取为 before-cut;默认读和写结果为 unknown;恢复后全部副本为 majority-committed;三个孤立节点下,写在截止时间内没有成功。超时写会在恢复后核对,不断言它必然回滚。
在真实回放中选择 D · Peer partitions · 完整网络实测 JSON · 哈希清单。
范围限定为一台主机、固定实现和小型故障调度;不证明所有分区历史正确,不测试磁盘丢失或备份还原。原有进程故障、重试和 fencing 基线分别保留,未被本结果替换。
实现与原始资料
lab/peer_proxy.py:独占代理、来源识别、分组策略和清理。scripts/run_network.py:故障调度、独立断言和导出字段。- 固定版本 etcd stream transport:来源与目标请求头。
- etcd 故障模式与 MIT 第 6 讲:协议背景。