The Perl Toolchain Summit needs more sponsors. If your company depends on Perl, please support this very important event.

NAME

Proc::Launcher::Manager - spawn and manage multiple Proc::Launcher objects

VERSION

version 0.0.5

SYNOPSIS

    use Proc::Launcher::Manager;

    my $shared_config = { x => 1, y => 2 };

    my $monitor = Proc::Launcher::Manager->new( app_name  => 'MyApp',
                                                    );

    $monitor->spawn( daemon_name  => 'component1',
                     start_method => sub { MyApp->start_component1( $config ) }
                   );
    $monitor->spawn( daemon_name  => 'component2',
                     start_method => sub { MyApp->start_component2( $config ) }
                   );
    $monitor->spawn( daemon_name  => 'webui',
                     start_method => sub { MyApp->start_webui( $config ) }
                   );

    # start all registered daemons.  processes that are already
    # running won't be restarted.
    $monitor->start_all();

    # stop all daemons
    $monitor->stop_all();
    sleep 1;
    $monitor->force_stop_all();

    # get a specific daemon or perform actions on one (sorry demeter)
    my $webui = $monitor->daemon('webui');
    $monitor->daemon('webui')->start();

    # start the process supervisor.  this will start up an event loop
    # and won't exit until it is killed.  any processes not already
    # running will be started, and all processes will be monitored and
    # automatically restarted if they exit.
    $monitor->supervisor();

DESCRIPTION

This library makes it easier to deal with multiple Proc::Launcher processes by providing methods to start and stop all daemons with a single command. Please see the documentation in Proc::Launcher to understand how this these libraries differ from other similar forking and controller modules.

It also provides a supervisor() method which will spawn a child daemon that will monitor the other daemons at regular intervals and restart any that have stopped. Note that only one supervisor can be running at any given time for each pid_dir.

A tail() method also exists that will spawn a POE::Wheel::FollowTail for each daemon's stdout/stderr log files and allow you to provide a callback to process the output.

There is no tracking of inter-service dependencies nor predictable ordering of service startup. Instead, daemons should be designed to wait for needed resources. See Launcher::Cascade if you need to handle dependencies.

SUBROUTINES/METHODS

spawn( %options )

Create a new Proc::Launcher object with the specified options. If the specified daemon already exists, no changes will be made.

daemon( 'daemon_name' )

Return the Proc::Launcher object for a specified daemon.

See: http://en.wikipedia.org/wiki/Law_of_Demeter

daemons()

Return a list of Proc::Launcher objects.

daemons_names()

Return a list of the names of all registered daemons.

daemons_running()

Return a list of the names of daemons that are currently running.

This will begin by calling rm_zombies() on the first daemon, sleeping a second, and then calling rm_zombies() again. So far the test cases have always passed when using this strategy, and inconsistently passed with any subset thereof.

While it seems that this is more complicated than shutting down a single process, it's really just trying to be a bit more efficient. When managing a single process, is_running might be called a few times until the process exits. Since we might be managing a lot of daemons, this method is likely to be a bit more efficient and will hopefully only need to be called once (after the daemons have been given necessary time to shut down).

start_all( $data )

Call the start() method on all daemons. If the daemon is already running it will not be restarted.

stop_all()

Call the stop() method on all daemons.

force_stop_all()

Call the force_stop method on all daemons.

supervisor()

Launch a supervisor process that will poll all selected daemons at regular intervals and restart them in the event that they fail.

Only one supervisor can be running at a time. If you start a new supervisor process, it will replace the old one.

tail()