Deploy Go Application on EKS Cluster using GitHub Actions, Terraform, Helm, and ArgoCD
Introduction
To streamline the software development life cycle and ensure efficient and effective deployment, DevOps practices have become indispensable in today’s fast-paced technology world. To this end, as a DevOps engineer, you must create a strong portfolio demonstrating your knowledge and skills.| On how to build an impressive DevOps portfolio using powerful tools such as EKS, GitHub Actions, Terraform, and ArgoCD; we will look at this blog. At the end of this tutorial you will have a fully functional CI/CD pipeline for deploying a Go-based application to a private EKS cluster with code quality checks, Docker image management, Helm chart deployment, and Slack notifications It shall be a whole
Prerequisites
Before we dive into the details, ensure you have the following prerequisites in place:
- AWS Account: Set up an AWS account for creating and managing EKS clusters.
- GitHub Account: A GitHub account to host your repositories and configure GitHub Actions.
- Terraform: Installed on your local machine for managing infrastructure as code.
- Kubectl: Installed and configured to interact with your Kubernetes cluster.
- Helm: Installed for managing Kubernetes applications.
- AWS CLI: Installed and configured to manage AWS resources from the command line.
- Slack Webhook URL: (Optional) Integrating Slack notifications into your CI/CD pipeline.
So, I have created three repositories for this project.
EKS-Terraform-GitHub-Actions- Contains terraform code for EKS cluster and other required services along with GitHub actions workflow to deploy the infrastructure throw GitHub actions
https://github.com/AmanPathak-DevOps/EKS-Terraform-GitHub-Actions/tree/master
go-portfolio-project- Contains source code along with GitHub actions workflow including code analysis, docker image creation, image scanning, image tag updation, etc.
https://github.com/AmanPathak-DevOps/go-portfolio-project
go-app-devops- Contains helm chart where the manifests are present to deploy it on the EKS Cluster.
Deploy EKS using GitHub Actions
Repo- https://github.com/AmanPathak-DevOps/EKS-Terraform-GitHub-Actions
Click on Actions
Click on Terraform
Click on Run workflow and run the plan to validate what are we going to deploy
The Plan is successful and you can click on Terraform-Action to view the blueprint of action
Total of 37(repo update 38) AWS resources will be create
Now, we will run the apply
Go to Terraform workflow and click on Run Workflow
The Apply is successful and you can click on Terraform-Action to view the created resources list
Total of 37(update 38) aws resources have been created
You can validate whether the cluster has been created or not by going to the AWS console
Once you try to connect with your EKS cluster on your local it will add the context.
But while running kubectl commands like get nodes, pods, etc you will get an error
If you look at the snippet, you will observe your local is unable to connect to your server
The reason behind this is your EKS cluster is Private and to access the cluster your server needs to be in the same VPC as the EKS cluster.
I have created one more instance and attached the same VPC that is used in the EKS Cluster.
You can refer to the below snippet
Login to your server and do the following things mentioned below-
Install aws cli, kubectl
Configure aws cli by using the aws configure command and run the kubectl get nodes command
Install helm which is one of our prerequisites
sudo snap install helm — classic
Install the Nginx ingress controller by using the below command
kubectl apply -f https://raw.githubusercontent.com/kubernetes/ingress-nginx/controller-v1.11.1/deploy/static/provider/aws/deploy.yaml
Validate whether your ingress controller pods are running or not. It should be running
kubectl get all -n ingress-nginx
Now, we need to install argoCD as per our project-required tool
kubectl create namespace argocd
kubectl apply -n argocd -f https://raw.githubusercontent.com/argoproj/argo-cd/v2.4.7/manifests/install.yaml
Validate whether argocd pods are running or not by using the below command
kubectl get pods -n argocd
Now, we need to expose our argocd service to the Loadbalancer type as we need to access it outside of our cluster
kubectl patch svc argocd-server -n argocd -p ‘{“spec”: {“type”: “LoadBalancer”}}’
Validate whether the load balancer has been created or not by going to the AWS console
Copy the DNS name of your argocd and hit on your favorite browser
Click on Advanced as SSL is not configured on argoCD
Here is your ArgoCD
Now, the username is admin but we don’t know the password.
To get the password, we need to run a few commands in the next steps
Now, we require a password to log in to the argoCD console.
The below command will list the secrets of argocd
kubectl get secrets -n argocd
Run the below command and copy the password
kubectl edit secret argocd-initial-admin-secret -n argocd
Run the below command to decode the password
echo <your-argocd-password> | base64 — decode
Now, log in to your argoCD console
We have set everything up to deploy our application
But there is one more thing that is connected to the repository in argoCD
Why are we doing that?
So, our helm chart or manifest file is always stored in a private repository. To clone that repo, we need to set up our repository in argoCD.
Click on the settings icon on the left and then, click on Repositories
For now, we are going to connect the repo using HTTPS which means we need a Personal Access token(PAT)
So, kindly generate the Personal Access token(PAT) of your GitHub account
Provide the information accordingly
Once you see the connection status it means the repository has been connected successfully
Create an application on argocd
Let’s create a workflow for our source code
Navigate to Repo’s Settings -> Security(on the left side) -> Secrets and variables and click on Actions
Create required secrets in which docker PAT, docker username, GitHub PAT, and slack webhook URL
Note: I am configuring Slack notification, if you want to do it the same then, refer to this video https://www.youtube.com/watch?v=f8Tr3unIdNw and add a Slack webhook URL as well. But if you don’t want to integrate Slack then, you don’t need to add the secret. Also, skip the last job in the workflow.
This is our workflow code and you can check it out by clicking on the repo link
https://github.com/AmanPathak-DevOps/go-portfolio-project/blob/master/.github/workflows/go-app.yaml
Now, we are set to run our workflow/pipeline
Workflow got successful
The image has been pushed
The image tag has been updated in values.yaml file
Now, we will create an application on argocd to deploy our application on Kubernetes.
Provide the application name, repo URL, etc as shown in the below snippet
As soon as you create the application, it will be deployed.
You can click on the application to view all the resources that have been created by argoCD
You can also validate from your jump server by running the below command.
kubectl get all -n go-app
Check the ingress address by using the below command
kubectl get ing -n go-app
Go to your AWS console, navigate to the Load balancer, and copy the DNS name
Go to your domain provider and add A type record.
I am using AWS Route53 to add the record
Once you add the record you can hit your domain on your favorite browser and see the magic
Now, I will make a few changes to my portfolio website which will trigger the workflow and the entire application will be deployed without any human intervention
The updated image has been pushed to the docker hub
Received the Slack notification
Our v1.1.0 of go-portfolio has been deployed without any human intervention which means we achieved complete automation of CICD
Conclusion
Congratulations! You’ve built a comprehensive DevOps portfolio that shows an end-to-end automated CI/CD pipeline for deploying a Go-based application on the EKS cluster. This case demonstrates your knowledge of Terraform, GitHub Actions, and ArgoCD. The presentation of this portfolio reveals not only your technical abilities but also the ability to automate complex workflows, which is a desired characteristic of any DevOps team. Keep adding new projects and tools to your portfolio and continue experimenting because DevOps is an evolving field.
Stay connected on LinkedIn: LinkedIn Profile
Stay up-to-date with GitHub: GitHub Profile
Want to discuss trending technologies in DevOps & Cloud
Join the Discord Server- https://discord.gg/jdzF8kTtw2
Feel free to contact me if you have any other queries.
Happy Learning!