调用 Anoma gRPC 接口报 “node id does not exist“ 怎么排查?
2026/9/12 9:02:10 网站建设 项目流程

调用 Anoma gRPC 接口报 "node id does not exist" 怎么排查?

【免费下载链接】anoma-archiveReference implementation of Anoma项目地址: https://gitcode.com/GitHub_Trending/an/anoma-archive

你启动了一个 Anoma 节点,并通过它的 gRPC 端点发起了请求(例如Anoma.Proto.IntentpoolServiceListIntents/Add),调用返回了GRPC.RPCErrorstatus为 3,消息就是node id does not exist。这个错误说明请求里携带的 node id 并不是你实际连接的那个节点上注册的 id。本文依据本仓库的 USAGE.md 与 gRPC 相关源码,给出核对真实 node id、检查注册表、验证调用的完整排查路径。

这个报错从哪里来

先看服务端处理器 intents.ex:list/2add/2两个处理器在处理请求前各做两步检查:

# validate the request. will raise if not valid. validate_request!(request) # ensure the node id exists if Registry.whereis(request.node.id, IntentPool) == nil do raise_grpc_error!(:invalid_node_id) end

也就是说:请求的node字段非空(第一道校验通过),但Registry.whereis(request.node.id, IntentPool)返回nil—— 该节点上按这个 id 查不到任何 IntentPool 引擎 —— 处理器便抛出invalid_node_id,客户端收到status: 3、消息为node id does not exist的 gRPC 错误。仓库的示例 e_grpc.ex 用node = %Node{id: "wrong"}主动构造了这个场景,并断言返回:

{:error, %GRPC.RPCError{ __exception__: true, message: "node id does not exist", status: 3 }}

所以排查方向是固定的:把“请求里的 node id”和“节点上实际注册的 node id”对上,找出是哪一侧的值不对。

先拿到当前节点真正在用的 node id

按 USAGE.md,节点在 Elixir REPL 中启动,返回的 struct 里带有node_idgrpc_port

iex -S mix iex(1)> node = Anoma.Node.Examples.ENode.start_node() %Anoma.Node.Examples.ENode{ grpc_port: 58447, pid: #PID<0.318.0>, node_id: "2615099" }

上面的端口与node_id是文档示例值,你的环境会不同。两个要点:

  • gRPC 请求里要填的就是这个node_id,它不是固定配置;
  • USAGE.md 称这类节点是 "ephemeral":每次启动都是 clean slate,重启后 node id 会变。如果你拿着上一次启动残留的 id 发请求,就会得到node id does not exist

文档示例环境为 Erlang/OTP 27、Elixir 1.17。如果节点已经在运行,也可以在 REPL 里直接查询(registry.ex):

Anoma.Node.Registry.local_node_id() # 恰好一个节点时 => {:ok, "<node id>"}

该函数没有运行中的节点时返回{:error, :no_node_running},有多个节点时返回{:error, :multiple_nodes}。看到前一个值,说明问题根本不是 id 填错,而是节点没起;看到后一个,则需要逐个核对每个节点的node_id

核对注册表:这个 id 在节点上存在吗

报错路径用的就是Registry.whereis/3,你可以用同一个入口手工验证(registry.ex):

Anoma.Node.Registry.whereis(node_id, Anoma.Node.Intents.IntentPool) # 注册存在时返回 pid,否则返回 nil

返回nil即与 gRPC 处理器看到的情况一致。engines_for/1可以列出某个 id 下注册了哪些引擎(registry.ex),它按允许名单过滤,只可能出现Anoma.Node.Transaction.MempoolAnoma.Node.Intents.IntentPoolClient这三类:

Anoma.Node.Registry.engines_for(node_id)

想一次看全部注册内容用Anoma.Node.Registry.dump_register()(registry.ex)。

检查请求里的 node id 是从哪来的

确认节点侧后,回到请求侧核对它携带的 id 来自哪里:

  • Elixir 客户端:示例 e_grpc.ex 中请求用的节点取自已连接对象:node = %Node{id: client.node.node_id}。核对客户端对象里的node_id是否来自本次启动的节点。
  • REPL 启动的客户端{:ok, client} = Anoma.Client.connect("localhost", node.grpc_port, 50051, node.node_id),第四个参数就是 node id(USAGE.md 示例,客户端监听 50051)。
  • 以二进制启动的客户端:USAGE.md 示例(文档示例值):
./apps/anoma_client/anoma_client --listen-port 50051 --node-host localhost --node-port 63796 --node-id 62831092

--node-id必须是节点自己的node_id--node-port必须是节点的grpc_port,两者都要来自节点启动输出。

  • Postman / grpcurl:消息里的node字段同样要填当前节点 id。可以先用 grpcurl 确认端点上有哪些服务:
grpcurl -plaintext localhost:50051 list

文档示例输出:

Anoma.Proto.IndexerService Anoma.Proto.IntentpoolService Anoma.Proto.NockService

常见根因就两类:请求里的 id 是上一次启动的旧 id;或者你连的根本是另一个节点(多个节点同时运行时尤其容易)。

别和另外两个相似错误混淆

同一文件 e_grpc.ex 的示例测试还覆盖了两个消息相似但原因不同的错误(status均为 3):

错误消息对应场景
node can not be nil请求缺少node字段,未通过validate_request!校验(e_grpc.ex)
intent can not be nilAdd请求没有携带intent字段(e_grpc.ex)
node id does not existnode字段非空,但该 id 在你连接的节点上没有注册为 IntentPool 引擎(intents.ex)

消息是前两个时,修请求字段;是node id does not exist时,按上面的流程核对 id。

验证:用正确的 node id 再发一次

改用当前节点的 node id 后,同一调用不应再返回 RPCError。Elixir 客户端中 e_grpc.ex 的list_intents断言成功时返回{:ok, reply},且意图池为空时reply.intents == []。命令行同样可以发:

grpcurl -plaintext localhost:50051 Anoma.Proto.IntentpoolServiceListIntents

USAGE.md 记录该调用的输出为{}(文档示例)。收到正常响应而不是GRPC.RPCError,即说明 node id 已经对上。如果 grpcurl 提示方法名不识别,可以按文档中列服务方法的方式先执行grpcurl -plaintext localhost:50051 list Anoma.Proto.IntentpoolService查看可用方法再调用。

可选:用仓库测试复现核对

仓库自带能复现该错误路径的示例测试:test/grpc_test.exs 会为 EGRPC 模块的示例函数生成测试,其中包含上文“无效 node id”一例。运行仓库测试(Makefile 的test目标执行mix test):

make test

如果测试通过而你实际调用仍报node id does not exist,就可以排除服务端行为问题,把精力集中在请求携带的 id 值、以及它指向的节点是否是你要用的那个上。

【免费下载链接】anoma-archiveReference implementation of Anoma项目地址: https://gitcode.com/GitHub_Trending/an/anoma-archive

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询