Skip to content

Instantly share code, notes, and snippets.

@preaction
Created November 20, 2009 00:15
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save preaction/239167 to your computer and use it in GitHub Desktop.
Save preaction/239167 to your computer and use it in GitHub Desktop.
use strict;
use warnings;
my $TIMEOUT = 2;
# Automatically run commands on multiple systems
my @hosts = qw(
frozen fog frost dark
);
use Net::SSH::Expect;
use Term::ReadPassword qw(read_password);
use Getopt::Long qw(:config no_ignore_case);
my ( $pass_prompt_type, $user );
GetOptions(
'p' => sub { $pass_prompt_type = "once" },
'P' => sub { $pass_prompt_type = "every" },
'user|u:s' => \$user,
);
$user ||= $ENV{USER};
# Get the password once
my $password;
if ( $pass_prompt_type eq "once" ) {
$password = read_password( "Password: " );
}
for my $host ( @hosts ) {
my $ssh = Net::SSH::Expect->new(
host => $host,
raw_pty => 1,
);
unless ( $ssh->run_ssh ) {
warn "Couldn't start SSH: $!... Skipping $host\n";
next;
}
my $output;
$output = $ssh->peek($TIMEOUT);
if ( $output =~ /The authenticity of host/ ) {
$ssh->send("yes");
print "Sending yes\n";
}
$output = $ssh->peek($TIMEOUT);
if ( $output =~ /(^.+?password:)\s*\z/i ) {
if ( $pass_prompt_type eq "every" ) {
$ssh->send( read_password( $1 ) );
}
else {
$ssh->send( $password );
}
}
# Try to find the command prompt
$output = $ssh->read_all($TIMEOUT);
unless ( $output =~ /[\$>#]\s*\z/ ) {
warn "Couldn't find prompt... Skipping $host\n";
next;
}
# Do your real work
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment