handle_call/3 of behavior(gen_server), Erlang/OTP 的递归调用超时错误
Timeout error in recursive call of handle_call/3 of behaviour(gen_server), Erlang/OTP
我试图在回复之前对 handle_call/3 进行递归调用。
但是好像不行,因为会抛出timeout
退出异常。
您可以在下面看到代码和错误。
代码:
-module(test).
-behavior(gen_server).
%% API
-export([start_link/0,init/1,handle_info/2,first_call/1,second_call/1, handle_call/3, terminate/2]).
-record(state, {whatever}).
start_link() ->
gen_server:start_link({local, ?MODULE}, ?MODULE, [], []).
init(_Args) ->
{ok, #state{}}.
handle_info(Data, State) ->
{noreply, State}.
% synchronous messages
handle_call(_Request, _From, State) ->
case _Request of
first_call ->
{reply, data1, State};
second_call ->
{reply, {data2, first_call(self())}, State}
end.
first_call(Pid) ->
gen_server:call(Pid, first_call).
second_call(Pid) ->
gen_server:call(Pid, second_call).
terminate(_Reason, _State) ->
ok.
错误:
2> {_, PID} = test:start_link().
{ok,<0.64.0>}
3> test:second_call(PID).
** exception exit: {timeout,{gen_server,call,[<0.64.0>,second_call]}}
in function gen_server:call/2 (gen_server.erl, line 204)
此行为的一个可能原因是 gen_server 在第一个完成之前无法处理递归调用(造成死锁)。这是正确的理由吗?如果是,为什么?
谢谢。
是的,就是这个原因。 gen_server 是一个单独的进程,当 handle_call
正在执行时,它不会接收任何消息,也不会响应任何 gen_server:call
。因此 first_call(self())
超时。
我试图在回复之前对 handle_call/3 进行递归调用。
但是好像不行,因为会抛出timeout
退出异常。
您可以在下面看到代码和错误。
代码:
-module(test).
-behavior(gen_server).
%% API
-export([start_link/0,init/1,handle_info/2,first_call/1,second_call/1, handle_call/3, terminate/2]).
-record(state, {whatever}).
start_link() ->
gen_server:start_link({local, ?MODULE}, ?MODULE, [], []).
init(_Args) ->
{ok, #state{}}.
handle_info(Data, State) ->
{noreply, State}.
% synchronous messages
handle_call(_Request, _From, State) ->
case _Request of
first_call ->
{reply, data1, State};
second_call ->
{reply, {data2, first_call(self())}, State}
end.
first_call(Pid) ->
gen_server:call(Pid, first_call).
second_call(Pid) ->
gen_server:call(Pid, second_call).
terminate(_Reason, _State) ->
ok.
错误:
2> {_, PID} = test:start_link().
{ok,<0.64.0>}
3> test:second_call(PID).
** exception exit: {timeout,{gen_server,call,[<0.64.0>,second_call]}}
in function gen_server:call/2 (gen_server.erl, line 204)
此行为的一个可能原因是 gen_server 在第一个完成之前无法处理递归调用(造成死锁)。这是正确的理由吗?如果是,为什么? 谢谢。
是的,就是这个原因。 gen_server 是一个单独的进程,当 handle_call
正在执行时,它不会接收任何消息,也不会响应任何 gen_server:call
。因此 first_call(self())
超时。