Kubernetes YAML-ellenőrzés a legjobb gyakorlatokkal és irányelvekkel szemben

Jegyzet. ford.: A K8s környezetekhez készült YAML-konfigurációk számának növekedésével egyre sürgetőbbé válik ezek automatikus ellenőrzésének szükségessége. Az áttekintés szerzője nemcsak a meglévő megoldásokat választotta ki erre a feladatra, hanem a Deployment példáján keresztül megvizsgálta azok működését is. Nagyon tanulságosnak bizonyult azok számára, akiket érdekel ez a téma.

Kubernetes YAML-ellenőrzés a legjobb gyakorlatokkal és irányelvekkel szemben

TL, DR: Ez a cikk hat statikus eszközt hasonlít össze a Kubernetes YAML-fájlok érvényesítéséhez és kiértékeléséhez a bevált gyakorlatok és követelmények alapján.

A Kubernetes-munkaterhelések általában YAML-dokumentumok formájában vannak meghatározva. A YAML egyik problémája a jegyzékfájlok közötti kényszerek vagy kapcsolatok megadásának nehézsége.

Mi a teendő, ha meg kell győződnünk arról, hogy a fürtbe telepített összes kép egy megbízható rendszerleíró adatbázisból származik?

Hogyan akadályozható meg, hogy olyan központi telepítések kerüljenek a fürtbe, amelyeknél nincs beállítva PodDisruptionBudgets?

A statikus tesztelés integrációja lehetővé teszi a hibák és irányelvsértések észlelését a fejlesztési szakaszban. Ez növeli annak biztosítását, hogy az erőforrás-definíciók helyesek és biztonságosak, és megnő annak a valószínűsége, hogy a termelési munkaterhelés a legjobb gyakorlatokat követi.

A Kubernetes YAML statikus érvényesítési ökoszisztéma a következő kategóriákra osztható:

  • API-ellenőrzők. Az ebbe a kategóriába tartozó eszközök ellenőrzik a YAML-jegyzéket a Kubernetes API-kiszolgáló követelményei szerint.
  • Kész tesztelők. Az ebbe a kategóriába tartozó eszközökhöz kész tesztek tartoznak a biztonságra, a bevált gyakorlatoknak való megfelelésre stb.
  • Egyedi érvényesítők. A kategória tagjai lehetővé teszik egyedi tesztek létrehozását különböző nyelveken, például Rego és Javascript nyelven.

Ebben a cikkben hat különböző eszközt ismertetünk és hasonlítunk össze:

  1. kubeval;
  2. kube-pontszám;
  3. config-lint;
  4. réz;
  5. verseny;
  6. polaris.

Nos, kezdjük!

Telepítések ellenőrzése

Mielőtt elkezdené az eszközök összehasonlítását, hozzunk létre egy alapot, amelyen tesztelhetjük őket.

Az alábbi jegyzék számos hibát és következetlenséget tartalmaz a bevált gyakorlatokkal: hányat találhat?

apiVersion: apps/v1
kind: Deployment
metadata:
  name: http-echo
spec:
  replicas: 2
  selector:
    matchLabels:
      app: http-echo
  template:
    metadata:
      labels:
        app: http-echo
    spec:
      containers:
      - name: http-echo
        image: hashicorp/http-echo
        args: ["-text", "hello-world"]
        ports:
        - containerPort: 5678
---
apiVersion: v1
kind: Service
metadata:
  name: http-echo
spec:
  ports:
  - port: 5678
    protocol: TCP
    targetPort: 5678
  selector:
    app: http-echo

(base-valid.yaml)

Ezt a YAML-t fogjuk használni a különböző eszközök összehasonlításához.

A fenti megnyilvánulás base-valid.yaml és a cikk egyéb manifesztjei itt találhatók Git adattárak.

A jegyzék egy webalkalmazást ír le, amelynek fő feladata, hogy „Hello World” üzenettel válaszoljon az 5678-as porton. A következő paranccsal telepíthető:

kubectl apply -f hello-world.yaml

És így - a munka ellenőrzéséhez:

kubectl port-forward svc/http-echo 8080:5678

Most menj ide http://localhost:8080 és ellenőrizze, hogy az alkalmazás fut-e. De követi-e a legjobb gyakorlatokat? Nézzük meg.

1. Kubeval

A szív kubeval az az elképzelés, hogy a Kubernetes-szel való bármilyen interakció a REST API-n keresztül történik. Más szóval, egy API-séma segítségével ellenőrizheti, hogy egy adott YAML megfelel-e annak. Nézzünk egy példát.

Telepítési útmutató kubeval elérhetők a projekt honlapján.

Az eredeti cikk írásakor a 0.15.0 verzió elérhető volt.

A telepítés után adjuk meg a fenti jegyzéket:

$ kubeval base-valid.yaml
PASS - base-valid.yaml contains a valid Deployment (http-echo)
PASS - base-valid.yaml contains a valid Service (http-echo)

Ha sikeres, a kubeval 0 kilépési kóddal lép ki. Ezt a következőképpen ellenőrizheti:

$ echo $?
0

Most próbáljuk ki a kubevalt egy másik jegyzékkel:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: http-echo
spec:
  replicas: 2
  template:
    metadata:
      labels:
        app: http-echo
    spec:
      containers:
      - name: http-echo
        image: hashicorp/http-echo
        args: ["-text", "hello-world"]
        ports:
        - containerPort: 5678
---
apiVersion: v1
kind: Service
metadata:
  name: http-echo
spec:
  ports:
  - port: 5678
    protocol: TCP
    targetPort: 5678
  selector:
    app: http-echo

(kubeval-invalid.yaml)

Észreveszed a problémát? Elindítjuk:

$ kubeval kubeval-invalid.yaml
WARN - kubeval-invalid.yaml contains an invalid Deployment (http-echo) - selector: selector is required
PASS - kubeval-invalid.yaml contains a valid Service (http-echo)

# проверим код возврата
$ echo $?
1

Az erőforrás nincs érvényesítve.

Telepítések az API-verzió használatával apps/v1, tartalmaznia kell egy választót, amely megfelel a pod címkéjének. A fenti jegyzék nem tartalmaz választót, így a kubeval hibát jelentett, és nem nulla kóddal lépett ki.

Kíváncsi vagyok, mi történik, ha futsz kubectl apply -f ezzel a manifeszttel?

Nos, próbáljuk meg:

$ kubectl apply -f kubeval-invalid.yaml
error: error validating "kubeval-invalid.yaml": error validating data: ValidationError(Deployment.spec):
missing required field "selector" in io.k8s.api.apps.v1.DeploymentSpec; if you choose to ignore these errors,
turn validation off with --validate=false

Pontosan az a hiba, amelyre Kubeval figyelmeztetett. Kijelölő hozzáadásával javíthatja:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: http-echo
spec:
  replicas: 2
  selector:          # !!!
    matchLabels:     # !!!
      app: http-echo # !!!
  template:
    metadata:
      labels:
        app: http-echo
    spec:
      containers:
      - name: http-echo
        image: hashicorp/http-echo
        args: ["-text", "hello-world"]
        ports:
        - containerPort: 5678
---
apiVersion: v1
kind: Service
metadata:
  name: http-echo
spec:
  ports:
  - port: 5678
    protocol: TCP
    targetPort: 5678
  selector:
    app: http-echo

(base-valid.yaml)

Az olyan eszközök előnye, mint a kubeval, hogy ezeket a hibákat már a telepítési ciklus elején észlelni lehet.

Ezenkívül ezek az ellenőrzések nem igényelnek hozzáférést a fürthöz: offline is elvégezhetők.

Alapértelmezés szerint a kubeval a legújabb Kubernetes API-séma alapján ellenőrzi az erőforrásokat. A legtöbb esetben azonban előfordulhat, hogy egy adott Kubernetes-kiadás ellen kell érvényesítenie. Ezt megteheti a zászlóval --kubernetes-version:

$ kubeval --kubernetes-version 1.16.1 base-valid.yaml

Vegye figyelembe, hogy a verziónak a formátumban kell lennie Major.Minor.Patch.

Az ellenőrzés támogatott verzióinak listáját lásd: JSON-séma a GitHubon, amelyet a kubeval az érvényesítéshez használ. Ha offline szeretné futtatni a kubeval-t, töltse le a sémákat, és adja meg a helyi helyét a zászló segítségével --schema-location.

Az egyedi YAML fájlok mellett a kubeval könyvtárakkal és stdin-nel is működik.

Ezenkívül a Kubeval könnyen integrálható a CI-csővezetékbe. Azok, akik teszteket szeretnének futtatni, mielőtt a jegyzékeket a fürtbe küldenék, örömmel fogják tudni, hogy a kubeval három kimeneti formátumot támogat:

  1. Egyszerű szöveg;
  2. JSON;
  3. Test Anything Protocol (TAP).

A formátumok bármelyike ​​felhasználható a kimenet további elemzésére, így a kívánt típusú eredmények összegzését képezik.

A kubeval egyik hátránya, hogy jelenleg nem tudja ellenőrizni az egyéni erőforrás-meghatározásokat (CRD). A kubeval azonban konfigurálható figyelmen kívül hagyja őket.

A Kubeval egy nagyszerű erőforrás-érvényesítési és -értékelési eszköz; hangsúlyozni kell azonban, hogy a teszt sikeres teljesítése nem garantálja, hogy az erőforrás megfelel a legjobb gyakorlatoknak.

Például a címke használatával latest konténerben nem felel meg a legjobb gyakorlatoknak. A kubeval azonban nem tartja ezt hibának, és nem jelenti be. Vagyis az ilyen YAML ellenőrzése figyelmeztetés nélkül befejeződik.

De mi van akkor, ha ki kell értékelnie a YAML-t, és észlelnie kell a megsértéseket, például a címkét latest? Hogyan lehet ellenőrizni egy YAML-fájlt a legjobb gyakorlatokkal szemben?

2. Kube pontszáma

Kube pontszáma elemzi a YAML jegyzékeket, és kiértékeli azokat a beépített tesztek alapján. Ezeket a teszteket a biztonsági ajánlások és a legjobb gyakorlatok alapján választják ki, mint például:

  • Egy tároló futtatása nem rootként.
  • A hüvely állapotának ellenőrzése.
  • Kérések és korlátok beállítása az erőforrásokhoz.

A teszt három eredményt ad: OK, FIGYELEM и KRITIKAI.

A Kube-score online kipróbálható vagy helyben telepíthető.

Az eredeti cikk írásakor a kube-score legújabb verziója 1.7.0.

Teszteljük a jegyzékünkön base-valid.yaml:

$ kube-score score base-valid.yaml

apps/v1/Deployment http-echo
[CRITICAL] Container Image Tag
  · http-echo -> Image with latest tag
      Using a fixed tag is recommended to avoid accidental upgrades
[CRITICAL] Pod NetworkPolicy
  · The pod does not have a matching network policy
      Create a NetworkPolicy that targets this pod
[CRITICAL] Pod Probes
  · Container is missing a readinessProbe
      A readinessProbe should be used to indicate when the service is ready to receive traffic.
      Without it, the Pod is risking to receive traffic before it has booted. It is also used during
      rollouts, and can prevent downtime if a new version of the application is failing.
      More information: https://github.com/zegl/kube-score/blob/master/README_PROBES.md
[CRITICAL] Container Security Context
  · http-echo -> Container has no configured security context
      Set securityContext to run the container in a more secure context.
[CRITICAL] Container Resources
  · http-echo -> CPU limit is not set
      Resource limits are recommended to avoid resource DDOS. Set resources.limits.cpu
  · http-echo -> Memory limit is not set
      Resource limits are recommended to avoid resource DDOS. Set resources.limits.memory
  · http-echo -> CPU request is not set
      Resource requests are recommended to make sure that the application can start and run without
      crashing. Set resources.requests.cpu
  · http-echo -> Memory request is not set
      Resource requests are recommended to make sure that the application can start and run without crashing.
      Set resources.requests.memory
[CRITICAL] Deployment has PodDisruptionBudget
  · No matching PodDisruptionBudget was found
      It is recommended to define a PodDisruptionBudget to avoid unexpected downtime during Kubernetes
      maintenance operations, such as when draining a node.
[WARNING] Deployment has host PodAntiAffinity
  · Deployment does not have a host podAntiAffinity set
      It is recommended to set a podAntiAffinity that stops multiple pods from a deployment from
      being scheduled on the same node. This increases availability in case the node becomes unavailable.

A YAML átmegy a kubeval ellenőrzéseken, míg a kube-score a következő hiányosságokra mutat rá:

  • A készenléti ellenőrzések nincsenek konfigurálva.
  • Nincsenek kérések és korlátok a CPU és a memória erőforrásaira vonatkozóan.
  • A pod-megszakítási költségkeretek nincsenek beállítva.
  • A külön létezésnek nincsenek szabályai (affinitásellenes) a rendelkezésre állás maximalizálása érdekében.
  • A tároló rootként fut.

Mindezek ésszerű megjegyzések azokra a hiányosságokra vonatkozóan, amelyeket orvosolni kell annak érdekében, hogy a telepítés hatékonyabb és megbízhatóbb legyen.

Csapat kube-score ember által olvasható formában adja ki az információkat, beleértve a típus összes megsértését FIGYELEM и KRITIKAIami sokat segít a fejlődés során.

Azok, akik ezt az eszközt egy CI-folyamat részeként szeretnék használni, több tömörített kimenetet is engedélyezhetnek a flag használatával --output-format ci (ebben az esetben az eredményt tartalmazó tesztek is megjelennek OK):

$ kube-score score base-valid.yaml --output-format ci

[OK] http-echo apps/v1/Deployment
[OK] http-echo apps/v1/Deployment
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) CPU limit is not set
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) Memory limit is not set
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) CPU request is not set
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) Memory request is not set
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) Image with latest tag
[OK] http-echo apps/v1/Deployment
[CRITICAL] http-echo apps/v1/Deployment: The pod does not have a matching network policy
[CRITICAL] http-echo apps/v1/Deployment: Container is missing a readinessProbe
[CRITICAL] http-echo apps/v1/Deployment: (http-echo) Container has no configured security context
[CRITICAL] http-echo apps/v1/Deployment: No matching PodDisruptionBudget was found
[WARNING] http-echo apps/v1/Deployment: Deployment does not have a host podAntiAffinity set
[OK] http-echo v1/Service
[OK] http-echo v1/Service
[OK] http-echo v1/Service
[OK] http-echo v1/Service

A kubevalhez hasonlóan a kube-score nullától eltérő kilépési kódot ad vissza, ha egy teszt sikertelen. KRITIKAI. Hasonló feldolgozást is engedélyezhet FIGYELEM.

Ezenkívül lehetőség van az erőforrások különböző API-verziókkal való összehasonlítására (hasonlóan a kubevalhoz). Ez az információ azonban magában a kube-score-ban van "keménykódolva": nem választhatja ki a Kubernetes másik verzióját. Ez a korlátozás nagy problémát jelenthet, ha frissíteni kívánja a fürtöt, vagy ha több fürttel rendelkezik a K8s különböző verzióival.

Kérjük, vegye figyelembe, hogy a már van probléma javaslattal e lehetőség megvalósítására.

További információ a kube-score-ról a következő címen található: hivatalos honlapján.

A Kube-score tesztek nagyszerű eszközt jelentenek a legjobb gyakorlatok megvalósításához, de mi van akkor, ha módosítania kell a tesztet, vagy egyéni szabályokat kell hozzáadnia? Sajnos ezt nem lehet megtenni.

A Kube-score nem bővíthető: nem adhat hozzá házirendeket, és nem módosíthatja azokat.

Ha egyéni teszteket szeretne írni a vállalati szabályzatoknak való megfelelés érdekében, használhatja a következő négy eszköz egyikét: config-lint, copper, conftest vagy polaris.

3. Config-lint

A Config-lint egy eszköz a YAML, JSON, Terraform, CSV konfigurációs fájlok és Kubernetes jegyzékek érvényesítésére.

segítségével telepítheti utasítás a projekt honlapján.

A jelenlegi kiadás az eredeti cikk írásakor az 1.5.0.

A Config-lint nem tartalmaz beépített teszteket a Kubernetes-jegyzékek érvényesítésére.

A tesztek elvégzéséhez létre kell hoznia a megfelelő szabályokat. YAML-fájlokba vannak írva, amelyeket "szabálykészleteknek" neveznek. (szabálykészlet), és a következő szerkezettel rendelkezik:

version: 1
description: Rules for Kubernetes spec files
type: Kubernetes
files:
  - "*.yaml"
rules:
   # список правил

(rule.yaml)

Vizsgáljuk meg közelebbről:

  • Mező type megadja, hogy a config-lint milyen típusú konfigurációt fog használni. A K8s esetében ez az mindig Kubernetes.
  • A területen files a fájlok mellett megadhat egy könyvtárat is.
  • Mező rules felhasználói tesztek beállítására szolgál.

Tegyük fel, hogy meg akar bizonyosodni arról, hogy a telepítésben lévő képek mindig egy megbízható lerakatból, például my-company.com/myapp:1.0. Az ellenőrzést végző konfig-lint szabály így néz ki:

- id: MY_DEPLOYMENT_IMAGE_TAG
  severity: FAILURE
  message: Deployment must use a valid image tag
  resource: Deployment
  assertions:
    - every:
        key: spec.template.spec.containers
        expressions:
          - key: image
            op: starts-with
            value: "my-company.com/"

(rule-trusted-repo.yaml)

Minden szabályhoz meg kell adni a következő attribútumokat:

  • id — a szabály egyedi azonosítója;
  • severity - Lehet KUDARC, FIGYELEM и NON_COMPLIANT;
  • message - a szabály megsértése esetén ennek a sornak a tartalma jelenik meg;
  • resource — az erőforrás típusa, amelyre ez a szabály vonatkozik;
  • assertions - azoknak a feltételeknek a listája, amelyeket az erőforrással kapcsolatban értékelni fognak.

A fenti szabályban assertion hívott every ellenőrzi, hogy a Deployment'e (key: spec.templates.spec.containers) megbízható képeket használjon (azaz a következővel kezdődőket). my-company.com/).

A teljes szabályrendszer így néz ki:

version: 1
description: Rules for Kubernetes spec files
type: Kubernetes
files:
  - "*.yaml"
rules:

 - id: DEPLOYMENT_IMAGE_REPOSITORY # !!!
    severity: FAILURE
    message: Deployment must use a valid image repository
    resource: Deployment
    assertions:
      - every:
          key: spec.template.spec.containers
          expressions:
            - key: image
              op: starts-with
              value: "my-company.com/"

(ruleset.yaml)

A teszt kipróbálásához mentsük el másként check_image_repo.yaml. Nézzük meg a fájlt base-valid.yaml:

$ config-lint -rules check_image_repo.yaml base-valid.yaml

[
  {
  "AssertionMessage": "Every expression fails: And expression fails: image does not start with my-company.com/",
  "Category": "",
  "CreatedAt": "2020-06-04T01:29:25Z",
  "Filename": "test-data/base-valid.yaml",
  "LineNumber": 0,
  "ResourceID": "http-echo",
  "ResourceType": "Deployment",
  "RuleID": "DEPLOYMENT_IMAGE_REPOSITORY",
  "RuleMessage": "Deployment must use a valid image repository",
  "Status": "FAILURE"
  }
]

Az ellenőrzés nem sikerült. Most nézzük meg a következő jegyzéket a megfelelő képtárral:

apiVersion: apps/v1
kind: Deployment
metadata:
  name: http-echo
spec:
  replicas: 2
  selector:
    matchLabels:
      app: http-echo
  template:
    metadata:
      labels:
        app: http-echo
    spec:
      containers:
      - name: http-echo
         image: my-company.com/http-echo:1.0 # !!!
         args: ["-text", "hello-world"]
         ports:
         - containerPort: 5678

(image-valid-mycompany.yaml)

Ugyanezt a tesztet futtatjuk a fenti jegyzékkel. Nem található hiba:

$ config-lint -rules check_image_repo.yaml image-valid-mycompany.yaml
[]

A Config-lint egy előretekintő keretrendszer, amely lehetővé teszi egyéni tesztek létrehozását a Kubernetes YAML-jegyzékek YAML DSL használatával történő érvényesítéséhez.

De mi van akkor, ha bonyolultabb logikára és tesztekre van szükség? A YAML képességei nem túl kicsik ehhez? Mi lenne, ha teszteket készíthetne egy teljes értékű programozási nyelven?

4. Réz

Réz V2 egy keretrendszer a manifesztek egyéni tesztekkel történő érvényesítésére (hasonlóan a config-linthez).

Ez utóbbitól azonban abban különbözik, hogy nem YAML-t használ a tesztek leírására. Ehelyett a tesztek JavaScriptben írhatók. A Copper számos alapvető eszközt tartalmazó könyvtárat biztosíta Kubernetes-objektumokkal kapcsolatos információk olvasásához és a hibák jelentéséhez.

A Copper telepítésének lépései a következő helyen találhatók: hivatalos dokumentáció.

A 2.0.1 a segédprogram legújabb kiadása az eredeti cikk írásakor.

A config-linthez hasonlóan a Coppernek sincs beépített tesztje. Írjunk egyet. Engedje meg neki, hogy ellenőrizze, hogy a központi telepítések kizárólag megbízható adattárakból származó tárolóképeket használnak-e my-company.com.

Hozzon létre egy fájlt check_image_repo.js a következő tartalommal:

$$.forEach(function($){
    if ($.kind === 'Deployment') {
        $.spec.template.spec.containers.forEach(function(container) {
            var image = new DockerImage(container.image);
            if (image.registry.lastIndexOf('my-company.com/') != 0) {
                errors.add_error('no_company_repo',"Image " + $.metadata.name + " is not from my-company.com repo", 1)
            }
        });
    }
});

Most pedig teszteljük a manifestünket base-valid.yaml, használja a parancsot copper validate:

$ copper validate --in=base-valid.yaml --validator=check_image_tag.js

Check no_company_repo failed with severity 1 due to Image http-echo is not from my-company.com repo
Validation failed

Nyilvánvaló, hogy összetettebb teszteket is el lehet végezni réz használatával - például ellenőrizni lehet a domain neveket az Ingress manifestben, vagy elutasítani a privilegizált módban futó podokat.

A Copperbe különféle segédfunkciók vannak beépítve:

  • DockerImage beolvassa a megadott bemeneti fájlt, és létrehoz egy objektumot a következő attribútumokkal:
    • name - a kép neve,
    • tag - képcímke,
    • registry - képregisztráció
    • registry_url - protokoll (https://) és egy képnyilvántartást,
    • fqin — a kép teljes helye.
  • Funkció findByName segít megtalálni az erőforrást adott típus szerint (kind) és a név (name) a bemeneti fájlból.
  • Funkció findByLabels segít megtalálni a megadott típusú erőforrást (kind) és címkék (labels).

Az összes elérhető segédfunkció megtalálható itt.

Alapértelmezés szerint a teljes YAML bemeneti fájlt betölti egy változóba $$ és elérhetővé teszi a szkriptek számára (a jQuery tapasztalattal rendelkezők számára ismerős technika).

A Copper fő előnye nyilvánvaló: nem kell speciális nyelvet tanulnia, és különféle JavaScript-funkciókat használhat saját tesztek létrehozásához, mint például karakterlánc-interpoláció, függvények stb.

Azt is meg kell jegyezni, hogy a Copper jelenlegi verziója a JavaScript-motor ES5-ös verziójával működik, nem pedig az ES6-tal.

Részletek a címen érhetők el a projekt hivatalos weboldala.

Ha azonban nem vagy nagy JavaScript-rajongó, és egy kifejezetten a szabályzatok lekérdezéséhez és leírásához szükséges nyelvet részesít előnyben, akkor érdemes megvizsgálni a conftest.

5. Verseny

A Conftest egy keretrendszer a konfigurációs adatok ellenőrzésére. Kubernetes manifesztek tesztelésére/ellenőrzésére is alkalmas. A tesztek leírása speciális lekérdezési nyelv használatával történik Rego.

A conftest a következővel telepítheti utasításszerepel a projekt honlapján.

Az eredeti cikk írásakor a legújabb elérhető verzió a 0.18.2.

A config-linthez és a rézhez hasonlóan a conftest is beépített tesztek nélkül érkezik. Próbáljuk ki, és írjuk meg saját szabályzatunkat. Az előző példákhoz hasonlóan ellenőrizni fogjuk, hogy a tárolóképek megbízható forrásból származnak-e.

Hozzon létre egy könyvtárat conftest-checks, és benne - egy fájl a névvel check_image_registry.rego a következő tartalommal:

package main

deny[msg] {

  input.kind == "Deployment"
  image := input.spec.template.spec.containers[_].image
  not startswith(image, "my-company.com/")
  msg := sprintf("image '%v' doesn't come from my-company.com repository", [image])
}

Most pedig teszteljük base-valid.yaml keresztül conftest:

$ conftest test --policy ./conftest-checks base-valid.yaml

FAIL - base-valid.yaml - image 'hashicorp/http-echo' doesn't come from my-company.com repository
1 tests, 1 passed, 0 warnings, 1 failure

A teszt a vártnak megfelelően sikertelen volt, mert a képek nem megbízható forrásból származnak.

A Rego fájlban definiálunk egy blokkot deny. Igazságát jogsértésnek tekintik. Ha blokkolja deny többszörös, a conftest függetlenül ellenőrzi őket, és bármelyik blokk igazságtartalmát szabálysértésként kezeli.

Az alapértelmezett kimeneten kívül a conftest támogatja a JSON-t, a TAP-ot és a táblázatos formátumot – ez egy nagyon hasznos funkció, ha jelentéseket kell beágyazni egy meglévő CI-folyamatba. A kívánt formátumot a zászló segítségével állíthatja be --output.

Az irányelvek hibakeresésének megkönnyítése érdekében a conftest jelzővel rendelkezik --trace. Nyomot nyomtat arról, hogy a conftest hogyan elemzi a megadott házirend-fájlokat.

A conftest házirendek közzétehetők és megoszthatók az OCI (Open Container Initiative) nyilvántartásokban műtermékként.

parancsok push и pull lehetővé teszi egy műtermék közzétételét vagy egy meglévő műtermék lekérését egy távoli nyilvántartásból. Próbáljuk meg közzétenni az általunk létrehozott házirendet a helyi Docker-nyilvántartásban conftest push.

Indítsa el a helyi Docker-nyilvántartást:

$ docker run -it --rm -p 5000:5000 registry

Egy másik terminálban lépjen a korábban létrehozott könyvtárba conftest-checks és futtassa a következő parancsot:

$ conftest push 127.0.0.1:5000/amitsaha/opa-bundle-example:latest

Ha a parancs sikeres volt, egy ilyen üzenetet fog látni:

2020/06/10 14:25:43 pushed bundle with digest: sha256:e9765f201364c1a8a182ca637bc88201db3417bacc091e7ef8211f6c2fd2609c

Most hozzon létre egy ideiglenes könyvtárat, és futtassa a parancsot conftest pull. Le fogja tölteni az előző parancs által létrehozott csomagot:

$ cd $(mktemp -d)
$ conftest pull 127.0.0.1:5000/amitsaha/opa-bundle-example:latest

Az ideiglenes könyvtárban megjelenik egy alkönyvtár policy, amely a szabályzatfájlunkat tartalmazza:

$ tree
.
└── policy
  └── check_image_registry.rego

A tesztek közvetlenül a tárolóból futtathatók:

$ conftest test --update 127.0.0.1:5000/amitsaha/opa-bundle-example:latest base-valid.yaml
..
FAIL - base-valid.yaml - image 'hashicorp/http-echo' doesn't come from my-company.com repository
2 tests, 1 passed, 0 warnings, 1 failure

Sajnos a DockerHub még nem támogatott. Tehát tekintse magát szerencsésnek, ha használja Azure Container Registry (ACR) vagy a saját nyilvántartásában.

A műtermék formátuma megegyezik a Nyissa meg a Policy Agent csomagokat (OPA), amely lehetővé teszi a conftest használatával tesztek futtatását a meglévő OPA-csomagokból.

A szabályzat megosztásáról és a verseny egyéb funkcióiról a következő címen tudhat meg többet a projekt hivatalos weboldala.

6. Polaris

Az utolsó eszköz, amelyről ebben a cikkben lesz szó Polaris. (Tavalyi bejelentése mi már lefordítva - kb. ford.)

A Polaris telepíthető fürtbe vagy parancssori módban használható. Amint azt már sejtette, lehetővé teszi a Kubernetes-jegyzékek statikus elemzését.

Ha parancssori módban fut, beépített tesztek állnak rendelkezésre olyan területekre, mint a biztonság és a legjobb gyakorlatok (hasonlóan a kube-score-hoz). Ezenkívül létrehozhat saját teszteket (például a config-lint, a copper és a conftest esetében).

Más szóval, a Polaris mindkét eszközkategória előnyeit egyesíti: beépített és egyedi tesztekkel.

A Polaris parancssori módban történő telepítéséhez használja a utasításokat a projekt honlapján.

Az eredeti cikk írásakor az 1.0.3-as verzió elérhető.

A telepítés befejezése után futtathatja a polarist a jegyzékben base-valid.yaml a következő paranccsal:

$ polaris audit --audit-path base-valid.yaml

Egy JSON-karakterláncot ad ki, amely részletezi a futtatott teszteket és azok eredményeit. A kimenet szerkezete a következő lesz:

{
  "PolarisOutputVersion": "1.0",
  "AuditTime": "0001-01-01T00:00:00Z",
  "SourceType": "Path",
  "SourceName": "test-data/base-valid.yaml",
  "DisplayName": "test-data/base-valid.yaml",
  "ClusterInfo": {
    "Version": "unknown",
    "Nodes": 0,
    "Pods": 2,
    "Namespaces": 0,
    "Controllers": 2
  },
  "Results": [
    /* длинный список */
  ]
}

Teljes kivonás elérhető itt.

A kube-score-hoz hasonlóan a Polaris is azonosítja azokat a problémákat, amelyeknél a jegyzék nem követi a legjobb gyakorlatokat:

  • A hüvely állapotának ellenőrzése hiányzik.
  • Nincsenek címkék megadva a tárolóképekhez.
  • A tároló rootként fut.
  • A memória és a CPU kérése és határértéke nincs megadva.

Minden teszthez, az eredményektől függően, egy kritikussági fok tartozik: figyelmeztetés vagy veszély. Ha többet szeretne megtudni az elérhető beépített tesztekről, lásd: dokumentáció.

Ha nincs szükség részletekre, megadhat egy zászlót --format score. Ebben az esetben a Polaris 1 és 100 − közötti számot ad ki pontszám (azaz értékelés):

$ polaris audit --audit-path test-data/base-valid.yaml --format score
68

Minél közelebb van a pontszám a 100-hoz, annál magasabb a megfelelési fok. Ha ellenőrzi a parancs kilépési kódját polaris audit, kiderül, hogy egyenlő 0-val.

Kényszerítés polaris audit A nullától eltérő kóddal két jelzővel lehet kilépni:

  • zászló --set-exit-code-below-score argumentumként egy 1-100 közötti küszöbértéket vesz fel. Ebben az esetben a parancs 4-es kilépési kóddal lép ki, ha a pontszám a küszöb alatt van. Ez nagyon hasznos, ha van valamilyen küszöbértéke (mondjuk 75), és figyelmeztetést szeretne kapni, ha a pontszám alá csökken.
  • zászló --set-exit-code-on-danger hatására a parancs a 3-as kóddal kilép, ha valamelyik veszélyteszt sikertelen.

Most próbáljunk meg létrehozni egy egyéni tesztet, amely ellenőrzi, hogy a kép megbízható tárolóból származik-e. A felhasználói tesztek YAML formátumban vannak megadva, magát a tesztet pedig a JSON-séma írja le.

A következő YAML-részlet egy új nevű tesztet ír le checkImageRepo:

checkImageRepo:
  successMessage: Image registry is valid
  failureMessage: Image registry is not valid
  category: Images
  target: Container
  schema:
    '$schema': http://json-schema.org/draft-07/schema
    type: object
    properties:
      image:
        type: string
        pattern: ^my-company.com/.+$

Nézzük meg közelebbről:

  • successMessage - ez a sor jelenik meg, ha a teszt sikeresen befejeződött;
  • failureMessage - hiba esetén ez az üzenet jelenik meg;
  • category - az egyik kategóriát jelzi: Images, Health Checks, Security, Networking и Resources;
  • target--- meghatározza az objektum típusát (spec) a tesztet alkalmazzák. Lehetséges értékek: Container, Pod vagy Controller;
  • Maga a teszt az objektumban van megadva schema JSON séma használatával. Ebben a tesztben a kulcsszó pattern a képforrás és a kívánt forrás összehasonlítására szolgál.

A fenti teszt futtatásához létre kell hoznia a következő Polaris konfigurációt:

checks:
  checkImageRepo: danger
customChecks:
  checkImageRepo:
    successMessage: Image registry is valid
    failureMessage: Image registry is not valid
    category: Images
    target: Container
    schema:
      '$schema': http://json-schema.org/draft-07/schema
      type: object
      properties:
        image:
          type: string
          pattern: ^my-company.com/.+$

(polaris-conf.yaml)

Elemezzük a fájlt:

  • A területen checks teszteket és azok kritikussági szintjét írják elő. Mivel kívánatos a figyelmeztetés, ha egy kép nem megbízható forrásból készült, itt állítjuk be a szintet danger.
  • Maga a teszt checkImageRepo majd hozzárendeljük az objektumhoz customChecks.

Mentse el a fájlt másként custom_check.yaml. Most már futhatsz polaris audit érvényesítést igénylő YAML-jegyzékkel.

A jegyzékünk tesztelése base-valid.yaml:

$ polaris audit --config custom_check.yaml --audit-path base-valid.yaml

Csapat polaris audit csak a fent megadott egyéni tesztet futtatta, és az nem sikerült.

Ha javítja a képet my-company.com/http-echo:1.0, a Polaris sikeresen befejeződik. A változásokat tartalmazó kiáltvány már megvan adattárakígy ellenőrizheti az előző parancsot a jegyzékben image-valid-mycompany.yaml.

Felmerül a kérdés: hogyan lehet beépített teszteket futtatni egyedi tesztekkel? Könnyen! Csak hozzá kell adnia a beépített tesztazonosítókat a konfigurációs fájlhoz. Ennek eredményeként a következő formában jelenik meg:

checks:
  cpuRequestsMissing: warning
  cpuLimitsMissing: warning
  # Other inbuilt checks..
  # ..
  # custom checks
  checkImageRepo: danger # !!!
customChecks:
  checkImageRepo:        # !!!
    successMessage: Image registry is valid
    failureMessage: Image registry is not valid
    category: Images
    target: Container
    schema:
      '$schema': http://json-schema.org/draft-07/schema
      type: object
      properties:
        image:
          type: string
          pattern: ^my-company.com/.+$

(config_with_custom_check.yaml)

A teljes konfigurációs fájl példája elérhető itt.

Ellenőrizze a jegyzéket base-valid.yaml, a beépített és egyéni tesztek használatával a következő parancsot használhatja:

$ polaris audit --config config_with_custom_check.yaml --audit-path base-valid.yaml

A Polaris egyéni tesztekkel egészíti ki a beépített teszteket, így a két világ legjobbjait egyesíti.

Másrészt az erősebb nyelvek, például a Rego vagy a JavaScript használatának képtelensége korlátozó tényező lehet, ami megakadályozza, hogy kifinomultabb teszteket készítsen.

További információ a Polarisról a következő címen érhető el projekt honlapja.

Összegzés

Bár számos eszköz létezik a Kubernetes YAML fájlok érvényesítésére és értékelésére, fontos, hogy világosan megértsük a tesztek megtervezésének és végrehajtásának módját.

Például ha a Kubernetes manifeszteket vesz egy csővezetéken keresztül, a kubeval lehet az első lépés egy ilyen csővezetékben. Biztosítja, hogy az objektumdefiníciók megfeleljenek a Kubernetes API sémának.

Amint egy ilyen felülvizsgálat befejeződött, kifinomultabb teszteket lehet folytatni, például a szabványos legjobb gyakorlatoknak és a konkrét irányelveknek való megfelelést. Itt jól jönne a kube-score és a Polaris.

Azok számára, akiknek összetett követelményeik vannak, és finomítaniuk kell teszteiket, a réz, a config-lint és a conftest nagyszerű lenne..

A Conftest és a config-lint a YAML-t használja az egyéni tesztek meghatározásához, míg a réz hozzáférést biztosít a teljes programozási nyelvhez, így ez egy nagyon vonzó választás.

Másrészt használja-e ezen eszközök valamelyikét, és ezért manuálisan hozza létre az összes tesztet, vagy részesítse előnyben a Polarist, és csak azt adja hozzá, ami szükséges? Erre a kérdésre nincs egységes válasz.

Az alábbi táblázat az egyes eszközök rövid leírását tartalmazza:

szerszám
sors
Korlátozások
Felhasználói tesztek

kubeval
Ellenőrzi a YAML-jegyzékfájlt egy adott API-sémaverzióhoz képest
Nem tudja, hogyan kell dolgozni a CRD-vel
Nincs

kube pontszámot
Elemezi a YAML-jegyzékeket a legjobb gyakorlatokkal szemben
Nem választhatja ki a Kubernetes API verzióját az erőforrások ellenőrzéséhez
Nincs

réz
Általános keretrendszer egyéni JavaScript-tesztek létrehozásához YAML-jegyzékekhez
Nincsenek beépített tesztek. Kevés dokumentáció
Igen

config-lint
Általános keretrendszer tesztek készítéséhez YAML-be ágyazott tartományspecifikus nyelven. Különféle konfigurációs formátumokat támogat (pl. Terraform)
Nincsenek kész tesztek. Előfordulhat, hogy a beépített állítások és funkciók nem elegendőek
Igen

vetélkedő
Keretrendszer saját tesztek létrehozásához a Rego-ban (egy speciális lekérdezési nyelv). Lehetővé teszi a szabályzat megosztását OCI-csomagokon keresztül
Nincsenek beépített tesztek. Regót meg kell tanulnod. A Docker Hub nem támogatott házirendek közzétételekor
Igen

Polaris
Elemezi a YAML-jegyzékeket a szabványos bevált gyakorlatokkal szemben. Lehetővé teszi saját tesztek létrehozását a JSON-séma használatával
Előfordulhat, hogy a JSON-séma alapú tesztelési képességek nem elegendőek
Igen

Mivel ezek az eszközök nem függenek a Kubernetes-fürthöz való hozzáféréstől, könnyen telepíthetők. Lehetővé teszik a forrásfájlok szűrését, és gyors visszajelzést adnak a kérések szerzőinek lekéréséhez a projektekre.

PS a fordítótól

Olvassa el blogunkon is:

Forrás: will.com

Hozzászólás