The task is to block all non-SSH connections. My motivation for this was that when I checked /var/log/auth.log
, there were thousands of requests from bots trying to crack SSH passwords. I just didn’t want that. And, as we already use Tailscale at HYVOR for SSH, why not just block all other SSH connections.
This blog post is quite the same as Tailscale’s Use UFW to lock down an Ubuntu server, but I’ve included a few nuances I found along the way. Especially, some precautions to prevent you from getting locked out of your server from the firewall. Tailscale’s guide weirdly (as of today) doesn’t have any mention of enabling Tailscale connections via UFW.
Before getting started, make sure you have installed Tailscale on your server and have enabled SSH.
Setting up UFW
UFW, Uncomplicated Firewall, is a tool to configure a firewall. If this is the first time using it, I recommend quickly checking out DigitalOcean’s UFW guide to get the basic idea.
First, log into your server via Tailscale.
1ssh user@tailscale-ip
Reset ufw
to its initial state (in case it was changed):
1sudo ufw default deny incoming2sudo ufw default allow outgoing
Those two are the rules that run when no other rules match.
Block all incoming connections
Allow any outgoing connection
List all the apps that are registered with UFW. Many applications that depend on network connections will be registered here. For example, OpenSSH, NGINX, Apache, etc.
1sudo ufw app list
1Output2 OpenSSH3 NGINX
These are probably services you have installed (ex: NGINX for web server). I recommend enabling ALL OF THEM, including OpenSSH.
1sudo ufw allow OpenSSH2sudo ufw allow NGINX
In addition, enable incoming connections to port 22 on Tailscale:
1sudo ufw allow in on tailscale0 to any port 22
Once that’s done, enable UFW.
1sudo ufw enable
Verify everything
Before we block external SSH connections, open two new terminals.
1ssh root@public-ip2ssh root@tailscale-ip
Make sure you can access your server both ways.
Once you confirm, close those two new terminals and go back to the first terminal, where you are logged in to the server via Tailscale.
Disable Non-Tailscale SSH access
Warning! Before you continue, make sure that your hosting provider gives a way to connect to your SSH server in case you lose access to it due to firewall rules. In our case, Hetzner provides a Console for us to log in from the browser without SSH.
Let’s block non-tailscale incoming SSH connections. List the all rules, numbered.
1sudo ufw status numbered
1Status: active 2 3 To Action From 4 -- ------ ---- 5[ 1] 80 ALLOW IN Anywhere 6[ 2] 443 ALLOW IN Anywhere 7[ 3] 22 on tailscale0 ALLOW IN Anywhere 8[ 4] OpenSSH ALLOW IN Anywhere 9[ 5] 80 (v6) ALLOW IN Anywhere (v6) 10[ 6] 443 (v6) ALLOW IN Anywhere (v6) 11[ 7] 22 (v6) on tailscale0 ALLOW IN Anywhere (v6) 12[ 8] OpenSSH (v6) ALLOW IN Anywhere (v6)
Remove the rules that say OpenSSH (or port 22 without “tailscale”)
1sudo ufw delete 42sudo ufw delete 8
Finally, reload UFW and SSH services.
1sudo ufw reload2sudo service ssh restart
Again, open two terminals. Try to SSH using public and tailscale IP addresses. The public one should fail, and the tailscale one should connect.
Feel free to discuss pros/cons below.
Comments