Vorige week legde ik uit waarom we onlangs naar CloudLinux 8 wilden updaten. In ons geval bleek dat volgens de documentatie onmogelijk, maar die uitdaging wilden we wel aangaan… Na wat brainstormen en koffie hadden we een waterdicht plan. In theorie, want je hebt natuurlijk ook de praktijk. Vanaf daar pakken we nu de draad op! Bekijk hoe het plan tot leven kwam en welke uitdagingen er werden overwonnen.
Deel 1: hoe het toch gewoon kon!
Voordat je aan dit stuk begint, is het handig om het eerste deel te hebben gelezen. Daar ontdek je alle opties en hoe het plan tot stand kwam.
Even een opfrisser
In basis hadden we het plan van aanpak gekozen: nieuwe system-root ernaast, kiesbaar in grub. Nu was het de bedoeling om er een tweede systeempartitie bij te plaatsen. Die moest dan in de bootloader als keuze worden gezet om van te booten. Leuk bedacht natuurlijk, maar we hadden dit nog niet getest op haalbaarheid. Wanneer dit echt zou lukken, dan betekende het dat de upgrade van CloudLinux 6 naar 8 niet meer tijd zou kosten dan een reboot… Als iets te mooi lijkt om waar te zijn, dan is dat vaak ook zo. Toch zagen we in ons plan geen duidelijke hiaten en gingen we enthousiast aan de slag.
Wanneer je ruimte nodig hebt…
Vrijwel meteen kwam de eerste uitdaging om de hoek kijken. Zo’n extra systeempartitie moet je uiteraard ergens plaatsen. Daarvoor heb je op een server alleen wel vrije, niet-gepartitioneerde ruimte nodig. En dat was er niet genoeg. Gelukkig waren onze bestaande partities flink overgedimensioneerd, dus binnen de partities was wel vrije ruimte. We besloten hierdoor om een bestaande partitie kleiner te maken, zodat we ruimte vrijspeelden voor de nieuwe systeempartitie.
Nu is het belangrijk om te weten dat je een partitie alleen kunt verkleinen als deze niet in gebruik is. In eerste instantie hebben we dit geprobeerd zonder een reboot te doen. Hierbij stopten we alle processen die binnen de partie bestanden open hielden. Helaas bleek dit niet betrouwbaar genoeg te werken. We hebben het daarom aangepast naar een script die binnen het initramfs wordt gedraaid. Vervolgens was het simpelweg een kwestie van de server herstarten om de partitie te verkleinen.
En wanneer je weer ruimte hebt
Mooi, we hadden nu de ruimte! De volgende stap was om deze te vullen met data. Dit deden we door een ‘bronserver’ te maken, waarop we CloudLinux 8 installeerden middels ons puppet manifest. Voor het grootste gedeelte werkte het manifest voor CloudLinux 6 ook voor versie 8, maar desondanks waren er wel tientallen wijzigingen nodig. Hierna maakten we een tarball van de bronserver en pakten deze uit op de server die we wilden updaten.
Nu hadden we voor een succesvolle upgrade vier zaken nodig.
- De juiste kernel met bijbehorend initramfs
- Een bijpassend rootfs
- De serverspecifieke configuratie
- De klantspecifieke configuratie en data
Nummer twee uit de lijst hebben we hierboven geregeld, dus dat is mooi. De juiste kernel met bijbehorend initramfs staan ook op de bronserver, dus die konden we ook kopiëren. Tijd om de tussenstand op te maken…
De eerste tussenstand
Als test hadden we in de grub-bootloaderconfiguratie de juiste kernel toegevoegd, waarna we een reboot deden. De testserver herstartte, de kernel werd geladen en ook het initramfs werd gevonden. Alleen faalde de volgende stap – de switch naar het echte rootfs. Niet geheel onverwachts, daar was nog werk aan de winkel. Desondanks zag het er tot nu toe veelbelovend uit.
Configuraties op de root-partities
De volgende stap, serverspecifieke configuratie, bleek iets lastiger. Hierbij kun je denken aan MAC- of IP-adressen en namen van volumegroepen. Deze configuratie bleek op de root-partitie te staan – juist net de partitie die we wilden verwisselen… Dat zou betekenen dat de server de configuratie van het bronsysteem zou erven.
Om dit op te lossen, schreven we een script die de betreffende configuratie overzette van de oude naar de nieuwe root. Ook stond op het rootfs welke mounts er gedaan moesten worden in /etc/fstab. Dit moest een aangepaste variant worden van de versie die op het oude rootfs stond, dus daar hebben we ook wat voor moeten opnemen in het script. Uiteindelijk niet heel complex, maar wel iets wat zorgvuldig moest gebeuren.
Weer een stapje dichterbij
We hadden nu een systeem wat succesvol kon starten in zowel CloudLinux 6 als 8. Wanneer gestart met CloudLinux 8, werkten bijvoorbeeld websites van klanten nog niet. Niet geheel onbelangrijk om nog op te lossen 😉
Kom ook werken bij Antagonist
Op zoek naar een leuke, uitdagende baan en benieuwd naar wat Antagonist je kan bieden? Neem eens een kijkje bij onze vacatures.
De laatste drempel?
De meeste klantspecifieke configuraties staan bij ons op losse partities. Er zijn echter ook nog configuraties en data die op de systeempartitie staan. Je zou kunnen denken dat dit – net als de serverspecifieke configuratie – simpelweg kan worden overgezet van het oude naar het nieuwe rootfs. Daarmee zijn echter twee problemen. Als eerste kunnen de gegevens wijzigen nadat de kopieer-actie geweest is. Bijvoorbeeld, omdat er een nieuwe klant aan de server wordt toegevoegd, een klant een domein toevoegt of een pakket wordt uitgebreid.
Daarnaast vinden we een rollback ook belangrijk. Als er problemen blijken te zijn met CloudLinux 8, dan wilden we weer kunnen rebooten naar CloudLinux 6. Na even over dit probleem te hebben nagedacht, kwamen we tot de volgende oplossing. We schreven een script dat binnen de initramfs wordt gestart. Dat script controleerde of de huidige boot naar dezelfde versie ging als de laatste succesvolle boot. Was dit niet het geval, dan werden de geselecteerde data overgezet van het vorige rootfs naar het huidige.
Finish in zicht
We hadden nu een systeem wat succesvol kon starten in zowel CloudLinux 6 als 8. Beide versies werkten zonder problemen in onze testomgeving. Ook hadden we een puppetconfiguratie die werkte voor beide versies en ansible playbooks die de upgrade in gang konden zetten. Mooi! Nu was het alleen nog een kwestie van deze playbooks uitvoeren en de productieservers herstarten.
Wat je ervan merkt
Ben je klant bij ons, dan is ook de server waar jouw hostingpakket op staat op deze manier geüpgraded. Nu wil je als systeembeheerder bij alles wat je doet downtime voorkomen. Je beseft altijd de impact die je handelingen kunnen hebben op de klant en Support. Het uitvoeren van zo’n upgrade gaat dus uiterst zorgvuldig. Hoogstwaarschijnlijk heb je daardoor van deze upgrade niets van gemerkt en dat is ook precies de bedoeling.
Specifieke configuraties
In een handjevol gevallen werd er wel impact van de upgrade ervaren. Dit ging dan om configuraties van websites die zeer specifieke functionaliteiten gebruikten die we niet hadden voorzien. Zo was er bijvoorbeeld een website die een specifieke Perl-module gebruikte die op CloudLinux 8 niet meer aanwezig was. Nadat we van dergelijke problemen op de hoogte werden gesteld, hebben we dit uiteraard zo snel mogelijk verholpen.
Toch nog iets onverwachts
Daarnaast zagen we halverwege de migratie nog iets anders onverwachts opspelen. Op de systemen met CloudLinux 8 werd meer geheugen gebruikt dan op de systemen met versie 6. Dit gebruik was niet te herleiden tot een specifiek proces, maar leek opgeslokt te worden door de kernel. We konden zien dat de slab usage hoger was, maar niet waarom. Dit probleem bezorgde ons veel kopzorgen. We hebben dan ook op het punt gestaan om een rollback te doen naar versie 6. Tot er ineens een nieuwe kernel beschikbaar kwam met de volgende changelog entry:
“A new implementation of slab memory controller for the control groups technology is now available in RHEL 8. Currently, a single memory slab can contain objects owned by different memory control group. The slab memory controller brings improvement in slab utilization (up to 45%) and enables to shift the memory accounting from the page level to the object level. Also, this change eliminates each set of duplicated per-CPU and per-node slab caches for each memory control group and establishes one common set of per-CPU and per-node slab caches for all memory control groups. As a result, you can achieve a significant drop in the total kernel memory footprint and observe positive effects on memory fragmentation.”
We hebben dit meteen getest en de resultaten waren positief! We zaten weer op het niveau van CloudLinux 6 wat betreft het geheugengebruik.
Eind goed, al goed
Hiermee komt ook deel twee van dit verhaal tot zijn einde. Hopelijk vond je het interessant en heb je meer inzicht gekregen in wat er bij zo’n upgrade komt kijken. Het is altijd mooi als iets in eerste instantie niet lijkt te kunnen en het dan toch gewoon lukt. Zo blijft het werk uitdagend.
P.S. Blijf op de hoogte en volg ons via Facebook, X, Instagram, e-mail en RSS. Heb je vragen, tips of opmerkingen? Laat het achter als reactie. Vond je het artikel nuttig? Deel het dan met anderen!
Leuk te lezen. Ken Linux niet, maar kijkje in de keuken geeft waardering voor de complexiteit die beheerd wordt
Bedankt voor je reactie, Diederik. Fijn dat je het artikel leuk vond om te lezen!
Gefeliciteerd! Mooi dat het jullie gelukt is en dat wij als gebruikers daar weer van kunnen profiteren. Leuk om te lezen.
Eén dingetje moet me even van het hart: in je artikel maak je een taalfout die je helaas zeer regelmatig tegenkomt, namelijk dat je het woord ‘data’ als enkelvoud gebruikt. ‘Data’ is echter meervoud van ‘datum’. Het werkwoord dat je erbij gebruikt moet dus ook in het meervoud. Dus niet “kan de data wijzigen” maar “kunnen de data wijzigen”; en niet “werd geselecteerde data overgezet” maar “werden geselecteerde data overgezet”. Gelukkig heeft zo’n taalfout geen invloed op het functioneren van een server… 😉
Bedankt voor je oplettendheid, Harry! Klopt, dat is er inderdaad eentje die wel vaker misgaat… Handig ezelsbruggetje is om ‘data’ in je hoofd even te vervangen met ‘gegevens’. We hebben het artikel geüpdatet 🙂
(Y)