Remote ssh and return values..

hi

I'm executing below 2 cmds which is working file.. ( cmd will ssh to remote host and look for pattern in remote file)

ssh $USER@$HOST "grep -n \"$PATTERN\" $RDIR/$RFILE | awk -F":" '{print \$1}'|tr '\n' ':'|sed 's/:$//g'" > /tmp/_log_out
VAR=`cat /tmp/_log_out`

output in /tmp/_log_out comes as expected if any file having that pattern

I want to achieve in one line which wants to include in the ssh cmd itself if the no pattern found then a variable should be set to 0.

like ex. ( directly storing the result in a variable and result is nothing variable should be 0)

ssh user@host "VAR=`grep -n \"$PATTERN\" $RDIR/$RFILE | awk -F":" '{print \$1}'|tr '\n' ':'|sed 's/:$//g'"`; if [ -z "$VAR" ];then VAR="0";fi"

reason for asking this....after getting the line number executing below line also to get others details (no. of chars in file's 1st line & file inode) which is also working...

my intention is achieve this 2ssh cmds in one line.

ssh $USER@$HOST "cat $RDIR/$RFILE | grep -v '^$' | head -1 |wc -c;ls -li $RDIR/$RFILE|awk '{print \$1}'" |xargs -n 2 | awk '
{ print $1":"$2":" }' > /tmp/_log-chk-output_$$

[just fyi] ===> objective: This script ssh to many servers and looks for pattern in few log files and store in a local flat file in below format
line # of pattern found:total no. of chars in file's 1st line:file inode number

Script is working one, only concern im ssh to servers twice (first time to get the line of pattern & 2nd to get the rest of dtls). Now looking to optimize in 1ssh cmd to achieve both. appreciate your help

You can use something like this:

ssh -T > local_file hostname <<\!
perl -nle'BEGIN {
  $ino = (stat $ARGV[0])[1];
    }
  $. == 1 and $fl = length;
  /pattern/ and $ln = $.;
  END {
    print join ":", $ln ? $ln : 0, $fl ? $fl : 0, 
      $ino;
    }'  remote_file
!

Or, of course, use Net::SSH:Perl if it's available.

Here's How You Can Do That:

#! /usr/bin/perl

use strict;
use warnings;
use Net::SSH::Perl;

my $user = '';
my $pass = '';
my $host = '';
my $port = 22;
my $DEBUG = 0;
my $attr = { debug => $DEBUG, port => $port, protocol => '2,1'};

my $cmd = qq~perl -lne 'if ( /(PAT_HERE)/ ) { printf "PATTERN: %s LINE: %d FILE: %s INODE %s", \$1, \$., \$ARGV, (stat \$ARGV)[1]; }' *~;
my $ssh = Net::SSH::Perl->new($host, %$attr);
$ssh->login($user, $pass);
my ($stdout, $stderr, $exit) = $ssh->cmd($cmd);
print $stdout, "\n";

The above code expects you to replace the string "PAT_HERE" with the one you are looking for.

The code searches the files in the user-you-logged-in-as' ( $user ) home directory. If you want to search in other directories change the "cmd" line to something like this, where the the string " \/some\/dir\/* " is a directory you want to search:

my $cmd = qq~perl -lne 'if ( /(PAT_HERE)/ ) { printf "PATTERN: %s LINE: %d FILE: %s INODE %s", \$1, \$., \$ARGV, (stat \$ARGV)[1]; }' \/some\/dir\/*~;

More effort will be required if you want to handle situations in which no matches are returned gracefully.

Hope That Helps.