++ed by:

9 PAUSE users
3 non-PAUSE users.

Joel Berger


Mojo::IOLoop::ForkCall - run blocking functions asynchronously by forking


 use Mojo::IOLoop::ForkCall
 my $fc = Mojo::IOLoop::ForkCall->new;
   ['arg', 'list'], 
   sub { my ($fc, $err, @return) = @_; ... }
 $fc->ioloop->start unless $fc->ioloop->is_running;


Asynchronous programming can be benefitial for performance, however not all functions are written for nonblocking interaction and external processes almost never are. Still, all is not lost.

By forking the blocking call into a new process, the main thread may continue to run non-blocking, while the blocking call evaluates. Mojo::IOLoop::ForkCall manages the forking and will emit an event (or execute a callback) when the forked process completes. Return values are serialized and sent from the child to the parent via an appropriate pipe for your platform.

This module is heavily inspired by AnyEvent::Util's fork_call.


The forked process should not attempt any interaction with the parent process's event loop. This includes doing anything that would emit an event in the parent. In fact, it's probably best to avoid any event-based processing in the child.

Some platforms do not fork well, some platforms don't pipe well. This module and the libraries it relies on do their best to smooth over these differences. Still some attention should be paid to platform specific usage, especially on Windows. Efficiency/performance on Windows is not likely to be very good.


Upon request this module exports the following functions.


 fork_call { my @args = @_; child code; return @res } @args, sub { my @res = @_; parent callback }

This function is a drop-in replacement for AnyEvent::Util's fork_call. Because it is attempting to mimic that function the api is different to that provided by the OO interface descibed below.

The function takes a block to be performed in the child, a list of arguments to pass to the block, and a callback to be run on completion. Note that the callback is required and that the arguments are given as a list, not an arrayreference (unlike the OO style). The callback will receive the deserialized return values from the child block as @_. Any error will be available in $@.

The underlying ForkCall object will use the default attributes described below. As with run the return value is the Child object, just in case it is needed to kill the child process.


This module inherits all events from Mojo::EventEmitter and implements the following addtional ones.


 my $fc = Mojo::IOLoop::ForkCall->new;
 $fc->on( finish => sub {
   my ($fc, $err, @res) = @_;

Emitted in the parent process once the child process completes and sends its results. The callback is passed the ForkCall instance, any error, then all deserialized results from the child.


This module inherits all attributes from Mojo::EventEmitter and implements the following additional ones.


The Mojo::IOLoop instance which is used internally. Defaults to Mojo::IOLoop->singleton.


A code reference to serialize the results of the child process to send to the parent. Note that as this code reference is called in the child, some care should be taken when setting it to something other than the defaults. Defaults to \&Storable::freeze.

The code reference will be passed a single array reference. The first argument will be any error or undef if no error occured. If there was no error, the remaining element of the array will be the values returned by the job (evaluated in list context).


A code reference used to deserialize the results of the child process. Defaults to \&Storable::thaw. This should be the logical inverse of the serializer.


If true, the reference to the ForkCall object will be weakened in the internals to prevent a possible memory leak should the child process never close. In this case, if you do not maintain a reference to the ForkCall object, the first argument to the callback will be undef. Additionally, the finish event may not be emitted. Defaults to false. Do not use this unless you know what you are doing and why!


This module inherits all METHODS from Mojo::EventEmitter and implements the following additional ones.


 my $fc = Mojo::IOLoop::ForkCall->new;
 $fc->run( sub { my @args = @_; child code; return @res }, \@args, $cb );

Takes a code reference (required) which is the job to be run on the child. If the next argument is an array reference, these will be passed to the child job. If the last argument is a code reference, it will be called immediately before the finish event is emitted, its arguments are the same as the finish event.

Returns the Child object, just in case you should need to manually kill it.






Joel Berger, <joel.a.berger@gmail.com>


Copyright (C) 2013 by Joel Berger

This library is free software; you can redistribute it and/or modify it under the same terms as Perl itself.