Skip to content
Summer 2026: 20% off 12-month terms with code ATLAS10 stacked on top
Guides 9 min read

The first hour on a new Linux VPS: 10 commands that matter

A copy-paste sequence for Ubuntu and Debian — SSH keys, firewall, fail2ban, unattended upgrades, swap, and a sane monitoring baseline.

ML

Marek Lindqvist

Infrastructure Security

Published

Updated

Quick answerKey-only SSH on a non-standard port, UFW default-deny, fail2ban, unattended-upgrades, and a swap file. Fifteen minutes of work that eliminates every automated attack you will ever face on a public IPv4.

0. Log in and look around

ssh [email protected]
uname -a; lsb_release -a; free -h; df -h; nproc

Confirm you got what you paid for. If nproc or free -h disagrees with your invoice, open a ticket before you build anything on it.

1. Update everything

apt update && apt full-upgrade -y && apt autoremove -y

2. Create a real user

Working as root full-time means every typo is fatal and every process runs privileged.

adduser atlas
usermod -aG sudo atlas

3. Install your SSH key

From your local machine:

ssh-keygen -t ed25519 -C "laptop-2026"   # if you do not have one
ssh-copy-id [email protected]

Open a second terminal and confirm ssh [email protected] works before touching sshd config. Locking yourself out of a fresh VPS is recoverable through our VNC console, but it is a tedious ten minutes you can avoid.

4. Harden SSH

sudo nano /etc/ssh/sshd_config
Port 2222
PermitRootLogin no
PasswordAuthentication no
KbdInteractiveAuthentication no
PubkeyAuthentication yes
X11Forwarding no
MaxAuthTries 3
ClientAliveInterval 300
AllowUsers atlas
sudo systemctl restart ssh

On Ubuntu 24.04 with socket activation you may also need sudo systemctl restart ssh.socket. Test the new port from the second terminal before closing the first.

5. Firewall: default deny

sudo ufw default deny incoming
sudo ufw default allow outgoing
sudo ufw allow 2222/tcp
sudo ufw allow 80,443/tcp     # only if this box serves web traffic
sudo ufw enable
sudo ufw status verbose

Add the SSH rule before ufw enable. This is the most common way people lock themselves out.

6. fail2ban

sudo apt install -y fail2ban
sudo tee /etc/fail2ban/jail.local >/dev/null <<'EOF'
[DEFAULT]
bantime  = 1h
findtime = 10m
maxretry = 4
backend  = systemd

[sshd]
enabled = true
port    = 2222
EOF
sudo systemctl enable --now fail2ban
sudo fail2ban-client status sshd

7. Automatic security updates

sudo apt install -y unattended-upgrades
sudo dpkg-reconfigure -plow unattended-upgrades
sudo tee /etc/apt/apt.conf.d/51atlas >/dev/null <<'EOF'
Unattended-Upgrade::Automatic-Reboot "true";
Unattended-Upgrade::Automatic-Reboot-Time "04:30";
EOF

Only enable automatic reboot if your services come back on their own. Check with systemctl is-enabled for each one.

8. Swap (yes, even with plenty of RAM)

Swap does not make a busy machine fast, but it stops the OOM killer from destroying your database at 3 a.m. because a log rotation spiked memory for four seconds.

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
sudo sysctl -w vm.swappiness=10
echo 'vm.swappiness=10' | sudo tee /etc/sysctl.d/99-swap.conf

9. Timezone, hostname, NTP

sudo hostnamectl set-hostname atlas-prod-01
sudo timedatectl set-timezone UTC
timedatectl status | grep -E 'synchronized|Time zone'

Keep servers on UTC. Correlating logs across regions in local time is a special kind of misery.

10. A monitoring baseline

sudo apt install -y htop ncdu iotop sysstat
sudo sed -i 's/ENABLED="false"/ENABLED="true"/' /etc/default/sysstat
sudo systemctl enable --now sysstat

sar now records CPU, memory, disk and network history every 10 minutes. When something goes wrong next month, you will have the data to explain it instead of a guess.

Verify

sudo ss -tulpn                     # what is actually listening?
sudo ufw status numbered
sudo fail2ban-client status sshd
sudo systemctl list-units --state=failed
sar -u 1 3

Anything listening on 0.0.0.0 that you did not deliberately expose should be bound to 127.0.0.1 instead. Databases in particular — an exposed Redis or Postgres with a weak password is found within hours.

Snapshot nowTake a snapshot once this baseline is in place. Every future server can start from that image, and if you break something during setup you roll back to a clean, hardened machine instead of reinstalling from scratch.
#linux#ubuntu#debian#security#ssh
ML

Marek Lindqvist

Infrastructure Security

Runs our hardening baselines and incident response. Previously a network engineer at a Nordic transit provider.

Put this into practice for $5 a month

Windows RDP from $12/month, Linux VPS from $5/month, delivered in about four minutes with a 72-hour money-back guarantee.