http://qs1969.pair.com?node_id=1138169

mariog has asked for the wisdom of the Perl Monks concerning the following question:

Hello

I want to have a script in perl that is running in windows that test the connection to a ssh server.

If the ssh is up and running I need it to display the version. If ssh timeout I need it say socket timeout after x seconds If the connection is refused. simple display Connection refused.

I have the following bit of code that displays the version but I do not know how to handle the errors (timeout and connection refused

#!C:\Dwimperl\perl\bin\perl use IO::Socket::INET; use strict; use warnings; my $socket = IO::Socket::INET->new( PeerHost => $np->opts->host, PeerPort => $np->opts->port, proto => 'tcp', timeout => 10, ); die "$!\n" unless $socket; $socket->print("\n"); my $output = join '', $socket->getline(); print $output;
also, the timeout is taking more than 10 seconds..so I do not think that is working.

Replies are listed 'Best First'.
Re: test version of ssh from windows
by stevieb (Canon) on Aug 11, 2015 at 15:05 UTC

    Wrapping the socket operations within an eval block will help fix both issues. First, if connection is refused, the error will be put into $@ for later processing if you desire. Second, the timeout effect I believe you're after can be achieved with a local alarm signal handler, and setting the number of seconds before the alarm is raised (this error will also be put into $@ if triggered)...

    #!/usr/bin/perl use strict; use warnings; use IO::Socket::INET; eval { local $SIG{ALRM} = sub { die 'timeout'; }; alarm 10; my $socket = IO::Socket::INET->new( PeerHost => $ARGV[0], PeerPort => 22, Proto => 'tcp', ); die "$!\n" unless $socket; $socket->print("\n"); my $output = join '', $socket->getline(); print $output; }; # if eval set an error... handle it if ($@){ ... if $@ eq 'timeout'; ... if $@ eq 'Connection refused'; }

    -stevieb

    ps. Note that in the IO::Socket::INET documentation, all of the parameters start with an upper-case letter (you mistyped 'Proto' and 'Timeout'). I don't know whether that's operationally important or not in this case, but I wanted to point it out. Not using an API according to the documentation can lead to incorrect results.

Re: test version of ssh from windows
by naunga (Initiate) on Aug 11, 2015 at 15:10 UTC

    I ran your code on my OS X machine, and it worked in the way you described that you wanted it to work.

    I got a success, I tried an invalid port and got a "connection refused" message, and I tried an invalid host and got an "Invalid argument" message.

    Feels like this is an issue with host & port you're trying to connect to, instead of a code probelm.

      Hello

      it works but the messages are too long.

      I do not know if I can change the text of the variable $!?

      .

      This script will be integrated into nagios later with nsclient and nrpe so the messages have be short.

        In my reply above using eval, you can trap and then reword the errors as you see fit. Here's a short example.

        eval { open my $fh, '<', 'asdf' or die $!; }; if ($@ =~ /No such file or directory/){ print "short error msg\n"; # or... die "short msg"; }
Re: test version of ssh from windows
by Anonymous Monk on Aug 11, 2015 at 15:05 UTC
    What is $np in this piece of code?
      The host and port information. It just appears as though it was left in by accident after being snipped out of a larger script.