emqttd_pool_sup.erl 2.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869
  1. %%--------------------------------------------------------------------
  2. %% Copyright (c) 2012-2016 Feng Lee <feng@emqtt.io>.
  3. %%
  4. %% Licensed under the Apache License, Version 2.0 (the "License");
  5. %% you may not use this file except in compliance with the License.
  6. %% You may obtain a copy of the License at
  7. %%
  8. %% http://www.apache.org/licenses/LICENSE-2.0
  9. %%
  10. %% Unless required by applicable law or agreed to in writing, software
  11. %% distributed under the License is distributed on an "AS IS" BASIS,
  12. %% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13. %% See the License for the specific language governing permissions and
  14. %% limitations under the License.
  15. %%--------------------------------------------------------------------
  16. %% @doc Common Pool Supervisor
  17. -module(emqttd_pool_sup).
  18. -behaviour(supervisor).
  19. %% API
  20. -export([spec/1, spec/2, start_link/3, start_link/4]).
  21. %% Supervisor callbacks
  22. -export([init/1]).
  23. -spec spec(list()) -> supervisor:child_spec().
  24. spec(Args) ->
  25. spec(pool_sup, Args).
  26. -spec spec(any(), list()) -> supervisor:child_spec().
  27. spec(ChildId, Args) ->
  28. {ChildId, {?MODULE, start_link, Args},
  29. transient, infinity, supervisor, [?MODULE]}.
  30. -spec start_link(atom(), atom(), mfa()) -> {ok, pid()} | {error, any()}.
  31. start_link(Pool, Type, MFA) ->
  32. Schedulers = erlang:system_info(schedulers),
  33. start_link(Pool, Type, Schedulers, MFA).
  34. -spec start_link(atom(), atom(), pos_integer(), mfa()) -> {ok, pid()} | {error, any()}.
  35. start_link(Pool, Type, Size, MFA) ->
  36. supervisor:start_link({local, sup_name(Pool)}, ?MODULE, [Pool, Type, Size, MFA]).
  37. sup_name(Pool) when is_atom(Pool) ->
  38. list_to_atom(atom_to_list(Pool) ++ "_pool_sup").
  39. init([Pool, Type, Size, {M, F, Args}]) ->
  40. ensure_pool(Pool, Type, [{size, Size}]),
  41. {ok, {{one_for_one, 10, 3600}, [
  42. begin
  43. ensure_pool_worker(Pool, {Pool, I}, I),
  44. {{M, I}, {M, F, [Pool, I | Args]},
  45. transient, 5000, worker, [M]}
  46. end || I <- lists:seq(1, Size)]}}.
  47. ensure_pool(Pool, Type, Opts) ->
  48. try gproc_pool:new(Pool, Type, Opts)
  49. catch
  50. error:exists -> ok
  51. end.
  52. ensure_pool_worker(Pool, Name, Slot) ->
  53. try gproc_pool:add_worker(Pool, Name, Slot)
  54. catch
  55. error:exists -> ok
  56. end.