Files
MajorWiki/02-selfhosting/security/linux-server-hardening-checklist.md
MajorLinux 87d63039af wiki: audit fixes — broken links, wikilinks, frontmatter, stale content (66 files)
- Fixed 4 broken markdown links (bad relative paths in See Also sections)
- Corrected n8n port binding to 127.0.0.1:5678 (matches actual deployment)
- Updated SnapRAID article with actual majorhome paths (/majorRAID, disk1-3)
- Converted 67 Obsidian wikilinks to relative markdown links or plain text
- Added YAML frontmatter to 35 articles missing it entirely
- Completed frontmatter on 8 articles with missing fields

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-04-02 11:16:29 -04:00

6.1 KiB

title, domain, category, tags, status, created, updated
title domain category tags status created updated
Linux Server Hardening Checklist selfhosting security
security
hardening
linux
ssh
firewall
server
published 2026-03-08 2026-03-08

Linux Server Hardening Checklist

When I set up a fresh Linux server, there's a standard set of things I do before I put anything on it. None of this is exotic — it's the basics that prevent the most common attacks. Do these before the server touches the public internet.

The Short Answer

New server checklist: create a non-root user, disable root SSH login, use key-based auth only, configure a firewall, keep packages updated. That covers 90% of what matters.

1. Create a Non-Root User

Don't work as root. Create a user, give it sudo:

# Create user
adduser yourname

# Add to sudo group (Debian/Ubuntu)
usermod -aG sudo yourname

# Add to wheel group (Fedora/RHEL)
usermod -aG wheel yourname

Log out and log back in as that user before doing anything else.

2. SSH Key Authentication

Passwords over SSH are a liability. Set up key-based auth and disable password login.

On your local machine, generate a key if you don't have one:

ssh-keygen -t ed25519 -C "yourname@hostname"

Copy the public key to the server:

ssh-copy-id yourname@server-ip

Or manually append your public key to ~/.ssh/authorized_keys on the server.

Test that key auth works before disabling passwords.

3. Harden sshd_config

Edit /etc/ssh/sshd_config:

# Disable root login
PermitRootLogin no

# Disable password authentication
PasswordAuthentication no

# Disable empty passwords
PermitEmptyPasswords no

# Limit to specific users (optional but good)
AllowUsers yourname

# Change the port (optional — reduces log noise, not real security)
Port 2222

Restart SSH after changes:

sudo systemctl restart sshd

Keep your current session open when testing — if you lock yourself out you'll need console access to fix it.

4. Configure a Firewall

ufw (Ubuntu/Debian):

sudo apt install ufw

# Default: deny incoming, allow outgoing
sudo ufw default deny incoming
sudo ufw default allow outgoing

# Allow SSH (use your actual port if you changed it)
sudo ufw allow 22/tcp

# Allow whatever services you're running
sudo ufw allow 80/tcp
sudo ufw allow 443/tcp

# Enable
sudo ufw enable

# Check status
sudo ufw status verbose

firewalld (Fedora/RHEL):

sudo systemctl enable --now firewalld

# Allow SSH
sudo firewall-cmd --permanent --add-service=ssh

# Allow HTTP/HTTPS
sudo firewall-cmd --permanent --add-service=http
sudo firewall-cmd --permanent --add-service=https

# Apply changes
sudo firewall-cmd --reload

# Check
sudo firewall-cmd --list-all

5. Keep Packages Updated

Security patches come through package updates. Automate this or do it regularly:

# Ubuntu/Debian — manual
sudo apt update && sudo apt upgrade

# Enable unattended security upgrades (Ubuntu)
sudo apt install unattended-upgrades
sudo dpkg-reconfigure --priority=low unattended-upgrades

# Fedora/RHEL — manual
sudo dnf upgrade

# Enable automatic updates (Fedora)
sudo dnf install dnf-automatic
sudo systemctl enable --now dnf-automatic.timer

6. Fail2ban

Fail2ban watches log files and bans IPs that fail authentication too many times. Helps with brute force noise.

# Ubuntu/Debian
sudo apt install fail2ban

# Fedora/RHEL
sudo dnf install fail2ban

# Start and enable
sudo systemctl enable --now fail2ban

Create /etc/fail2ban/jail.local to override defaults:

[DEFAULT]
bantime = 1h
findtime = 10m
maxretry = 5

[sshd]
enabled = true
sudo systemctl restart fail2ban

# Check status
sudo fail2ban-client status sshd

7. Disable Unnecessary Services

Less running means less attack surface:

# See what's running
systemctl list-units --type=service --state=active

# Disable something you don't need
sudo systemctl disable --now servicename

Common ones to disable on a dedicated server: avahi-daemon, cups, bluetooth.

8. Mail Server: SpamAssassin

If you're running Postfix (like on majormail), SpamAssassin filters incoming spam before it hits your mailbox.

Install (Fedora/RHEL):

sudo dnf install spamassassin
sudo systemctl enable --now spamassassin

Integrate with Postfix by adding a content filter in /etc/postfix/master.cf. See the full setup guide for Postfix integration on RedHat-based systems.

Train the filter with sa-learn:

SpamAssassin gets better when you feed it examples of spam and ham (legitimate mail):

# Train on known spam
sa-learn --spam /path/to/spam-folder/

# Train on known good mail
sa-learn --ham /path/to/ham-folder/

# Check what sa-learn knows
sa-learn --dump magic

Run sa-learn periodically against your Maildir to keep the Bayesian filter accurate. The more examples it sees, the fewer false positives and missed spam you'll get.

Reference: sa-learn documentation

Gotchas & Notes

  • Don't lock yourself out. Test SSH key auth in a second terminal before disabling passwords. Keep the original session open.
  • If you changed the SSH port, make sure the firewall allows the new port before restarting sshd. Block the old port after you've confirmed the new one works.
  • fail2ban and Docker don't always play nicely. Docker bypasses iptables rules in some configurations. If you're running services in Docker, test that fail2ban is actually seeing traffic.
  • SELinux on RHEL/Fedora may block things your firewall allows. Check ausearch -m avc if a service stops working after hardening.
  • This is a baseline, not a complete security posture. For anything holding sensitive data, also look at: disk encryption, intrusion detection (AIDE, Tripwire), log shipping to a separate system, and regular audits.

See Also