How to connect input/output to SSH session

Viewed 3230

What is a good way to be able to directly send to STDIN and receive from STDOUT of a process? I'm specifically interested in SSH, as I want to do the following:

[ssh into a remote server]
[run remote commands]
[run local commands]
[run remote commands]
 etc...

For example, let's say I have a local script "localScript" that will output the next command I want to run remotely, depending on the output of "remoteScript". I could do something like:

output=$(ssh myServer "./remoteScript")
nextCommand=$(./localScript $output)
ssh myServer "$nextCommand"

But it would be nice to do this without closing/reopening the SSH connection at every step.

2 Answers

You can redirect SSH input and output to FIFO-s and then use these for two-way communication.

For example local.sh:

#!/bin/sh

SSH_SERVER="myServer"

# Redirect SSH input and output to temporary named pipes (FIFOs)
SSH_IN=$(mktemp -u)
SSH_OUT=$(mktemp -u)
mkfifo "$SSH_IN" "$SSH_OUT"
ssh "$SSH_SERVER" "./remote.sh" < "$SSH_IN" > "$SSH_OUT" &

# Open the FIFO-s and clean up the files
exec 3>"$SSH_IN"
exec 4<"$SSH_OUT"
rm -f "$SSH_IN" "$SSH_OUT"

# Read and write
counter=0
echo "PING${counter}" >&3
cat <&4 | while read line; do
    echo "Remote responded: $line"
    sleep 1
    counter=$((counter+1))
    echo "PING${counter}" >&3
done

And simple remote.sh:

#!/bin/sh

while read line; do
    echo "$line PONG"
done

The method you are using works, but I don't think you can reuse the same connection everytime. You can, however, do this using screen, tmux or nohup, but that would greatly increase the complexity of your script because you will now have to emulate keypresses/shortcuts. I'm not even sure if you can if you do directly in bash. If you want to emulate keypresses, you will have to run the script in a new x-terminal and use xdotool to emulate the keypresses.

Another method is to delegate the whole script to the SSH server by just running the script on the remote server itself:

ssh root@MachineB 'bash -s' < local_script.sh
Related