Just about every IT environment has some sort of remotely managed environment which requires that they have SSH open to the Internet. Perhaps this is a VPS, dedicated server, or colocation. Regardless of your reason, the fact is that there is just some times where you need to have SSH open to the internet.
However regardless of if it is necessary doesn’t mean that you should just do it… One look at your auth.log will reveal that.
# tail /var/log/auth.log Feb 5 21:12:32 mail sshd: pam_unix(sshd:auth): authentication failure; logname= uid=0 euid=0 tty=ssh ruser= rhost=69-214-200-46.pool.ukrtel.net Feb 5 21:12:34 mail sshd: Failed password for invalid user admin from 220.127.116.11 port 1714 ssh2 Feb 5 21:12:35 mail sshd: pam_unix(sshd:auth): authentication failure; logname= uid=0 euid=0 tty=ssh ruser= rhost=69-214-200-46.pool.ukrtel.net user=root Feb 5 21:12:38 mail sshd: Failed password for root from 18.104.22.168 port 1817 ssh2
The fact of that matter is that once you have SSH open folks will try and hit it and brute force there way in. Now there are many ways around this.
1) Move SSH to a non-standard port number.
2) Disable Root Logins over SSH and use non-standard usernames.
3) Use fail2ban to proactively disconnect users who are attempting to brute force your server.
4) Use SSH keys to secure your logins, and disable all password authentication.
Now options 1 and 2 are really just garbage. They don’t actually do anything with regards to security, they simply obfuscate your environment in the hopes that your attacker will give up and go home. Option 3 is good, and option 4 is a sledge hammer which is crude in its implementation.
Instead I will be implementing a modified version of option 4. What we will be doing is allowing Public Key authentication from the entire internet while allowing Password authentication from trusted IP space, this can be an entire IP block, or single IPs. This relies on the match directive in ssh, so please make sure your version of ssh supports this before attempting.
Configure SSH Keys
# ssh-keygen -t rsa
Copy SSH Keys to your Server
# ssh-copy-id firstname.lastname@example.org
Validate SSH Key Authentication
If you did it properly then you will not be asked for a password.
# ssh email@example.com
Secure SSH to Only Allow Password Auth from Trusted Networks
Before you mess with this part ensure you have an alternate way of getting into the system in case you make a mistake which keeps you from using SSH.
In the /etc/ssh/sshd_config disable Password Authentication
# cat /etc/ssh/sshd_config ... PasswordAuthentication no ...
Then add the following to the end of the file, where x.x.x.x and y.y.y.y are your trusted IP addresses, and /32 is used to represent a single IP address.
# cat /etc/ssh/sshd_config ... Match Address x.x.x.x/24,y.y.y.y/32 Password Authentication yes
Validate your Configuration
Once everything is configured you can restart ssh and test.
# /etc/init.d/ssh restart