Erlang erl_call导致gen_server模块退出

ErJ*_*Jab 9 erlang

我有一个genserver模块,我需要将其作为在后台运行的服务器启动.在开发过程中,我使用标准的erl终端来启动它

$erl
Erlang R13B01 (erts-5.7.2) [source] [smp:2:2] [rq:2] [async-threads:0] [hipe] [kernel-poll:false]

Eshell V5.7.2  (abort with ^G)
1> myserver:start_link().
<ok, some_pid>
Run Code Online (Sandbox Code Playgroud)

一切都很好,我能够从其他模块调用服务器.

现在,我需要连续运行它作为服务器并偶然发现erl_call函数.所以现在我做:

erl_call -d -s -a 'myserver start_link' -sname myserver_node
Run Code Online (Sandbox Code Playgroud)

但是,服务器启动,但会自动关闭.我启用-d标志以查看出错的地方.这是我在调试跟踪文件中看到的:

===== Log started ======
Fri Oct  2 04:42:32 2009

erl_call: sh -c exec erl -noinput -sname myserver_node -s erl_reply reply 174.143.175.70 42457 5882

=ERROR REPORT==== 2-Oct-2009::04:44:05 ===
** Generic server myserver terminating
** Last message in was {'EXIT',<0.59.0>,normal}
** When Server state == {20499,24596,28693,32790,36887,40984,45081}
** Reason for termination ==
** {function_clause,[{myserver,terminate,
                               [normal,
                                {20499,24596,28693,32790,36887,40984,45081}]},
                     {gen_server,terminate,6},
                     {proc_lib,init_p_do_apply,3}]}
Run Code Online (Sandbox Code Playgroud)

知道是什么导致服务器自动关闭吗?跟踪甚至说终止的原因是正常的.但我没有发起终止.

arc*_*lus 12

erl_call使用rpcerlang节点上的函数来完成它的工作 - 与连接到的另一个erlang节点erl_call -sname Node M F A相同.rpc:call(Node, M, F, A)Node

rpc:call产生一个执行M:F(A)你要求它的进程,所以在你的情况下它会产生一个执行my_server:start_link()然后退出的进程.因为my_server它与rpc进程相关联,所以它将在rpc进程执行时退出 - rpc进程链接到进程并向进程发送退出信号my_server.您可以在错误报告中看到它:Last message in was {'EXIT',<0.59.0>,normal}- 这rpc是关闭您的进程的进程的退出信号my_server.

我怀疑你要么打电话my_server:start(),要么my_server不会与rpc过程挂钩,并且会在rpc退出流程后继续存在.更好的是,创建一个OTP应用程序,my_app以及my_supmy_server节点启动时开始的顶级管理程序.


Adam还指出你的终止函数不处理terminate(normal, {20499,24596,28693,32790,36887,40984,45081})大小写并在my_server关闭时崩溃.


Ada*_*erg 5

服务器正在退出,因为有人告诉它这样做,这就是为什么你看到这个:

Last message in was {'EXIT',<0.59.0>,normal}
Run Code Online (Sandbox Code Playgroud)

它可能来自gen_server本身,或者通过向它发送退出消息,如下所示:

exit(PidOfServer, normal)
Run Code Online (Sandbox Code Playgroud)

terminate/2的gen_server中的函数似乎有问题,因为它不接受给它的参数(如果它们是有效的,那就是).这就是你崩溃的原因.

** {function_clause,[{myserver,terminate,
                           [normal,
                            {20499,24596,28693,32790,36887,40984,45081}]},
                 {gen_server,terminate,6},
                 {proc_lib,init_p_do_apply,3}]}
Run Code Online (Sandbox Code Playgroud)