Onze handen zijn niet voor niets: het herstellen van de Rook-cluster in K8s

Onze handen zijn niet voor niets: het herstellen van de Rook-cluster in K8s

Wij al eerder over hebben gesproken, hoe/waarom we Rook leuk vinden: het vereenvoudigt in grote mate het werken met opslag in Kubernetes-clusters. Maar bij deze eenvoud komen ook bepaalde complicaties. We hopen dat dit nieuwe materiaal helpt om beter om te gaan met deze complicaties nog vóórdat ze zich aandienen.

En om het lezen interessanter te maken, beginnen we met de gevolgen van een hypothetisch probleem in het cluster.

«Alles is verloren!»

Stel je voor dat je ooit Rook hebt ingesteld en gestart in je K8s-cluster, het werkte naar tevredenheid, maar op een gegeven moment gebeurt het volgende:

  • Nieuwe pods kunnen RBD-images van Ceph niet monteren.
  • Commando's zoals lsblk en df werken niet op de Kubernetes-knooppunten. Dit betekent automatisch: ‘ergens klopt iets niet’ met de gemonteerde RBD-images. Ze kunnen niet gelezen worden, wat wijst op het onbereikbaar zijn van de monitoren…
  • Ja, er zijn geen werkende monitoren in het cluster. Sterker nog — er zijn zelfs geen pods met OSD's, noch een pod met MGR.

Wanneer de pod werd gestart rook-ceph-operator? Не так давно, как его деплоили. Почему? Rook-operator решил сделать новый кластер… Как же нам теперь восстановить работу кластера и данные в нём?

Laten we eerst de langere, interessante weg kiezen en een grondig onderzoek doen naar de ‘binnenkant’ van Rook en stapsgewijs zijn componenten herstellen. Natuurlijk is er ook een kortere en correcte weg: het gebruik van back-ups. Zoals bekend, zijn er twee soorten beheerders: degene die geen back-ups maakt, en degene die dit al doet… Maar daarover later na het onderzoek.

Een beetje praktijk, of de lange weg

Laten we ons om ons heen kijken en de monitoren herstellen

Laten we dus eens kijken naar de lijst van ConfigMaps: daar zijn de noodzakelijke voor de back-up rook-ceph-config en rook-config-override. Deze verschijnen bij een succesvolle deployment van het cluster.

NB: In nieuwe versies, na de acceptatie van deze PR, zijn ConfigMaps geen indicator meer van de succesvolle deployment van het cluster.

Voor verdere acties hebben we een hard reboot nodig van alle servers waarop de gemonteerde RBD-images aanwezig zijn (ls /dev/rbd*). Dit moet worden uitgevoerd via sysrq (of ‘te voet’ in het datacenter). Deze eis is voortgekomen uit de noodzaak om de gemonteerde RBD's ontkoppelen, omdat een normale reboot niet werkt (het zal vruchteloos proberen om ze normaal te ontkoppelen).

Het theater begint met een kapstok, en een Ceph-cluster begint met monitoren. Laten we naar hen kijken.

Rook monteert in de monitorpod zulke entiteiten:

Volumes:
 rook-ceph-config:
   Type:      ConfigMap (een volume bevolkt door een ConfigMap)
   Name:      rook-ceph-config
 rook-ceph-mons-keyring:
   Type:        Secret (een volume bevolkt door een Secret)
   SecretName:  rook-ceph-mons-keyring
 rook-ceph-log:
   Type:          HostPath (bare host directory volume)
   Path:          /var/lib/rook/kube-rook/log
 ceph-daemon-data:
   Type:          HostPath (bare host directory volume)
   Path:          /var/lib/rook/mon-a/data
Mounts:
  /etc/ceph van rook-ceph-config (ro)
  /etc/ceph/keyring-store/ van rook-ceph-mons-keyring (ro)
  /var/lib/ceph/mon/ceph-a van ceph-daemon-data (rw)
  /var/log/ceph van rook-ceph-log (rw)

Laten we eens kijken wat er in de secret zit rook-ceph-mons-keyring:

kind: Secret
data:
 keyring: LongBase64EncodedString=

We decoderen en krijgen een gewone keyring met rechten voor de admin en monitors:

[mon.]
       key = AQAhT19dlUz0LhBBINv5M5G4YyBswyU43RsLxA==
       caps mon = "allow *"
[client.admin]
       key = AQAhT19d9MMEMRGG+wxIwDqWO1aZiZGcGlSMKp==
       caps mds = "allow *"
       caps mon = "allow *"
       caps osd = "allow *"
       caps mgr = "allow *"

Laten we dit onthouden. En nu kijken we naar de keyring in de secret rook-ceph-admin-keyring:

kind: Secret
data:
 keyring: anotherBase64EncodedString=

Wat zit erin?

[client.admin]
       key = AQAhT19d9MMEMRGG+wxIwDqWO1aZiZGcGlSMKp==
       caps mds = "allow *"
       caps mon = "allow *"
       caps osd = "allow *"
       caps mgr = "allow *"

Dezelfde. Laten we nog eens kijken… Hier is bijvoorbeeld de secret rook-ceph-mgr-a-keyring:

[mgr.a]
       key = AQBZR19dbVeaIhBBXFYyxGyusGf8x1bNQunuew==
       caps mon = "allow *"
       caps mds = "allow *"
       caps osd = "allow *"

Uiteindelijk vinden we nog enkele secrets in de ConfigMap rook-ceph-mon:

kind: Secret
data:
 admin-secret: AQAhT19d9MMEMRGG+wxIwDqWO1aZiZGcGlSMKp==
 cluster-name: a3ViZS1yb29r
 fsid: ZmZiYjliZDMtODRkOS00ZDk1LTczNTItYWY4MzZhOGJkNDJhCg==
 mon-secret: AQAhT19dlUz0LhBBINv5M5G4YyBswyU43RsLxA==

En dit is de oorspronkelijke lijst met keyrings, waaruit alle bovenstaande secrets voortkomen.

Zoals bekend (zie dataDirHostPath in de documentatie), bewaart Rook dergelijke gegevens op twee plaatsen. Laten we dus naar de knooppunten gaan om de keyrings te bekijken die in de mappen liggen die zijn gemonteerd in pods met monitors en OSD. Laten we deze vinden op de knooppunten /var/lib/rook/mon-a/data/keyring en zien:

# cat /var/lib/rook/mon-a/data/keyring
[mon.]
       key = AXAbS19d8NNUXOBB+XyYwXqXI1asIzGcGlzMGg==
       caps mon = "allow *"

Verassing bleek hier de secret anders te zijn - niet zoals in de ConfigMaps.

Wat betreft de admin keyring? Die hebben we ook:

# cat /var/lib/rook/kube-rook/client.admin.keyring
[client.admin]
       key = AXAbR19d8GGSMUBN+FyYwEqGI1aZizGcJlHMLgx= 
       caps mds = "allow *"
       caps mon = "allow *"
       caps osd = "allow *"
       caps mgr = "allow *"

Hier is het probleem. Er was een soort fout: het cluster werd opnieuw aangemaakt… maar in werkelijkheid niet.

Het wordt duidelijk dat in de secrets opnieuw gegenereerde keyrings zijn opgeslagen, en ze niet komen van onze oude cluster. Daarom:

  • nemen we de keyring van de monitor uit het bestand /var/lib/rook/mon-a/data/keyring (of uit een backup);
  • veranderen we de keyring in de secret rook-ceph-mons-keyring;
  • schrijven we de keyring van de admin en monitor in de ConfigMap rook-ceph-mon;
  • verwijderen we de controllers van de pods met monitors.

Een wonder zal niet lang op zich laten wachten: de monitors verschijnen en starten op. Hoera, de eerste stap is gezet!

Laten we de OSD herstellen

Laten we de pod binnengaan rook-operator: aanroep ceph mon dump toont aan dat alle monitors aanwezig zijn, en ceph -s — dat ze in quorum zijn. Maar als we naar de OSD-boom kijken (ceph osd tree), zien we iets raars: OSD's beginnen op te duiken, maar ze zijn leeg. Dat betekent dat we ze ook op een of andere manier moeten herstellen. Maar hoe?

Ondertussen zijn er de ConfigMaps verschenen die we zo hard nodig hebben rook-ceph-config en rook-config-override, evenals verschillende andere ConfigMaps met namen als rook-ceph-osd-$nodename-config. Laten we er eens in kijken:

kind: ConfigMap
data:
 osd-dirs: '{"/mnt/osd1":16,"/mnt/osd2":18}'

Het is helemaal niet goed, alles is door elkaar!

Laten we de pod van de operator naar nul schalen, de gegenereerde deployments van de OSD-pods verwijderen en deze ConfigMaps corrigeren. Maar waar krijgen we de juiste OSD-kaart per knoop?

  • Laten we opnieuw naar de mappen /mnt/osd[1-2] op de knopen kijken — in de hoop dat we daar iets kunnen vinden.
  • In de map /mnt/osd1 er zijn 2 submappen: osd0 en osd16. De laatste is precies die ID die in de ConfigMap wordt vermeld (16)?
  • Laten we de groottes controleren en zien dat osd0 veel groter osd16.

is. We concluderen dat osd0 — dit is de benodigde OSD die werd aangeduid als /mnt/osd1 in de ConfigMap (want we gebruiken directory based osd.)

Stap voor stap controleren we alle knopen en corrigeren we de ConfigMaps. Na alle aanwijzingen kunnen we de pod van de Rook-operator starten en zijn logboeken bekijken. En daarin is alles geweldig:

  • ik ben de clusteroperator;
  • ik heb de schijven op de knopen gevonden;
  • ik heb de monitoren gevonden;
  • de monitoren hebben contact gemaakt, dat wil zeggen, ze hebben quorum gevormd;
  • ik start de OSD-deployments...

Laten we opnieuw naar de pod van de Rook-operator gaan en de levensvatbaarheid van de cluster controleren… ja, we hebben een beetje verkeerd gedacht over de namen van de OSD op sommige knopen! Geen probleem: we hebben de ConfigMaps weer gecorrigeerd, we hebben overbodige mappen van nieuwe OSD's verwijderd en hebben de langverwachte toestand bereikt HEALTH_OK!

Laten we de afbeeldingen in de pool controleren:

# rbd ls -p kube
pvc-9cfa2a98-b878-437e-8d57-acb26c7118fb
pvc-9fcc4308-0343-434c-a65f-9fd181ab103e
pvc-a6466fea-bded-4ac7-8935-7c347cff0d43
pvc-b284d098-f0fc-420c-8ef1-7d60e330af67
pvc-b6d02124-143d-4ce3-810f-3326cfa180ae
pvc-c0800871-0749-40ab-8545-b900b83eeee9
pvc-c274dbe9-1566-4a33-bada-aabeb4c76c32
…

Alles is op zijn plaats — de cluster is gered!

Ik ben lui met back-ups maken, of de snelle weg

Als de back-ups voor Rook zijn gemaakt, wordt het herstelproces aanzienlijk eenvoudiger en beperkt zich tot het volgende:

  1. We schalen de deployment van de Rook-operator naar nul;
  2. We verwijderen alle deployments, behalve de Rook-operator;
  3. We herstellen alle secrets en ConfigMaps vanuit de back-up;
  4. We herstellen de inhoud van mappen /var/lib/rook/mon-* op de knopen;
  5. We herstellen (als we ze toevallig kwijt zijn) de CRD CephCluster, CephFilesystem, CephBlockPool, CephNFS, CephObjectStore;
  6. We schalen de deployment van de Rook-operator weer op naar 1.

Nuttige tips

Maak back-ups!

En om situaties te voorkomen waarin herstel nodig is:

  1. Voordat u ingrijpende werkzaamheden aan de cluster uitvoert, die herstarten van servers omvatten, schaalt u de Rook-operator naar nul, zodat deze niets overbodigs doet.
  2. Voeg van tevoren nodeAffinity toe aan de monitoren.
  3. Let goed op voorafgaand aan timeoutinstellingen ROOK_MON_HEALTHCHECK_INTERVAL en ROOK_MON_OUT_TIMEOUT.

Ter afsluiting

Er is geen argument te maken dat Rook, als een extra 'laag' (in het algemene schema van opslagorganisatie in Kubernetes), zowel veel vereenvoudigt als nieuwe complicaties en potentiële problemen aan de infrastructuur toevoegt. Het is aan de 'kleine dingen': maak een weloverwogen, onderbouwde keuze tussen deze risico's aan de ene kant en de voordelen die de oplossing in uw specifieke geval biedt aan de andere kant.

Overigens is er onlangs aan de Rook-documentatie toegevoegd de sectie 'Adopt an existing Rook Ceph cluster into a new Kubernetes cluster'. Hierin wordt gedetailleerd beschreven wat nodig is om met bestaande gegevens naar een nieuw Kubernetes-cluster te verhuizen of om een cluster dat om de een of andere reden is ingestort, weer operationeel te maken.

P.S.

Lees ook op onze blog:

Bron: habr.com

Koop betrouwbare webhosting met bescherming tegen DDoS, VPS VDS servers 🔥 Koop betrouwbare webhosting met bescherming tegen DDoS, VPS VDS servers | ProHoster