Commençons
Pour que l'application Web soit disponible sur toutes les machines, nous devons la conteneuriser et lorsque la conteneurisation est le mot, quoi de mieux que Docker.
J'ai créé un Dockerfile pour exécuter l'application mais j'ai utilisé un format en plusieurs étapes
La raison est simple : si je crée une image en une seule étape, cela consommerait plus d'espace sur la machine alors qu'en utilisant des builds en plusieurs étapes, nous optimisons la taille finale de l'image en séparant les environnements de build et d'exécution et réduisons également l'attaque. surface de notre image pour une meilleure sécurité
Voici comment procéder
# Start with a base image FROM golang:1.22 as base WORKDIR /app COPY go.mod ./ RUN go mod download COPY . . RUN go build -o main . ####################################################### # Reduce the image size using multi-stage builds # We will use a distroless image to run the application FROM gcr.io/distroless/base # Copy the binary from the previous stage COPY --from=base /app/main . # Copy the static files from the previous stage COPY --from=base /app/static ./static # Expose the port on which the application will run EXPOSE 8080 # Command to run the application CMD ["./main"]
Maintenant que nous avons le fichier docker, construisons-le et déployons-le sur dockerhub
docker build -t pankaj892/webapp:v1 .
Nous essayons de vérifier si l'application fonctionne comme prévu sur la machine locale
docker run -p 8080:8080 pankaj892-webapp:v1
Poussons-le vers Dockerhub
docker push pankaj892/webapp:v1 .
Vous pouvez créer un cluster localement à l'aide de mininkube/kind ou utiliser l'une des solutions gérées sur le cloud. J'utiliserai Elastic Kubernetes Service (EKS) d'AWS.
Vous pouvez lancer un cluster dans EKS à l'aide de la console ou depuis la ligne de commande. J'utiliserai la ligne de commande
eksctl create cluster--instance-selector-vcpus=2 --instance-selector-memory=4 --name <name-of-cluster> --region <region-code>
Cela choisira uniquement les types de machines pour les groupes de nœuds dotés de 2 processeurs virtuels et d'une mémoire de 4 Go
Nous pouvons déployer toutes les ressources une par une mais il serait difficile de les gérer à mesure qu'elles évoluent, c'est là que Helm entre en jeu, il agit comme un gestionnaire de packages pour gérer toutes nos ressources à l'aide de graphiques
Créer un graphique de barre
# Start with a base image FROM golang:1.22 as base WORKDIR /app COPY go.mod ./ RUN go mod download COPY . . RUN go build -o main . ####################################################### # Reduce the image size using multi-stage builds # We will use a distroless image to run the application FROM gcr.io/distroless/base # Copy the binary from the previous stage COPY --from=base /app/main . # Copy the static files from the previous stage COPY --from=base /app/static ./static # Expose the port on which the application will run EXPOSE 8080 # Command to run the application CMD ["./main"]
Helm créera des fichiers pour notre usage mais nous n'en avons pas besoin de la plupart pour notre projet.
Créez les fichiers suivants et ajoutez-les dans le répertoire helm
Déploiement
eksctl create cluster--instance-selector-vcpus=2 --instance-selector-memory=4 --name <name-of-cluster> --region <region-code>
Service
helm create web-app
Entrée
# This is a sample deployment manifest file for a simple web application. apiVersion: apps/v1 kind: Deployment metadata: name: web-app labels: app: web-app spec: replicas: 1 selector: matchLabels: app: web-app template: metadata: labels: app: web-app spec: containers: - name: web-app image: {{ .Values.image.repository }}:{{ .Values.image.tag }} ports: - containerPort: 8080
Mettez à jour le fichier de valeurs avec ceci
# Service for the application apiVersion: v1 kind: Service metadata: name: web-app labels: app: web-app spec: ports: - port: 80 targetPort: 8080 protocol: TCP selector: app: web-app type: ClusterIP
La partie Helm est terminée maintenant passons au déploiement de notre CI
Les actions Github nous permettent d'automatiser le processus de construction de notre application en fonction de certains événements de notre dépôt comme push,pull.
Créons notre fichier pipeline
Le fichier de workflow est stocké dans (.github/workflows/cicd.yml)
# Ingress resource for the application apiVersion: networking.k8s.io/v1 kind: Ingress metadata: name: web-app annotations: nginx.ingress.kubernetes.io/rewrite-target: / spec: ingressClassName: nginx rules: - host: web-app.local http: paths: - path: / pathType: Prefix backend: service: name: web-app port: number: 80
Ce fichier de workflow construit d'abord notre image à partir de dockerfile, puis la transmet à dockerhub, puis met à jour la balise de l'image dans notre fichier charts.yaml dans helm.
Nous utiliserons argocd pour notre pipeline Cd car argocd pourra récupérer les modifications de notre dépôt git et les mettre à jour dans l'application.
Installons argocd sur notre cluster
kubectl crée un espace de noms argocd
kubectl apply -n argocd -f https://raw.githubusercontent.com/argoproj/argo-cd/stable/manifests/install.yaml
Pour accéder au serveur argocd, nous devons changer le service en type d'équilibrage de charge
kubectl patch svc argocd-server -n argocd -p '{"spec": {"type": "LoadBalancer"}}'
Pour Windows, ce serait
kubectl patch svc argocd-server -n argocd -p '{"spec": {"type": "LoadBalancer"}}'
Si cela ne fonctionne pas, modifiez simplement le service via kubectl et changez le type en LoadBalancer, cela devrait fonctionner
Obtenez maintenant l'adresse IP du service
kubectl obtient svc argocd-server -n argocd
Nous avons l'adresse IP mais nous avons besoin du mot de passe pour nous connecter à argocd
kubectl obtient le secret argocd-initial-admin-secret -n argocd -o jsonpath="{.data.password}" | base64 --decode
Cette commande obtiendrait le mot de passe et décoderait le mot de passe puisque le mot de passe est codé au format base64
Après vous être connecté, cliquez sur Nouveau projet > Ajoutez le nom de votre projet > Ajoutez le dépôt pour qu'argocd puisse synchroniser le dépôt. Argocd recherchera automatiquement le fichier de valeurs et le récupérera après cela, cliquez sur soumettre
Nous avons construit notre pipeline, mais comment accéder à notre application, vous ne pouvez pas saisir l'URL du cluster d'EKS à chaque fois pour y accéder, nous devons utiliser une entrée pour cela
J'utilise Nginx Ingress d'AWS pour pouvoir accéder à l'application
Déployer l'ingress sur notre cluster
kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.11.1/deploy/static/provider/aws/deploy.yaml
Maintenant, l'entrée est déployée et nous devons ajouter l'adresse IP de notre cluster depuis EKS dans notre fichier d'hôtes local pour Linux, son /etc/hosts pour Windows, il se trouve dans C:WindowsSystem32etchosts
# Start with a base image FROM golang:1.22 as base WORKDIR /app COPY go.mod ./ RUN go mod download COPY . . RUN go build -o main . ####################################################### # Reduce the image size using multi-stage builds # We will use a distroless image to run the application FROM gcr.io/distroless/base # Copy the binary from the previous stage COPY --from=base /app/main . # Copy the static files from the previous stage COPY --from=base /app/static ./static # Expose the port on which the application will run EXPOSE 8080 # Command to run the application CMD ["./main"]
Nous pouvons désormais accéder à notre application sur web-app.local
Nous avons effectué toutes les étapes, testons notre application
Comme vous pouvez le voir, l'url en haut est ce que nous avons défini dans notre fichier hosts
Nous avons l'application en cours d'exécution, ajoutons quelque chose et validons notre dépôt afin qu'argocd puisse récupérer ce changement et le déployer sur l'application
J'ai apporté une modification à mon dépôt et cela devrait déclencher le pipeline
Le pipeline a démarré et une fois terminé, voyons si argocd récupère ce changement
Oui, nous constatons des changements dans notre application, argocd a récupéré les modifications et synchronisé notre application avec les dernières modifications
Si vous êtes arrivé jusqu'ici, alors félicitations !!!
Ce projet a été une excellente expérience d'apprentissage pour moi, depuis le déploiement de Kubernetes sur AWS jusqu'à la création de mes pipelines et déploiements et leur dépannage. Ce projet m'a aidé à créer un pipeline DevOps de bout en bout pour une application Go et il peut être évolutif en fonction des besoins. Je prévois d'explorer davantage, comme peut-être le déploiement de l'eks clutser à l'aide de piles terraform ou cloudformation et d'affiner davantage.
Si vous êtes bloqué quelque part, vous pouvez référencer ce dépôt
Faites-moi savoir dans les commentaires quelle a été votre expérience dans la création de ce pipeline.
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!