Asterisk-AMI

 view release on metacpan or  search on metacpan

Changes  view on Meta::CPAN


	- Added SSL support

	- Internal changes to how we keep track of active actions

	- Fixed some bad grammar/spelling/typos in documentation,
	most likely added a few more as well

0.1.7	- Removed Asterisk::AMI::completed(). Seemed pointless with callbacks.

	- Added TCP_Keepalive option, enables socket level TCP keepalive for detecting dead connections.

	- Fixed possible undefined value for timeout when sending a keepalive.

	- We were being a bit overzealous when we encounted an error on the socket (during connect or otherwise).
	We now callback any outstanding actions (as if they had timed out) before we issue the on_error callbacks
	and do internal cleanup. This bug was causing the hang during login if a socket connection could not
	be made.

	- Fixed a bug with older version of ExtUtils::MakeMaker

	- Fix to properly us \v when perl >=5.10, we were only doing it when perl >5.10. This only affects performance.

	- 'Keepalive' was not being set if Blocking was set to 1. Now 'Keepalive' is always set if configured,
	it just may not be helpful if you are not running an event loop.

	- Updated Dependancy to AnyEvent version 5.0 or greater

	- Switch to AE interface for AnyEvent for timers and condvars. Lowers overhead when using alot of timers.

	- Some general code cleanups

0.1.6 	- Fixes calling wrong modules (leftover from name change)

examples/cmd_server.pl  view on Meta::CPAN

$list .= 'list - Displays this list' . $EOL . $EOR;

#Keep a list of clients
my %clients;

#Connect to asterisk
my $astman = Asterisk::AMI->new(PeerAddr => '127.0.0.1',
				Username => 'test',
				Secret	=> 'supersecret',
				Timeout => 3, #Default timeout for all operations, 3 seconds
				Keepalive => 60, #Send a keepalive every minute
				on_error => sub { print "Error occured on socket\r\n"; exit; },
				on_timeout => sub { print "Connection to asterisk timed out\r\n"; exit; },
                                Blocking => 0
			);

die "Unable to connect to asterisk" unless ($astman);

#Callback on mailbox command
sub mailboxcb {
	my ($asterisk, $action, $client) = @_;

examples/event_proxy.pl  view on Meta::CPAN

#Keep a list of clients
my %clients;

#Connect to asterisk
my $astman = Asterisk::AMI->new(PeerAddr => '127.0.0.1',
				Username => 'admin',
				Secret	=> 'supersecret',
				Events	=> 'on', #Give us something to proxy
				Timeout => 3, #Default timeout for all operations, 3 seconds
				Handlers => { default => \&proxy_event }, #Install default handler
				Keepalive => 60, #Send a keepalive every minute
				on_error => sub { print "Error occured on socket\r\n"; exit; },
				on_timeout => sub { print "Connection to asterisk timed out\r\n"; exit; }
			);

die "Unable to connect to asterisk" unless ($astman);

#Handler for events
sub proxy_event {
	my ($asterisk, $event) = @_;

lib/Asterisk/AMI.pm  view on Meta::CPAN

        PeerAddr        Remote host address        <hostname>
        PeerPort        Remote host port        <service>
        Events Enable/Disable Events 'on'|'off'
        Username        Username to access the AMI
        Secret Secret used to connect to AMI
        AuthType        Authentication type to use for login        'plaintext'|'MD5'
        UseSSL Enables/Disables SSL for the connection 0|1
        BufferSize        Maximum size of buffer, in number of actions
        Timeout Default timeout of all actions in seconds
        Handlers        Hash reference of Handlers for events        { 'EVENT' => \&somesub };
        Keepalive        Interval (in seconds) to periodically send 'Ping' actions to asterisk
        TCP_Keepalive        Enables/Disables SO_KEEPALIVE option on the socket        0|1
        Blocking        Enable/Disable blocking connects        0|1
        on_connect        A subroutine to run after we connect
        on_connect_err        A subroutine to call if we have an error while connecting
        on_error        A subroutine to call when an error occurs on the socket
        on_disconnect        A subroutine to call when the remote end disconnects
        on_timeout        A subroutine to call if our Keepalive times out
        OriginateHack        Changes settings to allow Async Originates to work 0|1

        'PeerAddr' defaults to 127.0.0.1.
        'PeerPort' defaults to 5038.
        'Events' default is 'off'. May be anything that the AMI will accept as a part of the 'Events' parameter for the
        login action.
        'Username' has no default and must be supplied.
        'Secret' has no default and must be supplied.
        'AuthType' sets the authentication type to use for login. Default is 'plaintext'.  Use 'MD5' for MD5 challenge
        authentication.
        'UseSSL' defaults to 0 (no ssl). When SSL is enabled the default PeerPort changes to 5039.
        'BufferSize' has a default of 30000. It also acts as our max actionid before we reset the counter.
        'Timeout' has a default of 0, which means no timeout on blocking.
        'Handlers' accepts a hash reference setting a callback handler for the specified event. EVENT should match
        the contents of the {'Event'} key of the event object will be. The handler should be a subroutine reference that
        will be passed the a copy of the AMI object and the event object. The 'default' keyword can be used to set
        a default event handler. If handlers are installed we do not buffer events and instead immediately dispatch them.
        If no handler is specified for an event type and a 'default' was not set the event is discarded.
        'Keepalive' only works when running with an event loop. Used with on_timeout, this can be used to detect if
        asterisk has become un-responsive.
        'TCP_Keepalive' default is disabled. Activates the tcp keep-alive at the socket layer. This does not require
        an event-loop and is lightweight. Useful for applications that use long-lived connections to Asterisk but
        do not run an event loop.
        'Blocking' has a default of 1 (block on connecting). A value of 0 will cause us to queue our connection
        and login for when an event loop is started. If set to non blocking we will always return a valid object.

        'on_connect' is a subroutine to call when we have successfully connected and logged into the asterisk manager.
        it will be passed our AMI object.

        'on_connect_err', 'on_error', 'on_disconnect'
        These three specify subroutines to call when errors occur. 'on_connect_err' is specifically for errors that
        occur while connecting, as well as failed logins. If 'on_connect_err' or 'on_disconnect' it is not set,
        but 'on_error' is, 'on_error' will be called. 'on_disconnect' is not reliable, as disconnects seem to get lumped
        under 'on_error' instead. When the subroutine specified for any of theses is called the first argument is a copy
        of our AMI object, and the second is a string containing a message/reason. All three of these are 'fatal', when
        they occur we destroy our buffers and our socket connections.

        'on_timeout' is called when a keep-alive has timed out, not when a normal action has. It is non-'fatal'.
        The subroutine will be called with a copy of our AMI object and a message.

        'OriginateHack' defaults to 0 (off). This essentially enables 'call' events and says 'discard all events
        unless the user has explicitly enabled events' (prevents a memory leak). It does its best not to mess up
        anything you have already set. Without this, if you use 'Async' with an 'Originate' the action will timeout
        or never callback. You don't need this if you are already doing work with events, simply add 'call' events
        to your eventmask.

=head2 Disabling Warnings

lib/Asterisk/AMI.pm  view on Meta::CPAN

                        $self->{CONFIG}->{EVENTS} .= ',call';
                }
        }

        #Initialize the seq number
        $self->{idseq} = 1;

        #Weaken reference for use in anonsub
        weaken($self);

        #Set keepalive
        $self->{CONFIG}->{KEEPALIVE} = AE::timer($self->{CONFIG}->{KEEPALIVE}, $self->{CONFIG}->{KEEPALIVE}, sub { $self->_send_keepalive }) if ($self->{CONFIG}->{KEEPALIVE});
        
        return 1;
}

#Handles connection failures (includes login failure);
sub _on_connect_err {

        my ($self, $message) = @_;

        warnings::warnif('Asterisk::AMI', "Failed to connect to asterisk - $self->{CONFIG}->{PEERADDR}:$self->{CONFIG}->{PEERPORT}");

lib/Asterisk/AMI.pm  view on Meta::CPAN

                $self->{CONFIG}->{ON_ERROR}->($self, $message);
        }

        $self->{SOCKERR} = 1;

        $self->destroy();

        return;
}

#What happens if our keep alive times out
sub _on_timeout {
        my ($self, $message) = @_;

        warnings::warnif('Asterisk::AMI', $message);

        if (exists $self->{CONFIG}->{ON_TIMEOUT}) {
                $self->{CONFIG}->{ON_TIMEOUT}->($self, $message);
        } elsif (exists $self->{CONFIG}->{ON_ERROR}) {
                $self->{CONFIG}->{ON_ERROR}->($self, $message);
        }

lib/Asterisk/AMI.pm  view on Meta::CPAN


        #Build a hash of our anyevent::handle options
        my %hdl = (     connect => [$self->{CONFIG}->{PEERADDR} => $self->{CONFIG}->{PEERPORT}],
                        on_connect_err => sub { $self->_on_connect_err($_[1]); },
                        on_error => sub { $self->_on_error($_[2]) },
                        on_eof => sub { $self->_on_disconnect; },
                        on_connect => sub { $self->{handle}->push_read( line => sub { $self->_on_connect(@_); } ); });

        #TLS stuff
        $hdl{'tls'} = 'connect' if ($self->{CONFIG}->{USESSL});
        #TCP Keepalive
        $hdl{'keeplive'} = 1 if ($self->{CONFIG}->{TCP_KEEPALIVE});

        #Make connection/create handle
        $self->{handle} = AnyEvent::Handle->new(%hdl);

        #Return login status if blocking
        return $self->_login if ($self->{CONFIG}->{BLOCKING});

        #Queue our login
        $self->_login;

lib/Asterisk/AMI.pm  view on Meta::CPAN


        return 0;
}

#Check whether there was an error on the socket
sub error {
        my ($self) = @_;
        return $self->{SOCKERR};
}

#Sends a keep alive
sub _send_keepalive {
        my ($self) = @_;
        #Weaken ref for use in anonysub
        weaken($self);
        my $cb = sub { 
                        unless ($_[1]->{'GOOD'}) {
                                $self->_on_timeout("Asterisk failed to respond to keepalive - $self->{CONFIG}->{PEERADDR}:$self->{CONFIG}->{PEERPORT}");
                        };
                 };

        my $timeout = $self->{CONFIG}->{TIMEOUT} || 5;
        
        return $self->send_action({ Action => 'Ping' }, $cb, $timeout);
}

#Calls all callbacks as if they had timed out Used when an error has occured on the socket
sub _clear_cbs {



( run in 1.041 second using v1.01-cache-2.11-cpan-df04353d9ac )