轻量可靠可扩展的分布式任务调度系统:基于etcd实现服务注册与元数据协调,grpc通信,lease+watch保障容错;scheduler单点多活,worker主动注册续租,etcd统一存储三类任务数据,通过txn+watch闭环处理“谁在干活”“任务发给谁”“失败了怎么办”。

核心设计思路:轻量、可靠、可扩展
不依赖复杂中间件,用 Go 原生能力构建调度中心主体:基于 etcd 做服务注册与任务元数据协调,用 gRPC 实现 Worker 与 Scheduler 通信,通过 Lease + Watch 机制保障节点存活与任务容错。重点不是功能堆砌,而是把“谁在干活”“任务发给谁”“失败了怎么办”三件事闭环。
关键组件职责划分
Scheduler(调度器):单点逻辑(可多活,但同一时刻仅一个 Active),负责从 etcd 读取待执行任务、根据 Worker 心跳状态筛选可用节点、按策略(如轮询或负载权重)分发任务、监听任务执行结果并更新状态。
Worker(执行节点):主动向 etcd 注册自身信息(IP、CPU/内存快照、标签等),定期续租 Lease;监听 etcd 中分配给自己的任务路径,拉取后执行,完成后上报结果或失败原因。
etcd 集群:统一存储三类数据——/workers/{id}(带 Lease)、/tasks/pending(队列式 key)、/tasks/running/{task_id}(临时任务锁)、/tasks/history/{task_id}(归档结果)。所有协调均通过 CompareAndDelete / Txn + Watch 完成,避免竞态。
任务生命周期与容错处理
一个任务从创建到完成需经历:提交 → 入 pending → 被 Scheduler 拣选 → 分配到 Worker → Worker 创建 running 锁 → 执行 → 上报 → 清理锁与 pending 记录。任一环节中断都需自动兜底:
- Worker 意外退出:etcd Lease 自动过期,Scheduler Watch 到 workers 删除事件,立即回收其 running 中的任务,重新入 pending
- 任务执行超时:Scheduler 启动定时协程扫描 /tasks/running/ 下过期(如 5 分钟无更新)的 task_id,触发重调度
- Scheduler 故障:借助 etcd 的 leader election(使用 Session + Mutex),新当选 leader 自动接管 pending 队列,无需人工干预
Go 实现要点提示
用 go.etcd.io/etcd/client/v3 操作键值与 Lease;gRPC 接口定义尽量精简——SubmitTask、FetchNextTask、ReportResult 三个核心方法足矣;Worker 端用 clientv3.NewKeepAliveChannel 维持心跳;Scheduler 对每个任务分发做 context.WithTimeout 控制 RPC 阻塞;所有 etcd 写操作务必加 Revision 检查或 Txn 断言,防止覆盖写。
golang免费学习笔记(深入):立即使用
在学习笔记中,你将探索golang的核心概念和高级技巧!











