在OTP的源代碼中,我發現了一個陌生的behaviour,名爲supervisor_bridge
。它的做用是什麼,和普通的supervisor又有什麼區別呢?函數
因而我找到了supervisor_bridge.erl
這個文件。ui
首先它是一個gen_server.code
-module(supervisor_bridge). -behaviour(gen_server). -include("logger.hrl"). %% External exports -export([start_link/2, start_link/3]). %% Internal exports -export([init/1, handle_call/3, handle_cast/2, handle_info/2, terminate/2]). -export([code_change/3]).
這個behaviour只有兩個回調,描述其如何啓動,如何終止。orm
-callback init(Args :: term()) -> {ok, Pid :: pid(), State :: term()} | ignore | {error, Error :: term()}. -callback terminate(Reason :: (shutdown | term()), State :: term()) -> Ignored :: term().
發現了這樣一段註釋,大意是這個模塊的功能是當其做爲supervisor時,啓動和終止子進程都是調用特定的模塊中自定義的函數,而不是系統默認的。server
%%% This module is built to function as process code %%% for a process sitting inbetween a real supervisor %%% and a not start&recovery complient server/system %%% The process inbetween simulates start&recovery %%% behaviour of the server/system below.
啓動時,會調用特定模塊中的啓動函數,並link到對應的進程。進程
init([Mod, StartArgs, Name0]) -> process_flag(trap_exit, true), Name = supname(Name0, Mod), case Mod:init(StartArgs) of {ok, Pid, ChildState} when is_pid(Pid) -> link(Pid), report_progress(Pid, Mod, StartArgs, Name), {ok, #state{mod = Mod, pid = Pid, child_state = ChildState, name = Name}}; ignore -> ignore; {error, Reason} -> {stop, Reason} end. supname(self, Mod) -> {self(),Mod}; supname(N, _) -> N.
子進程退出後,並不會重啓,而是直接退出。it
handle_info({'EXIT', Pid, Reason}, State) when State#state.pid =:= Pid -> case Reason of normal -> ok; shutdown -> ok; {shutdown, _Term} -> ok; _ -> report_error(child_terminated, Reason, State) end, {stop, Reason, State#state{pid = undefined}};
主動終結,調用對應模塊中的終結函數來結束子進程。io
terminate(_Reason, #state{pid = undefined}) -> ok; terminate(Reason, State) -> terminate_pid(Reason, State). ... %% This function is supposed to terminate the 'real' server. terminate_pid(Reason, #state{mod = Mod, child_state = ChildState}) -> Mod:terminate(Reason, ChildState).
當使用supervisor_bridge的時候,對應的子進程是否真的啓動或者終結了,仍是在進行一些別的操做,均可以根據需求自定義。在外界看來,它們的行爲和普通的supervisor、worker無異。ast