[erlang-questions] supervisors & slow init's

Sean Cribbs <>
Thu Dec 5 17:47:23 CET 2013


I'd echo Jesper's comments in saying that is most important to make sure
the supervisor tree starts up quickly. There are several options I see:

1) Change A into an FSM (optional, but useful IMHO). Have its initial state
be 'connect_to_hardware' with a timeout of 0 returned from init/1, e.g.
{ok, connect_to_hardware, State, 0}. Then in 'connect_to_hardware', match
timeout and do the connection there, then transition to the 'ready' state.
Note that this state will be entered before any other messages are
received, meaning that B and C should probably use sync_send_event to
communicate with A.

2) Keep A as a gen_server, but do the same timeout trick in init/1. Have A
connect in handle_info when receiving 'timeout', and then notify B and C
that it's ready after.

3) Use Loic's proc_lib:init_ack + gen_server:enter_loop hack instead of the
regular gen_server/gen_fsm flow. This is less clean, but allows you to do
those slower blocky things at startup.

I think the moral of the story is that starting up your system and
implementing a protocol between processes should not be conflated. If
there's a sequence of steps to be done with potential exit points or
branches at each step, FSMs plus messages feels the most sane to me.


On Thu, Dec 5, 2013 at 7:19 AM, David Welton <> wrote:

> > Fire up the supervisor tree as fast as possible, then do the
> connectivity. A
> > good example is how mnesia does it. You have to call
> > mnesia:wait_for_tables/1,2 in order to wait for tables to come online,
> but
> > the bootup of mnesia itself is very fast. So in your case, you would
> call:
> > hardware:wait_ready(arduino, 8000) to wait at most 8000ms for the
> arduino to
> > come online and so on.
> >
> > There is a recent post by Fred Hebert on this subject,
> >
> > http://ferd.ca/it-s-about-the-guarantees.html
> >
> > you might want to read as well.
>
> I already read it - it's a great post, as usual.
>
> However, perhaps I have not spelled out my problem very well.
>
> We have several bits of C code in external processes - let's call them
> A, B and C to be creative.  A starts, and does some stuff.  It's kind
> of slow to do it, so it'd be easy enough to just start it, and
> handle_info in the gen_server that supervises it to find out when it's
> really ready.  But B and C cannot start until A is ready.  So A should
> send messages to them, too?  I can see how to do it, but it all seems
> kind of complicated compared to just letting them start in the order
> they are supposed to start in, one after the other.
>
> --
> David N. Welton
>
> http://www.welton.it/davidw/
>
> http://www.dedasys.com/
> _______________________________________________
> erlang-questions mailing list
> 
> http://erlang.org/mailman/listinfo/erlang-questions
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20131205/b4ca5ae6/attachment.html>


More information about the erlang-questions mailing list