Search "SSH hardening" and you get a 20-item checklist: change the port, disable protocol 1, set a login banner, tweak ciphers, install fail2ban, rate-limit, add 2FA, port-knock… Most of it is security theater — it feels productive and moves almost no risk. Three changes do the real work. Here they are, and why the popular ones don't matter.
The 3 that actually move risk
1. Keys only — turn off password auth
This is the whole ballgame. Password auth means your servers are exposed to credential-stuffing and brute force 24/7. Keys make that class of attack impossible.
# /etc/ssh/sshd_config
PasswordAuthentication no
PubkeyAuthentication yes
Add your public key to ~/.ssh/authorized_keys first, test a new session, then reload sshd. Do this one thing and you've closed the door most attacks come through.
2. No direct root login
Even with keys, don't let anyone log in straight as root. Log in as a normal user, sudo when needed — so every privileged action is attributable and a single leaked key isn't instant root.
PermitRootLogin no
3. Limit who can log in
Most boxes have one or two humans who should ever SSH in. Say so explicitly:
AllowUsers alice bob
Now an attacker needs a valid username too, and a forgotten service account can't be used as a door.
That's it. Keys-only + no-root + an allow-list closes the paths real attacks use. Reload and you're done:
sudo systemctl reload sshd
The theater (and why)
-
Changing the port (22 → 2222). Doesn't stop anyone — a scanner finds the new port in seconds. Its only effect is a quieter
auth.log. That's a nice-to-have, not security. If you've done keys-only, the noise was already harmless. - fail2ban / rate-limiting. Great for log noise and password auth. But if you turned passwords off (#1), there's no password to brute-force — you're banning bots from a door that's already sealed. Defense in depth, not a load-bearing wall.
- Fancy cipher/MAC tuning. Modern OpenSSH defaults are already strong. Hand-tweaking the cipher list mostly risks locking out a client while adding no real protection.
- Login banners, protocol 1 disable. Protocol 1 has been dead for years; banners are legal cover, not defense.
None of these are wrong — they're just not where the risk is. Do them after the three that matter, if you like, not instead of.
Don't undo it all on your phone
The one place hardening quietly leaks: how you connect from mobile. A keys-only server is pointless if the private key is sitting in a synced note or a screenshot. On a phone the key should live in the secure enclave and unlock with biometrics — which is exactly how I built key handling into TermAI — but the rule holds for any client: the hardening on the server is only as good as where the key lives on the device.
TL;DR
Skip the 20-item checklist. Do three things: PasswordAuthentication no, PermitRootLogin no, AllowUsers <you>. That closes the paths attacks actually use. The port change and fail2ban are for a tidy log, not for security — do them last, or not at all. And keep your private key in your phone's secure enclave so none of it is wasted.
What's on your SSH hardening list that you'd defend as more than theater?
Top comments (0)