ABONAMENTE VIDEO REDACȚIA
RO
EN
NOU
Numărul 150
Numărul 149 Numărul 148 Numărul 147 Numărul 146 Numărul 145 Numărul 144 Numărul 143 Numărul 142 Numărul 141 Numărul 140 Numărul 139 Numărul 138 Numărul 137 Numărul 136 Numărul 135 Numărul 134 Numărul 133 Numărul 132 Numărul 131 Numărul 130 Numărul 129 Numărul 128 Numărul 127 Numărul 126 Numărul 125 Numărul 124 Numărul 123 Numărul 122 Numărul 121 Numărul 120 Numărul 119 Numărul 118 Numărul 117 Numărul 116 Numărul 115 Numărul 114 Numărul 113 Numărul 112 Numărul 111 Numărul 110 Numărul 109 Numărul 108 Numărul 107 Numărul 106 Numărul 105 Numărul 104 Numărul 103 Numărul 102 Numărul 101 Numărul 100 Numărul 99 Numărul 98 Numărul 97 Numărul 96 Numărul 95 Numărul 94 Numărul 93 Numărul 92 Numărul 91 Numărul 90 Numărul 89 Numărul 88 Numărul 87 Numărul 86 Numărul 85 Numărul 84 Numărul 83 Numărul 82 Numărul 81 Numărul 80 Numărul 79 Numărul 78 Numărul 77 Numărul 76 Numărul 75 Numărul 74 Numărul 73 Numărul 72 Numărul 71 Numărul 70 Numărul 69 Numărul 68 Numărul 67 Numărul 66 Numărul 65 Numărul 64 Numărul 63 Numărul 62 Numărul 61 Numărul 60 Numărul 59 Numărul 58 Numărul 57 Numărul 56 Numărul 55 Numărul 54 Numărul 53 Numărul 52 Numărul 51 Numărul 50 Numărul 49 Numărul 48 Numărul 47 Numărul 46 Numărul 45 Numărul 44 Numărul 43 Numărul 42 Numărul 41 Numărul 40 Numărul 39 Numărul 38 Numărul 37 Numărul 36 Numărul 35 Numărul 34 Numărul 33 Numărul 32 Numărul 31 Numărul 30 Numărul 29 Numărul 28 Numărul 27 Numărul 26 Numărul 25 Numărul 24 Numărul 23 Numărul 22 Numărul 21 Numărul 20 Numărul 19 Numărul 18 Numărul 17 Numărul 16 Numărul 15 Numărul 14 Numărul 13 Numărul 12 Numărul 11 Numărul 10 Numărul 9 Numărul 8 Numărul 7 Numărul 6 Numărul 5 Numărul 4 Numărul 3 Numărul 2 Numărul 1
×
▼ LISTĂ EDIȚII ▼
Numărul 91
Abonament PDF

Kubernetes - salvatorul zilei

Mate Lang
Infrastructure Team Lead @ Connatix



PROGRAMARE

În ultima perioadă cuvântul Kubernetes se aude mai des în lumea IT decât cuvântul antibiotic în farmacii. Amândouă sunt unelte utile, care se pot aplica după o analiză aprofundată de situație.. Asupra fiecăreia dintre ele planează riscul de aplicare inutilă sau necorespunzătoare care cauzează complicații nedorite.

Ce este Kubernetes?

Wikipedia definește Kubernetes (în mod obișnuit prescurtat ca k8s) ca fiind "un sistem de gestionare a containerelor open source pentru automatizarea implementării, scalării și distribuirii aplicațiilor. Acesta a fost inițial proiectat de Google și este acum un proiect întreținut de Cloud Native Computing Foundation. Funcționează cu o gamă largă de unelte pentru containerizare, inclusiv cu Docker."

În termeni practici, Kubernetes ne permite să ne gândim la infrastructura noastră ca la o colecție de resurse de computație pe care putem rula aplicații containerizate conform regulilor și necesităților definite de către ingineri, fără a depinde de locul și particularitățile execuţiei. Nu întâmplător, termenul grecesc kubernetes înseamnă "guvernator", " cârmaci " sau "căpitan". Acesta ascultă cerințele declarate de către călători (ingineri) și se asigură că navele (serviciile containerizate) ajung la destinația (starea) dorită, printr-un traseu fezabil și optim.

Detaliile sistemului

K8s este compus din două sisteme mari: Master și Nodes.

Multitudinea componentelor care alcătuiesc sistemul Master se mai numesc și Control Plane, fiindcă scopul lor principal este de a controla starea clusterului. Interacțiunile externe cu un cluster de k8s se declanșează prin apelarea metodelor oferite de kube-apiserver. Obiectele durabile sunt salvate într-un cluster de etcd, care este un key-value store distribuit, redundant și highly available, care implementează protocolul Raft. Componenta kube-scheduler este responsabilă să ofere un nod din cluster care este ales să ruleze un serviciu containerizat, respectând restricțiile definite de către inginer. Aceste restricții pot fi legate de necesitățile resurselor de computație a unei aplicații: CPU sau Memorie, dar și reguli mai sofisticate de afinitate: un cache și un web api să fie co-locate, sau anti afinitate: o instanță de PostgreSQL primary și replicile ei să nu fie executate pe același nod, pentru a nu le pierde simultan în caz de defecțiune.

Fiecare obiect gestionat de k8s are o specificație, în care este definită starea dorită a obiectului, numit spec. Pe de altă parte, este monitorizată periodic starea fiecărui obiect, starea observată reflectându-se în proprietatea numită status. Componenta kube-controller-manager este responsabilă să reconcilieze starea observată și să acționeze asupra obiectului într-un mod prin care să ajungă în starea dorită.

Decizia autorilor de a oferi o semantică declarativă oferă un avantaj major, atât în definirea manifestelor de obiecte, cât și în procesele de investigare a eventualelor probleme. Putem să fim siguri că k8s aplică consistent strategiile implementate în controllerele de obiecte, fără a fi nevoie ca operatorul să solicite schimbări în mod imperativ. Putem observa acest trend al folosirii DSL-urilor (Domain Specific Language) declarative și la alte unelte pentru gestionarea infrastructurii (ex. HashiCorp Terraform), dar și în paradigme de programare actuale, cum ar fi programarea funcțională și reactivă.

Ultima componentă și singura opțională a Control Plane-ului, cloud-controller-managerul, este specifică mediului de rulare, fiind implementată de către companiile de IaaS și cloud. Scopul ei este de a ușura integrarea dintre concepte din k8s și servicii de cloud, cum ar fi un load balancer, definit independent de implementare și în mod abstract într-un obiect de tip Service în k8s. Implementarea se realizează prin asocierea unui load balancer specific platformei de cloud (de ex. AWS ELB/ALB/NLB).

Celălalt sistem principal dintr-o instalație de k8s este colecția node-urilor, numit și Data Plane. Ele rulează două servicii: kubelet, care este un agent responsabil de comunicarea cu control plane-ul, și kube-proxy care facilitează comunicarea între serviciile instalate pe cluster, indiferent unde se află acestea.

Ce putem rula pe k8s?

Obiectul principal care definește o unitate executabilă pe un cluster de k8s este numit pod (adică păstăi), care este o abstracție asupra unor sau a mai multor containere(de ex. Docker). Această abstracție permite rularea mai multor componente care alcătuiesc un serviciu. Este anti-pattern folosirea podului pentru a rula stackuri întregi de aplicații, ca : Spring Boot App + PostgreSQL, Memcached rulat într-un singur pod. Cazurile de containere multiple în același pod sunt în mare majoritate situații în care podul este alcătuit dintr-un container serviciu principal, care implementează o capabilitate de business și unul sau mai multe containere auxiliare, cum ar fi un sidecar pentru mTLS. Mai există și noțiunea de init-container, care va fi pornit înainte de containerele standard și care permite inițializarea și configurarea mediului de execuție.

Chiar dacă podul este entitatea principală a ecosistemei k8s, aproape niciodată nu le creăm în mod direct. Există posibilitatea să creăm poduri în mod explicit. Dar în acest caz nici un mecanism al clusterului nu va veghea asupra existenței lui: dacă se oprește pentru o eroare, sau se pierde node-ul pe care este executat, acesta nu va mai fi repornit sau relocat. Există concepte și resurse de nivel mai înalt, cum ar fi Deployment, DaemonSet sau StatefulSet cu care putem rula poduri și prin care predăm Control Plane-ului, mai exact controllerelor specifice(ex. DeploymentController, DaemonSetController), responsabilitatea de a le controla ciclul de viață.

Un obiect de tip Deployment, odată definit, va avea atașat un ReplicaSet care la rândul lui definește un număr fix de poduri de același tip și servește ca mecanism direct de scalare orizontală. În afară de asigurarea unui număr de poduri rulate simultan prin ReplicaSet-ul atașat, un Deployment ne ajută și la orchestrarea schimbării acestora: la un potențial upgrade înlocuirea podurilor se va întâmpla după strategia stabilită în Deployment.

Majoritatea podurilor sunt efemere și nu au nevoie ca starea lor să fie durabilă între execuții. În cazuri în care avem nevoie de poduri cu stare durabilă, putem opta pentru a le crea prin StatefulSet-uri, care vor asocia un volum persistent la fiecare pod. Un exemplu bun ar fi rularea a 3 node-uri de HashiCorp Consul în mod HA, folosind un cvorum de 3 instanțe, unde fiecare pod are atașat un sistem de fișiere bine definit care se păstrează și la o eventuală schimbare a imaginii. Acest lucru este ușor de sesizat și dacă ne uităm la podurile care sunt create de către un StatefulSet, putem observa un număr de indice în numele lor(ex. consul-1, consul-2, consul-3).

O altă necesitate în privința rulării de poduri apare în momentul în care vrem să rulăm un anumit pod, pe fiecare k8s node din cluster și să ne asigurăm ca numărul podurilor va fi ajustat automat, indiferent dacă mărimea clusterului crește sau se reduce. Această strategie de rulare o putem defini prin folosirea unui DaemonSet. Câteva exemple de poduri care, de regulă, se definesc prin DaemonSet sunt : un agent de forwardarea logurilor sau un agent -atenție! nu server- de Consul.

Este ușor de constatat că aspectele execuției unor aplicații sunt elegant controlabile, tot ceea ce trebuie să facem este să definim starea dorită, iar controllerul specific tipului de obiect va executa acțiunile necesare pentru a ajunge în această stare.

Merită menționat că, dacă necesitățile noastre nu sunt acoperite de către mecanismele standard ale k8s-ului, atunci putem să implementăm propria noastră componentă de orchestrare. Această posibilitate este destul de nouă, fiind implementată de către cei de la RedHat (pentru varianta lor de k8s, numit OpenShift). Astfel de componente se numesc operatori (operators).

În compania unde lucrez, utilizăm practici moderne de machine learning, mai exact învățăm modele vaste și le actualizăm periodic. De fiecare dată când se salvează un model actualizat și proaspăt învățat, avem nevoie să se execute un rolling-update pe componenta care depinde de modelul respectiv pentru a lua decizii. Astfel putem actualiza datele pe baza cărora facem decizii, în mod elegant și frecvent. Această problemă a fost relativ ușor de rezolvat implementând operatorul nostru, cu logică customizată de orchestrare. Există un framework prin care putem scrie ușor un operator numit operator-sdk, care necesită implementarea logicii de orchestrare în limbajul de programare Go și atașându-se la punctele de extensii oferite de către k8s.

Concluzie

În companiile mari cu infrastructuri stufoase și complexe, necesitatea de a avea o abstracție asupra resurselor de computație este una evidentă. Nu poate exista Google, Facebook sau Amazon fără că echipele de dezvoltare să fie înzestrate cu un limbaj de nivel înalt în care își pot exprima expectanțele în legătură cu aspectele de operare a serviciilor gestionate. În astfel de contexte, nici nu este dezbătută legitimitatea unor soluții pentru scheduling distribuit. Nu este o coincidență că Google este autorul original a k8s-ului, ci există o cauzalitate: Google și-a creat o soluție prin care a fost capabil să gestioneze milioanele de servere pe care le deține.

Din ce în ce mai multe companii cu inventar mai modest prezintă interes pentru a se migra pe k8s sau în a-l încerca. Chiar și startupuri mici care au de gestionat o platformă SaaS pot beneficia de un cluster de k8s. Pană la urmă farmecul și avantajul unei cluster constă în simplitatea de a scala în plan orizontal. Folosite corespunzător, uneltele oferite de k8s pot fi arme esențiale în mână inginerilor, ușurând viața atât în timp de dezvoltare cât și în timpul deploymentului și a operațiilor zilnice. Trendul și paradigma de a dezvolta produse ca microservicii aduce simplitate și posibilitatea de a identifica entitățile unui context limitat și specific de domeniu. Complexitatea arhitecturală și operațională crește proporțional cu granularitatea și numărul serviciilor, interacțiunea dintre componente, iar definirea și urmărirea planului de operare devin complexe în mod exponențial.

Revizitând analogia din deschiderea articolului, în care am afirmat trendul incontestabil în ceea ce privește adopția k8s, conștienți de riscul de a fi aplicat în situații în care nu este o nevoie întemeiată, dar în cunoștință de cauză, cred că putem afirma că acest kubernetes nu este salvatorul neamului de programatori. Cu toate acestea, putem cădea de acord că oferă soluții bine gândite pentru probleme des întâlnite în viața unui proiect de software, nemaivorbind de multitudinea uneltelor și soluțiilor auxiliare pe care le primim gata integrate.

Resurse:

  1. https://ro.wikipedia.org/wiki/Kubernetes

  2. https://kubernetes.io/docs/concepts/overview/components/

  3. https://raft.github.io/

  4. https://www.cncf.io/

  5. https://www.consul.io/

  6. https://aws.amazon.com/elasticloadbalancing/

  7. https://www.openshift.com/

  8. https://github.com/operator-framework/operator-sdk

  9. https://thenewstack.io/how-the-u-s-air-force-deployed-kubernetes-and-istio-on-an-f-16-in-45-days/

NUMĂRUL 149 - Development with AI

Sponsori

  • Accenture
  • BT Code Crafters
  • Accesa
  • Bosch
  • Betfair
  • MHP
  • BoatyardX
  • .msg systems
  • P3 group
  • Ing Hubs
  • Cognizant Softvision
  • Colors in projects