GitOps Explained: Why Teams Are Moving from CI/CD to GitOps
Learn what GitOps is, how it differs from traditional CI/CD, and why teams use Git as the source of truth for Kubernetes and cloud infrastructure deployments.
Modern DevOps teams increasingly manage application deployments and infrastructure through Git. This approach is commonly known as GitOps.
Traditional CI/CD pipelines often connect directly to target environments and execute deployment commands. GitOps changes this model by making Git the source of truth and using an agent or controller to continuously reconcile the actual environment with the desired configuration stored in Git.
This approach is especially common in Kubernetes environments, where tools such as Argo CD and Flux can continuously monitor Git repositories and synchronize workloads with the declared configuration.
What Is GitOps?
GitOps is an operational model where application and infrastructure configuration is stored declaratively in Git, and automated systems continuously ensure that the running environment matches that configuration.
Git Repository
|
| Desired State
v
GitOps Controller
|
| Reconcile
v
Kubernetes Cluster
|
v
Running Workloads
The key idea is that engineers change the desired state through Git rather than manually modifying production resources.
What Does "Git as the Source of Truth" Mean?
In a GitOps environment, the repository contains the configuration that describes how the system should look.
For example:
application/
├── deployment.yaml
├── service.yaml
├── ingress.yaml
└── kustomization.yaml
If the repository specifies three replicas, the desired state is three replicas.
replicas: 3
If somebody manually changes the Kubernetes deployment to two replicas, the cluster has now diverged from the desired state stored in Git.
A GitOps controller can detect this difference and, depending on its configuration, reconcile the cluster back to the declared state.
Traditional CI/CD vs GitOps
Traditional CI/CD pipelines commonly follow a push-based deployment model.
Developer
|
v
Git Push
|
v
CI Pipeline
|
+---- Build
|
+---- Test
|
+---- Package
|
v
Deployment Command
|
v
Production
In this model, the CI/CD system usually has credentials that allow it to modify the target environment.
GitOps introduces a pull-based reconciliation model.
Developer
|
v
Git Push
|
v
Git Repository
^
|
| Pull / Watch
|
GitOps Controller
|
v
Kubernetes
Push vs Pull Deployment
Push-Based Deployment
CI/CD System
|
| Push changes
v
Production Cluster
The deployment pipeline actively connects to the production environment and applies changes.
Pull-Based Deployment
Git Repository
^
|
| Pull desired state
|
GitOps Controller
|
v
Production Cluster
The controller running inside or close to the target environment observes the repository and applies the desired state.
Why Are Teams Adopting GitOps?
GitOps can address several operational problems that become more difficult as infrastructure and application environments grow.
- Configuration drift.
- Limited deployment traceability.
- Manual production changes.
- Complex deployment credentials.
- Difficult rollbacks.
- Inconsistent environments.
- Limited visibility into infrastructure changes.
1. Git Provides an Audit Trail
Git already provides a history of changes, including commits, branches, pull requests and authorship.
Commit A
|
v
Commit B
|
v
Commit C
|
v
Commit D
Instead of asking who manually changed a production resource, teams can inspect the repository history and determine when the desired configuration changed and who made the change.
The exact audit capabilities still depend on the Git platform, deployment tooling and organizational controls.
2. Pull Requests Become Deployment Controls
GitOps allows infrastructure and deployment changes to go through the same review process used for application code.
Developer
|
v
Create Branch
|
v
Change Kubernetes YAML
|
v
Pull Request
|
+---- Review
|
+---- Automated Tests
|
v
Merge
|
v
GitOps Controller
|
v
Cluster
This creates a clear separation between proposing a change and actually applying that change.
3. GitOps Helps Reduce Configuration Drift
Configuration drift occurs when the actual environment becomes different from the configuration that the team expects.
Desired State
Git
|
| replicas: 3
v
Controller
|
v
Cluster
|
| replicas: 2
|
+---- Drift Detected
A reconciliation-based model can continuously compare desired and actual state and take corrective action according to the configured policy.
4. Rollbacks Become Easier
Because deployment configuration is stored in Git, reverting a change can often be performed by reverting the corresponding Git commit or changing the desired configuration back to a known version.
Version 1
|
v
Version 2
|
v
Version 3
|
X Problem
|
v
Revert to Version 2
A rollback should still be tested against the application's database migrations, API compatibility and stateful components. Git reverting the manifest does not automatically make every application change reversible.
5. Better Separation of Responsibilities
GitOps can separate application delivery from cluster access.
CI
|
+---- Build
|
+---- Test
|
+---- Create Image
|
v
Container Registry
|
v
Git
|
v
GitOps Controller
|
v
Kubernetes
The CI system can focus on building and testing artifacts while the GitOps controller handles deployment and reconciliation.
GitOps and CI/CD Are Not Opposites
A common misconception is that GitOps completely replaces CI/CD.
In practice, GitOps is often used as the deployment and reconciliation component of a broader CI/CD platform.
CI
|
+---------+---------+
| |
Build Test
| |
+---------+---------+
|
v
Container Image
|
v
Git Update
|
v
GitOps CD
|
v
Kubernetes
CI can build and test the application, while GitOps handles delivery of the desired configuration to the runtime environment.
GitOps With Kubernetes
Kubernetes is particularly well suited to GitOps because Kubernetes itself uses declarative configuration and continuously works toward the desired state.
Git
|
| Deployment YAML
v
GitOps Controller
|
| Apply Desired State
v
Kubernetes API
|
v
Controllers
|
v
Pods / Services / Ingress
The GitOps controller effectively extends the reconciliation model beyond individual Kubernetes resources to the configuration stored in Git.
Example Kubernetes Deployment
<deployment>
<spec>
<replicas>3</replicas>
<template>
<spec>
<containers>
<container name="web" image="example/web:v2">
</container>
</containers>
</spec>
</template>
</spec>
</deployment>
The repository describes the desired configuration. The GitOps controller continuously works to make the cluster match that configuration.
What Is Reconciliation?
Reconciliation is the process of comparing desired state with actual state and taking action when they differ.
Desired State
|
v
Compare
^
|
Actual State
|
v
Difference?
/ \
Yes No
| |
v v
Sync Nothing
This concept is one of the most important ideas behind GitOps.
Argo CD
Argo CD is a widely used GitOps continuous delivery tool for Kubernetes.
It can monitor Git repositories and synchronize Kubernetes resources with the desired configuration.
Git Repository
|
v
Argo CD
|
v
Kubernetes Cluster
|
+---- Deployment
+---- Service
+---- ConfigMap
+---- Ingress
Flux
Flux is another Kubernetes-focused GitOps toolkit.
Flux follows the same broad GitOps principle: configuration is stored declaratively and controllers reconcile the cluster against the desired state.
GitOps Repository Structure
A GitOps repository can be organized in many ways. A simple example might look like:
gitops/
├── apps/
│ ├── frontend/
│ │ ├── deployment.yaml
│ │ └── service.yaml
│ └── backend/
│ ├── deployment.yaml
│ └── service.yaml
│
├── environments/
│ ├── dev/
│ ├── staging/
│ └── production/
│
└── README.md
Larger organizations may use Kustomize, Helm or other configuration-management approaches to manage differences between environments.
GitOps With Helm
Helm can be used alongside GitOps to package Kubernetes applications.
Git
|
+---- Helm Chart
|
+---- values-dev.yaml
|
+---- values-prod.yaml
|
v
GitOps Controller
|
v
Kubernetes
The exact repository strategy depends on the team's deployment model and the complexity of its environments.
GitOps With Kustomize
Kustomize can also be used to maintain environment-specific configuration without duplicating complete manifests.
base/
├── deployment.yaml
└── service.yaml
overlays/
├── dev/
│ └── kustomization.yaml
└── production/
└──