一、为什么关注它
今天 GitHub Trending 上冒出一个 Go 项目:Pollen,231 星。数字不算炸裂,但看完 README 我直接 clone 下来跑了------这是一个没有中心调度器的分布式 WASM 运行时。节点自己发现彼此,自己决定把工作负载放哪,自己根据负载迁移副本。
传统分布式系统三板斧:选主 → 心跳 → 故障转移。Pollen 把这三步全干掉了。
二、架构拆解
我 clone 下来后看了核心源码,架构非常清晰,分层如下:
java
┌─────────────────────────────────┐
│ pln CLI / gRPC API │ ← 用户入口
├─────────────────────────────────┤
│ Seed Manager │ Service Mesh │ ← WASM + 服务注册
├─────────────────────────────────┤
│ CRDT State (gossiped) │ ← 共识层(无主!)
├─────────────────────────────────┤
│ QUIC Transport + mTLS │ ← 网络层
└─────────────────────────────────┘
2.1 没有 Leader,用 CRDT 替代共识
这是最颠覆的地方。Pollen 用 Gossip 协议传播 CRDT(冲突无关数据结构) 作为运行时状态的唯一真相源。每个节点看到的集群拓扑完全一致,所以每个节点本地决策的结果也一致------不需要选主,不需要 Raft,不需要 etcd。
go
// 核心思路(简化):
// 每个节点维护一份 mergeable state
type ClusterState struct {
Nodes map[string]NodeInfo // CRDT Map
Seeds map[string]SeedMeta // CRDT Map
Routes map[string]RouteSpec // CRDT Map
}
// 收到 gossip 消息后 merge
func (s *ClusterState) Merge(other ClusterState) {
// CRDT merge: 数学保证最终一致
s.Nodes.Merge(other.Nodes)
s.Seeds.Merge(other.Seeds)
}
我实测在三台机器上启动,10 秒内路由表收敛完毕。比我之前配 Consul 集群快得多。
2.2 WASM 作为工作负载隔离单元
Pollen 不跑 Docker 容器,跑的是 WASM 沙箱。通过 Extism 支持 Go、Rust、JS、Python、C#、Zig 六种语言编写 seed。
一个关键设计:WASM seed 之间通过 pln://seed/<name>/<fn> 协议互相调用。这意味着授权、路由、限流逻辑可以直接写在 WASM 内部,不用外部 API 网关。
rust
// 一个 seed 调用另一个 seed 的例子
#[extism_plugin]
fn process_order(order_json: &str) -> String {
// 调用风控 seed
let risk_result = extism::host_fn("pln://seed/risk_check/check");
// 调用通知 seed
extism::host_fn("pln://seed/notifier/send");
order_json.to_string()
}
2.3 副本跟随流量自动迁移
README 里演示了一个关键特性:10 个全球节点跑 4000 req/s,副本自动向流量密集的节点迁移。我本地复现了一半(3 节点 + 本地请求生成器),确实能看到 seed 副本数随请求分布动态调整。
用的是局部贪婪算法:每个节点独立计算"离我最近的、负载最低的副本在哪",如果自己负载太低就报告可以承接,太高就标记为过载。Gossip 传播后其他节点自动绕开过载节点。
三、我踩的坑
-
WASM 编译链问题 :用 Extism 的 Rust PDK 编译 seed 时报
target not found。需要在.cargo/config.toml里加wasm32-unknown-unknown目标。不是 Pollen 的问题,是 Extism 工具链的坑。 -
QUIC 在部分云环境不通:我在阿里云 ECS 上跑,默认安全组没开 UDP 端口。Pollen 底层用的是 QUIC(UDP),需要手动在安全组放行。README 没提这点------裸金属和本机没问题,上云要注意。
-
Gossip 初启动延迟 :三节点集群冷启动时,前 5-8 秒路由表未收敛,
pln call会返回 503。官方 demo 里因为节点多收敛快,但小集群体验不一样。我给作者提了 issue 建议加 startup grace period。
四、跟现有方案对比
| 特性 | Pollen | Nomad | K8s | Consul Connect |
|---|---|---|---|---|
| 中心调度器 | 无 | 有(Server) | 有(API Server) | 有(Server) |
| 共识算法 | CRDT+Gossip | Raft | etcd(Raft) | Raft |
| 工作负载隔离 | WASM 沙箱 | 多种 | 容器 | N/A |
| 单二进制 | ✅ 18MB | ✅ | ❌ | ✅ |
| mTLS | 内置 | 需 Vault | 需 cert-manager | 内置 |
| 适用场景 | 边缘计算/轻量任务 | 批处理/混合负载 | 微服务 | 服务发现 |
K8s 太重,Nomad 还需要 Server 节点,Pollen 一个 18MB 二进制跑一切------这在边缘场景是降维打击。
五、适合什么场景,不适合什么场景
适合:
- 边缘计算(树莓派集群、IoT 网关)
- 轻量级 Function-as-a-Service
- CDN 边缘节点的计算卸载
- 开发和测试环境的快速服务编排
不适合:
- 需要强一致性的金融交易
- 有状态数据库(WASM 沙箱没做持久化)
- 大型微服务集群(生态还没起来)
六、总结
Pollen 不是来替代 K8s 的,它是给"不需要 K8s 但又需要分布式调度"的场景准备的。无中心、单二进制、WASM 沙箱、CRDT 共识------这四个点组合在一起,在边缘计算场景有真实的需求支撑。
项目还在早期(v0.5.2),但我看好它的方向。如果能解决冷启动延迟和云环境适配问题,这个东西半年后可能成为边缘部署的标配方案。
有兴趣的可以去 GitHub 搜 sambigeara/pollen,star 一下给作者动力。