Clustering¶
Notă
Această caracteristică este în prezent o previzualizare tehnică cu următoarele limitări temporare:
În cazul în care un cluster este pierdut (quorum-ul este pierdut), singurul mijloc de recuperare este resetarea din fabrică + restaurarea. Asigurați-vă că faceți des copii de siguranță. Versiunile viitoare vor include mijloace de recuperare a datelor de pe disc.
Configurarea activă/pasivă pentru a susține clustere cu două noduri, fie prin utilizarea etcd Learner sau Mirror, nu este încă disponibilă.
Ora sistemului între noduri trebuie sincronizată manual pentru moment. O versiune viitoare va include sincronizarea automată a ceasului.
NetHSM 4.0 și versiunile ulterioare acceptă gruparea pentru sincronizarea directă a datelor între mai multe NetHSM-uri. Acest lucru susține frecvența ridicată a generațiilor de chei, realizează disponibilitatea ridicată și echilibrarea sarcinii. Un cluster NetHSM se bazează pe etcd care utilizează algoritmul de consens Raft pentru o coerență puternică. Acest lucru garantează că datele (de exemplu, cheile) sunt corecte în toate NetHSM-urile în orice moment.
Înainte de a configura un cluster NetHSM, familiarizați-vă cu această tehnologie și cu constrângerile sale pentru a evita întreruperile accidentale și pierderea de date. În plus față de acest document, este posibil să doriți să consultați și documentația etcd.
Operational Redundancy¶
Vom numi „nod” un NetHSM care se așteaptă să facă parte dintr-un cluster. Un grup de N noduri va continua să funcționeze atâta timp cât cel puțin (N/2)+1 noduri sunt sănătoase și accesibile. Acest număr minim de noduri sănătoase și accesibile se numește cvorum **** .
Acest lucru implică următoarele scenarii.
Un nod cade și cvorumul este totuși atins¶
Într-un cluster cu 3 noduri, dacă un nod cedează (se blochează sau devine inaccesibil din cauza condițiilor de rețea), celelalte două noduri vor continua să lucreze și să servească cererile.
În cazul în care nodul defect este încă sănătos (de exemplu, a fost doar o problemă de rețea), acesta va fi inutilizabil în timp ce este izolat (nici măcar numai pentru citire).
Cu toate acestea, dacă nodul își revine, acesta se va resincroniza în mod curat cu restul clusterului și va deveni din nou operațional, fără a pierde date.
Dacă nu își revine, trebuie să fie scos din cluster (a se vedea secțiunea următoare), resetat din fabrică și să treacă din nou prin procesul de conectare de la zero.
Are loc o partiție a rețelei și cvorumul este totuși atins¶
Aceasta este doar o generalizare a scenariului anterior. Într-un cluster cu 5 noduri în care, de exemplu, 3 noduri sunt într-o locație fizică A și 2 noduri sunt într-o altă locație B, o problemă de rețea care izolează A și B ar însemna următoarele:
Cele 3 noduri din locația A îndeplinesc cvorumul (3 în acest caz), deci continuă să funcționeze.
Cele 2 noduri din locația B sunt nu întrunesc cvorumul (încă 3), astfel încât acestea vor înceta să funcționeze (chiar și numai în citire).
Dacă problema de rețea este rezolvată, cele 2 noduri se vor alătura cu ușurință celorlalte 3.
Cvorumul este pierdut definitiv¶
O defecțiune care face ca toate subseturile clusterului să piardă cvorumul va face ca clusterul și datele sale să fie complet pierdute, cu excepția cazului în care defecțiunea este rezolvată. În acest caz, nodurile trebuie resetate din fabrică și trebuie restaurată o copie de rezervă.
Acest lucru se poate întâmpla, de exemplu, dacă un singur nod cedează într-un cluster cu 2 noduri (unde cvorumul este 2). În această situație, nodul defect nu poate fi eliminat curat din cluster după ce s-a întâmplat, deoarece nodul sănătos rămas este deja inoperabil, deoarece a pierdut cvorumul.
Prin urmare, este recomandat să aveți întotdeauna un număr impar de noduri într-un cluster și să efectuați des copii de rezervă.
Pentru a fi clar, ** pierderea temporară a cvorumului (de exemplu, dacă reporniți toate nodurile unui cluster împreună sau dacă o defecțiune temporară a rețelei izolează nodurile) nu este o problemă: odată ce suficiente noduri sunt reconectate (fără a fi necesară reconectarea manuală) pentru a atinge cvorumul, clusterul își va relua funcționarea normală. Doar defecțiunile permanente, cum ar fi partițiile de rețea, configurațiile greșite ale rețelei, problemele de autentificare sau defecțiunile hardware, vor necesita o acțiune manuală.
Pentru mai multe informații, consultați ÎNTREBĂRI FRECVENTE etcd.
Cluster cu 2 noduri¶
Un cluster activ/pasiv cu două noduri nu este încă acceptat și va fi adăugat într-o versiune viitoare. Recomandăm introducerea unui al treilea nod, fie un al treilea NetHSM, fie un „martor” etcd care ar putea fi operat pe orice gazdă. Consultați secțiunea următoare „Martor”.
Martor¶
Natura clusterizării cu etcd face ca aceasta să fie mai fiabilă cu cât există mai multe noduri în cluster. După cum se explică în secțiunea Operational Redundancy (Redundanță operațională), clusterele ar trebui să aibă în mod ideal cel puțin 3 noduri pentru a avea spațiu de eroare, deoarece un cluster cu 2 noduri va ceda în întregime dacă numai unul dintre ele cedează.
Cu toate acestea, concepția funcției este astfel încât nu trebuie să adăugați un dispozitiv NetHSM complet și real la clusterul dvs. pentru a atinge un număr stabil de noduri. În schimb, puteți implementa și adăuga singur un nod „martor”. Un astfel de nod este doar o instanță a etcd care rulează pe mașina aleasă de dvs. (sau într-un container) și care este conectată la cluster. Acesta va fi recunoscut ca un nod normal de către dispozitivele reale din cluster și va primi toate datele și actualizările de la dispozitive (dar, desigur, nu veți putea efectua nicio operațiune HSM cu el - acesta doar stochează date).
Security Considerations¶
Nodul martor (sau oricine are acces la acesta) are acces direct la backend-ul de stocare al tuturor nodurilor din cluster (de exemplu, puteți descărca toate intrările și valorile corespunzătoare cu etcdctl get "/" "0").
Cu toate acestea, cu excepția versiunii config (/config/version, care ar trebui să fie întotdeauna „1”), strict toate valorile sunt criptate (fie cu o cheie de dispozitiv pentru valorile specifice nodului, fie cu cheile domeniului pentru celelalte), asigurând confidențialitatea datelor sensibile.
Rețineți totuși că un nod rău intenționat poate:
scrieți gunoi ca valoare pentru orice intrare din magazin, ceea ce va face ca nodurile să nu reușească să o decripteze (ceea ce poate duce la blocări pentru unele intrări de sistem).
lista de nume de intrări, cum ar fi utilizatori, spații de nume și chei, pe care le puteți considera sensibile.
Creating a Cluster¶
Orice cluster va porni inițial de la un singur nod. Noi noduri se vor alătura clusterului unul câte unul.
Preparing Nodes¶
Traficul de rețea între noduri este criptat și autentificat utilizând certificatul TLS al acestora.
Toate nodurile care se așteaptă să facă parte din același cluster trebuie să instaleze mai întâi o autoritate de certificare (CA) comună care le va permite să verifice dacă celelalte noduri sunt legitime.
În cele ce urmează, presupunem că toate nodurile sunt proaspăt provizionate și operaționale.
Networking¶
Nodes must first be reconfigured with their expected final network configuration using the /config/network endpoint (refer to the API documentation).
Crearea și instalarea unui CA¶
Utilizatorii trebuie să creeze o AC prin propriile mijloace și în conformitate cu propriile constrângeri operaționale, asigurându-se că aceasta permite cel puțin utilizarea cheii keyCertSign.
De exemplu, o AC minimă poate fi creată cu openssl:
$ openssl genrsa -out CA.key 2048 # create a key
$ openssl req -x509 -new -nodes -key CA.key -sha256 -days 1825 -out CA.pem -addext keyUsage=critical,keyCertSign
Acest CA trebuie să fie instalat pe fiecare nod.
To do this, first generate a Certificate Signing Request (CSR) from the node with the /config/tls/csr.pem endpoint (refer to the API documentation).
Notă
Pentru autentificarea corectă a nodurilor, backend-ul de clustering (etcd) se așteaptă ca fiecare nod să aibă un certificat cu un câmp Subject Alt Names (SAN) completat corespunzător. În special, nodurile la care se așteaptă să se ajungă numai prin IP trebuie să aibă un SAN IP corespunzător în certificat. SAN-urile IP pot fi solicitate pentru CSR prin adăugarea prefixului „IP:” la nume, ca în openssl:
"subjectAltNames": [ "normalname.org", "IP:192.168.1.1" ]
Având în vedere CSR-ul obținut (să îl numim nethsm.csr), putem genera un certificat pentru acesta, gata de instalare. De exemplu, cu openssl:
$ openssl x509 -req -days 1825 -in nethsm.csr -CA CA.pem -copy_extensions copy \
-CAkey CA.key -out new_cert.pem -set_serial 01 -sha256
Then install the obtained new_cert.pem with the /config/tls/cert.pem endpoint (refer to the API documentation).
În cele din urmă, CA (CA.pem) poate fi acum instalat cu punctul final /config/tls/cluster-ca.pem (consultați documentația API ` <https://nethsmdemo.nitrokey.com/api_docs/index.html>` __). Acest lucru este posibil numai după ce certificatul TLS instalat este semnat de aceasta. În caz contrar, operațiunea va fi respinsă.
Notă
Acest proces trebuie să fie repetat pentru fiecare nod.
Sincronizare ceas¶
Asigurați-vă că fiecare nod a fost prevăzut cu o oră exactă a sistemului. În caz contrar, reglați ceasurile acestora cu punctul final /config/time.
Adding a New Node¶
Adăugarea unui nod la un cluster se face în doi pași:
înregistrați adăugarea la cluster (prin oricare dintre membrii acestuia)
spune nodului nou să se alăture
Configure a Backup Passphrase¶
În primul rând, asigurați-vă că o frază de acces de rezervă este configurată pe nodul care va fi utilizat pentru a înregistra un nou membru (consultați documentația API a punctului final /config/backup-passphrase).
Înregistrarea unui nod nou¶
Atenționare
Înregistrarea unui nod introduce imediat un nou nod în cluster, modificând pragul de cvorum, chiar dacă nodul nu s-a alăturat încă efectiv. Acest lucru poate face ca nodurile existente să devină inoperabile până când noul nod se alătură efectiv. Consultați documentația API și secțiunea Operational Redundancy din prezentul document.
Aveți la îndemână IP-ul nodului care se va alătura. URL-ul complet ** (denumit și peer URL în terminologia etcd) al nodului respectiv va fi https://<IP_of_node>:2380 (de exemplu, https://192.168.1.1:2380). Portul trebuie să fie 2380, deci asigurați-vă că orice firewall dintre noduri va permite traficul TCP pe acest port.
Puteți verifica de două ori dacă URL-ul este corect apelând GET /cluster/members pe nodul care se așteaptă să se alăture. Aceasta ar trebui să listeze un singur membru: el însuși.
Apoi înregistrați URL-ul așteptat pe orice nod existent al clusterului (dacă nu aveți încă un cluster, faceți acest lucru pe NetHSM care va servi ca nod inițial al clusterului). Acest lucru se face utilizând punctul final POST /cluster/members (consultați documentația API), transmițându-i un corp JSON care conține URL-ul.
În caz de succes, aceasta returnează un corp JSON al formularului:
{
"members": [
{
"name": "",
"urls": [
"https://172.22.1.3:2380"
]
},
{
"name": "9ZVNM2MNWP",
"urls": [
"https://172.22.1.2:2380"
]
}
],
"joinerKit": "eyJiYWNrdXBfc2FsdCI6IkVlUzNPOEhHSEc5NnlNRktrdG1NZmc9PSIsInVubG9ja19zYWx0IjoiU3phMkEvYW13NlhxVWsrdHZMMmFubm5SZFlWd2ZQUjdpZ3IxK1RSdTdVaU14dmh3d0x2NWIvYVNkY2c9IiwibG9ja2VkX2RvbWFpbl9rZXkiOiIyMnNGVlkyelhQUVZ6S1pQenI3MmkwTk1WM3lmQ2k5dGwzeDhUbGtuOXM0WjFOd3JoZkRQTFZIVHp1WVl0YkQxaVZCMlovV3JHUHJlMXlwN0t4U0w4WkxjY2ZUTmUzcFg0WXE4YXNlY0wwREhXNGlIaXlPMlZnPT0ifQ=="
}
care conține informațiile necesare pentru ca noul nod să se alăture clusterului. În special, acesta enumeră toți membrii clusterului (unde membrul cu numele gol este noul membru). Acesta conține, de asemenea, cheia de domeniu criptată atât de fraza de acces de deblocare, cât și de cea de rezervă - astfel încât trebuie să fi fost configurată anterior o frază de acces de rezervă.
Păstrați acest răspuns pentru pasul următor.
Intrarea efectivă în cluster¶
Luați răspunsul de la ultimul pas și adăugați la acesta un câmp backupPassphrase care conține fraza de rezervă a nodului pe care a fost înregistrat noul membru și transmiteți aceste date unui apel către POST /cluster/join (consultați documentația API ` <https://nethsmdemo.nitrokey.com/api_docs/index.html>` __) pe nodul care se așteaptă să se alăture.
Presupunând că atât clusterul, cât și nodul pot ajunge unul la celălalt, această operațiune va pune în aplicare aderarea efectivă, ștergând datele de pe noul membru pentru a sincroniza starea acestuia cu cea a clusterului.
În funcție de condițiile de rețea și de cluster, această operațiune poate dura câteva zeci de secunde. Dacă această operațiune eșuează imediat (de exemplu, clusterul nu a fost accesibil sau autentificarea a eșuat), starea acestui nod nu va fi ștearsă, iar alăturarea va fi reluată. Cu toate acestea, de îndată ce o primă alăturare are succes, această operațiune este definitivă și poate fi anulată numai printr-o resetare din fabrică.
În cazul în care această alăturare are succes, nodul va ajunge în starea Locked și trebuie deblocat cu fraza de acces de deblocare a nodului care a fost utilizat pentru înregistrare. Ulterior, fraza de deblocare poate fi modificată (frazele de deblocare rămân specifice nodului și nu sunt partajate între noduri).
Notă
Chiar și după ce unirea a reușit, dacă baza de date a clusterului este mare sau dacă clusterul este ocupat, poate dura ceva timp până când noul membru își sincronizează complet starea. În acest timp, este posibil ca toate nodurile (inclusiv, în special, noul membru) să fie mai puțin receptive sau să nu răspundă. Este posibil ca noul conector, în special, să returneze inițial erori atunci când încearcă să îl deblocheze, de exemplu. În acest caz, acordați-i puțin timp și încercați din nou.
Adding a Witness Node¶
Prepare a Witness¶
Veți avea nevoie de un mediu cu etcd v3.6 disponibil, cu o adresă IPv4 (cel puțin) care poate fi accesată de ceilalți membri ai clusterului. Traficul TCP către și de la portul 2380 trebuie să fie permis.
Creați un director gol în care etcd își va stoca datele și scrieți calea sa (vom folosi /var/etcd/data). Asigurați-vă că utilizatorul care va lansa procesul are permisiunea de a citi și de a scrie în director.
Transferați pe computer certificatul CA care este utilizat pentru autentificarea nodurilor din cluster. Ar fi trebuit să creați unul în secțiunea Creating and Installing a CA. Îl vom stoca în /var/etcd/CA.pem.
Apoi va trebui să creați un certificat pentru martor și să îl semnați cu CA, astfel încât acesta să poată comunica cu colegii săi. Acest lucru se poate face, de exemplu, prin openssl:
# Create a key
$ openssl genrsa -out witness.key 2048
# Create a CSR with a SAN that corresponds to the witness's IP or hostname
$ openssl req -new -sha256 -key own.key -subj "/C=US/ST=CA/O=MyOrg, Inc./CN=witness" \
-addext "subjectAltName=IP:172.22.1.3" --out witness.csr
# Sign it
$ openssl x509 -req -days 1825 -in witness.csr -CA CA.pem -copy_extensions copy \
-CAkey CA.key -out witness.pem -set_serial 01 -sha256
Stocați rezultatele witness.key și witness.pem /var/etcd de asemenea.
Register Witness to Cluster¶
Urmați instrucțiunile normale din secțiunea Înregistrarea unui nod nou pentru a semnala clusterului existent adăugarea unui nou membru cu URL-ul (URL-urile) dat(e).
Notați răspunsul din partea clusterului: acesta ar trebui să conțină lista membrilor clusterului și un kit de aderare (nu veți avea nevoie de această parte).
Configure etcd¶
Spre deosebire de NetHSM care își aleg automat un nume de nod (folosind ID-ul dispozitivului), trebuie să alegeți un nume pentru fiecare martor pe care îl adăugați, asigurându-vă că numele sunt unice. Vom folosi „martor1” în exemplele următoare.
Odată cu răspunsul NetHSM de înregistrare a martorului, pregătiți variabilele formularului:
export ETCD_NAME="witness1"
export ETCD_DATA_DIR="/var/etcd/data"
export ETCD_INITIAL_CLUSTER="peer1=url1,peer1=url2,peer2=url1,peer2=url2,..."
export ETCD_INITIAL_ADVERTISE_PEER_URLS="my_url1,my_url2,..."
Presupunând că răspunsul NetHSM este stocat într-un fișier response.json, puteți genera automat aceste ultime două variabile cu următoarele expresii jq:
export ETCD_INITIAL_CLUSTER=$(jq --raw-output '[.members[] | ["\(if .name == "" then "witness1" else .name end)=\(.urls[])"]] | flatten | join(",")' < response.json)
export ETCD_INITIAL_ADVERTISE_PEER_URLS=$(jq --raw-output '.members[] | select(.name=="") | .urls | join(",")' < response.json)
De exemplu, cu exemplul de răspuns furnizat în secțiunea Înregistrarea unui nod nou, veți avea:
ETCD_NAME="witness1"
ETCD_DATA_DIR="/var/etcd/data"
ETCD_INITIAL_CLUSTER="witness1=https://172.22.1.3:2380,9ZVNM2MNWP=https://172.22.1.2:2380"
ETCD_INITIAL_ADVERTISE_PEER_URLS="https://172.22.1.3:2380"
În cele din urmă, creați un fișier etcd.conf.yml utilizând fișierul șablon furnizat în docs/etcd_witness.conf.template:
$ envsubst < NETHSM_ROOT/docs/etcd_witness.conf.template > /var/etcd/witness.conf.yml
$ cat witness.conf.yml
Acest lucru ar trebui să vă ofere un fișier al formularului:
name: witness1
data-dir: /var/etcd/data
log-level: warn
log-format: console
listen-peer-urls: https://0.0.0.0:2380
listen-client-urls: http://localhost:2379
initial-advertise-peer-urls: https://172.22.1.3:2380
advertise-client-urls: http://localhost:2379
initial-cluster: witness1=https://172.22.1.3:2380,9ZVNM2MNWP=https://172.22.1.2:2380
initial-cluster-state: 'existing'
peer-transport-security:
cert-file: witness.pem
key-file: witness.key
client-cert-auth: true
trusted-ca-file: CA.pem
skip-client-san-verification: true
Start etcd¶
Porniți etcd în modul preferat (manual, systemd serviciu, container etc.), direcționându-l către fișierul de configurare creat în etapa anterioară:
$ cd /var/etcd
$ etcd --config-file witness.conf.yml
Ar trebui să-l vedeți pornind, alăturându-se clusterului și recuperând datele. După ceva timp, ar trebui să puteți verifica dacă este sănătos cu ajutorul clientului etcdctl:
etcdctl get /config/version
Această cheie trebuie să existe și să conțină „1”.
Asigurați-vă că acest proces continuă să ruleze, deoarece acum este un membru adecvat al clusterului dvs. Dacă trebuie să îl dezafectați, mai întâi eliminați-l corespunzător din cluster (consultați secțiunea dedicată). Dacă IP-ul său accesibil se modifică, actualizați-i URL-ul din cluster.
Operating a Cluster¶
Backup și restaurare¶
Operațiunea de backup funcționează la fel ca în absența unui cluster și poate fi solicitată de la orice nod al clusterului. Operațiunea va efectua o copie de siguranță a datelor pentru întregul cluster, inclusiv a câmpurilor specifice nodului (deși acestea vor fi ignorate dacă nu se restabilește copia de siguranță pe un nod neaprovizionat).
O copie de rezervă efectuată pe un cluster poate fi restaurată pe același cluster, chiar dacă unele noduri au fost adăugate sau eliminate de atunci. Astfel de restaurări efectuate pe clustere operaționale nu vor afecta valorile de configurare (doar cheile, utilizatorii, spațiile de nume), ca orice altă restaurare parțială.
Restaurarea unei copii de siguranță pe un nod neaprovizionat va restabili câmpurile specifice nodului (cum ar fi configurația rețelei, certificatele etc.) ale nodului care a fost utilizat pentru a crea copia de siguranță.
Restaurarea unei copii de rezervă mari poate copleși clusterul pentru o anumită perioadă de timp, în timp ce nodul care aplică restaurarea transmite modificările către celelalte noduri.
Această operațiune rămâne compatibilă cu salvările efectuate pe versiunile anterioare ale NetHSM.
Notă
Restaurarea pe un nod A a unei copii de siguranță efectuate pe un alt nod Z cu o cheie de domeniu diferită va rescrie corect cheia de domeniu a lui A, ca înainte. Cu toate acestea, dacă A se afla într-un cluster cu nodul B, B va deveni inoperabil, deoarece cheia de domeniu a lui Z nu va fi restaurată pe B.
Cu alte cuvinte, efectuați o restaurare numai într-un cluster cu copii de rezervă efectuate în același cluster (deși, din nou, nodurile pot fi eliminate sau adăugate de atunci). Dacă doriți să restaurați o copie de rezervă străină pe un nod, mai întâi scoateți-l în siguranță din clusterul său, apoi resetați-l din fabrică și restaurați copia de rezervă.
Îndepărtarea curată a unui nod¶
Atât timp cât o parte a clusterului îndeplinește cvorumul, oricare dintre membrii săi poate fi folosit pentru a elimina un alt nod din cluster, indiferent dacă acest nod este deja inaccesibil sau se așteaptă să fie.
Mai întâi trebuie să cunoașteți ID-ul nodului pe care doriți să îl eliminați, enumerând toate nodurile prin GET /cluster/members și căutându-l pe cel potrivit.
Apoi, acesta poate fi eliminat prin apelarea DELETE /cluster/members/<id>. Dacă nodul în cauză era încă sănătos, acest lucru îl va izola de restul clusterului și îl va face inoperabil.
Software Updates in Clusters¶
Actualizările viitoare vor fi marcate ca „cluster-safe” (aceasta ar trebui să fie majoritatea) sau „cluster-unsafe”.
Actualizările sigure pentru cluster pot fi aplicate nodurilor care fac parte dintr-un cluster fără a le elimina mai întâi din cluster. Cu toate acestea, la fel ca în cazul tuturor operațiunilor, trebuie să vă asigurați că faceți acest lucru pe câte un nod și într-un cluster în care eliminarea unui nod nu scade cvorumul (de exemplu, dacă actualizarea eșuează).
Actualizările nesigure pentru clustere trebuie aplicate nodurilor izolate. Ar trebui să dezmembrați clusterul (eliminând nodurile unul câte unul), să resetați din fabrică toate nodurile cu excepția unuia, să aplicați actualizarea la fiecare nod, apoi să faceți ca toate nodurile resetate să se alăture nodului rămas.
Asigurați-vă că efectuați o copie de siguranță înainte de astfel de operațiuni.
Reconfigurarea unui cluster existent¶
Changing the Cluster CA¶
Un cluster existent (cu două sau mai multe noduri) nu poate să își schimbe CA-ul clusterului în timpul funcționării. Dacă trebuie să modificați acest certificat: alegeți un nod, eliminați toate celelalte noduri, actualizați CA, apoi cereți celorlalți membri să se alăture din nou.
Changing the Network Configuration of Nodes¶
Modificarea configurației de rețea a unui nod (de exemplu, schimbarea IP-ului acestuia) va informa automat celelalte noduri cu privire la actualizare. Cu toate acestea, trebuie să vă asigurați că efectuați astfel de actualizări numai pe un singur nod la un moment dat și într-un cluster în care pierderea nodului respectiv nu va duce la pierderea cvorumului.