Canary-implementatie in Kubernetes #1: Gitlab CI

We zullen Gitlab CI en handmatige GitOps gebruiken om de Canary-implementatie in Kubernetes te implementeren en te gebruiken

Canary-implementatie in Kubernetes #1: Gitlab CI

Artikelen uit deze serie:

We zullen de Canary-implementatie handmatig uitvoeren via GitOps en de belangrijkste Kubernetes-bronnen maken/aanpassen. Dit artikel is vooral bedoeld als introductie met hoe de implementatie werkt in Kubernetes Canary, omdat er effectievere automatiseringsmethoden zijn, die we in de volgende artikelen zullen bespreken.


Canary-implementatie in Kubernetes #1: Gitlab CI

https://www.norberteder.com/canary-deployment/

Canarische inzet

Met de Canary-strategie worden updates eerst toegepast op slechts een subset van gebruikers. Via monitoring, loggegevens, handmatig testen of andere feedbackkanalen wordt de release getest voordat deze aan alle gebruikers wordt vrijgegeven.

Kubernetes-implementatie (rollende update)

De standaardstrategie voor Kubernetes-implementatie is rolling-update, waarbij een bepaald aantal pods wordt gelanceerd met nieuwe versies van de installatiekopieën. Als ze zonder problemen zijn gemaakt, worden pods met oude versies van afbeeldingen beëindigd en worden parallel nieuwe pods gemaakt.

Gitops

We gebruiken GitOps in dit voorbeeld omdat we:

  • Git gebruiken als enige bron van waarheid
  • we gebruiken Git Operations voor build en implementatie (er zijn geen andere commando's nodig dan git tag/merge)

Voorbeeld

Laten we een goede gewoonte nemen: één opslagplaats voor applicatiecode en één voor infrastructuur.

Applicatie-opslagplaats

Dit is een heel eenvoudige Python+Flask API die een antwoord retourneert als JSON. We zullen het pakket bouwen via GitlabCI en het resultaat naar de Gitlab Registry pushen. In het register hebben we twee verschillende releaseversies:

  • wuestkamp/k8s-deployment-example-app:v1
  • wuestkamp/k8s-deployment-example-app:v2

Het enige verschil tussen beide is de wijziging in het geretourneerde JSON-bestand. Wij gebruiken deze applicatie om zo eenvoudig mogelijk te visualiseren met welke versie wij communiceren.

Opslagplaats voor infrastructuur

In deze raap gaan we via GitlabCI inzetten bij Kubernetes, .gitlab-ci.yml ziet er zo uit:

image: traherom/kustomize-docker

before_script:
   - printenv
   - kubectl version

stages:
 - deploy

deploy test:
   stage: deploy
   before_script:
     - echo $KUBECONFIG
   script:
     - kubectl get all
     - kubectl apply -f i/k8s

   only:
     - master

Om het zelf uit te voeren heb je een cluster nodig, je kunt Gcloud gebruiken:

gcloud container clusters create canary --num-nodes 3 --zone europe-west3-b

gcloud compute firewall-rules create incoming-80 --allow tcp:80

Je moet vorken https://gitlab.com/wuestkamp/k8s-deployment-example-canary-infrastructure en maak een variabele KUBECONFIG in GitlabCI, dat de configuratie voor toegang zal bevatten kubectl naar uw cluster.

U leest hoe u inloggegevens voor een cluster (Gcloud) kunt verkrijgen hier.

Infrastructuur Yaml

In de infrastructuurrepository hebben we service:

apiVersion: v1
kind: Service
metadata:
 labels:
   id: app
 name: app
spec:
 ports:
 - port: 80
   protocol: TCP
   targetPort: 5000
 selector:
   id: app
 type: LoadBalancer

En inzet in deploy.yaml:

apiVersion: apps/v1
kind: Deployment
metadata:
 name: app
spec:
 replicas: 10
 selector:
   matchLabels:
     id: app
     type: main
 template:
   metadata:
     labels:
       id: app
       type: main
   spec:
     containers:
     - image: registry.gitlab.com/wuestkamp/k8s-deployment-example-app:v1
       name: app
       resources:
         limits:
           cpu: 100m
           memory: 100Mi

En nog een implementatie in deploy-canary.yaml:

kind: Deployment
metadata:
 name: app-canary
spec:
 replicas: 0
 selector:
   matchLabels:
     id: app
     type: canary
 template:
   metadata:
     labels:
       id: app
       type: canary
   spec:
     containers:
     - image: registry.gitlab.com/wuestkamp/k8s-deployment-example-app:v2
       name: app
       resources:
         limits:
           cpu: 100m
           memory: 100Mi

Houd er rekening mee dat er voor app-implementatie nog geen replica's zijn gedefinieerd.

Eerste implementatie uitvoeren

Om de eerste implementatie te starten, kunt u de GitlabCI-pijplijn handmatig starten op de masterbranch. Daarna kubectl zou het volgende moeten opleveren:

Canary-implementatie in Kubernetes #1: Gitlab CI

Wij zien app implementatie met 10 replica's en app-canary met 0. Er is ook een LoadBalancer waartoe we toegang hebben via curl via extern IP:

while true; do curl -s 35.198.149.232 | grep label; sleep 0.1; done

Canary-implementatie in Kubernetes #1: Gitlab CI

We zien dat onze testapplicatie alleen “v1” retourneert.

Kanarie-implementatie uitvoeren

Stap 1: breng een nieuwe versie uit voor sommige gebruikers

We hebben het aantal replica's ingesteld op 1 in het bestandployment-canary.yaml en de nieuwe versie-image:

kind: Deployment
metadata:
 name: app-canary
spec:
 replicas: 1
 selector:
   matchLabels:
     id: app
     type: canary
 template:
   metadata:
     labels:
       id: app
       type: canary
   spec:
     containers:
     - image: registry.gitlab.com/wuestkamp/k8s-deployment-example-app:v2
       name: app
       resources:
         limits:
           cpu: 100m
           memory: 100Mi

In bestand deploy.yaml we hebben het aantal replica's gewijzigd naar 9:

kind: Deployment
metadata:
 name: app
spec:
 replicas: 9
 selector:
   matchLabels:
     id: app
...

We pushen deze wijzigingen naar de repository van waaruit de implementatie zal starten (via GitlabCI) en zien als resultaat:

Canary-implementatie in Kubernetes #1: Gitlab CI

Onze Service verwijst naar beide implementaties, aangezien beide over de app-kiezer beschikken. Vanwege de standaardrandomisatie van Kubernetes zouden we voor ongeveer 10% van de verzoeken verschillende reacties moeten zien:

Canary-implementatie in Kubernetes #1: Gitlab CI

De huidige status van onze applicatie (GitOps, overgenomen van Git als Single Source Of Truth) is de aanwezigheid van twee implementaties met actieve replica's, één voor elke versie.

~10% van de gebruikers raakt vertrouwd met een nieuwe versie en test deze onbedoeld. Dit is het moment om te controleren op fouten in de logboeken en monitoringgegevens om problemen te vinden.

Stap 2: Geef de nieuwe versie vrij voor alle gebruikers

We hebben besloten dat alles goed is gegaan en nu moeten we de nieuwe versie voor alle gebruikers uitrollen. Om dit te doen, updaten we gewoon deploy.yaml het installeren van een nieuwe versie van de afbeelding en het aantal replica's gelijk aan 10. In deploy-canary.yaml we hebben het aantal replica's teruggezet op 0. Na implementatie is het resultaat als volgt:

Canary-implementatie in Kubernetes #1: Gitlab CI

Samengevat

Voor mij helpt het handmatig uitvoeren van de implementatie op deze manier om te begrijpen hoe gemakkelijk het kan worden geconfigureerd met k8s. Omdat je met Kubernetes alles via een API kunt updaten, kunnen deze stappen via scripts worden geautomatiseerd.

Iets anders dat geïmplementeerd moet worden is een tester-ingangspunt (LoadBalancer of via Ingress) waardoor alleen de nieuwe versie toegankelijk is. Het kan worden gebruikt voor handmatig bladeren.

In toekomstige artikelen zullen we andere geautomatiseerde oplossingen bekijken die het meeste van wat we hebben gedaan implementeren.

Lees ook andere artikelen op onze blog:

Bron: www.habr.com

Voeg een reactie