[Thamesvalley-pm] using ssh within perl scripts
Stephen Cardie
stephenca at ls26.net
Wed Oct 31 05:07:57 PDT 2007
Greg Matthews wrote:
> [cut]
> hope this makes sense and someone can point me the right direction
>
Greg,
You can do this with IPC::Run. A trivial example is shown below. The
@hosts data structure contains a list of hosts to interrogate; each
element of this is a reference to a hash, the keys of which are
hostname, username and cmds. The last is an array of filename and
command pairs, the command will be executed on the remote host and the
output recorded in the file. Obviously, this could be the same for every
host, in which case you'd remove if from the hash ref and just re-use
the array for each host (i.e. call it @cmds and remove the line
'my(@cmds) = @{$host->{cmds}};' below.
This is quite Expect-like, and, as has been suggested, you could achieve
the same thing with Expect.pm, if you are more comfortable with that
environment.
### BEGINS ####
#!/usr/bin/perl
use strict;
use warnings;
use IO::File;
use IPC::Run qw( start pump finish timeout );
my(@hosts) = (
{ hostname => 'myhost.mydomain.com',
username => 'myusername',
cmds => [
# Filename Command
[ 'uname_a.txt', "uname -a\n"],
[ 'uname_s.txt', "uname -s\n"],
],
},
);
my($ssh_bin) = '/usr/bin/ssh';
my($ssh_opts) = '-2';
for my $host (@hosts) {
my(@login) =
($ssh_bin, $ssh_opts, join '@' => @{$host}{qw(username hostname)});
my(@cmds) = @{$host->{cmds}};
my($h,$in,$out,$err);
$h = start( \@login, \$in, \$out, \$err, timeout( 3 ) );
$in .= "\n";
while (@cmds) {
my($file,$cmd) = @{(shift @cmds)};
$in .= $cmd;
pump $h until ( $out=~/\n/ );
my($fh) = IO::File->new($file, 'w');
defined( $fh ) or die "Can\'t write to $file:$!";
$fh->print( $out );
$fh->close;
$out = '';
}
$h->finish;
}
exit;
#### ENDS #####
More information about the Thamesvalley-pm
mailing list