收集有关 simple_one_for_one 工作人员的信息

发布于 2024-11-17 13:11:02 字数 370 浏览 3 评论 0原文

我有一个主管(叫爱丽丝),他启动了一群“一劳永逸”的工作人员。现在我想了解所有作品的一些信息。例如,假设工作人员是 TCP 服务器,我想获取工作人员使用的所有端口号,或连接到这些工作人员的所有远程地址。我应该把这个功能放在哪里?

Supervisor 没有 gen_server 功能,无法接听电话。所以,在我看来,最合理的方法是有另一个主管(称为 bob),它产生主管 alice 和另一个 gen_server(charile),它通过调用主管:which_children(alice)然后询问来实现像 {get, ports_used_by_alices_workers} 这样的调用每个爱丽丝的孩子都是它的端口。所以,查理是爱丽丝的兄弟姐妹,接听有关爱丽丝孩子的电话。可以吗?或者有更优雅的方法吗?

I have a supervisor (called alice) which starts a bunch of_one_for_one workers. Now I'd like to get some info about all of the works together. For instance, let's say workers are TCP servers and I'd like to get all port numbers used by workers, or all remote addresses which are connected to those workers. Where should I put this functionality?

Supervisor doesn't have gen_server functionality and cannot answer calls. So, it seems to me, the most reasonable way is to have another supervisor (called bob) which spawns supervisor alice and another gen_server (charile) which implements calls like {get, ports_used_by_alices_workers} by calling supervisor:which_children(alice) and then asking each alice's child for it's port. So, charile is alice's sibling and answers calls about alice's children. Is that OK? Or is there a more elegant way of doing this?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

屋檐 2024-11-24 13:11:02

您不需要单独的进程来收集此信息 - 您可以让任何想要端口信息的人自己收集这些信息,方法是使用 supervisor:which_children/1 获取子项列表,然后查询每个子项。提供执行此操作的 API 函数,但让该函数在调用者的进程中运行。

或者,您可以走无文档记录(并且保修无效)的路线,在 erlang 的内部进行探索以获取您想要的信息,而无需与孩子们交谈:

[{Child, 
  %% Query linked port for socket information
  [{Link, prim_inet:sockname(Link),
          prim_inet:peername(Link)}
    || %% get list of linked process and ports for process 'Child'
       Link <- element(2, process_info(Child, links)),
       %% filter down to linked ports.
       is_port(Link)] 
  }
 %% Map over all children of the supervisor 'Sup'.
 || Child <- [Pid || {_,Pid,_,_} = supervisor:which_children(Sup)] 
 ]

您可以了解 < 的源代码中可用的信息a href="https://github.com/erlang/otp/blob/master/lib/kernel/src/inet.erl#L1170" rel="nofollow">inet:i/0。

You don't need a separate process to collect this information - you can just let whoever wants the port information collect it themselves by getting the list of children with supervisor:which_children/1 and then querying each child. Provide an API function that does this, but let that function run in the caller's process.

Alternately, you could go the undocumented (and warranty voiding) route, and poke around in the guts of erlang to get the information you want without talking to the children at all:

[{Child, 
  %% Query linked port for socket information
  [{Link, prim_inet:sockname(Link),
          prim_inet:peername(Link)}
    || %% get list of linked process and ports for process 'Child'
       Link <- element(2, process_info(Child, links)),
       %% filter down to linked ports.
       is_port(Link)] 
  }
 %% Map over all children of the supervisor 'Sup'.
 || Child <- [Pid || {_,Pid,_,_} = supervisor:which_children(Sup)] 
 ]

You can get an idea of the information available in the source for inet:i/0.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文