Erlang:如何使用 gproc

Erlang: how to use gproc

我对 gproc 和 Pub/Sub 方法 (https://github.com/uwiger/gproc#use-case-pubsub-patterns) 有点困惑。 我不明白如何从另一个进程接收消息。

示例:

    -module(ws_handler).
    -export([init/2]). 

 init(Req, Opts) ->
    lager:info("WS: init ws handler"),
    gproc:reg({p, l, {?MODULE, WSNewMsgKey}}),
    {cowboy_websocket, Req, Opts}.

 process_data(Data) ->
    lager:info("WS: start processing of json data"),
    gproc:send({p, l, WSNewMsgKey}, {self(), WSNewMsgKey, Data}).

有2个进程,都注册为订阅者。他们应该彼此共享传入的数据。我想我必须实施一些 interface/function 但文档没有说明具体是哪个。

我从来没有为此使用过 gproc,但它确实似乎缺少两件事:WSNewMsgKey 的定义(它从未在上面的代码段中的范围内)和某处接受子句的接收子句已发送消息:

-module(ws_handler).
-export([init/2]). 

init(Req, Opts) ->
    gproc:reg({p, l, {?MODULE, ws_event}}),
    {some_state_blah, Req, Opts}.

notify_peers(Event) ->
    gproc:send({p, l, ws_event}, {self(), ws_event, Event}).

...以及其他地方

handle_info({From, ws_event, Event}, State) ->
    ok = handle_ws_event(From, Event).

或在您的循环中(如果您手动编写流程):

loop(State) ->
  receive
    {From, ws_event, Event} ->
        ok = handle_ws_event(From, Event),
        loop(State);
    Whatever ->
        % other stuff...
  end.

我不确定发送的消息是通过呼叫、转换还是普通消息发送(我假设是 OTP 通用转换或普通消息)-- 但它似乎这是应该发生的事情。但是,在所有情况下,您都需要一个定义明确的键来标识所发送消息的类别,这里我使用原子 'ws_event' 来明确表示。

至于上面代码片段的详细信息...您似乎同时向一堆进程广播相同的 JSON 消息以进行某种处理?我不确定这对你有什么用——我想不出广播原始 JSON 有什么好处(除非可能需要广播 JSON系统并且您正在广播到一堆订阅的客户端套接字处理程序?)。所以我对上下文感到困惑(你想达到什么目的?)。

这似乎是文档打算使用它的方式 -- 但我必须实际使用它才能确定。