Ons ondervinding in die ontwikkeling van 'n CSI-bestuurder in Kubernetes vir Yandex.Cloud

Ons ondervinding in die ontwikkeling van 'n CSI-bestuurder in Kubernetes vir Yandex.Cloud

Ons is bly om aan te kondig dat Flant sy bydrae tot Open Source-nutsgoed vir Kubernetes uitbrei deur die vrystelling van alfa-weergawe van die CSI-bestuurder (Container Storage Interface) vir Yandex.Cloud.

Maar voordat ons verder gaan na die implementeringsbesonderhede, laat ons die vraag beantwoord waarom dit hoegenaamd nodig is as Yandex reeds 'n diens het Bestuurde diens vir Kubernetes.

Inleiding

Hoekom is dit?

Binne ons maatskappy, vanaf die begin van die gebruik van Kubernetes in produksie (d.w.s. vir 'n paar jaar nou), ontwikkel ons ons eie instrument (dekhuis), wat ons terloops ook beplan om binnekort as 'n oopbronprojek beskikbaar te stel . Met sy hulp konfigureer en konfigureer ons al ons clusters eenvormig, en tans is daar reeds meer as 100 van hulle, op 'n wye verskeidenheid hardeware-konfigurasies en in alle beskikbare wolkdienste.

Klusters wat dekhuis gebruik, het al die komponente wat nodig is vir werking: balanseerders, monitering met gerieflike kaarte, statistieke en waarskuwings, gebruikersverifikasie deur eksterne verskaffers vir toegang tot alle dashboards, ensovoorts. Dit is geen sin om so 'n "opgepompte" groepering in 'n bestuurde oplossing te installeer nie, aangesien dit dikwels onmoontlik is of daartoe sal lei om die helfte van die komponente te deaktiveer.

NB: Dit is ons ervaring, en dit is nogal spesifiek. Ons stel geensins voor dat almal Kubernetes-klusters op hul eie moet ontplooi in plaas van klaargemaakte oplossings te gebruik nie. Terloops, ons het geen werklike ervaring in die bedryf van Kubernetes vanaf Yandex nie en ons sal geen beoordeling van hierdie diens in hierdie artikel gee nie.

Wat is dit en vir wie?

Dus, ons het reeds gepraat oor die moderne benadering tot berging in Kubernetes: hoe werk CSI? и hoe die gemeenskap gekom het aan hierdie benadering.

Tans het baie groot wolkdiensverskaffers drywers ontwikkel om hul wolkskywe as aanhoudende volume in Kubernetes te gebruik. As die verskaffer nie so 'n drywer het nie, maar al die nodige funksies word via die API verskaf, dan verhinder niks jou om self die drywer te implementeer nie. Dit is wat met Yandex.Cloud gebeur het.

Ons het as basis vir ontwikkeling geneem CSI-bestuurder vir DigitalOcean-wolk en 'n paar idees van bestuurders vir GCP, aangesien interaksie met die API van hierdie wolke (Google en Yandex) 'n aantal ooreenkomste het. In die besonder, die API en GCP, en by Yandex 'n voorwerp teruggee Operation om die status van langlopende bedrywighede op te spoor (byvoorbeeld om 'n nuwe skyf te skep). Om met die Yandex.Cloud API te kommunikeer, gebruik Yandex.Cloud Go SDK.

Die resultaat van die werk wat gedoen is gepubliseer op GitHub en kan nuttig wees vir diegene wat om een ​​of ander rede hul eie Kubernetes-installasie op Yandex.Cloud virtuele masjiene gebruik (maar nie 'n klaargemaakte bestuurde groepie nie) en graag skywe deur CSI wil gebruik (bestel).

Implementering

Belangrike kenmerke

Tans ondersteun die bestuurder die volgende funksies:

  • Orden van skywe in alle sones van die groep volgens die topologie van die nodusse in die groep;
  • Die verwydering van voorheen bestelde skywe;
  • Vanlyn verander grootte vir skywe (Yandex.Cloud ondersteun nie verhoging van die skywe wat op die virtuele masjien gemonteer is). Vir inligting oor hoe die bestuurder aangepas moes word om die grootte so pynloos moontlik te maak, sien hieronder.

In die toekoms beplan ons om ondersteuning te implementeer vir die skep en uitvee van skyffoto's.

Die grootste probleem en hoe om dit te oorkom

Die gebrek aan die vermoë om skywe in reële tyd te verhoog in die Yandex.Cloud API is 'n beperking wat die grootteveranderingsbewerking vir PV (Persistent Volume) bemoeilik: in hierdie geval is dit nodig dat die toepassingpod wat die skyf gebruik, gestop word, en dit kan stilstandtoepassings veroorsaak.

Volgens CSI spesifikasies, as die CSI-beheerder rapporteer dat dit skywe slegs “vanlyn” kan verander (VolumeExpansion.OFFLINE), dan moet die proses om die skyf te vergroot soos volg verloop:

As die inprop net het VolumeExpansion.OFFLINE uitbreiding vermoë en volume is tans gepubliseer of beskikbaar op 'n nodus dan ControllerExpandVolume MOET SLEGS gebel word na óf:

  • Die inprop het beheerder PUBLISH_UNPUBLISH_VOLUME vermoë en ControllerUnpublishVolume is suksesvol opgeroep.

OF ANDERS

  • Die inprop het NIE kontroleerder nie PUBLISH_UNPUBLISH_VOLUME vermoë, die inprop het node STAGE_UNSTAGE_VOLUME vermoë, en NodeUnstageVolume suksesvol voltooi is.

OF ANDERS

  • Die inprop het NIE kontroleerder nie PUBLISH_UNPUBLISH_VOLUME vermoë, ook nie nodus nie STAGE_UNSTAGE_VOLUME vermoë, en NodeUnpublishVolume suksesvol voltooi is.

Dit beteken in wese dat jy die skyf van die virtuele masjien moet losmaak voordat jy dit uitbrei.

Ongelukkig egter implementering Die CSI-spesifikasie via sykarre voldoen nie aan hierdie vereistes nie:

  • In 'n syspanhouer csi-attacher, wat verantwoordelik moet wees vir die teenwoordigheid van die vereiste gaping tussen monterings, is hierdie funksionaliteit eenvoudig nie geïmplementeer in die vanlyn grootteverandering nie. 'n Bespreking hieroor is begin hier.
  • Wat presies is 'n syspanhouer in hierdie konteks? Die CSI-inprop self werk nie met die Kubernetes API nie, maar reageer slegs op gRPC-oproepe wat deur syspanhouers na hom gestuur word. Nuutste ontwikkel word deur die Kubernetes-gemeenskap.

In ons geval (CSI-inprop), lyk die werking van die verhoging van die skyf soos volg:

  1. Ons ontvang 'n gRPC oproep ControllerExpandVolume;
  2. Ons probeer om die skyf in die API te vergroot, maar ons ontvang 'n fout oor die onmoontlikheid om die operasie uit te voer omdat die skyf gemonteer is;
  3. Ons stoor die skyfidentifiseerder in kaart, wat die skywe bevat waarvoor die verhogingsbewerking uitgevoer moet word. Hieronder, kortheidshalwe, sal ons hierdie kaart as volumeResizeRequired;
  4. Verwyder die peul wat die skyf gebruik, handmatig. Kubernetes sal dit herbegin. Sodat die skyf nie tyd het om te monteer nie (ControllerPublishVolume) voordat ons die verhogingsbewerking voltooi wanneer ons probeer monteer, kyk ons ​​of die gegewe skyf nog in is volumeResizeRequired en gee 'n fout terug;
  5. Die CSI-bestuurder probeer om die grootteveranderingsbewerking weer uit te voer. As die operasie suksesvol was, verwyder dan die skyf uit volumeResizeRequired;
  6. Omdat Skyf-ID ontbreek in volumeResizeRequired, ControllerPublishVolume slaag suksesvol, die skyf is gemonteer, die peul begin.

Alles lyk eenvoudig genoeg, maar soos altyd is daar slaggate. Vergroot skywe eksterne-veranderaar, wat in die geval van 'n fout tydens die operasie gebruik 'n tou met 'n eksponensiële toename in uitteltyd tot 1000 sekondes:

func DefaultControllerRateLimiter() RateLimiter {
  return NewMaxOfRateLimiter(
  NewItemExponentialFailureRateLimiter(5*time.Millisecond, 1000*time.Second),
  // 10 qps, 100 bucket size.  This is only for retry speed and its only the overall factor (not per item)
  &BucketRateLimiter{Limiter: rate.NewLimiter(rate.Limit(10), 100)},
  )
}

Dit kan van tyd tot tyd daartoe lei dat die skyfuitbreidingsbewerking vir 15+ minute verleng word en dus die ooreenstemmende peul nie beskikbaar is nie.

Die enigste opsie wat ons redelik maklik en pynloos toegelaat het om potensiële stilstand te verminder, was die gebruik van ons weergawe van ekstern-veranderaar met 'n maksimum tydslimiet binne 5 sekondes:

workqueue.NewItemExponentialFailureRateLimiter(5*time.Millisecond, 5*time.Second)

Ons het dit nie nodig geag om dringend 'n bespreking te begin en die eksterne resizer te herstel nie, want vanlyn grootte van skywe is 'n terugslag wat binnekort van alle wolkverskaffers sal verdwyn.

Hoe om te begin gebruik?

Die bestuurder word ondersteun op Kubernetes weergawe 1.15 en hoër. Vir die bestuurder om te werk, moet aan die volgende vereistes voldoen word:

  • vlag --allow-privileged op waarde gestel true vir API-bediener en kubelet;
  • Ingesluit --feature-gates=VolumeSnapshotDataSource=true,KubeletPluginsWatcher=true,CSINodeInfo=true,CSIDriverRegistry=true vir API-bediener en kubelet;
  • Berg voortplanting (berg voortplanting) moet op die groepering geaktiveer word. Wanneer Docker gebruik word, moet die daemon gekonfigureer word om gedeelde monterings toe te laat.

Al die nodige stappe vir die installasie self beskryf in README. Installasie behels die skep van voorwerpe in Kubernetes vanaf manifeste.

Vir die bestuurder om te werk sal jy die volgende nodig hê:

  • Spesifiseer die gids identifiseerder in die manifes (folder-id) Yandex.Cloud (sien dokumentasie);
  • Om met die Yandex.Cloud API te kommunikeer, gebruik die CSI-bestuurder 'n diensrekening. In die manifes moet Geheim deurgegee word gemagtigde sleutels vanaf die diensrekening. In die dokumentasie beskryf, hoe om 'n diensrekening te skep en sleutels te kry.

Alles in ag geneem - probeer dit, en ons sal bly wees om terugvoer te ontvang en nuwe kwessiesas jy enige probleme ondervind!

Verdere ondersteuning

As gevolg hiervan, wil ons daarop let dat ons hierdie CSI-bestuurder geïmplementeer het nie uit 'n groot begeerte om pret te hê om toepassings in Go te skryf nie, maar as gevolg van 'n dringende behoefte binne die maatskappy. Dit lyk nie vir ons prakties om ons eie implementering te handhaaf nie, so as Yandex belangstelling toon en besluit om voort te gaan om die bestuurder te ondersteun, sal ons graag die bewaarplek na hulle oordra.

Daarbenewens het Yandex waarskynlik sy eie implementering van die CSI-bestuurder in sy bestuurde Kubernetes-groepering, wat in Open Source vrygestel kan word. Ons sien ook hierdie ontwikkelingsopsie as gunstig – die gemeenskap sal 'n bewese drywer van 'n diensverskaffer kan gebruik, en nie van 'n derdepartymaatskappy nie.

PS

Lees ook op ons blog:

Bron: will.com

Voeg 'n opmerking