Fail2ban su VPS Ubuntu: come proteggere SSH e WordPress dagli attacchi brute force

Basta guardare i log di un VPS appena messo online per accorgersi di una cosa: nel giro di poche ore arrivano già i primi tentativi di accesso. Sono bot che provano password a raffica su SSH, su wp-login.php e su xmlrpc.php. Dopo falle come PHP2Shell il traffico ostile cresce ancora, perché molti scanner cercano contemporaneamente server vulnerabili e password deboli.

Fail2ban è uno dei modi più semplici per ridurre questo rumore. Legge i log, individua gli indirizzi IP che sbagliano troppe volte e li blocca con il firewall per un po’ di tempo. In questa guida lo configuriamo per SSH e per WordPress su un server Ubuntu con OpenLiteSpeed.

Leggi anche: Aggiornare tutti i pacchetti PHP (lsphp) su OpenLiteSpeed: Guida a Snapshot e Rollback Senza Rischi

Pubblicità

1. Installazione

sudo apt update
sudo apt install -y fail2ban
sudo systemctl enable --now fail2ban
sudo fail2ban-client status

Per impostazione predefinita Ubuntu attiva già la protezione di SSH con valori standard. Il comando status te lo conferma, mostrando la jail sshd nell’elenco.

2. Non modificare jail.conf

Il file /etc/fail2ban/jail.conf viene sovrascritto a ogni aggiornamento del pacchetto. Le tue impostazioni vanno in un file separato, che ha la precedenza:

sudo nano /etc/fail2ban/jail.local

Parti da queste impostazioni generali:

[DEFAULT]
ignoreip = 127.0.0.1/8 ::1 IL_TUO_IP
bantime = 1h
findtime = 10m
maxretry = 5
bantime.increment = true
bantime.factor = 2
bantime.maxtime = 1w

Cosa significano:

  • ignoreip è l’elenco degli indirizzi che non verranno mai bloccati. Metti qui il tuo IP, altrimenti un errore di digitazione ti chiude fuori dal server.
  • maxretry e findtime insieme dicono che 5 errori in 10 minuti fanno scattare il blocco.
  • bantime è la durata del blocco, un’ora in questo caso.
  • bantime.increment raddoppia la durata a ogni recidiva, fino a un massimo di una settimana. Chi insiste viene fermato sempre più a lungo.

3. Proteggere SSH

Aggiungi in fondo allo stesso file:

[sshd]
enabled = true
backend = systemd
port = ssh
maxretry = 4
findtime = 10m
bantime = 2h

Se hai spostato SSH su una porta diversa dalla 22, scrivi il numero al posto di ssh, per esempio port = 2222. L’impostazione backend = systemd fa leggere gli accessi dal journal di sistema, che è dove Ubuntu li registra nelle versioni recenti.

Applica la configurazione:

sudo fail2ban-client reload
sudo fail2ban-client status sshd

Prima di chiudere il terminale, apri una seconda sessione SSH e verifica di riuscire ancora a entrare. Una configurazione sbagliata è meglio scoprirla quando hai ancora una sessione aperta da cui sistemare le cose.

4. Proteggere il login di WordPress

Qui serve qualche passaggio in più, perché Fail2ban non sa da solo cosa sia un tentativo fallito di accesso a WordPress. Glielo spieghiamo con un filtro.

Prima individua il file di log degli accessi del tuo sito. Con OpenLiteSpeed di solito è /usr/local/lsws/logs/access.log oppure un file dentro la cartella logs del Virtual Host. Con aaPanel i file sono in /www/wwwlogs/. Controlla che dentro ci siano le richieste del tuo sito:

sudo tail -n 5 /usr/local/lsws/logs/access.log

Ogni riga deve iniziare con l’indirizzo IP del visitatore. Se invece vedi sempre lo stesso IP, vuol dire che il sito è dietro un proxy o una CDN come Cloudflare e il server non vede l’IP reale. In quel caso Fail2ban bloccherebbe il proxy e quindi tutti i visitatori. Devi prima fare in modo che il log registri l’IP vero, ad esempio con l’intestazione X-Forwarded-For o CF-Connecting-IP, e solo dopo continuare.

Crea il filtro per il login:

sudo nano /etc/fail2ban/filter.d/wordpress-login.conf
[Definition]
failregex = ^<HOST> \S+ \S+ \[[^\]]+\] "POST /wp-login\.php[^"]*" 200
ignoreregex =

Il codice 200 è importante. Quando la password è sbagliata, WordPress ripresenta la pagina di login con risposta 200. Quando è giusta, risponde con un reindirizzamento 302. Così il filtro conta solo i tentativi falliti e non blocca chi accede correttamente.

Ora il filtro per xmlrpc.php, che non viene usato dai visitatori normali e di solito è il bersaglio preferito dei bot:

sudo nano /etc/fail2ban/filter.d/wordpress-xmlrpc.conf
[Definition]
failregex = ^<HOST> \S+ \S+ \[[^\]]+\] "POST /xmlrpc\.php
ignoreregex =

Se usi l’app mobile di WordPress o Jetpack, che sfruttano xmlrpc.php, ricorda che questo filtro può bloccare anche richieste legittime. In quel caso puoi alzare maxretry oppure non attivare questa jail.

Registra le due jail in jail.local, sostituendo il percorso del log con il tuo:

[wordpress-login]
enabled = true
port = http,https
filter = wordpress-login
logpath = /usr/local/lsws/logs/access.log
maxretry = 5
findtime = 10m
bantime = 2h

[wordpress-xmlrpc]

enabled = true port = http,https filter = wordpress-xmlrpc logpath = /usr/local/lsws/logs/access.log maxretry = 3 findtime = 10m bantime = 24h

Se hai più siti con log separati, puoi indicare più file nella stessa riga, uno per riga sotto logpath, oppure usare un pattern come /www/wwwlogs/*.log.

5. Provare i filtri prima di attivarli

Fail2ban ha uno strumento che applica il filtro a un log reale e dice quante righe corrispondono:

sudo fail2ban-regex /usr/local/lsws/logs/access.log /etc/fail2ban/filter.d/wordpress-login.conf
sudo fail2ban-regex /usr/local/lsws/logs/access.log /etc/fail2ban/filter.d/wordpress-xmlrpc.conf

Nel risultato guarda la riga Lines: con i numeri di righe lette e corrispondenti. Se il numero di corrispondenze è zero ma sai che nel log ci sono tentativi di accesso, il formato del tuo log è diverso da quello previsto. Confronta una riga reale con l’espressione e adatta il filtro.

Quando è tutto a posto:

sudo fail2ban-client reload
sudo fail2ban-client status

Nell’elenco devono comparire sshd, wordpress-login e wordpress-xmlrpc.

6. Jail per i recidivi

Fail2ban può anche tenere d’occhio i propri blocchi. Se lo stesso IP viene bloccato più volte in un giorno, merita una pausa molto più lunga. Aggiungi:

[recidive]
enabled = true
logpath = /var/log/fail2ban.log
banaction = %(banaction_allports)s
bantime = 1w
findtime = 1d
maxretry = 3

Un IP bannato tre volte nell’arco di un giorno viene escluso da tutte le porte per una settimana.

7. Usarlo ogni giorno

Questi sono i comandi che ti serviranno più spesso:

# stato generale e stato di una singola jail
sudo fail2ban-client status
sudo fail2ban-client status wordpress-login

# sbloccare un indirizzo (per esempio il tuo)
sudo fail2ban-client set wordpress-login unbanip 203.0.113.10

# bloccare a mano un indirizzo
sudo fail2ban-client set sshd banip 203.0.113.10

# vedere gli ultimi blocchi e sblocchi
sudo grep -E "Ban|Unban" /var/log/fail2ban.log | tail -n 30

Se usi UFW come firewall, aggiungi nel blocco [DEFAULT] la riga banaction = ufw. Così i blocchi di Fail2ban compaiono tra le regole di UFW e non si creano due sistemi paralleli.

Cosa non fa Fail2ban

Va detto con chiarezza, per non farsi false sicurezze. Fail2ban rallenta chi attacca da pochi indirizzi, ma una botnet che prova una password per volta da migliaia di IP diversi lo aggira facilmente. Non sostituisce quindi le basi: password lunghe, chiavi SSH al posto delle password, nessun accesso diretto come root e WordPress con plugin aggiornati. Se vuoi un’altra barriera lato WordPress, nella guida ai comandi per wp-config.php trovi le costanti per disattivare l’editor dei file e forzare HTTPS sull’amministrazione.

Leggi anche: Aggiornamenti automatici di sicurezza su Ubuntu: come configurare unattended-upgrades su un VPS

Un ultimo consiglio pratico: dopo il primo giorno di attività guarda cosa è stato bloccato. Se vedi finire in lista solo IP sconosciuti e con tentativi ripetuti, la configurazione sta lavorando bene. Se trovi bloccato un tuo collaboratore o il tuo stesso IP, aggiungilo a ignoreip e sblocca l’indirizzo con il comando visto sopra.

Altro per te

PHP
PHP Compatibility Checker
Controlla il tuo plugin WordPress prima di aggiornare PHP Verifica la compatibilità con PHP 8.0–8.5 Scopri eventuali problemi nel codice PHP Analizza il tuo plugin WordPress online Preparati a PHP 8.5
Verifica ora →
PDF Strumenti PDF gratis Nel browser, senza upload Apri gli strumenti

🔒

Contenuto riservato

Per scaricare questo file devi prima registrarti oppure accedere con il tuo account.

XWhatsAppTelegram