Discover GitOps with Argo CD
Tags: gitops, kubernetes, devops, docker
Published: 2021-11-16 15:14:23

This post offers a brief introduction to **GitOps** and an overview of **Argo CD,** an open-source project implementing the GitOps approach. We had this opportunity at [Packmind](https://packmind.com) to experiment Argo CD, so we wanted to share with your our insights. 

## ❓ What is GitOps?

GitOps is a concept promoted by WeaveWorks in 2017, with the core idea of describing the state of infrastructure in a Git repository. And Git is in the **single source of truth**.

Do you use Kubernetes and have dozens of YAML files? Maybe you even use Helm to deploy your app as a Chart? You now assume that all these configuration files are stored within a Git repository. 

Every time developers perform modifications in the source code of your applications, your existing continuous integration process is executed: unit tests, packaging, and finally, a new Docker image is pushed. Your new Docker image is ready, and your CI pipeline ends by **patching** the infrastructure configuration on Git.

Finally, the Git **operator** (your GitOps tool) listens to any changes in the Git repo, identifies the delta between the current deployment and the configuration in Git, and applies the modification in production. This operator is thus the **only entity** allowed to perform changes in your environments.

Here is an overview of the GitOps workflow: 

![GitOps Workflow](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/h89ljjclzmv7d2czjkvy.png)
*Source: Shipa.io*

## ✨ Benefits of GitOps

Adopting a GitOps workflow presents many advantages: 

- Using Git as a single truth of source reduces the **risks of errors** due to manual operations through any CLI or web interface. All the modifications in your production environment come from a Git commit.
- Each modification to the deployment environment is **recorded** in Git: we know what changed, when, and why (thanks to a commit message). You can consider it as documentation of your infrastructure. It's easy to review each modification and validate it through a pull request.
- Do you face issues after a new deployment and need to restore to the previous version? Very simple: revert the last commit and **rollback** your application.
- It becomes trivial to observe the **difference** between the configuration in Git and what is really deployed in your environment. So before each redeployment, you know what has changed.

## 🔎 Discover Argo CD

[Argo CD](https://argo-cd.readthedocs.io/en/stable/) is a declarative, GitOps continuous delivery tool for Kubernetes. It's an open-source project and part of the Cloud Native Computing Foundation. We're now going to provide a quick demo on how to deploy your applications through Argo CD. 

### Setup

You'll find on the documentation a [Getting Started](https://argo-cd.readthedocs.io/en/stable/getting_started/) section explaining how to install Argo CD, and expose it outside your Kubernetes Cluster.  

```bash
$> kubectl create namespace argocd
$> kubectl apply -n argocd -f https://raw.githubusercontent.com/argoproj/argo-cd/stable/manifests/install.yaml
```

### Get default password

When you first reach the welcome screen, you'll be prompted with a login/password. The default login is *admin*. To retrieve that password, you need to run the following command: 

```bash
$> kubectl -n argocd get secret argocd-initial-admin-secret -o jsonpath="{.data.password}" | base64 -d
```

The documentation explains how to update this password.

### Configure our first project

On the menu on the left side, select the item "Manage your repositories, project, settings" item.

![ArgoCD Menu](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/0bb0bcj6ys1qcl1s14v9.png)

We're going to add first a repository (use yours, of course):

![ArgoCD Menu](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/86hpurro5sbvidkcu4uj.png)

I'm using a public one here containing some charts. Now let's add a new project called **wordpress**. We're adding our source repository : 

![ArgoCD Menu](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/f26v3s56gf9u7ok1buhj.png)

Let's also add the possible destination for this project. In this example, we will use the "dev" namespace we've created for this tutorial.

![ArgoCD Menu](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/nw4nyrc7l2hlk886sbgf.png)

Now, let's go back to the main menu and let's create a new Application:

- Choose the project created previously
- Let the "Sync policy" as Manual
- Choose the repository containing your Git files, and set the path and/or the Git branch to synchronize. If it's a Helm chart, specify which values to use.

Validate the application, and click on "Sync". You'll see all your K8S components deployed. The UI is pretty cool, by the way:

![Argo UI](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/i5ag5har88g4cq6s2tir.png)

### Example of redeployment

In this example, we're now going to upgrade the WordPress version we're using. We update the Docker image tag : 

![New Docker Image](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/jbbwtvbk7kjmlenyfdz8.png)

Now, let's see what happens in Argo. If we click on the "Refresh" button, it forces the *Git pull* operation, but otherwise, it's automatic and takes a few seconds/minutes to be detected. This detects the new commit and marks the app as **OutOfSync**:

![OutOfSync](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/2ukuzzmds3unnvzneibn.png)

And then, if we click on "Diff", we can see the delta between what's deployed and configuration in the Git repository:

![Argo Delta](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/remwpupjw4967sftlkjs.png)

If we click on "Sync", Argo will redeploy the app. 🚀

Note that you've got the option to sync and deploy your app automatically. This can make sense in Dev environments if you're pushing new modifications every day. You need to edit the project and click on **Enable Auto-Sync**.

That's it for the Argo CD tour. The tool is very intuitive and does not offer a wide range of features. It goes straight to the goal. 

## 🔣 Handle multiple environments of the same application

It's common to have different environments for your application: dev, staging, production,... Argo CD, like any GitOps, is designed to handle this situation. With Argo CD, we chose to create **separate applications** for each environment.

You can also create one project per application. The way you create an application depends on your infrastructure configuration. One method consists of using different branches in your Git repository and applying the pull request mechanism when changes need to be applied from a dev environment to staging and then to production, for instance. If you use Helm or any templating module, you can also use **specific files** in YAML containing all the values for your environments: values-dev.yaml, values-staging.yaml, values-prod.yaml, ... 

## ✏️ Patch your infrastructure during your CI/CD

In our context, we had a dozen of micro-services, each having its own **Docker image** and a separate Git repository for the source code. The description of our Kubernetes infrastructure was in a single Git repository. One challenge we had was to redeploy the app on the *Dev* environment every day after each commit. However, as the Docker image name did not change after each commit, we had to find a way to inform the GitOps operator that something had changed. 

Our strategy was to use metadata for each K8S *Deployment* element with a **label** corresponding to the Git commit (of the micro-service) used to build to Docker image. Something like this:

```yaml
apiVersion: v1
kind: Pod
metadata:
  labels:
    app: analyzer
    commit: 06d604bad53b
```

During our CI process with Jenkins (but you can do it with any tool), we used the script [yq](https://mikefarah.gitbook.io/yq/) to **patch** the Git repository with the commit ID. So after each CI build, we patched the Git infrastructure.

That suited our needs, so we kept this process. Please note that there are certainly more proper ways to handle this situation: feel free to tell us in comments how you did ;)

🤗 That's all folks! We hope you now understand what **GitOps is** and how powerful it can be in managing your deployments. The feedback we had at [Packmind](https://packmind.com) was very positive. We'd be happy to receive your feedback and thoughts about Argo CD if you had a chance to use it.