SSH – A Brief Software Engineer’s Masterclass

SSH is a secure protocol for communicating between computers. There are many useful tools built on top of this protocol and they should be a part of every Software Engineers toolkit. This blog will detail how to connect to remote computers super quick and more securely, several ways to transfer files between computer (and edit them), and how to connect to ports so that services (such as databases) appear to be running locally.

Image of console using SSH

These commands are most easily ran on Linux OS’s but they have equivalents on other systems too. In particular the rise in popularity of mini computers, like the Raspberry Pi, which have no screens means these techniques are much more widely needed than ever.

Basics

First of all you’ll need to have a remote computer which is running an SSH Server service. Make sure to use a strong password if you are setting it up now, we’ll see a better way to connect later.

The basic connect command takes just a server name, like so :

 $ ssh example.com

If you need a different username to the one you are currently logged in with add it before the address followed by an  @  sign:

 $ ssh joe@example.com

There are other setting you can add on the command line but these are the basic ones you’ll need.

Escape Sequences

Occasionally when connected an SSH connection will freeze and they’ll appear no way to end the session, but SSH has some hidden escape sequences you can use. In particular, this key combination:

   <return>  ~  .

(i.e. press return then type the two symbols  ~  and  .   ), that will immediately close the connection whether it has hung or not and return you to the local machine. In the rare case were you’ll need a command line to begin with the character  ~  this sequence will help:

   <return>  ~  ~

And this one is worth remembering:

   <return>  ~  ?

as it will print a list of all the available escape sequences (but most you are unlikely to need). You can find a full description of all the escape sequences in the SSH man page.

Configuration file

It can become quite tedious to remember the details for multiple servers so the SSH application provides a configuration file. Here where you can place all the settings for each under a server nickname, one hopefully you’ll be more likely to remember.

By default this file will be located in your home directory and called: ~/.ssh/config . If it’s not there you can simply crete it. Inside the file you can add a new server entry with the following:

host  <nick name>
    hostname    <server address>
    user        <user name>

for example, this file contains two servers:

host  examp
    hostname   example.com
    user       joe

host  ano
    hostname   another.example.com
    user       sarah

There are other possible settings too, for example, later on we’ll be adding a further one called LocalForward to route remote ports. It is possible to put plaintext passwords in there too but I don’t recommend it. You can also add comments, they should appear on their own line and start with a  #  symbol, for instance:

host  examp
    # My example server for examples
    hostname   example.com
    user       joe

Now when we want to connect to one of these servers we just need to specify the nickname and the correct settings will be used.

 $ ssh examp

As a bonus if you are using Bash (or an equivalent) the nicknames should “tab complete” too.

You can also overwrite the settings in the configuration file with command line parameters, for instance:

 $ ssh andrew@examp

will use the configuration specifications for “examp” but use “andrew” instead of “joe” for the user.

Key Generation

A nice way to authenticate your access is through an SSH key, at the very least it avoids having to type in passwords. This process involves two files known as a public key and a private key, the public key sits on the remote server. When you attempt to log in the public keys are checked against your private ones, only the computer with matching keys will be allowed to connect.

Generation of the files is easy as SSH comes with all the tools you’ll need. ssh-keygen is the basic command. If you run it direct on the command line it will guide you through the creation process with several questions, you can press the return key to accept the defaults which should be fine in the majority of cases. You can also run the whole thing in a single command like so:

 $ ssh-keygen -t rsa -b 4096 -C "<label>"

The label can be anything but a good standard to use is “<user>@<server>”, you can get the command line to do the hard work for you, like this:

 $ ssh-keygen -t rsa -b 4096 -C "$(whoami)@$(hostname)"

By default the keys are stored in the folder ~/.ssh/ and named id-rsa and id-rsa.pub.

Once generated we need to move the public file (id-rsa.pub) to our remote server. Once again SSH comes with a nifty command, ssh-copy-id. Use it with the nickname you’ve already set up, it’ll ask for the current password one last time, then place the correct file in the correct place with the correct access rights, for instance:

 $ ssh-copy-id examp

Now you’ll automatically be logged in when you use ssh. You could now turn off password access if you liked but as long as your password is a good one it’s not necessary in my opinion (it also restricts others from having access, and if something happens to your computer you could lose the private key it needs to connect.)

If you decide to use different keys for different servers, you can specify which one to use in the configuration file, add:

host  <nick name>
    ...
    IdentityFile    <file position>

As an example:

host  examp
    ...
    IdentityFile   ~/.ssh/id_rsa

You can use multiple files per host if you wish, each will be tried in turn.

Port tunnelling

This is one of my favourite features and a very valuable tool for developers. It allows you to connect to remote services and then use them like they’re running on your local machine – no need to open up ports on firewalls, everything passes through the SSH connection.

You can apply a connection on the command line but it’s more useful to add it to the configuration file, add a line like this:

host  <nick name>
    ...
    # <Helpful comment>
    LocalForward   <LOCAL PORT>  127.0.0.1:<REMOTE PORT>

For example:

host  examp
    ...
    # MySQL service:
    LocalForward   5555  127.0.0.1:3306

Here, the MySQL server running on the remote server on port 3306 is tunnelled to the local machine and is available on port 5555. Now you can connect to it in the usual way, just as you would if it was running on the local machine. In most situations the localhost IP address (127.0.0.1) will be the one you want, but you can use a different IP if the remote server has access to another server.

You can connect to as many services as you want, just ensure each uses a unique local port number. A remote and local port can be the same if you wish. The comments are useful to remind you what each service the ports connect to. A full example:

host  examp
    hostname       example.com
    user           joe

    # My first service
    LocalForward   1111  127.0.0.1:1111

    # My second service
    LocalForward   1112  127.0.0.1:4000

host  ano
    hostname       another.example.com
    user           sarah

    # My mongodb
    LocalForword   5000  127.0.0.1:5001

Now when we connect to the server the port forwarding also connects automatically. Alternatively, it is possible to connect to these services without opening a full SSH connection, just add -N :

 $ ssh -N examp

and you can leave it running in the background if you add an ampersand.

SFTP

Another great tool to master is sftp, it looks complicated but it’s really very simple. It allows you to securely upload and download files to and from a remote server. Once again we can use our configuration file settings to connect:

 $ sftp examp

Now you’ ll get a special prompt. In this you can navigate the remote file system with the normal cd and ls commands you would usually use but you also have the commands lcd and lls which are the same commands but for the local file system (  l  for local). The two other essential commands are get and put which are clearly download and upload commands. The local folder is set to which ever folder you were in when you gave the sftp command, the remote folder defaults to the user folder. You might do something like this (text after sftp> are the ones typed):

$ sftp examp
Connected to examp.
sftp> cd mydocs
sftp> ls
films.txt    books.txt
sftp> lls
myhobbies
sftp> lcd myhobbies
sftp> get books.txt
Fetching /home/joe/mydocs/books.txt to books.txt
/home/joe/mydocs/books.txt      100%  2MB  9.7MB/s  00:02
sftp> exit

Here we connect with sftp, then move the remote folder location (ls, cd), then move the local folder location (lls, lcd), and then download the file books.txt (get) where it shows the download progress. There are other commands but these are the ones you’ll use the most.

SSHFS

This is another useful tool, it’s an SSH File System meaning you can mount a remote systems’ file system with just one simple command.

While the program sftp is usually installed with SSH, sshfs is a separate install and you’ll need to install it in your usual manner.

The command is :

sshfs  <remote address>:<remote folder>  <local folder>

for example (it will again use the nicknames you’ve defined):

 $ sshfs examp:/home/joe  servers/examp

Here we connect to our example.com server and mount the remote folder /home/joe in to a sub folder of our local folder at servers/examp .

Now you can edit remote files as if they are on your local machine with any application you like.

Any remote application

With the help of Linux’s X Window system (on both the remote and local servers) you can run an application located on the remote machine with its GUI part appearing on your local machine. Just another simple command:

ssh <nick_name> -XC <remote_application>

-X triggers the  application X Window connection and -C compresses information for a faster response time, then just add the name of the application at the end, for instance:

$ ssh examp -XC  firefox

Thanks

Thanks for reading, hopefully I’ve shown you something you’ll be able to use, and while there’s much more things these programs can do, these points should get you most of the way to becoming a great SSH master.

Further reading

  • https://linux.die.net/man/1/ssh
  • https://linux.die.net/man/5/ssh_config
  • https://linux.die.net/man/1/sftp
  • https://linux.die.net/man/1/sshfs

Leave a Reply

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.