How do you integrate Crossplane with ArgoCD for GitOps infrastructure management?
Quick Answer
Crossplane integrates with ArgoCD by storing Crossplane claims and compositions in a Git repository, where ArgoCD syncs them to the Kubernetes cluster, enabling GitOps workflows where infrastructure changes follow the same pull request review process as application deployments with full audit trails and automated drift correction.
Detailed Answer
The combination of Crossplane and ArgoCD creates a powerful GitOps infrastructure management platform where Git becomes the single source of truth for both application deployments and cloud infrastructure provisioning. ArgoCD handles the synchronization of desired state from Git to the Kubernetes cluster, and Crossplane handles the reconciliation of that desired state from Kubernetes to the cloud provider. This two-layer reconciliation means the payments-api team can request infrastructure through a pull request, get peer review from the platform team, merge to trigger automatic provisioning, and have continuous drift detection at both the Kubernetes layer through ArgoCD and the cloud layer through Crossplane.
The repository structure for a Crossplane-ArgoCD integration typically follows one of two patterns. The first pattern stores platform definitions and application claims in separate repositories. The platform repository contains CompositeResourceDefinitions, Compositions, ProviderConfigs, and provider packages, managed by the platform team through a dedicated ArgoCD Application that syncs to the crossplane-system namespace. The application repository contains Crossplane Claims organized by team and environment, such as teams/checkout-service/prod/database-claim.yaml and teams/order-processing-service/staging/cache-claim.yaml. Each team directory gets its own ArgoCD Application pointing to their folder, with RBAC restrictions ensuring the checkout-service team can only modify their own directory. This separation of concerns means platform changes go through the platform team's review process while application infrastructure requests go through the application team's process.
ArgoCD Application configuration for Crossplane requires specific health check customizations because ArgoCD does not natively understand Crossplane resource health. By default, ArgoCD considers a resource healthy if it exists in the cluster, but a Crossplane Claim might exist while the underlying cloud resources are still provisioning or in an error state. Custom health checks in the ArgoCD ConfigMap teach ArgoCD to inspect the Synced and Ready conditions on Crossplane resources. When the user-auth-service claim is synced by ArgoCD, the health check reads the Ready condition and maps True to Healthy, False to Degraded, and missing to Progressing. This integration ensures the ArgoCD dashboard accurately reflects whether the inventory-sync database is actually available in AWS, not just whether the Kubernetes resource exists. Without these health checks, teams get false confidence from green ArgoCD status while their infrastructure is actually broken.
Sync waves and hooks in ArgoCD orchestrate the ordering of Crossplane resource deployment. Platform resources like ProviderConfigs and XRDs must be synced before Compositions, and Compositions must be synced before Claims that reference them. ArgoCD sync waves handle this by assigning wave numbers through annotations, where wave zero deploys providers and ProviderConfigs, wave one deploys XRDs, wave two deploys Compositions, and wave three deploys Claims. ArgoCD processes waves sequentially and waits for resources in each wave to become healthy before proceeding to the next wave. For the checkout-service, this ensures the database Composition is registered before the database Claim is applied, preventing the rejected-by-API-server errors that occur when a Claim references a CRD that does not exist yet.
Operational considerations for this integration include handling the eventual consistency gap between ArgoCD sync and Crossplane reconciliation. When ArgoCD syncs a new database Claim, it creates the Kubernetes resource immediately, but the underlying RDS instance might take fifteen minutes to provision. ArgoCD should be configured with a sync timeout that accounts for cloud provisioning times, and the custom health check should return Progressing rather than Healthy during this window. Teams should also configure ArgoCD's resource exclusion rules to ignore Crossplane-managed external resources, because ArgoCD might detect drift on managed resources that are controlled by Crossplane's reconciliation loop rather than by Git. Setting the argocd.argoproj.io/managed-by annotation or using resource tracking annotations prevents ArgoCD from fighting with Crossplane over the same resource's state. The payments-api team benefits from ArgoCD notifications that integrate with Slack, sending messages when infrastructure claims are synced, when health checks transition to Degraded, or when sync operations fail due to validation errors.