Super User is a question and answer site for computer enthusiasts and power users. It's 100% free, no registration required.

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

I want to be able to broadcast the same commands to multiple servers interactively, meaning I want to send a command, view the result and send another command. The commands are arbitrary and cannot be scripted.

The question How can I automate running commands remotely over SSH? solves this problem very well if you're prone to using the tools suggested like: pssh, sdh, gsh, cluster-ssh.
But I am trying to find out if there a more low level solution, only by using the standard SSH.

My question is can you think of a way in BASH to open multiple SSHs, redirect into them a file, so everytime I write into the file, the new text is redirected into the SSH and executed.
If there is a reasoning behind why the above can't be done, I'd be happy to learn why is it not possible.

share|improve this question
    
You might have better luck with this kind of question on ServerFault. – Rob H Mar 2 '11 at 17:52
up vote 1 down vote accepted

One way is to use coprocesses.

$ coproc foo { ssh -T foo.domain; }

Now $foo is an array of two file descriptors; ${foo[0]} is ssh's stdout and writing to fd ${foo[1]} will send to ssh's stdin.

$ echo "whoami" >&${foo[1]}
$ head -n 1 <&${foo[0]}
grawity
$

(Accessing /proc/$$/fd/${foo[1]} would work as well.)


Another way - named pipes.

$ mkfifo {foo,bar}.{in,out}
$ ssh foo <foo.in >foo.out &
$ ssh bar <bar.in >bar.out &
$ echo "whoami" | tee foo.in bar.in

Similar - process substitution.

$ echo "whoami" | tee >(ssh foo) >(ssh bar)

For more than one command:

$ mkfifo in
$ tee >(ssh foo) >(ssh bar) <in &
$ echo "whoami" >in

But since pipes break easily, you might have to resort to regular files.

(This example will put the file in /dev/shm to avoid hitting the disk every time.)

$ f=/dev/shm/in; touch $f
$ tail -f $f | ssh foo &
$ tail -f $f | ssh bar &
$ echo foo > $f 
$ echo bar >> $f; # note: >> for appending

And:

$ f=/dev/shm/in; touch $f
$ tail -f $f | tee >(ssh foo) >(ssh bar) &
$ echo foo >> $f
share|improve this answer
    
>&${foo[1]} won't work; there's no variable substitution in the file descriptor portion of redirections. Your alternative using /proc/ would be necessary, since variables do work in filenames (even as part of redirections). Additionally, {in.out} should be {in,out} (typo). – Zenexer Aug 25 '15 at 4:00
    
@Zenexer: I can assure you that >&$var works just fine in bash, and it seems to work even in ksh. (Otherwise they wouldn't have added exec {var}<>…, which kinda requires that to be useful.) – grawity Aug 25 '15 at 5:46
    
Interestingly, it seems to be working now. I'm sure I was trying it with bash 4 before, so I'm not sure what the issue was. I seem to recall it worked with exec but not other commands. – Zenexer Aug 26 '15 at 3:23

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.