SSD Nodes Learn Hosting plans →
Guide Matt ConnorDi Matt Connor

Gestire più server Linux: strumenti efficaci

SSH config, tmux, Ansible, Uptime Kuma, Zabbix e Webmin ordinati per numero di server: cosa sostituiscono, minuti di setup e un problema concreto per ciascuno.

Cosa stai costruendo

Non un singolo strumento, ma uno stack essenziale, scelto in base al numero effettivo di server. Questo è l'unico dato realmente importante, ed è proprio quello che ogni raccolta di «strumenti per la gestione dei server Linux» ignora. L'errore classico è adottare una soluzione pensata per 200 server quando se ne gestiscono quattro VPS e passare un mese a configurare lo strumento invece dei server. Il secondo errore classico è continuare ad accedere manualmente via SSH a ciascuno dei diciotto server, applicando «la stessa» modifica in diciotto modi leggermente diversi.

Per questo la guida è organizzata in base alle dimensioni dell'infrastruttura: da 2 a 5 server, da 5 a 20 e oltre 20, oltre al livello trasversale che si applica a ogni dimensione e che quasi nessuno documenta: un inventario, una corretta gestione delle chiavi, un unico punto di accesso e backup che siano stati effettivamente ripristinati. Per ogni strumento vengono indicati tre elementi: cosa sostituisce, quanto tempo richiede la configurazione, espresso in minuti, e l'unico problema concreto che può causare. Gestisco un host VPS da quindici anni; l'elenco seguente comprende ciò che resiste a un'interruzione alle 2 di notte, non ciò che fa una buona impressione in una demo.

Prerequisiti e aspetti critici da considerare

È necessario che l’accesso SSH con chiavi sia già funzionante su ogni server. Se dovete ancora inserire password, risolvete prima questo problema: richiede dieci minuti e tutto ciò che segue presuppone l’uso delle chiavi. Serve inoltre un utente con privilegi sudo diverso da root e server che eseguano software aggiornato. I comandi riportati presuppongono Ubuntu 24.04, ma nulla è specifico di Ubuntu, tranne apt.

Prima degli strumenti, considerate due avvertenze importanti. Primo: la proliferazione degli strumenti è di per sé un problema di gestione. Ogni agent che installate è un altro daemon da aggiornare su ogni server. Pertanto, la soglia per aggiungerne uno dovrebbe essere «sostituisce un’attività manuale che ho svolto questa settimana», non «sembra utile». Secondo: tutto il software qui descritto è libero e il costo reale è il tempo di configurazione. Per questo ogni strumento include una stima in minuti. Quando la stima indica un pomeriggio, consideratela attendibile.

Da 2 a 5 server: ~/.ssh/config è lo strumento più sottovalutato che hai già

Cosa sostituisce: il file di testo con gli indirizzi IP, l'archeologia della cronologia della shell (ssh 203.0, poi Ctrl-R e si spera), e la digitazione continua di -p 2222 -i ~/.ssh/other_key. Costo di configurazione: 15 minuti, una volta sola. Problema: socket di multiplexing obsoleti, descritti più avanti.

A questa scala non ti serve un software dedicato. Ti serve configurare il client che hai già, in modo coerente con il tuo utilizzo. ~/.ssh/config trasforma ogni server in un nome di una sola parola e definisce il routing, così non devi più pensarci:

Host *
    ServerAliveInterval 30
    ControlMaster auto
    ControlPath ~/.ssh/cm-%r@%h-%p
    ControlPersist 10m

Host bastion
    HostName 10.0.0.10
    User matt

Host web1
    HostName 10.8.0.11
    User matt
    ProxyJump bastion

Host db1
    HostName 10.8.0.12
    User matt
    Port 2222
    ProxyJump bastion

Tre impostazioni svolgono tutto il lavoro. ProxyJump instrada le connessioni attraverso un bastion host in un solo passaggio, quindi ssh db1 da una caffetteria crea in modo trasparente un tunnel attraverso bastion, senza inoltro dell'agent e senza incantesimi ProxyCommand. Inoltre, i server privati non devono esporre affatto porte SSH pubbliche (approfondiremo il tema nella sezione trasversale). ControlMaster auto con ControlPersist esegue il multiplexing delle connessioni su una sola sessione TCP. La seconda e tutte le successive ssh, scp o rsync verso lo stesso host si connettono immediatamente invece di rinegoziare la sessione. La differenza diventa notevole quando entra in gioco Ansible. Poiché scp, rsync e Ansible leggono tutti lo stesso file, ogni nome definito qui funziona ovunque.

Il problema è che la connessione master può restare attiva anche quando non è più utile, e le due modalità di errore sono diverse. Quando il server si riavvia o la connessione Wi-Fi cade, il processo master mantiene una sessione TCP interrotta che non ha ancora rilevato. La successiva ssh web1 resta quindi bloccata in silenzio su un socket che non porta da nessuna parte. Separatamente, sshd limita a 10 il numero di sessioni per connessione (MaxSessions in sshd_config), quindi l'undicesima sessione multiplexata verso un host mostra:

mux_client_request_session: session request failed: Session open refused by peer

La correzione è la stessa in entrambi i casi: ssh -O exit web1 termina il master e la connessione successiva ne avvia uno nuovo. Puoi inoltre vedere occasionalmente ControlSocket /home/matt/.ssh/cm-matt@10.8.0.11-22 already exists, disabling multiplexing. È innocuo: due sessioni hanno tentato di connettersi contemporaneamente e la connessione continua a funzionare, semplicemente senza multiplexing.

A questa scala sono utili anche due strumenti complementari. tmux su ogni server sostituisce nohup, evita di perdere il lavoro quando cade la connessione Wi-Fi e risolve il problema del «non posso chiudere il portatile, è in corso una migrazione». Costo di configurazione: sudo apt install -y tmux, due minuti, oltre al necessario apprendimento mnemonico di tmux new -s work e tmux attach -t work. Il problema è il nesting: tmux dentro tmux intercetta il tasto del prefisso. Eseguilo quindi sul server oppure sul portatile, non su entrambi. Se esegui sessioni agent di lunga durata, questo aspetto è ancora più importante. È lo stesso schema di eseguire Claude Code in tmux su un VPS, dove la sessione deve sopravvivere alla connessione SSH.

Un file condiviso di alias evita di riscrivere su ogni macchina i tuoi dodici one-liner preferiti. Mantieni un .bash_aliases in un repository git e scaricalo su ogni server. Il problema è che il file diverge non appena lo modifichi direttamente su un server invece che nel repository. È anche il primo esempio del motivo per cui esiste il livello successivo.

5-20 server: configurazione come codice, oppure vince il drift

Superati circa cinque server, «lo faccio su ogni macchina» smette di essere un metodo e diventa una giustificazione. Tutti gli strumenti di questo livello affrontano lo stesso problema: il drift.

Ansible sostituisce il ciclo della shell sui nomi host, la pagina wiki intitolata «configurazione di un nuovo server» ormai obsoleta di tre passaggi e il dubbio di non sapere se web3 abbia effettivamente ricevuto la correzione. Il tempo di configurazione è di 30 minuti per ottenere il primo playbook funzionante, sudo apt install -y ansible sul laptop o su un server di gestione (apt fornisce una release di Ansible meno recente, sufficiente per tutto ciò che viene descritto qui; il percorso pipx del tutorial installa le versioni correnti), senza agenti sui server e con tutte le operazioni eseguite tramite la configurazione SSH già predisposta. È il miglioramento più significativo di questa pagina. La procedura completa è disponibile nel tutorial sul primo playbook Ansible; questa è la struttura dell'inventory necessaria:

[web]
web1 ansible_host=10.8.0.11
web2 ansible_host=10.8.0.12

[db]
db1 ansible_host=10.8.0.21 ansible_port=2222

[all:vars]
ansible_user=matt
ansible_ssh_common_args='-o ProxyJump=bastion'

Poiché Ansible esegue il binario OpenSSH, il ~/.ssh/config scritto nella sezione precedente è già applicato. Un inventory con nomi semplici come web1 funzionerebbe anche senza variabili. Le variabili riportate sopra rendono invece l'inventory autonomo. Questo è utile quando lo si esegue da una macchina diversa dal laptop.

Esegui il test con ansible all -i inventory.ini -m ping. Un risultato corretto stampa "ping": "pong" per ogni host, in verde. Il primo errore che probabilmente incontrerai è simile al seguente:

web1 | UNREACHABLE! => {
    "changed": false,
    "msg": "Failed to connect to the host via ssh: matt@10.8.0.11: Permission denied (publickey).",
    "unreachable": true
}

Non è un problema di Ansible: anche un semplice ssh matt@10.8.0.11 fallisce nello stesso modo. Risolvi prima il problema SSH, sempre. Ansible è affidabile solo quanto il livello sottostante. L'unico problema aggiuntivo è che Ansible richiede Python sulla macchina locale e, per quasi tutti i moduli incluso ping, anche sul server. Per questo un'immagine realmente minimale può restituire /usr/bin/python3: not found. Un singolo apt install python3 risolve il problema definitivamente. Per un'intera flotta di immagini minimali, il modulo raw, uno dei pochi che non richiedono Python sul sistema remoto, può eseguire direttamente l'installazione.

unattended-upgrades sostituisce l'amministratore che applica le patch di sicurezza a N server. Ubuntu Server 24.04 lo include già e, normalmente, lo abilita per gli aggiornamenti di sicurezza. In questo caso devi quindi verificarne la configurazione, non installarlo:

cat /etc/apt/apt.conf.d/20auto-upgrades

Entrambe le righe dovrebbero terminare con "1". Alcune immagini minimali e cloud lo forniscono disabilitato. sudo dpkg-reconfigure -plow unattended-upgrades riscrive il file se necessario. Il tempo di configurazione è di due minuti per server, oppure una sola attività Ansible per tutti i server. Il problema è che, per impostazione predefinita, non riavvia mai il sistema. Gli aggiornamenti di sicurezza del kernel restano quindi applicati solo parzialmente finché non esegui il riavvio. La guida dedicata a unattended-upgrades descrive i riavvii automatici, la selezione degli aggiornamenti da applicare e la lettura dei log.

Monitoraggio centralizzato. Evita di scoprire un problema da un cliente, che è il sistema di monitoraggio più costoso che si possa progettare. Due strumenti, con una riga ciascuno su quando usarli: Uptime Kuma risponde alla domanda «il servizio è attivo?». Esegue controlli HTTP, TCP e ping, invia notifiche a qualsiasi destinazione e richiede dieci minuti per la configurazione in Docker. Zabbix risponde invece alla domanda «sta per avere un guasto?». Raccoglie gli andamenti di disco, memoria e CPU tramite un agent su ogni host e richiede realisticamente un pomeriggio. Inizia con Kuma. Aggiungi Zabbix quando lo stato «attivo ma degradato» inizia a causare costi. Il problema comune a entrambi è il posizionamento. È abbastanza importante da essere trattato nella sezione sugli errori riportata di seguito.

Un pannello web, solo se necessario. Webmin evita di dover ricordare dove Ubuntu conserva le varie impostazioni. Per un team con competenze miste o per un server che gestisci due volte all'anno può essere realmente utile. La configurazione richiede dieci minuti. Il problema è che si tratta di un'applicazione web equivalente a root, in ascolto sulla porta 10000, e Internet la sottopone continuamente a scansioni. Se lo utilizzi, collegalo a localhost o a un indirizzo VPN, mai a 0.0.0.0 su un'interfaccia pubblica. Se stai valutando un pannello perché SSH sembra lento, rileggi prima la sezione precedente: ~/.ssh/config insieme ad Ansible è più veloce di qualsiasi pannello dopo la configurazione.

Oltre 20 server: dove questa guida termina davvero

Oltre 20 server stai gestendo una flotta e la toolchain cambia struttura: Terraform o OpenTofu per rendere riproducibili i server stessi, cloud-init o golden image per fare in modo che un sistema sia sostituibile anziché riparabile, configurazione pull-based o pipeline CI che eseguono Ansible perché il push da un laptop non scala più, e una gestione reale dei secret. Ansible non smette di funzionare a 20 server; molte organizzazioni lo usano su centinaia di nodi. Tuttavia, le procedure che lo circondano devono diventare più rigorose, e questo argomento esula da ciò che tratta questo sito. Se operi su questa scala, la sezione seguente riguarda comunque anche te, perché inventory, chiavi e disciplina degli accessi sono esattamente gli elementi che gli strumenti per la gestione delle flotte presuppongono tu abbia già.

Il livello che nessuno documenta

Quattro pratiche si applicano a flotte di qualsiasi dimensione. Ignorarle è il motivo per cui il numero di server sembra più oneroso di quanto sia realmente.

Un file di inventario, anche di testo. Non appena hai tre server, annota: nome, IP, provider, cosa vi è in esecuzione e perché esiste. Un servers.md in un repository git va bene; l'inventario Ansible riportato sopra è migliore perché costituisce documentazione eseguibile. Cosa sostituisce: la domanda delle 2 di notte «aspetta, che cos'è 10.0.0.40?». Costo di configurazione: dieci minuti. Attenzione: funziona solo se la creazione di un server e l'aggiunta della riga avvengono nello stesso momento, mai in due momenti distinti.

Gestione corretta delle chiavi: rotazione subito, una CA SSH quando la gestione diventa onerosa. Elenca dove si trovano le tue chiavi (cat ~/.ssh/*.pub sul tuo sistema, ~/.ssh/authorized_keys sul lato di ciascun server), rimuovi quelle presenti su ex-laptop e associate a ex-colleghi e ruota tutte quelle abbastanza vecchie da non permetterti di dire dove siano state utilizzate. Una Certification Authority SSH, con certificati firmati e a validità breve al posto di chiavi statiche, è la soluzione più strutturata. Tuttavia, il consiglio onesto è che sotto i dieci server una gestione disciplinata di authorized_keys tramite Ansible offre il 90% dei vantaggi con il 10% della complessità procedurale.

Un solo punto di accesso, non venti. Ogni porta SSH pubblica aumenta la superficie di attacco, moltiplicata per N. Il modello che scala è questo: un bastion host oppure, meglio ancora, una VPN WireGuard su un VPS sotto il tuo controllo, mentre SSH di tutti gli altri server deve essere associato soltanto al relativo indirizzo privato. Le righe ProxyJump nella configurazione riportata sopra presuppongono già questo modello. Tutto ciò che deve restare pubblico deve avere fail2ban come misura standard. Costo di configurazione: un'ora, una sola volta. Attenzione: verifica che il fallback, cioè l'accesso alla console del provider, funzioni prima di chiudere la porta 22 ovunque, non dopo.

Backup verificati tramite un ripristino. Un backup non verificato è solo un'ipotesi. Qualunque meccanismo utilizzi, snapshot del provider, restic, rsync su un secondo server, lo strumento realmente importante è l'evento in calendario in cui ripristini un server su un VPS appena creato e confermi che si avvii e risponda alle richieste. In ogni storia di problemi con i backup che ho sentito nei miei quindici anni di hosting compare la frase «avevamo i backup».

Gli errori

I problemi che si verificano su più server non dipendono dagli strumenti, ma dalle abitudini operative. Quattro cause spiegano quasi tutti i casi.

Server snowflake. Ogni macchina è stata configurata manualmente, presenta differenze difficili da individuare e nessuno sa ricrearla. Il problema emerge quando si guasta un disco. La soluzione è poco appariscente ma efficace: ogni modifica deve passare da Ansible oppure, come minimo, deve essere aggiunta alla sezione relativa a quel server nel documento dell'inventario. Qualsiasi server che oggi non si potrebbe ricreare usando soltanto la documentazione è debito tecnico con una scadenza che non si può scegliere.

Eccezioni "temporanee" nel firewall. ufw allow 5432 per eseguire il troubleshooting e, 18 mesi dopo, Postgres è ancora esposto a Internet. Eseguire un audit con sudo ufw status numbered su ogni macchina oppure, in un'unica operazione, con ansible all -i inventory.ini -a "ufw status numbered" --become, quindi eliminare ogni regola per cui non si riesce a indicare un motivo attuale. Se una regola è davvero temporanea, il relativo ufw delete deve essere inserito nella stessa finestra tmux prima di chiuderla.

Monitoraggio ospitato su una macchina monitorata. Se Uptime Kuma viene eseguito sul server che monitora, anche l'avviso che segnala "è tutto non disponibile" non può funzionare. Si ottiene una versione più piccola e meno efficiente di il datacenter meno efficiente del mondo. Il monitoraggio deve risiedere in un dominio di errore diverso: la soluzione classica è un VPS economico presso un altro provider oppure, come minimo, un controllo esterno su un piano gratuito che monitori il sistema di monitoraggio.

SSH come root ovunque. Una chiave root condivisa nell'intero parco server significa che un solo laptop compromesso consente di controllare tutto e che non esiste una traccia di audit per sapere chi ha eseguito ogni operazione. Creare utenti personali, usare sudo e configurare PermitRootLogin no in /etc/ssh/sshd_config su ogni host. Anche in questo caso si tratta di un'attività Ansible di tre righe, non di una serata passata a digitare comandi.

Quando il parco server supera poche macchine, il primo playbook Ansible automatizza le attività ripetitive.

FAQ

Qual è il migliore strumento gratuito per gestire più server Linux?

Per 2-5 server, un ~/.ssh/config scritto correttamente insieme a tmux è migliore di qualsiasi strumento installabile. Da circa cinque server in poi, Ansible è la scelta standard: non richiede agent, è gratuito, usa SSH, che è già disponibile, e trasforma la configurazione dei server in file versionabili in git. Aggiungete Uptime Kuma per gli avvisi sullo stato dei servizi; tutti gli strumenti citati in questa guida sono software libero.

Posso gestire più server Linux senza Ansible?

Sì. Al di sotto di circa cinque server sono sufficienti una buona configurazione SSH, un file di alias condiviso e disciplina; molte persone lavorano così per anni. Oltre questa soglia, l'alternativa ad Ansible non è "niente", ma una deriva di configurazione non documentata: diciotto server configurati manualmente in modo leggermente diverso. Se Ansible sembra troppo complesso, iniziate con un playbook che gestisca soltanto authorized_keys e unattended-upgrades; da solo ripaga il tempo necessario per impararlo.

Come posso eseguire contemporaneamente lo stesso comando su più server Linux?

ansible all -i inventory.ini -a "uptime" è la soluzione più lineare e non richiede playbook, ma soltanto il file di inventario. Per lavorare interattivamente affiancando più sessioni, tmux può trasmettere i tasti a ogni pannello con setw synchronize-panes on, ma consideratela una dimostrazione: trasmettere comandi interattivi ai server di produzione è il modo in cui un singolo errore di battitura diventa un'interruzione del servizio moltiplicata per N.

Mi serve un pannello di controllo come Webmin per gestire i server Linux?

No. Tutte le operazioni eseguibili da un pannello possono essere svolte da SSH e Ansible in modo più riproducibile. Webmin è utile quando persone con livelli di competenza diversi amministrano gli stessi server, oppure quando si interviene su un server così raramente che ritrovare i percorsi della configurazione richiede tempo significativo. Se lo utilizzate, trattatelo come l'applicazione web equivalente a root che è: collegatelo a localhost o a un indirizzo VPN, mai a un'interfaccia pubblica.

Quanti server Linux può gestire realisticamente una sola persona?

Con l'amministrazione manuale, la qualità inizia a diminuire prima di arrivare a dieci server. Con la configurazione come codice, il patching automatizzato e il monitoraggio centralizzato, una persona scrupolosa può gestire da 20 a 50 server come attività part-time; il limite dipende dalla frequenza con cui si verificano problemi nuovi, non dalla manutenzione ordinaria. Il numero importante non è quello dei server per amministratore, ma quello dei server configurati in modo unico per amministratore: mantenetelo vicino a zero e il limite operativo resta elevato.