The First Ten Minutes on a New Linux Server

The First Ten Minutes on a New Linux Server

A new server is on the public internet from the moment it boots, and the automated scanning starts within minutes. This is the short list, in order, before you install anything you actually came for.

1. Update everything

sudo apt update && sudo apt full-upgrade -y     # Debian and Ubuntu
sudo dnf upgrade --refresh -y                   # Fedora and RHEL

The image you provisioned was built at some point in the past and there are known vulnerabilities with public exploits between then and now.

2. Create a user and stop using root

sudo adduser deploy
sudo usermod -aG sudo deploy      # Debian and Ubuntu
sudo usermod -aG wheel deploy     # Fedora and RHEL

Our useradd builder generates this, and note the -aG rather than -G, which appends rather than replacing every group the user is in.

3. Install your SSH key

From your local machine, not the server:

ssh-copy-id deploy@your.server.ip

Then confirm it works in a new terminal while the old one stays open:

ssh deploy@your.server.ip
sudo whoami     # should print root

Do not proceed until both succeed. Our SSH keys guide covers generating one if you have not.

4. Lock down SSH

sudo nano /etc/ssh/sshd_config
PermitRootLogin no
PasswordAuthentication no
KbdInteractiveAuthentication no
PubkeyAuthentication yes
AllowUsers deploy
sudo sshd -t                      # validate before restarting
sudo systemctl restart sshd

Test in a third terminal before closing anything. This step is what actually secures the server, and it is worth being careful with.

The SSH config builder handles the client side, and SSH hardening covers the rest of the options.

5. Firewall

Default deny inbound, then open only what you need.

# Debian and Ubuntu
sudo ufw default deny incoming
sudo ufw default allow outgoing
sudo ufw limit 22/tcp
sudo ufw allow 80/tcp
sudo ufw allow 443/tcp
sudo ufw enable
# Fedora and RHEL
sudo firewall-cmd --permanent --add-service=ssh
sudo firewall-cmd --permanent --add-service=http
sudo firewall-cmd --permanent --add-service=https
sudo firewall-cmd --reload

Add the SSH rule before enabling, or you will disconnect yourself. The ufw rule builder and firewalld guide cover both.

6. Automatic security updates

# Debian and Ubuntu
sudo apt install unattended-upgrades
sudo dpkg-reconfigure -plow unattended-upgrades

# Fedora and RHEL
sudo dnf install dnf-automatic
sudo systemctl enable --now dnf-automatic-install.timer

Configure it for security updates only. Unpatched known vulnerabilities compromise far more servers than automatic updates break.

7. Check what is listening

sudo ss -tlnp

Anything bound to 0.0.0.0 is reachable from your entire network, and from the internet if the firewall allows it. Database servers and admin interfaces should bind to 127.0.0.1 and be reached through a reverse proxy or a VPN.

Distribution images sometimes ship services you did not ask for. Disable them:

sudo systemctl list-units --type=service --state=running
sudo systemctl disable --now something-unnecessary

8. Set the timezone and hostname

sudo hostnamectl set-hostname web-01
sudo timedatectl set-timezone UTC
timedatectl status

UTC on servers saves confusion when correlating logs across machines. Confirm NTP synchronisation is active, because certificate validation and log correlation both depend on an accurate clock.

9. Swap, if there is none

Many VPS images ship without swap, and a small amount prevents the OOM killer from terminating your application during a brief spike.

sudo fallocate -l 2G /swapfile
sudo chmod 600 /swapfile
sudo mkswap /swapfile
sudo swapon /swapfile
echo '/swapfile none swap sw 0 0' | sudo tee -a /etc/fstab

See swap space explained for how much and why.

10. Decide the backup plan now

Not later. Later means after the first incident.

Snapshots from your provider are a good start and are not sufficient, because they live in the same account that an attacker who compromises the server may be able to reach.

Set up restic or Borg to somewhere else, and test a restore. A backup you have never restored from is a hypothesis.

The short version

Update, create a user, install a key, disable passwords and root login, enable a default-deny firewall, turn on security updates, and check what is listening. Everything else can wait; those seven steps eliminate essentially all of the opportunistic attacks a new server faces.

Frequently Asked Questions

What is the single most important step?

Key-based SSH with password authentication disabled. Almost every automated attack against a new server is a password guess, and removing passwords entirely removes that whole category rather than mitigating it.

Should I change the SSH port?

It reduces log noise from untargeted scanning and provides no real security, since a port scan finds it in seconds. Do it if quieter logs help you spot real events, but do not count it as a defence, and never as a substitute for key authentication.

Do I need fail2ban if passwords are disabled?

It becomes far less important, because there is nothing to brute force. It still trims log noise and can protect other services, so it is worth having, but key authentication is what actually secures SSH.

Are automatic security updates safe on a server?

For security patches only, yes, and the alternative is worse. Unpatched known vulnerabilities are a far more common cause of compromise than an update breaking something. Configure security updates automatically and schedule everything else.

Why disable root SSH login if I use keys?

Defence in depth. Attackers know root exists and its name never varies. Requiring a login to a named account and then sudo means an attacker needs the right key and the right username, and you get an audit trail of who did what.

How do I avoid locking myself out?

Keep your working session open while you test changes in a second terminal. Never close the connection that still works until a new one succeeds. Also confirm your provider offers console access before you begin.