Un server nou cu Ubuntu primește conexiuni SSH din toată lumea din prima clipă în care are IP public. Înainte să instalezi pe el un site sau o aplicație, merită să faci o dată câțiva pași de bază: un utilizator separat pentru lucru, acces doar cu cheie, root blocat pentru SSH, firewall și actualizări de securitate care se instalează singure.

Ghidul e scris pentru Ubuntu 24.04 LTS, care primește actualizări standard până în 2029. Pe Ubuntu 22.04 LTS pașii sunt aceiași. Unde Debian 12/13 sau AlmaLinux/Rocky Linux 9 se comportă altfel, ai o notă. Înlocuiește vechile noastre articole pentru Ubuntu 16.04 și CentOS 7, sisteme care nu mai primesc actualizări standard de ani de zile.

La final vei avea:

  • un utilizator cu drepturi sudo, pe care îl folosești în locul lui root;
  • autentificare SSH doar cu cheie, fără parole și fără login direct ca root;
  • firewall UFW care lasă să treacă doar SSH;
  • actualizări de securitate instalate automat;
  • fus orar, sincronizare a orei și hostname setate corect.

Ce îți trebuie

  • Un VPS cu Ubuntu 24.04 LTS și acces root. Pe un VPS BTS alegi sistemul de operare la configurare; varianta Self îți dă root complet și administrezi tu sistemul, deci ghidul ăsta e pentru tine. Pe Managed, actualizările, securizarea și monitorizarea serverului sunt la noi.
  • Adresa IP a serverului. În exemple folosim 203.0.113.10; o înlocuiești peste tot cu a ta.
  • O pereche de chei SSH pe calculatorul de pe care lucrezi. Dacă n-ai încă una, vezi cum setezi o cheie SSH.
  • Un terminal: Terminal pe macOS sau Linux, PowerShell sau Windows Terminal pe Windows 10/11 (clientul OpenSSH e inclus).

În comenzi, utilizator e numele contului pe care îl creezi, iar exemplu.ro e domeniul tău. Le înlocuiești cu valorile tale.

Pasul 1: primul login ca root

De pe calculatorul tău:

ssh root@203.0.113.10

La prima conexiune, clientul SSH îți arată amprenta cheii serverului și te întreabă dacă o accepți. Răspunzi yes; amprenta se salvează în ~/.ssh/known_hosts și nu te mai întreabă data viitoare.

Dacă ai pus cheia publică la crearea serverului, intri direct. Dacă ai primit doar o parolă pentru root, intri cu ea acum. O vei dezactiva la pasul 7, după ce cheia funcționează.

Pe unele imagini (cele pregătite cu cloud-init și opțiunea disable_root), ssh root@203.0.113.10 nu te lasă să intri, ci afișează Please login as the user "ubuntu" rather than the user "root". și închide conexiunea. Atunci intri cu utilizatorul indicat (ssh ubuntu@203.0.113.10) și rulezi pașii din ghid cu sudo în față. La pasul 6, varianta A, copiezi cheia din /home/ubuntu/.ssh/authorized_keys, nu din /root/.ssh/: acolo cheia e legată de comanda care afișează mesajul, iar copiată la utilizator îl blochează la fel.

Pasul 2: actualizează sistemul

Imaginea din care a pornit serverul are deja câteva săptămâni sau luni. Aduci totul la zi înainte de orice altceva:

apt update
apt upgrade -y

apt update descarcă lista de pachete, apt upgrade le instalează versiunile noi. Dacă actualizarea a adus un kernel nou sau biblioteci de sistem, Ubuntu creează fișierul /var/run/reboot-required. Verifici așa:

ls /var/run/reboot-required

Dacă fișierul există, repornești și te reconectezi după un minut. Dacă primești No such file or directory, nu e nevoie de repornire.

reboot

Ai un server pe o versiune mai veche de Ubuntu?

Dacă serverul rulează 20.04 sau 22.04 și vrei să-l aduci pe 24.04, faci întâi un backup complet (snapshot sau copie a datelor), actualizezi sistemul cu comenzile de mai sus, apoi pornești upgrade-ul de versiune:

sudo do-release-upgrade

Comanda te duce doar la următoarea versiune LTS, fără salturi: de pe 20.04 ajungi întâi pe 22.04, repornești, apoi o rulezi din nou pentru 24.04. Ce verifici înainte și cum decurge upgrade-ul găsești în ghidul oficial de upgrade Ubuntu Server.

Pasul 3: creează un utilizator cu drepturi sudo

Contul root poate face orice, fără nicio confirmare, iar o greșeală de tastare ca root se plătește scump. Lucrezi zilnic cu un cont obișnuit și ceri drepturi de administrator doar pentru comanda care are nevoie de ele, cu sudo. În plus, fiecare comandă rulată cu sudo rămâne în jurnal, în /var/log/auth.log.

Creezi utilizatorul:

adduser utilizator

adduser creează contul, grupul cu același nume și directorul /home/utilizator, apoi îți cere parola de două ori. Alege o parolă lungă, generată de un manager de parole: după pasul 7 nu o vei mai folosi la login, dar sudo ți-o va cere. Câmpurile următoare (nume complet, telefon) sunt opționale; treci peste ele cu Enter și confirmi cu Y.

Adaugi utilizatorul în grupul sudo:

usermod -aG sudo utilizator

Opțiunea -a (append) contează: fără ea, -G înlocuiește toate grupurile secundare ale utilizatorului cu cel dat, în loc să-l adauge la listă. Verifici:

groups utilizator

Rezultatul trebuie să conțină sudo:

utilizator : utilizator sudo users

Testezi dreptul de sudo trecând pe noul cont:

su - utilizator
sudo whoami

sudo îți cere parola utilizatorului (nu pe cea de root), iar whoami răspunde root. Revii la sesiunea de root cu:

exit

Diferența dintre cele două comenzi: su - utilizator te mută complet pe alt cont și îți cere parola contului respectiv, pe când sudo rulează o singură comandă ca root cu parola ta.

Pasul 4: reguli sudo personalizate, cu visudo și /etc/sudoers.d

Pentru majoritatea serverelor, grupul sudo de la pasul 3 e suficient. Uneori însă vrei ca un cont să poată face un singur lucru ca root, de exemplu un cont de deploy care doar repornește serviciul web. Pentru asta scrii o regulă în sudoers.

Regulile implicite de pe Ubuntu 24.04 arată așa (fără comentarii):

root	ALL=(ALL:ALL) ALL
%admin ALL=(ALL) ALL
%sudo	ALL=(ALL:ALL) ALL
@includedir /etc/sudoers.d

Citirea unei reguli: cine (root, sau %sudo pentru un grup), pe ce host (ALL), ca cine ((ALL:ALL) = orice utilizator și orice grup), ce comenzi (ALL). Ultima linie include toate fișierele din /etc/sudoers.d/.

Nu edita /etc/sudoers direct. O actualizare a pachetului sudo poate intra în conflict cu modificările tale, iar o greșeală de sintaxă în el blochează sudo pentru toată lumea. Pui regulile tale în fișiere separate în /etc/sudoers.d/ și le editezi doar cu visudo, care verifică sintaxa înainte să salveze.

Exemplu: contul deploy (creat cu adduser deploy, ca la pasul 3) poate reporni Nginx fără parolă și nimic altceva.

visudo -f /etc/sudoers.d/deploy

În editor scrii o singură linie:

deploy ALL=(root) NOPASSWD: /usr/bin/systemctl restart nginx

Comenzile din reguli se scriu cu calea completă (/usr/bin/systemctl), altfel sudo nu le acceptă. Salvezi și închizi editorul. Dacă ai greșit sintaxa, visudo îți arată linia cu problema și întreabă What now?: apeși e ca să revii în editor sau x ca să renunți fără să salvezi. Nu alege Q, care salvează fișierul greșit. Dacă fișierul era nou, x lasă în urmă un fișier gol; îl ștergi cu rm /etc/sudoers.d/deploy, altfel visudo -c îl semnalează.

Pe Ubuntu 24.04, visudo -f creează fișierul nou cu drepturile 0640, iar verificarea generală îl semnalează:

visudo -c
/etc/sudoers: parsed OK
/etc/sudoers.d/README: parsed OK
/etc/sudoers.d/deploy: bad permissions, should be mode 0440

Corectezi drepturile și rulezi verificarea din nou, până când toate fișierele apar cu parsed OK:

chmod 0440 /etc/sudoers.d/deploy
visudo -c

Vezi ce are voie să ruleze un utilizator:

sudo -l -U deploy

La finalul răspunsului, sub User deploy may run the following commands, apare regula ta:

    (root) NOPASSWD: /usr/bin/systemctl restart nginx

Două detalii care te pot încurca:

  • Numele fișierului din /etc/sudoers.d/ nu are voie să conțină punct și nici să se termine în ~. Un fișier deploy.conf e ignorat în tăcere: regula pur și simplu nu se aplică.
  • NOPASSWD doar pentru comenzi precise. Un NOPASSWD: ALL transformă orice cheie SSH furată a acelui cont în acces root complet.

Pasul 5: blochezi sau ștergi un cont

Când cineva nu mai lucrează pe server, ai trei variante: îi iei doar drepturile de administrator, îi blochezi contul și îi păstrezi fișierele, sau îl ștergi de tot. În comenzile de mai jos, nume_cont e contul vizat. Nu le rula pe contul tău de administrator: după pasul 7, root nu mai intră prin SSH, iar dacă îți scoți singur dreptul de sudo sau îți blochezi contul, rămâi fără acces de administrator.

În loc să ștergi contul

Îi iei doar drepturile de administrator, fără să-i atingi contul:

deluser nume_cont sudo

Schimbarea se vede de la următorul login al contului; o sesiune deja deschisă păstrează grupurile vechi.

Sau blochezi contul temporar, fără să-i ștergi fișierele:

usermod --lock --expiredate 1 nume_cont

--lock blochează parola, iar --expiredate 1 face contul expirat, ceea ce oprește și login-ul cu cheie SSH (blocarea parolei singură nu îl oprește). Deblocarea:

usermod --unlock --expiredate "" nume_cont

Ștergerea contului

Întâi verifici dacă mai are procese pornite:

ps -u nume_cont

Dacă lista nu e goală (de exemplu, are o sesiune SSH deschisă), îi închizi sesiunile. Altfel deluser se oprește cu mesajul userdel: user ... is currently used by process, după ce apucase deja să-i șteargă directorul, iar contul rămâne pe jumătate șters.

loginctl terminate-user nume_cont

Apoi ștergi contul împreună cu directorul lui din /home:

deluser --remove-home nume_cont

Dacă avea reguli proprii în /etc/sudoers.d/, ștergi și fișierul lor (pentru contul deploy de la pasul 4, /etc/sudoers.d/deploy) și verifici din nou sintaxa:

rm /etc/sudoers.d/deploy
visudo -c

Fișierul din /etc/sudoers.d/ nu dispare odată cu contul. Dacă îl lași acolo și, peste un an, altcineva primește același nume de utilizator, moștenește regula.

Pasul 6: cheia SSH pentru utilizatorul nou

Utilizatorul are nevoie de cheia ta publică în /home/utilizator/.ssh/authorized_keys. Ai două variante.

Varianta A: root are deja cheia ta. Dacă ai intrat ca root cu cheie la pasul 1, copiezi aceeași listă de chei, cu proprietarul și drepturile corecte:

install -d -m 700 -o utilizator -g utilizator /home/utilizator/.ssh
install -m 600 -o utilizator -g utilizator /root/.ssh/authorized_keys /home/utilizator/.ssh/authorized_keys

Varianta B: de pe calculatorul tău, cu ssh-copy-id. Rulezi comanda local, pe macOS sau Linux. Funcționează doar dacă serverul acceptă încă login cu parolă. Pe multe imagini cloud, inclusiv cele de Ubuntu, login-ul cu parolă e oprit de la început; atunci folosești varianta A:

ssh-copy-id utilizator@203.0.113.10

Îți cere o dată parola lui utilizator și adaugă cheia ta publică în authorized_keys, cu drepturile corecte.

Acum, fără să închizi sesiunea de root, deschizi un terminal nou și testezi:

ssh utilizator@203.0.113.10
sudo whoami

Dacă intri fără să ți se ceară parola contului (eventual doar parola cheii, dacă ai pus una) și sudo whoami răspunde root, poți trece mai departe. Dacă nu, nu continua: fără o cheie care funcționează, pasul următor te lasă pe dinafară.

Pasul 7: dezactivează login-ul root și autentificarea cu parolă

Din acest punct lucrezi ca utilizator, cu sudo.

Nu modifici /etc/ssh/sshd_config, ci adaugi un fișier propriu în /etc/ssh/sshd_config.d/. Rămâne neatins la actualizările pachetului openssh-server și vezi imediat ce ai schimbat.

Capcana: pentru majoritatea opțiunilor, sshd folosește prima valoare pe care o citește. Linia Include /etc/ssh/sshd_config.d/*.conf e chiar la începutul lui sshd_config, iar fișierele din director se citesc în ordine alfabetică. Pe imaginile care folosesc cloud-init poți găsi acolo un 50-cloud-init.conf cu PasswordAuthentication yes. Dacă fișierul tău se numește 60-securizare.conf sau 99-securizare.conf, se citește după cel de la cloud-init și parola rămâne activă. De aceea îl numești cu un prefix mai mic, de exemplu 10-.

Vezi întâi ce fișiere setează deja aceste opțiuni:

sudo grep -rE '^\s*(PermitRootLogin|PasswordAuthentication|KbdInteractiveAuthentication)' /etc/ssh/sshd_config /etc/ssh/sshd_config.d/

Creezi fișierul:

sudo tee /etc/ssh/sshd_config.d/10-securizare.conf > /dev/null <<'EOF'
PermitRootLogin no
PasswordAuthentication no
KbdInteractiveAuthentication no
EOF

Ce face fiecare linie: PermitRootLogin no refuză orice login SSH direct ca root, inclusiv cu cheie; PasswordAuthentication no și KbdInteractiveAuthentication no închid cele două căi prin care SSH poate cere o parolă.

Verifici sintaxa. Dacă sshd -t nu afișează nimic, configurația e validă:

sudo sshd -t

Apoi verifici valorile pe care le va folosi efectiv serverul, după ce a citit toate fișierele:

sudo sshd -T | grep -E '^(permitrootlogin|passwordauthentication|kbdinteractiveauthentication) '
permitrootlogin no
passwordauthentication no
kbdinteractiveauthentication no

Dacă permitrootlogin sau passwordauthentication nu apar no, un alt fișier câștigă în fața ta: vezi rezultatul lui grep de mai sus. Abia când totul arată corect, reîncarci serviciul. Pe Ubuntu și Debian se numește ssh:

sudo systemctl reload ssh

Sesiunile deschise nu se închid la reîncărcare. Păstrează sesiunea curentă deschisă și testează din alt terminal, de pe calculatorul tău:

ssh utilizator@203.0.113.10
ssh root@203.0.113.10

Prima comandă trebuie să te lase să intri, a doua trebuie să se oprească cu Permission denied (publickey). Abia după ce ambele se comportă așa închizi sesiunea veche.

Pasul 8: pornește firewall-ul UFW

UFW e deja instalat pe Ubuntu Server, dar e oprit. Regula pentru SSH se adaugă înainte să-l pornești, altfel pierzi conexiunea curentă și nu te mai poți conecta.

Vezi profilurile de aplicații disponibile:

sudo ufw app list

Permiți SSH, apoi pornești firewall-ul. ufw enable întreabă Command may disrupt existing ssh connections. Proceed with operation (y|n)?; confirmi cu y:

sudo ufw allow OpenSSH
sudo ufw enable

Verifici:

sudo ufw status verbose
Status: active
Logging: on (low)
Default: deny (incoming), allow (outgoing), deny (routed)
New profiles: skip

To                         Action      From
--                         ------      ----
22/tcp (OpenSSH)           ALLOW IN    Anywhere
22/tcp (OpenSSH (v6))      ALLOW IN    Anywhere (v6)

Tot ce intră e blocat, cu excepția SSH. Când instalezi un server web, deschizi și porturile lui:

sudo ufw allow 80,443/tcp

O regulă o scoți cu sudo ufw delete allow 80,443/tcp, iar lista numerotată o vezi cu sudo ufw status numbered.

Pasul 9: actualizări automate de securitate

Pe Ubuntu Server, pachetul unattended-upgrades e instalat și de obicei deja pornit. Verifici:

cat /etc/apt/apt.conf.d/20auto-upgrades
APT::Periodic::Update-Package-Lists "1";
APT::Periodic::Unattended-Upgrade "1";

Dacă fișierul lipsește sau valorile sunt "0", îl instalezi și îl pornești, răspunzând Yes la întrebare:

sudo apt install unattended-upgrades
sudo dpkg-reconfigure --priority=low unattended-upgrades

Verifici din nou cu cat /etc/apt/apt.conf.d/20auto-upgrades. Dacă fișierul tot lipsește sau valorile au rămas "0" (fișierul a fost modificat de mână, iar dpkg-reconfigure nu mai scrie peste el), îl refaci din copia pachetului:

sudo cp /usr/share/unattended-upgrades/20auto-upgrades /etc/apt/apt.conf.d/20auto-upgrades

Implicit se instalează automat doar actualizările din depozitele -security (plus ESM, dacă e activ). Actualizările obișnuite rămân pe seama ta, la apt upgrade. Vezi ce ar face la următoarea rulare, fără să instaleze nimic:

sudo unattended-upgrade --dry-run --debug

Unele actualizări, cum ar fi kernelul, se aplică abia după repornire. Dacă vrei ca serverul să repornească singur când e nevoie, la o oră fără trafic, pui setarea într-un fișier propriu, nu în 50unattended-upgrades:

sudo tee /etc/apt/apt.conf.d/52unattended-upgrades-local > /dev/null <<'EOF'
Unattended-Upgrade::Automatic-Reboot "true";
Unattended-Upgrade::Automatic-Reboot-Time "04:00";
EOF

Repornirea automată e o decizie, nu o setare implicită: pe un server cu o singură aplicație importantă, poate preferi să repornești tu, după ce vezi mesajul la login.

Pasul 10: fus orar și sincronizarea orei

De obicei, imaginile de server pornesc pe UTC. Dacă vrei ca jurnalele și sarcinile programate (cron) să folosească ora României:

sudo timedatectl set-timezone Europe/Bucharest
timedatectl

În răspuns cauți Time zone: Europe/Bucharest, System clock synchronized: yes și NTP service: active. Ubuntu 24.04 sincronizează ora prin systemd-timesyncd, pornit implicit. Detalii despre serverul de timp folosit:

timedatectl timesync-status

Mulți administratori lasă serverele pe UTC, ca orele din jurnale să se potrivească între mașini aflate în țări diferite. Oricare ai alege, alegi o dată și rămâi la ea.

Pasul 11: setează hostname-ul

Numele serverului apare în prompt, în jurnale și în antetele e-mailurilor trimise de pe server. Setezi numele scurt ca hostname, iar numele complet (FQDN), sub un domeniu pe care îl controlezi, îl treci în /etc/hosts:

sudo hostnamectl set-hostname srv1

Până salvezi /etc/hosts, fiecare comandă cu sudo afișează sudo: unable to resolve host srv1: Name or service not known. E normal: comanda rulează, doar că serverul nu-și găsește încă noul nume.

Deschizi /etc/hosts, ca serverul să-și poată rezolva singur numele:

sudo nano /etc/hosts

Linia de adăugat, sub 127.0.0.1 localhost:

127.0.1.1 srv1.exemplu.ro srv1

Dacă în fișier există deja o linie 127.0.1.1 cu numele vechi, o înlocuiești cu aceasta, nu adaugi una nouă.

Verifici:

hostname
hostname -f

Prima comandă răspunde srv1, a doua numele complet, srv1.exemplu.ro. Dacă imaginea folosește cloud-init și, după o repornire, numele sau /etc/hosts revin la vechile valori, setezi preserve_hostname: true în /etc/cloud/cloud.cfg. Dacă acolo apare și manage_etc_hosts: true, /etc/hosts e regenerat la fiecare pornire din /etc/cloud/templates/hosts.debian.tmpl, iar modificarea o faci în acel șablon.

Verificare finală

Pe server, logat ca utilizator:

sudo sshd -T | grep -E '^(permitrootlogin|passwordauthentication) '
sudo ufw status
cat /etc/apt/apt.conf.d/20auto-upgrades
timedatectl
hostname -f

Ce trebuie să vezi: permitrootlogin no și passwordauthentication no, Status: active cu OpenSSH permis, ambele valori "1" în 20auto-upgrades, fusul orar ales și System clock synchronized: yes, apoi numele complet al serverului.

De pe calculatorul tău, ssh root@203.0.113.10 trebuie să se oprească cu Permission denied (publickey)., iar ssh utilizator@203.0.113.10 să intre cu cheia.

Diferențe pe Debian 12 și 13

Pașii sunt aceiași, cu câteva pachete care pe Debian nu vin instalate:

  • sudo lipsește dacă ai setat o parolă de root la instalare. Îl instalezi ca root, înainte de pasul 3: apt install sudo.
  • Jurnalul sudo nu ajunge în /var/log/auth.log, ca la pasul 3: pe Debian fișierul nu există implicit, pentru că rsyslog nu e instalat. Comenzile rulate cu sudo le vezi în jurnalul systemd, ca root: journalctl _COMM=sudo.
  • ufw nu e instalat implicit: apt install ufw. După instalare, ufw app list conține profilul OpenSSH, ca pe Ubuntu.
  • unattended-upgrades trebuie instalat (apt install unattended-upgrades), apoi verifici 20auto-upgrades ca la pasul 9.
  • Serviciul SSH se numește tot ssh, iar /etc/ssh/sshd_config.d/ se citește la fel, de la începutul lui sshd_config.
  • Dacă timedatectl arată NTP service: n/a, instalezi sincronizarea: apt install systemd-timesyncd.

Diferențe pe AlmaLinux și Rocky Linux 9

Dacă ai venit aici de la vechiul ghid pentru CentOS 7: acel sistem nu mai primește actualizări din iunie 2024. Succesorii lui direcți sunt AlmaLinux și Rocky Linux, iar pe versiunea 9 pașii se schimbă așa:

Actualizare:

dnf upgrade -y

Utilizator și sudo. Grupul de administratori se numește wheel, nu sudo. adduser există, dar nu cere parola, așa că o setezi separat:

adduser utilizator
passwd utilizator
usermod -aG wheel utilizator

Regulile din /etc/sudoers.d/ se scriu la fel, cu visudo -f și chmod 0440. Un utilizator se șterge cu:

userdel -r utilizator

SSH. Același fișier 10-securizare.conf în /etc/ssh/sshd_config.d/. Înainte, te uiți ce mai e în director:

ls /etc/ssh/sshd_config.d/

Pe AlmaLinux 9 poți găsi acolo un 25-permitrootlogin.conf cu PermitRootLogin yes, scris de scriptul de instalare al pachetului openssh-server când instalatorul a permis login-ul root; pe Rocky 9 de obicei lipsește. Fișierul tău cu prefixul 10- se citește înaintea lui, deci valoarea ta câștigă. Dacă însă sistemul a fost instalat din ISO cu opțiunea de login root cu parolă bifată, instalatorul creează un 01-permitrootlogin.conf, tot cu PermitRootLogin yes, care se citește înaintea fișierului tău și câștigă. Dacă îl vezi în listă, îl ștergi:

sudo rm /etc/ssh/sshd_config.d/01-permitrootlogin.conf

Apoi verifici sintaxa și valorile efective. Trebuie să vezi permitrootlogin no și passwordauthentication no:

sudo sshd -t
sudo sshd -T | grep -E '^(permitrootlogin|passwordauthentication) '

Serviciul se numește sshd:

sudo systemctl reload sshd

Firewall. În loc de UFW, AlmaLinux și Rocky folosesc firewalld, iar zona implicită permite deja SSH. Verifici și, când ai nevoie, adaugi serviciile web:

sudo firewall-cmd --state
sudo firewall-cmd --list-services
sudo firewall-cmd --permanent --add-service=http --add-service=https
sudo firewall-cmd --reload

Dacă firewall-cmd --state spune că nu rulează, îl pornești cu sudo systemctl enable --now firewalld.

Actualizări automate. Echivalentul lui unattended-upgrades este dnf-automatic. Îl setezi să instaleze doar actualizările de securitate:

sudo dnf install -y dnf-automatic
sudo sed -i -e 's/^upgrade_type = .*/upgrade_type = security/' -e 's/^apply_updates = .*/apply_updates = yes/' /etc/dnf/automatic.conf
sudo systemctl enable --now dnf-automatic.timer

Ora. timedatectl set-timezone funcționează la fel; sincronizarea se face prin chronyd, pe care îl verifici cu chronyc tracking.

Probleme frecvente

Permission denied (publickey) pentru utilizator, după pasul 7. Cheia nu e acolo unde o caută serverul sau are drepturi prea largi. ~/.ssh trebuie să fie 700, authorized_keys 600, ambele cu proprietarul utilizator. Din sesiunea de root pe care ai lăsat-o deschisă, reiei varianta A de la pasul 6. Dacă ai închis-o deja, ai nevoie de consola serverului, nu de SSH.

Serverul acceptă încă parole sau login ca root. Ai uitat systemctl reload ssh, sau un alt fișier din /etc/ssh/sshd_config.d/ se citește înaintea celui scris de tine. sudo sshd -T arată valoarea folosită efectiv, iar grep-ul de la pasul 7 îți arată fișierul vinovat.

sshd -t afișează Bad configuration option. Ai o greșeală de scriere într-o opțiune, de exemplu PasswordAuthentcation. Mesajul îți dă fișierul și linia. Nu reîncărca serviciul până când sshd -t nu mai afișează nimic.

utilizator is not in the sudoers file. Utilizatorul nu e în grupul sudo (sau wheel, pe AlmaLinux/Rocky), ori e în grup dar sesiunea e mai veche decât modificarea. Grupurile se citesc la login: ieși și intri din nou.

deluser --remove-home cere pachetul perl. Pe instalările minimale de Ubuntu și Debian, opțiunea --remove-home are nevoie de perl, iar comanda se oprește înainte să șteargă ceva. Rezolvi cu sudo apt install perl și rulezi din nou deluser.

Ai pornit UFW fără regula pentru SSH. Conexiunile noi sunt blocate. Din consola serverului rulezi ufw allow OpenSSH sau ufw disable, apoi reiei pasul 8 în ordinea corectă.

O regulă din /etc/sudoers.d/ nu se aplică. Numele fișierului conține un punct (deploy.conf) sau se termină în ~. Redenumește-l fără punct și verifică cu sudo -l -U nume.

Rezumat

  1. Intri ca root și actualizezi: apt update && apt upgrade.
  2. Creezi un utilizator și îl pui în grupul sudo: adduser, usermod -aG sudo.
  3. Regulile sudo speciale merg în /etc/sudoers.d/, editate cu visudo -f, cu drepturi 0440.
  4. Conturile care nu mai sunt folosite se șterg cu deluser --remove-home, după ce le închizi sesiunile, împreună cu regulile lor sudo.
  5. Copiezi cheia SSH la noul utilizator și testezi login-ul înainte de orice altceva.
  6. Închizi root-ul și parolele printr-un fișier 10-securizare.conf în sshd_config.d, verificat cu sshd -t și sshd -T.
  7. Pornești UFW abia după ufw allow OpenSSH.
  8. Verifici că actualizările de securitate se instalează automat.
  9. Setezi fusul orar, verifici sincronizarea orei și dai serverului un nume, cu forma completă în /etc/hosts.

După acești pași ai o bază curată pe care instalezi serverul web, baza de date sau aplicația ta. Documentația oficială pentru detalii: ghidul Ubuntu Server, UFW pe Ubuntu și manualele OpenSSH.