Calico Kubernetes vÔrgus: tutvustus ja veidi kogemustest

Calico Kubernetes vÔrgus: tutvustus ja veidi kogemustest

Artikli eesmÀrk on tutvustada lugejat Kubernetes'i vÔrgutegevuse ja vÔrgupoliitikate haldamise alustega, samuti Calico kolmanda osapoole pluginaga, mis laiendab standardseid vÔimalusi. Samuti demonstreeritakse mugavust konfigureerimisel ja mÔningaid funktsioone reaalsetest kasutuskogemustest.

Kiire sissejuhatus Kubernetes'i vÔrguseadmesse

Kubernetes'i klastri ettekujutamine on vÔimatu ilma vÔrku. Oleme juba avaldanud materjale nende aluselistest pÔhimÔtetest: "Kubernetes'i vÔrgu toimimise illustreeritud juhend" ja "Kubernetesi vÔrgupoliitikate sissejuhatus turbespetsialistidele».

Selle artikli kontekstis on oluline mĂ€rkida, et konteinerite ja sĂ”lmede vahelise vĂ”rguĂŒhenduse eest ei vastuta ise K8s: selleks kasutatakse erinevaid CNI pluginaid (Container Networking Interface). Selle kontseptsiooni kohta oleme ka rÀÀkinud.

NĂ€iteks, kĂ”ige levinum selline plugin — Flannel — tagab tĂ€ieliku vĂ”rguĂŒhenduvuse kĂ”igi klastri sĂ”lmede vahel, luues iga sĂ”lme peale sillad ja kinnitades sellele alamvĂ”rgu. Kuid tĂ€ielik ja reguleerimata kergesti ligipÀÀsetavus ei ole alati kasulik. Teatud minimaalse isolatsiooni tagamiseks klastris on vajalik sekkuda tulemĂŒri seadistusse. Üldiselt on see usaldatud selle sama CNI kĂ€e alla, mistĂ”ttu mistahes kolmandate osapoolte sekkumised iptables'isse vĂ”ivad olla valesti tĂ”lgendatud vĂ”i tĂ€ielikult ignoreeritud.

Ja "karbist vÀlja" on Kubernetes'i klastris vÔrgu poliitikate haldamiseks ette nÀhtud NetworkPolicy API. See ressurss, mis laienevad valitud nimede ruumides, vÔib sisaldada reegleid, mis eraldavad juurdepÀÀsu erinevate rakenduste vahel. Samuti vÔimaldab see seadistada ligipÀÀsetavust konkreetsete pod'ide, keskkondade (nimede ruumide) vÔi IP-aadressi plokkide vahel:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: test-network-policy
  namespace: default
spec:
  podSelector:
    matchLabels:
      role: db
  policyTypes:
  - Ingress
  - Egress
  ingress:
  - from:
    - ipBlock:
        cidr: 172.17.0.0/16
        except:
        - 172.17.1.0/24
    - namespaceSelector:
        matchLabels:
          project: myproject
    - podSelector:
        matchLabels:
          role: frontend
    ports:
    - protocol: TCP
      port: 6379
  egress:
  - to:
    - ipBlock:
        cidr: 10.0.0.0/24
    ports:
    - protocol: TCP
      port: 5978

See ei ole kÔige primitiivsem nÀide ametlikust dokumentatsioonist see, et vÔib igaveseks Àra vÔtta soovi mÔista vÔrgupoliitika tööloogikat. Siiski proovime mÔista pÔhimÔtteid ja meetodeid, millega liiklust voogusid töödeldakse vÔrgupoliitikate abil...

MÔistagi on kaks liiki liiklust: pod'i sisenemine (Ingress) ja pod'ist vÀljumine (Egress).

Calico Kubernetes vÔrgus: tutvustus ja veidi kogemustest

Need kaks kategooriat jagunevad liikumissuuna jÀrgi.

JĂ€rgmine kohustuslik atribuut on selektor; see, kellele reegel kehtib. See vĂ”ib olla pod (vĂ”i pod'ide grupp) vĂ”i keskkond (st nime ruum). Oluline detail: mĂ”lemad tĂŒĂŒbid peavad sisaldama sildit (label Kubernetes'i terminoloogias) — just nendega opereerivad poliitikad.

Lisaks lÔpliku arvu selektoritele, mis on seotud mingi sildiga, on vÔimalik kirjutada reegleid nagu "Lubada/keelata kÔik/kÔigile" erinevates variatsioonides. Selleks kasutatakse konstruktsioone nagu:

  podSelector: {}
  ingress: []
  policyTypes:
  - Ingress

— selles nĂ€ites on kĂ”ikide pod'ide sisenemine blokeeritud. Vastupidist kĂ€itumist saab saavutada jĂ€rgmise konstruktsiooniga:

  podSelector: {}
  ingress:
  - {}
  policyTypes:
  - Ingress

Sarnane lÀhtudes vÀljaminevast liiklusest:

  podSelector: {}
  policyTypes:
  - Egress

— selle keelamiseks. Ja siin on selle lubamiseks:

  podSelector: {}
  egress:
  - {}
  policyTypes:
  - Egress

Tagasi minnes CNI-plugin'i valimise juurde klastrile, tasub mĂ€rkida, et kĂ”ik vĂ”rgu pluginad ei toeta NetworkPolicy'ga töötamist.NĂ€iteks juba mainitud Flannel ei oska konfigureerida vĂ”rgu poliitikaid, millest on otseselt öeldud ametlikus hoidlas. Seal on mainitud alternatiivi — Open Source projekt Calico, mis oluliselt laiendab Kubernetes'i standard API kogumit vĂ”rgu poliitikate osas.

Calico Kubernetes vÔrgus: tutvustus ja veidi kogemustest

Tutvume Calicoga: teooria

Calico pluginat saab kasutada Flannel'iga (alaprojekt Canal) vĂ”i iseseisvalt, katab nii vĂ”rgu ĂŒhenduse tagamise funktsioonid kui ka juurdepÀÀsu juhtimise vĂ”imalused.

Milliseid vÔimalusi pakub "karbi" lahenduse K8s ja Calico API kogumi kasutamine?

Siin on, mis on NetworkPolicy's sisse ehitatud:

  • poliitikad on piiratud keskkonnaga;
  • poliitikad kehtivad pod'idele, mis on mĂ€rgitud siltidega;
  • reeglid vĂ”ivad kehtida pod'idele, keskkondadele vĂ”i alamvĂ”rkudele;
  • reeglid vĂ”ivad sisaldada protokolle, nimelisi vĂ”i sĂŒmboolseid portide viiteid.

Ja nii laiendab Calico neid funktsioone:

  • poliitikad vĂ”ivad kehtida mis tahes objektile: pod, konteiner, virtuaalmasin vĂ”i liides;
  • reeglid vĂ”ivad sisaldada konkreetset tegevust (keeld, lubamine, logimine);
  • reeglite eesmĂ€rgiks vĂ”i allikaks vĂ”ivad olla port, portide vahemik, protokollid, HTTP- vĂ”i ICMP-attribuudid, IP vĂ”i alamvĂ”rk (4 vĂ”i 6 pĂ”lvkond), kĂ”ik valijad (sĂ”lmed, hostid, keskkonnad);
  • tĂ€iendavalt saab reguleerida liikluse lĂ€bimist DNAT-i seadete ja liikluse edastamise poliitikate abil.

Esimene commit GitHubis Calico hoidlas pĂ€rineb 2016. aasta juulist ja juba aasta hiljem saavutas projekt juhtivad positsioonid Kubernetes'i vĂ”rgustikukonnektiivsete lahenduste seas — sellest rÀÀgivad nĂ€iteks kĂŒsitluse tulemused, mille viis lĂ€bi The New Stack.:

Calico Kubernetes vÔrgus: tutvustus ja veidi kogemustest

Paljud suured hallatud K8s lahendused, nagu Amazon EKS, Azure AKS,, Google GKE, ja teised, on hakanud seda soovitama.

Mis puudutab jĂ”udlust, siis seal on kĂ”ik suurepĂ€rane. Calico arendustiim demonstreeris oma toote testimisel astronoomilisi tulemusi, kĂ€ivitades ĂŒle 50000 konteineri 500 fĂŒĂŒsilisel sĂ”lmelt 20 konteinerit sekundis. Probleeme skaleerimisel ei esinenud. Selliseid tulemusi toodi vĂ€lja juba esimese versiooni kuulutamisel. Iseseisvad uuringud, mis on suunatud lĂ€bilaskevĂ”ime ja ressursside kasutamise analĂŒĂŒsimisele, kinnitavad samuti Calico jĂ”udlust, mis on peaaegu sarnane Flanneliga. NĂ€iteks:

Calico Kubernetes vÔrgus: tutvustus ja veidi kogemustest

Projekt areneb vÀga kiiresti, seda toetatakse populaarsetes hallatud K8s lahendustes, OpenShiftis, OpenStackis, on vÔimalus kasutada Calicot klastrite seadistamiseks kops, esinevad viidatud Service Mesh-vÔrkude ehitamisel (siin on nÀide kasutamisest koos Istio-ga).

Praktika Calicoga

Üldine vanilje Kubernetes'e kasutamise puhul tĂ€hendab CNI paigaldamine failide kasutamist calico.yaml,, mis on alla laaditud ametlikult veebilehelt., kasutades kubectl apply -f.

Reeglina on aktuaalne pistikprogramm ĂŒhilduv 2-3 viimase Kubernetes'e versiooniga: vanemate versioonidega ei testita ja ei garanteerita tööd. Arendajate sĂ”nul töötab Calico Linuxi kerneliga ĂŒle 3.10 CentOS 7, Ubuntu 16 vĂ”i Debian 8 all, iptables'i vĂ”i IPVS'i peal.

Isolatsioon keskkonnas

Üldise arusaama saamiseks vaatleme lihtsat juhtumit, et mĂ”ista, kuidas Calico vĂ”rgupoliitikad erinevad tavalisest ja kuidas reeglite koostamise lĂ€henemine lihtsustab nende lugemist ja konfigureerimise paindlikkust:

Calico Kubernetes vÔrgus: tutvustus ja veidi kogemustest

Klastris on paigaldatud 2 veebirakendust: Node.js ja PHP, millest ĂŒks kasutab Redis't. Et sulgeda PHP juurdepÀÀs Redis'ile, jĂ€ttes samas ĂŒhenduse Node.js'iga, piisab, kui rakendada jĂ€rgmist poliitikat:

kind: NetworkPolicy
apiVersion: networking.k8s.io/v1
metadata:
  name: allow-redis-nodejs
spec:
  podSelector:
    matchLabels:
      service: redis
  ingress:
  - from:
    - podSelector:
        matchLabels:
          service: nodejs
    ports:
    - protocol: TCP
      port: 6379

Sisuliselt lubasime sissetulevat liiklust Redis'ile Node.js'ist. Ja ei keelanud midagi muud. Kui NetworkPolicy on olemas, hakkavad kÔik selles mainitud valijad isoleeruma, kui ei ole mÀrgitud teisiti. Samuti ei laiene isoleerimisse reeglid teistele objektidele, mis ei ole katvat valijat.

NĂ€ites kasutatakse apiVersion Kubernetes'ist "kastist vĂ€lja", kuid miski ei takista kasutamast selle nimega ressurssi Calico tarnest. SĂŒnaktsioon seal on laiem, seega tuleb ĂŒlaltoodud juhtumi reegel ĂŒmber kirjutada jĂ€rgmisel kujul:

apiVersion: crd.projectcalico.org/v1
kind: NetworkPolicy
metadata:
  name: allow-redis-nodejs
spec:
  selector: service == 'redis'
  ingress:
  - action: Allow
    protocol: TCP
    source:
      selector: service == 'nodejs'
    destination:
      ports:
      - 6379

Ülalmainitud konstruktsioonid, mis lubavad vĂ”i keelavad kogu liikluse tavalise NetworkPolicy API kaudu, sisaldavad keerulisi, mis on raskesti mĂ”istetavad ja meeldejÀÀvad sĂŒntaksid sulgudes. Calico puhul piisab tulemĂŒĂŒri reegli loogika muutmiseks vastupidiseks "action: Allow" muutmisest action: Allow . Tundub, et action: Deny.

Isolatsioon keskkondade kaupa

Kujutame nĂŒĂŒd olukorda, kus rakendus genereerib Ă€rimÔÔdikud, et neid koguda Prometheusesse ja edasiseks analĂŒĂŒsiks Grafanas. Ekspordis vĂ”ivad olla tundlikud andmed, mis vaikimisi on taas kĂ”ikidele nĂ€htavad. Sulgeme need andmed vÔÔraste silmade eest:

Calico Kubernetes vÔrgus: tutvustus ja veidi kogemustest

Prometheus on tavaliselt paigutatud eraldi teeninduskeskkonda — selles nĂ€ites on see jĂ€rgmise nimega namespace:

apiVersion: v1
kind: Namespace
metadata:
  labels:
    module: prometheus
  name: kube-prometheus

VÀli metadata.labels see ei olnud juhuslik. Nagu eespool mainitud, namespaceSelector (nagu ka podSelector) opereerib siltidega. Seega, et lubada metrikate kogumist kÔigist pod'idest teatud portidel, tuleb lisada mÔni silt (vÔi vÔtta olemasolevatest) ja seejÀrel rakendada konfigureerimist nagu:

apiVersion: networking.k8s.io/v1
kind: NetworkPolicy
metadata:
  name: allow-metrics-prom
spec:
  podSelector: {}
  ingress:
  - from:
    - namespaceSelector:
        matchLabels:
          module: prometheus
    ports:
    - protocol: TCP
      port: 9100

Ja Calico poliitikate kasutamisel on sĂŒntaks jĂ€rgmine:

apiVersion: crd.projectcalico.org/v1
kind: NetworkPolicy
metadata:
  name: allow-metrics-prom
spec:
  ingress:
  - action: Allow
    protocol: TCP
    source:
      namespaceSelector: module == 'prometheus'
    destination:
      ports:
      - 9100

Üldiselt, lisades selliseid poliitikaid konkreetsete vajaduste jaoks, saab Ă€ra hoida pahatahtlikku vĂ”i juhuslikku sekkumist rakenduste tööse klastris.

Parimaks praktikaks, nagu Calico loojad usuvad, on lĂ€henemine "Keela kĂ”ik ja ava selgelt vajalik", kinnitatud ametlikust dokumentatsioonist (sarnast lĂ€henemist jĂ€rgivad ka teised — eelkĂ”ige, juba mainitud artiklis).

Lisa Calico objekte

Tuletan meelde, et laienenud Calico API abil saab reguleerida sÔlmede kÀttesaadavust, piirdumata ainult pod'idega. JÀrgnevas nÀites, kasutades GlobalNetworkPolicy suletakse ICMP pÀringute edastamine klastris (nÀiteks pingid pod'ist sÔlmele, pod'ide vahel vÔi sÔlmelt IP pod'ile):

apiVersion: crd.projectcalico.org/v1
kind: GlobalNetworkPolicy
metadata:
  name: block-icmp
spec:
  order: 200
  selector: all()
  types:
  - Ingress
  - Egress
  ingress:
  - action: Deny
    protocol: ICMP
  egress:
  - action: Deny
    protocol: ICMP

Ülaltoodud juhul jÀÀb sĂ”lmedel klastris vĂ”imalus omavahel ICMP kaudu "ĂŒhenduda". Ja see probleem lahendatakse GlobalNetworkPolicy, mis on rakendatud ĂŒksusele HostEndpoint:

apiVersion: crd.projectcalico.org/v1
kind: GlobalNetworkPolicy
metadata:
  name: deny-icmp-kube-02
spec:
  selector: "role == 'k8s-node'"
  order: 0
  ingress:
  - action: Allow
    protocol: ICMP
  egress:
  - action: Allow
    protocol: ICMP
---
apiVersion: crd.projectcalico.org/v1
kind: HostEndpoint
metadata:
  name: kube-02-eth0
  labels:
    role: k8s-node
spec:
  interfaceName: eth0
  node: kube-02
  expectedIPs: ["192.168.2.2"]

VPNi juhtum

LÔpuks toon vÀlja tÀiesti reaalse nÀite Calico funktsioonide kasutamisest klastriga seotud suhtlemisel, kus tavaliste poliitikate komplektist ei piisa. Veebirakendusele juurdepÀÀsuks klientide poolt kasutatakse VPN tunnelit, ja see juurdepÀÀs on rangelt kontrollitav ja piiratud teatud lubatud teenuste nimekirjaga:

Calico Kubernetes vÔrgus: tutvustus ja veidi kogemustest

Kliendid ĂŒhendatakse VPN-iga lĂ€bi standardse UDP-porti 1194 ja ĂŒhenduse loomisel saavad nad marsruudid klusterministe pod'ide ja teenuste alavĂ”rkudesse. AlamvĂ”rgud push'itakse tĂ€ielikult, et mitte kaotada teenuseid taaskĂ€ivitamise ja aadresside muutumise ajal.

Konfiguratsioonis olev port on standardne, mis toob kaasa teatud nĂŒansid rakenduse konfigureerimise protsessis ja selle ĂŒleviimisel Kubernetes-kliendisse. NĂ€iteks ilmnes AWS LoadBalancer'is UDP tugi alles eelmisel aastal piiratud piirkondades, ja NodePort'i ei saa kasutada, kuna see suunab kĂ”ikidesse klusteri sĂ”lmedesse ning see muudab serverite eksemplaride arvu skaleerimise tĂ”rkeotstarbeliseks vĂ”imatuks. Peale selle tuleb muuta vaikimisi valitud portide vahemikku...

VÔimalike lahenduste lÀbivaatamise tulemusena valiti jÀrgmine:

  1. VPN pod'id on planeeritud sĂ”lmele reĆŸiimis hostNetwork, st tegeliku IP-aadressiga.
  2. Teenust eksponeeritakse vĂ€ljapoole lĂ€bi ClusterIP. SĂ”lmel tĂ”stetakse fĂŒĂŒsiliselt port, mis on vĂ€ljastpoolt kergelt kergesti ligipÀÀsetav (tingimuslikult on olemas tegelik IP-aadress).
  3. Pod'i tĂ”usmise sĂ”lme mÀÀratlemine jÀÀb meie jutust vĂ€ljapoole. Ütlen vaid, et teenust on vĂ”imalik rangelt "kinni panna" sĂ”lmele vĂ”i kirjutada vĂ€ike sidecar-teenus, mis jĂ€lgib VPN-teenuse praegust IP-aadressi ja muudab DNS-kirjeid klientide juures — kellel jagub fantaasiat.

Marsruudi seisukohalt saame selgelt tuvastada VPN'i kliendi tema IP-aadressi jĂ€rgi, mida VPN-server vĂ€lja annab. Allpool on primitiivne nĂ€ide juurdepÀÀsu piiramisest sellisele kliendile teenustele, joonistus ĂŒlaltoodud Redis'il:

apiVersion: crd.projectcalico.org/v1
kind: HostEndpoint
metadata:
  name: vpnclient-eth0
  labels:
    role: vpnclient
    environment: production
spec:
  interfaceName: "*"
  node: kube-02
  expectedIPs: ["172.176.176.2"]
---
apiVersion: crd.projectcalico.org/v1
kind: GlobalNetworkPolicy
metadata:
  name: vpn-rules
spec:
  selector: "role == 'vpnclient'"
  order: 0
  applyOnForward: true
  preDNAT: true
  ingress:
  - action: Deny
    protocol: TCP
    destination:
      ports: [6379]
  - action: Allow
    protocol: UDP
    destination:
      ports: [53, 67]

Siin on rangelt keelatud ĂŒhendamine porti 6379, kuid samas on sĂ€ilinud DNS-teenuse töö, mille toimimine kannatab reeglite koostamisel ĂŒsna tihti. Sest nagu eelnevalt mainitud, kehtib valiku korral vaikimisi keelav poliitika, kui ei öelda teisiti.

Summary

Seega vĂ”imaldab Calico laiendatud API paindlikult konfigureerida ja dĂŒnaamiliselt muuta suunamist klastris ja selle ĂŒmber. Üldiselt vĂ”ib selle kasutamine tunduda nagu, et tulistatakse ubadega kanade pihta, ning L3-vĂ”rgu juurutamine BGP- ja IP-IP-tunnelitega nĂ€ib monstruuosne lihtsustatud Kubernetes'i paigaldises tasapinnalises vĂ”rgus
 Siiski on tööriist muus osas tĂ€iesti elujĂ”uline ja kasulik.

Klastri isolatsiooni tagamine turvanÔuete tÀitmiseks ei ole alati rakendatav, ja just sellistel juhtudel tuleb appi Calico (vÔi sarnane lahendus). Artiklis toodud nÀited (pÀrast vÀikest kohandamist) on kasutusel mitmes meie klientide paigalduses AWS-is.

P.S.

Lugege ka meie blogist:

Allikas: habr.com

Osta usaldusvÀÀrne hostimine veebilehtede jaoks DDoS-i kaitsega, VPS VDS serverid đŸ”„ Osta usaldusvÀÀrne hostimine veebilehtede jaoks DDoS-i kaitsega, VPS VDS serverid | ProHoster