回答两个方向性问题:① 我们与 aastar-sdk 的关系/防循环切割;② 未来演进到 Go/Rust,达成 Node/Go/Rust 三实现并行,现在必须提前设计什么、阻塞在哪。核心论点:节点的产品是「协议契约」,不是「代码」——这一条同时解决①和②。
A. 与 SDK 的关系:单向、无环(现状已干净,需固化)
事实核查(已验证):
- 本节点
package.json 对 @aastar/* 零依赖(纯 ethers/@noble/nest)。
- aastar-sdk 不把本节点当包依赖;它在
@aastar/core 自带 DVT 客户端实现(dvtActions / DVTClient / dvt-wire-format.md / blsSigner.dvt / bls-signature-service / weighted-signature-service),经 HTTP 调本节点。
- ⇒ 当前不存在循环。
要固化的切割原则(单向依赖):
SDK / 协调器 / 任何客户端 ──HTTP──▶ aNode(服务端)
(client) (server, 叶子)
aNode 永不 import @aastar/*;永不反向依赖 SDK。
- 规则1:节点
package.json 禁止出现任何 @aastar/*(可加一条 CI lint 守门)。
- 规则2:节点自带自己的 DTO/类型,不为了省事去依赖 SDK 的类型。
- 规则3:若 Phase 2 节点要"够签即发 bundler",用直连 RPC,不要用 SDK 提交(否则就成环)。
- 规则4:共享的是契约,不是代码——
docs/design/dvt-node-protocol.md(本仓库)与 SDK 的 dvt-wire-format.md 必须同源/对齐(理想是一份 canonical spec,另一份引用)。SDK 里重复实现签名/聚合是好事(独立实现 = 互为一致性校验),前提是二者逐字节对齐(靠下面的 conformance 向量保证)。
- ⚠️ 待对齐:SDK 有
weighted-signature-service(加权门限?),本节点目前是等权聚合——这是一个契约差异点,需在协议 spec 里明确是否支持 weighted,避免两边语义漂移。
B. 演进到 Go / Rust:Node/Go/Rust 三实现并行,现在必须做的前置设计
第一性原理:三种语言实现是"合法的同一个 aNode"当且仅当它们通过同一套 conformance 测试。所以要并行,先把"代码无关的契约"冻结成产品。
现在必须锁定(否则就是阻塞)
- 语言无关的规范协议 spec(已有雏形
docs/design/dvt-node-protocol.md + golden vector,需提升为唯一真相源):BLS12-381、DST _POP_、EIP-2537 G1/G2 字节布局、聚合(G2 点加)、nodeId/注册 slot 位序、[nodeIds][blsSig] wire、userOpHash 派生(EntryPoint.getUserOpHash)、Stage1 owner-auth(EIP-191 / 403 fail-closed)、Stage2 策略(IPolicyRegistry ABI + 本地规则)、确认/通知/限流契约。
- OpenAPI 作为 REST 真相源(已有 Swagger):
/signature/sign|aggregate|verify、/node/*、/signature/confirm 的请求/响应 schema,语言无关。
- 跨语言 conformance 向量(golden fixtures,JSON) —— 最关键的防漂移骨架:
userOp → userOpHash → hashToCurve(msg, DST=_POP_) 点 → 各 key 签名 → 聚合 → 链上 validate=0。建 conformance/ fixtures 目录 + 每语言一个 runner,三实现都必须过。我们已有 hash_to_curve golden vector,要在写 Go/Rust 之前把它固化成共享 fixtures。
- BLS 库一致性预验证(最高密码学风险):noble(JS) vs gnark-crypto / kilic-bls12-381(Go) vs blst / arkworks(Rust)。RFC 9380 hash-to-curve +
_POP_ DST 覆盖必须逐字节一致(noble 默认 _NUL_ 必须覆盖,各库都有自己的 DST/编码坑)。承诺并行前,先证三库对 golden fixtures 产出相同聚合 + 链上 validate=0。
- Gossip 互操作决策(真实阻塞,需拍板):三实现是否要在同一个 gossip 集群里互相发现?
- 若是 → gossip wire 协议必须规范化且跨语言实现(难;旧 Go 节点用 memberlist,我们用自研 SWIM/WS,二者不通)。
- 若否(推荐) → 跨语言互操作只发生在签名 + 聚合 + 链上层:协调器经 HTTP 收集各节点签名,与节点语言无关;gossip 退化为每部署内部实现,可各语言自便。这一刀把风险砍掉绝大半。
node_state.json 格式(BLS 私钥 + 身份):语言无关 JSON,需明确 key 编码,要么可互读、要么明确"不共享 state"。
- 配置/env 契约:
ENTRY_POINT_ADDRESS / POLICY_* / *_ENABLED 等命名语义三实现一致。
可以各语言不同(不是阻塞)
Web 框架(NestJS / Go Gin / Rust axum)、内部模块结构、存储、gossip 实现细节(若独立集群)、语言习惯。
组织内已有的 Go/Rust 起点(来自归档)
建议落地顺序
- 冻结 协议 spec + OpenAPI + conformance fixtures(Node.js 作参考实现)。
- 在 Go & Rust 各选 BLS 库,对 fixtures 跑通一致性(只验密码学层,不写整服务)。
- 通过后再按 OpenAPI 实现各语言整服务,以 conformance 为验收。
- 因为 A 的无环 HTTP 边界,SDK/协调器对三实现一视同仁 → 天然 drop-in。
关联:#45(aNode monorepo 整合)· #59/#60 · #61/#62 · #50(KMS 也需跨语言抽象)。
A. 与 SDK 的关系:单向、无环(现状已干净,需固化)
事实核查(已验证):
package.json对@aastar/*零依赖(纯 ethers/@noble/nest)。@aastar/core自带 DVT 客户端实现(dvtActions/DVTClient/dvt-wire-format.md/blsSigner.dvt/bls-signature-service/weighted-signature-service),经 HTTP 调本节点。要固化的切割原则(单向依赖):
package.json禁止出现任何@aastar/*(可加一条 CI lint 守门)。docs/design/dvt-node-protocol.md(本仓库)与 SDK 的dvt-wire-format.md必须同源/对齐(理想是一份 canonical spec,另一份引用)。SDK 里重复实现签名/聚合是好事(独立实现 = 互为一致性校验),前提是二者逐字节对齐(靠下面的 conformance 向量保证)。weighted-signature-service(加权门限?),本节点目前是等权聚合——这是一个契约差异点,需在协议 spec 里明确是否支持 weighted,避免两边语义漂移。B. 演进到 Go / Rust:Node/Go/Rust 三实现并行,现在必须做的前置设计
第一性原理:三种语言实现是"合法的同一个 aNode"当且仅当它们通过同一套 conformance 测试。所以要并行,先把"代码无关的契约"冻结成产品。
现在必须锁定(否则就是阻塞)
docs/design/dvt-node-protocol.md+ golden vector,需提升为唯一真相源):BLS12-381、DST_POP_、EIP-2537 G1/G2 字节布局、聚合(G2 点加)、nodeId/注册 slot 位序、[nodeIds][blsSig]wire、userOpHash派生(EntryPoint.getUserOpHash)、Stage1 owner-auth(EIP-191 / 403 fail-closed)、Stage2 策略(IPolicyRegistry ABI + 本地规则)、确认/通知/限流契约。/signature/sign|aggregate|verify、/node/*、/signature/confirm的请求/响应 schema,语言无关。userOp → userOpHash → hashToCurve(msg, DST=_POP_) 点 → 各 key 签名 → 聚合 → 链上 validate=0。建conformance/fixtures 目录 + 每语言一个 runner,三实现都必须过。我们已有 hash_to_curve golden vector,要在写 Go/Rust 之前把它固化成共享 fixtures。_POP_DST 覆盖必须逐字节一致(noble 默认_NUL_必须覆盖,各库都有自己的 DST/编码坑)。承诺并行前,先证三库对 golden fixtures 产出相同聚合 + 链上 validate=0。node_state.json格式(BLS 私钥 + 身份):语言无关 JSON,需明确 key 编码,要么可互读、要么明确"不共享 state"。ENTRY_POINT_ADDRESS/POLICY_*/*_ENABLED等命名语义三实现一致。可以各语言不同(不是阻塞)
Web 框架(NestJS / Go Gin / Rust axum)、内部模块结构、存储、gossip 实现细节(若独立集群)、语言习惯。
组织内已有的 Go/Rust 起点(来自归档)
AnotherAirAccountCommunityNode(memberlist gossip、go-webauthn、BN254 BLS)→ [archive] 旧版 Go aNode (AnotherAirAccountCommunityNode) 营养归档 — 架构/密码学/passkey/P2P 经验(源仓库已 archived, 可能删除) #59/[direction] 旧 aNode 借鉴行动清单 — provider 抽象/schema 标注/passkey-relay/插件化 评估(采用-评估-跳过) #60。AAStarCommunity/aNode的relay-server/src/core(gas_estimator/paymaster/policy_engine/types)→ [archive] AAStarCommunity/aNode 营养归档 — 四阶段 aNode 愿景/Rust relay/策略系统/KMS/管道(仓库将 transfer 给个人) #61/[direction] AAStarCommunity/aNode 借鉴清单 — KMS signer/层级策略/可插拔管道/安全过滤 + 4阶段愿景(采用-评估-跳过) #62,可作 Rust 版 DVT 节点的骨架候选。建议落地顺序
关联:#45(aNode monorepo 整合)· #59/#60 · #61/#62 · #50(KMS 也需跨语言抽象)。