How to Setup a Hetzner Server
A simple walkthrough of purchasing a Hetzner cloud server, then locking it down with SSH hardening, a firewall, automatic updates, and Fail2ban.

By Kenny Tran
- devops
- hetzner
- linux
- security
- self-hosting
- vps
- hermes
I recently picked up a Hetzner Cloud server to host my Hermes agent and was surprised by how straightforward the process was. This post covers both: getting the server, then making it reasonably secure.
They offer two products worth knowing:
- Hetzner Cloud — VPS instances, managed with a web UI or API. Good for most workloads.
- Hetzner Robot (Dedicated) — bare metal servers. Much more power but requires a reboot into rescue mode to reinstall.
For most projects, Hetzner Cloud is a good starting point.
Provisioning the Server
- Create an account at hetzner.com and navigate to the Cloud Console.
- Create a new project, then click Add Server.
- Pick a location.
- Select a type. The CX23 is a good starting point; scale up if needed.
- Choose an image — Ubuntu 26.04 LTS is a safe pick with long-term support.
- Under SSH keys, paste your public key. This is mandatory, you should never rely on password auth.
- Optionally enable backups (adds 20% to the monthly cost but is worth it).
Once created, you’ll have an IP address and root SSH access within seconds.
First Login
Connect as root using your SSH key:
ssh root@<your-server-ip>Before anything else, update the system:
apt update && apt upgrade -yCreate a Non-Root User
Running everything as root is asking for trouble. Create a user with sudo access:
usermod -aG sudo kennyCopy your SSH key to the new user:
rsync --archive --chown=kenny:kenny ~/.ssh /home/kennyTest the new user in a separate terminal before continuing:
ssh kenny@<your-server-ip>Harden SSH
Edit /etc/ssh/sshd_config:
sudo nano /etc/ssh/sshd_configSet or confirm these values:
Port 2222PermitRootLogin noPasswordAuthentication noPubkeyAuthentication yesAuthorizedKeysFile .ssh/authorized_keysX11Forwarding noAllowUsers kennyChanging the port from 22 to something like 2222 cuts noise from automated scanners significantly. It is not a security measure on its own, but it reduces log spam.
Restart SSH — do not close your existing session yet:
sudo systemctl restart sshdOpen a new terminal and verify you can connect on the new port:
ssh -p 2222 kenny@<your-server-ip>Once confirmed, close the old session.
Configure the Firewall with UFW
Ubuntu ships with UFW (Uncomplicated Firewall). Enable it and set sensible defaults:
sudo ufw default deny incomingsudo ufw default allow outgoing
# Allow your new SSH portsudo ufw allow 2222/tcp
sudo ufw enablesudo ufw status verboseHetzner also provides a Cloud Firewall at the network level in the console. Using both is a good idea — the cloud firewall drops packets before they reach the OS.
Enable Automatic Security Updates
Install unattended-upgrades to automatically apply security patches:
sudo apt install unattended-upgrades -ysudo dpkg-reconfigure --priority=low unattended-upgradesTo confirm the configuration:
cat /etc/apt/apt.conf.d/20auto-upgradesIt should contain:
APT::Periodic::Update-Package-Lists "1";APT::Periodic::Unattended-Upgrade "1";Install Fail2ban
Fail2ban watches log files and bans IPs that show malicious behaviour (repeated failed SSH logins, etc.):
sudo apt install fail2ban -yCreate a local override so your config survives package updates:
sudo cp /etc/fail2ban/jail.conf /etc/fail2ban/jail.localsudo nano /etc/fail2ban/jail.localFind the [sshd] section and update it:
[sshd]port = 2222Restart and check the service:
sudo systemctl restart fail2bansudo fail2ban-client status sshdSummary
Here is the full checklist:
- ✅ Provisioned server with SSH key, no root password
- ✅ Created non-root user with sudo access
- ✅ Disabled root login and password authentication in sshd
- ✅ Moved SSH to a non-standard port
- ✅ Configured UFW with deny-by-default
- ✅ Enabled automatic security updates
- ✅ Installed and configured Fail2ban
This gets you to a reasonable baseline.