2

I've heard multiple answers of rights and wrongs and I still don't know if its possible. I ssh to a server then want to run a block of script.

while read server <&3; do   #read server names into the while loop    
serverName=$(uname -n)
 if [[ ! $server =~ [^[:space:]] ]] ; then  #empty line exception
    continue
 fi   
 echo server on list = "$server"
 echo server signed on = "$serverName"
 if [ $serverName == $server ] ; then #makes sure a server doesn't try to ssh to itself
    continue
 fi
    echo "Connecting to - $server"
    ssh "$server"   #SSH login
    echo Connected to "$serverName"
    exec < filelist.txt
    while read updatedfile oldfile; do
    #   echo updatedfile = $updatedfile #use for troubleshooting
    #   echo oldfile = $oldfile   #use for troubleshooting
               if [[ ! $updatedfile =~ [^[:space:]] ]] ; then  #empty line exception
                continue # empty line exception
               fi
               if [[ ! $oldfile =~ [^[:space:]] ]] ; then  #empty line exception
                continue # empty line exception
               fi 
            echo Comparing $updatedfile with $oldfile
            if diff "$updatedfile" "$oldfile" >/dev/null ; then
                echo The files compared are the same. No changes were made.
            else
                echo The files compared are different.
                cp -f -v $oldfile /infanass/dev/admin/backup/`uname -n`_${oldfile##*/}_$(date +%F-%T)
                cp -f -v $updatedfile $oldfile 
            fi          
    done        
 done 3</infanass/dev/admin/servers.txt

I want to run the block of code after sshing to the servers.

5
  • What part of the above script do you want to run on the target machine inside the SSH session?
    – John
    Commented Jul 16, 2013 at 14:43
  • Everything after the ssh connection to the second to last done.
    – mkrouse
    Commented Jul 16, 2013 at 14:46
  • 2
    I would split the script into 2 and have the first be the controller, looping to each machine, and scp the 2nd script to each system and then ssh <mach> script to run it .
    – slm
    Commented Jul 16, 2013 at 15:02
  • 2
    also asked on stackoverflow Commented Jul 16, 2013 at 16:04
  • I answered pretty similar to this once. If anything in here seems like it might be remotely useful and you'd like me to expand on it just ask - unix.stackexchange.com/a/120863/52934
    – mikeserv
    Commented Apr 4, 2014 at 2:53

3 Answers 3

2

The problem you're having currently is that the SSH connection "pauses" the script, and the script resumes with the echo Connected to "$serverName" line only after the SSH session exits.

As I see it, you have two options. (There are probably more, but these are the two I can think of currently.)

Option one is to use expect to start an SSH session you can control through the script, effectively sending commands back and forth from the master script to the SSH session. Option two is to put the block you want to run remotely on the remote server as a different script, and run SSH in a non-interactive way: ssh $server $script-to-run.

2

If you're absolutely convinced that you want to structure this as a single script you can make use of a HEREDOC when you open your connection to the remote ssh server.

For example:

$ ssh user@server << EOT

...
commands
...

EOT
2
  • it still wont work for some reason
    – mkrouse
    Commented Jul 17, 2013 at 14:52
  • @mkrouse - you can't have spaces before the string "EOT" which closes the block of the HEREDOC. Can you paste what you tried on pastebin, or update your question with the details?
    – slm
    Commented Jul 17, 2013 at 18:39
1

Alternatively, simple echo to pipe and then execute all from stdin.

echo " \
uname -a; \
whoami; \
uname " \
| ssh -l root localhost 'cat | sh -'

This site is temporarily in read-only mode and not accepting new answers.

Not the answer you're looking for? Browse other questions tagged .