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

NAME

IO::Events - Non-blocking IO using events

SYNOPSIS

Example 1, run 'bc' as a co-process:

        use IO::Events;

        my $loop = IO::Events::Loop-> new();

        my $stdin_alive = 1;
        my $calculator = IO::Events::Process::ReadWrite-> new(
                owner    => $loop,
                process  => 'bc -l', 
                on_read  => sub {
                        while ( my $line = $_[0]-> readline) {
                                print "bc says: $line";
                        }
                },
                on_close => sub {
                        exit 1 if $stdin_alive; # fork/exec error
                }
        );

        my $stdin = IO::Events::stdin-> new(
                owner => $loop,
                on_read => sub { 
                $calculator-> write( $_[0]-> read );
                },
                on_close => sub {
                        $stdin_alive = 0;
                        exit;
                },
        );

        $loop-> yield while 1;

Example 2, connect to/listen on a TCP port within a single process:

        use IO::Events;
        
        my $loop = IO::Events::Loop-> new();
        IO::Events::Socket::TCP-> new(
                owner    => $loop,
                listen   => 1,
                port     => 10000,
                on_read => sub {
                        my $new = shift-> accept( 
                                read   => 1,
                                on_read => sub {
                                        while ( my $line = $_[0]-> readline) {
                                                print "client says: $line\n";
                                                exit;
                                        }
                                }
                        );
                        print "connect from $new->{remote_addr}:$new->{remote_port}\n";
                },
        );
        
        IO::Events::Socket::TCP-> new(
                owner   => $loop,
                connect => 'localhost',
                port    => 10000,
        )-> write("hello, tcp socket!\n");
        
        $loop->yield while 1;

Example 3, connect to/listen on a UDP port within a single process:

        use Socket;
        use IO::Events;
        
        my $loop = IO::Events::Loop-> new();
        IO::Events::Socket::UDP-> new(
                owner    => $loop,
                port     => 10000,
                on_read => sub {
                        my $self = $_[0];
                        my $data = $self-> recv;
                        print "$self->{remote_host}:$self->{remote_port} says: $data";
                        exit;
                },
        );
        
        IO::Events::Socket::UDP-> new(
                owner   => $loop,
        )-> send( 'localhost', 10000, "hello, udp socket!\n");
        
        $loop->yield while 1;

DESCRIPTION

The module implements object-oriented approach to select-driven events and contains set of convenience objects for inter-process communication.

The main part of the module is the 'loop' instance of IO::Events::Loop class, which knows about all IO handles subject to select(). The handles are inherited from IO::Events::Handle class, which property handle holds reference to a IO handle object, - a file scalar or IO::Handle instance. IO::Events::Handle object propagates select-based events - on_read, on_write, on_exception, as well as generic on_create, on_close and on_error. It is a requirement that handles are non-blocking.

All instances are created by calling new with arbitrary number of named parameters. The unrecognized parameters are stored in the object and cause no conflict:

        my $a = IO::Events::Handle-> new( my_var => 1 );
        die $a->{my_var};

The module is not meant to serve as replacement of IO::Select and IPC::Open, and can perfectly live together with the first and counteract with the handles managed by the second. The example in "SYNOPSIS" section displays how to harness the non-blocking IO between stdin and a co-process.

Advices

  • Set $SIG{PIPE} = 'IGNORE', usually a sound idea.

  • Set $|=1 first in your script if you use ::Fork or ::Process classes.

  • If you use on_fork, never terminate a child process by die or exit, because otherwise everything Perl allocated in parent process will be de-allocated twice, both in the parent and in the child process. If you must, use POSIX::exit instead.

IO::Events::Loop

new() parameters

timeout INTEGER

Number of seconds passed to select() as the fourth parameter.

Default value: 50

waitpid BOOLEAN

In addition to select(), IO::Events::Loop also waits for finished processes, automatically getting rid of handles associated with them, if set to 1.

Default value: 1

Methods

handles

Returns number of handles owner by loop object. When a program automatically disposes of handles, not needed anymore, it may choose to stop when there are no more handles to serve.

yield %HASH

Enters select() loop and dispatches pending IO if data are available to read or write. Hash values of 'block_read', 'block_write', and 'block_exc' can be set to 1 if read, write, or exception events are not to be used. Practically,

        $loop-> yield( block_read => 1, block_exc => 1, timeout => 0 )

call effectively ( but still in the non-blocking fashion ) flushes write buffers.

Returns result of select() call, the number of streams handled.

flush

Flushes write sockets, if possible.

Fields

%id

All handles are assigned an unique id, and are stored in internal {id} hash. This hash is read-only, and can be used to look-up a handle object by its id string.

%filenos

Hash of file numbers, read-only.

%processes

Hash of PIDs associated with handles, read-only. Used for IPC and waitpid results processing.

IO::Events::Handle

Root of IO handle object hierarchy, dispatches IO events and auto-destructs when handle is closed or an IO error occurs. The explicit destruction is invoked by calling destroy, which is reentrant-safe.

Parameters to new()

auto_close BOOLEAN

If set to 1, IO handle is explicitly closed as the object instance is destroyed. Doesn't affect anything otherwise.

Default value: 1

flush [ DISCARD = 0]

Flushes not yet written data. If DISCARD is 1, does not return until all data are written or error is signalled. If 0, discards all data.

handle IOHANDLE

IO::Handle object or a file scalar. If not specified, a new IO::Handle instance is created automatically.

The handle is set to non-blocking mode. If this is already done, nonblock optional boolean parameter can be set to 1 to prevent extra fcntl calls.

read BOOLEAN

Set to 1 if handle is to be read from.

Default value: 0

shutdown @WHO

Defined in IO::Events::Fork::ReadWrite and IO::Event::IPC::Process::ReadWrite namespaces. @WHO can contain string 'read' and 'write', to tell what part of bidirectional IPC is to be closed.

write BOOLEAN

Set to 1 if handle is to be written from.

Default value: 0

pid INTEGER

If a handle is associated with a process, IO::Events::Loop uses this field to waitpid() and auto-destruct the handle.

Default value: undef

Methods

can_read BOOLEAN

Selects whether the handle is readable.

can_write BOOLEAN

Selects whether the handle is writable.

can_exception BOOLEAN

Selects whether the handle accepts exception events.

readline

Returns newline-ended read data, if available.

read

Return contents of the read buffer.

write DATA

Appends DATA to the write buffer

destroy

Destructs handle instance

notify $EVENT, @PARAMETERS

Dispatches EVENT, passing PARAMETERS to each callback.

Events

A single event can cause several callback routines to be called. This is useful when a class declares its own, for example, cleanup code in on_close sub, whereas the class instance user can add another listener to the same on_close notification:

        package MyHandle;
        ...
        sub on_close { ... }
        ...

        MyHandle-> new( on_close => sub { ... });

The class declares static ( per-class ) instance of hash %events, which contains declaration of events and their execution flow. SINGLE-declared events call only single callback, be it static or dynamic. MULTIPLE-declared events call all callbacks, but execution flow can be stopped by setting {event_flag} to 1. This is useful, for example, to dynamically override default behavior of IO::Events::Handle::on_error which emits a warning message to stderr and destroys the handle.

on_close

Called before object instance is destroyed.

In a special case for ReadWrite objects, on_close is called twice, when read and write handles are closed. To distinuish between the cases, the second parameter is set to 1 when on_close is called due to the writer handle destruction.

Declared as MULTIPLE.

on_create

Called after object instance is created.

Declared as MULTIPLE.

on_error

Called when read or write calls encounter error.

Declared as MULTIPLE.

on_exception

Called when exception is arrived. Consult your system select manpage to see what events and on what socket types can be expected.

on_fork

Special event, called by IO::Events::Fork objects when a new process is instantiated. Although the syntax for specifying on_fork is the same as for the other events, on_fork does not interact with these, and is not called from within yield.

When on_fork returned, process is terminated. If you wish to terminate process yourself, do not call perl's exit but rather POSIX::_exit, since otherwise perl stuctures created before fork will be destroyed twice.

on_read

Called after data is read.

on_write

Called when handle is writable and the write buffer is empty. If the event doesn't fill the write buffer, the handle write flag is cleared and further on_write notifications are suppressed until the write buffer is filled.

IO::Events::Process::Read

Runs a process with its stdout tied to a newly created handle. The process name is passed to process parameter to the new() contructor.

IO::Events::Process::Write

Runs a process with its stdin tied to a newly created handle. The process name is passed to process parameter to the new() contructor.

IO::Events::Process::ReadWrite

Runs a process with its stdin and stdout tied to two newly created handles. The both handles are transparently mapped to a single handle object.

Note: check IPC::Open2 and IPC::Open3 also.

IO::Events::Fork::Read

Forks a child with its stdout tied to a newly created handle.

IO::Events::Fork::Write

Forks a child with its stdin tied to a newly created handle.

IO::Events::Fork::ReadWrite

Forks a child with its stdin and stdout tied to two newly created handles. The both handles are transparently mapped to a single handle object.

IO::Events::stdin

Shortcut class for STDIN handle.

IO::Events::stdout

Shortcut class for STDOUT handle.

IO::Events::stderr

Shortcut class for STDERR handle.

IO::Events::Socket::TCP

Shortcut class for TCP socket. Parameters accepted:

connect HOSTNAME

If set, connect() call is issued on the socket to HOSTNAME and port set in port parameter.

listen

If set, socket listens on port.

port INTEGER

Number of a port to bind to.

addr STRING

If set, socket listens on addr IP address, otherwise INADDR_ANY.

accept %PROFILE

Creates a new IO handle and accepts a connection into it. Returns the newly created IO::Events::Handle object with %PROFILE fields.

IO::Events::Socket::UDP

Shortcut class for UDP socket. Parameters accepted:

port INTEGER

Number of a port to bind to.

addr STRING

If set, socket listens on addr IP address, otherwise INADDR_ANY.

send HOSTNAME, PORT, DATA, %OPTIONS

Issues send(2) call, returns number of bytes sent or an error. See "send" in perldoc for more details.

Options accepted: oob, dontroute, eor, eof.

recv %OPTIONS

Issues recv(2) call, returns data block or under if error. See "recv" in perldoc for more details.

Options accepted: oob, peek, waitall, nonblock, maxlen.

IO::Events::Socket::UNIX

A handle class, used to connect to and listen on UNIX sockets.

accept %PROFILE

Creates a new IO handle and accepts a connection into it. Returns the newly created IO::Events::Handle object with %PROFILE fields.

connect PATHNAME

Connects to a socket over a given PATHNAME

listen PATHNAME

Listens on a socket over a given PATHNAME

IO::Events::Timer

A tiny hackish hask to add time-based events. The class is not inherited from IO::Event::Handle, and the only property it shared with the other handle classes is owner.

timeout SECONDS

Invokes on_tick callback in SECONDS, which can be float.

active BOOLEAN

If on, timer is started immediately, otherwise is stopped.

repetitive BOOLEAN

If on, timer fires off event each SECONDS interval, otherwise goes off after the first on_tick.

start

Starts the timer

stop

Stops the timer

on_tick

Callback invoked each time SECONDS interval is expired.

SEE ALSO

perlipc, POE, IO::Handle, IO::Select, IPC::Open2.

COPYRIGHT

Copyright (c) 2004 catpipe Systems ApS. All rights reserved.

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

AUTHOR

Dmitry Karasik <dmitry@karasik.eu.org>