Chaining/Multiplexing an SSH Connection
Author: MikeW Date: 2015-07-14 00:22:11 UTC Tweet
Ever want to run multiple SSH scripts but get annoyed by having to authenticate for each one? Well it turns out you can configure SSH to accept multiple commands over a period of time. The name I found on the net for this is SSH multiplexing. Command chaining would be a better name in my opinion. Anyway, this technique allows you to call several commands that use SSH but you only authenticate once! That’s right, authentication happens on the first command, no long waits for each step.
For example, I need to execute 2 rsync commmands to copy files to different parts of my web site. Here are the two commands.
rsync -vaz --rsh="ssh -l username" --exclude=bin/ --exclude=*.DS_Store /Users/username/www/blog/ example.com:~/blog rsync -vaz --rsh="ssh -l username" /Users/username/www/index.html example.com:~/index.html
For each command I would need to authenticate with SSH and each step would have to wait a few seconds for that to happen. So now I can replace this with a series of commands, but before I do that, a little configuration and explanation.
To get this to work, you need to create two things in your
- An empty file named
- An empty directory named
config file, enter the following:
host * ControlMaster auto ControlPath ~/.ssh/sockets/%r@%h-%p ControlPersist 600
The first line tells SSH that any host can use this command chaining feature. If you want to limit it to certain hosts it can be changed to just example.com:
The second line enables the multi command feature. It tells SSH that if an SSH socket alread exists for a host, it is ok to reuse it.
The third line tells SSH where to store the socket information. This is why we created a
sockets directory. The string
%r@%h-%p tells SSH to name the socket file
username@hostname-port. If the username you log in with is different then your login username, then you will need to change the name so it matches the remote host. For example:
Finally, the fourth line tells SSH how long to leave the socket open if the open socket is not closed. In this case a value of 600 seconds (10m) is specified. You can also use minutes:
60m as a unit of measure for this option.
With everything setup, let’s take a look at our
rsync commands. This time, we will wrap them in special SSH commands.
ssh -l remote-username -Nf example.com rsync -vaz --rsh="ssh -l username" --exclude=bin/ --exclude=*.DS_Store /Users/username/www/blog/ example.com:~/blog rsync -vaz --rsh="ssh -l username" /Users/username/www/index.html example.com:~/index.html ssh -O exit example.com
The first command sets up the shared socket. The
-l option specifies the login name. The
-N option tells SSH not execute a remote command. The
-f option tell SSH to wait in the background.
The last command closes the open socket for that host. The
-O option passes a command for SSH to execute on the open socket. In this case,
exit tells SSH to close the connection.
Well that is the short version, though not very short. If you need more information on this topic please take a look at the resources linked below from which this post was built.