《轻松实现可伸缩性,容错性,和负载平衡的大规模多人在线系统》一文里面对“Erlang的分布式进程组(Distributed Named Process Groups)”大吹特吹,就是说的pg2这个module。文档那里虽然写了支持分布式节点,但是并没有说如何如何,只提供了一个join(Name, Pid)。
看了一下openpoker的源码,原来很简单,对于连接上的node,用 which_groups() 多调用几次就可以同步过来了:
主节点先创建一个Group:
1. (foo@localhost)1> pg2:create(group).
2. ok
3. (foo@localhost)2> pg2:get_members(group).
4. []
5. (foo@localhost)3> pg2:join(group, self()).
6. ok
7. (foo@localhost)4> pg2:get_members(group).
8. [<0.35.0>]
其他节点先连上主节点,然后调用pg2:which_groups().
1. (bar@localhost)1> net_adm:ping('foo@localhost').
2. pong
3. (bar@localhost)2> pg2:which_groups().
4. []
5. (bar@localhost)3> pg2:which_groups().
6. [group]
7. (bar@localhost)4> pg2:join(group, self()).
8. ok
已经加入了:
1. (foo@localhost)5> pg2:get_members(group).
2. [<4835.35.0>,<0.35.0>]
使用就是那么简单。但是在pg2的底层实现上,使用了ets,global等模块,下次继续研究。
注:正如它的名称所暗示的 pg2 可以用于管理成组 process 的场景,如:每一个 game session 是一个 process ,由这些 process 形成一个 group ,那么你可以通过这个 group 获取 session 的数目(eg. 在线人数),即便你的 session counter process 死掉,那么在它被自动恢复的时候,可以连上 group 并从中找回 session 数目。