NAME
RMI::Client - work with out-of-process objects and data transparently
SYNOPSIS
# typical
$c = RMI::Client::Tcp->new(host => 'server1', port => 1234);
# simple
$c = RMI::Client::ForkedPipes->new();
# roll-your-own...
$c = RMI::Client->new(reader => $fh1, writer => $fh2); # generic
$c->call_use('IO::File');
$c->call_use('Sys::Hostname');
$o = $c->call_class_method('IO::File','new','/tmp/myfile');
print $o->getline;
print <$o>;
$host = $c->call_function('Sys::Hostname::hostname')
$host eq 'server1'; #!
$remote_hashref = $c->call_eval('$main::h = { k1 => 111, k2 => 222, k3 => 333}');
$remote_hashref->{k4} = 444;
print sort keys %$remote_hashref;
print $c->call_eval('sort keys %$main::h'); # includes changes!
$c->use_remote('Sys::Hostname'); # this whole package is on the other side
$host = Sys::Hostname::hostname(); # possibly not this hostname...
BEGIN {$c->use_lib_remote;}
use Some::Class; # remote!
# see the docs for B<RMI> for more examples...
DESCRIPTION
This is the base class for a standard RMI connection to an RMI::Server.
In most cases, you will create a client of some subclass, typically RMI::Client::Tcp for a network socket, or RMI::Client::ForkedPipes for an out-of-process object server.
METHODS
- call_class_method($class, $method, @params)
-
Does $class->$method(@params) on the remote side.
Calling remote constructors is the primary way to make a remote object.
$remote_obj = $client->call_class_method('Some::Class','new',@params); $possibly_another_remote_obj = $remote_obj->some_method(@p);
- call_function($fname, @params)
-
A plain function call made by name to the remote side. The function name must be fully qualified.
$c->call_use('Sys::Hostname'); my $server_hostname = $c->call_function('Sys::Hostname::hostname');
- call_sub($fname, @params)
-
An alias for call_function();
- call_eval($src,@args)
-
Calls eval $src on the remote side.
Any additional arguments are set to @_ before eval on the remote side, after proxying.
my $a = $c->call_eval('@main::x = (11,22,33); return \@main::x;'); # pass an arrayref back push @$a, 44, 55; # changed on the server scalar(@$a) == $c->call_eval('scalar(@main::x)'); # ...true!
- call_use($class)
-
Uses the Perl package specified on the remote side, making it available for later calls to call_class_method() and call_function().
$c->call_use('Some::Package');
- call_use_lib($path);
-
Calls "use lib '$path'" on the remote side.
$c->call_use_lib('/some/path/on/the/server');
- use_remote($class)
-
Creases the effect of "use $class", but all calls of any kind for that namespace are proxied through the client. This is the most transparent way to get remote objects, since you can just call normal constructors and class methods as though the module were local. It does means that ALL objects of the given class must come from through this client.
# NOTE: you probably shouldn't do this with IO::File unless you # _really_ want all of its files to open on the server, # while open() opens on the client... $c->use_remote('IO::File'); # never touches IO/File.pm on the client $fh = IO::File->new('myfile'); # actually a remote call print <$fh>; # printing rows from a remote file require IO::File; # does nothing, since we've already "used" IO::File
The @ISA array is also bound to the remote @ISA, but all other variables must be explicitly bound on the client to be accessible. This may be changed in a future release.
Also note that "export" does not currently work via the RMI client. This may also change in a future release.
- use_lib_remote($path)
-
Installs a special handler into the local @INC which causes it to check the remote side for a class. If available, it will do use_remote() on that class.
use A; use B; BEGIN { $c->use_remote_lib; }; # do everything remotely from now on if possible... use C; #remote! use D; #remote! use E; #local, b/c not found on the remote side
- bind($varname)
-
Create a local transparent proxy for a package variable on the remote side.
$c->bind('$Some::Package::somevar') $Some::Package::somevar = 123; # changed remotely $c->bind('@main::foo'); push @main::foo, 11, 22 33; #changed remotely
EXAMPLES
- Making a remote hashref
-
This makes a hashref on the server, and makes a proxy on the client:
my $fake_hashref = $c->call_eval('{}');
This seems to put a key in the hash, but actually sends a message to the server to modify the hash.
$fake_hashref->{key1} = 100;
Lookups also result in a request to the server:
print $fake_hashref->{key1};
When we do this, the hashref on the server is destroyed, as since the ref-count on both sides is now zero:
$fake_hashref = undef;
- Making a remote CODE ref, and using it with a mix of local and remote objects
-
my $local_fh = IO::File->new('/etc/passwd'); my $remote_fh = $c->call_class_method('IO::File','new','/etc/passwd'); my $remote_coderef = $c->call_eval(' sub { my $f1 = shift; my $f2 = shift; my @lines = (<$f1>, <$f2>); return scalar(@lines) } '); my $total_line_count = $remote_coderef->($local_fh, $remote_fh);
BUGS AND CAVEATS
See general bugs in RMI for general system limitations
SEE ALSO
RMI::Server RMI::Client
IO::Socket, Tie::Handle, Tie::Array, Tie:Hash, Tie::Scalar