Argo CD Audit Log: A Complete Guide to Kubernetes Event Tracking

Argo CD records operational activity as native Kubernetes Events through an internal AuditLogger that captures who performed an action, what resource was affected, and why it occurred.

The Argo CD audit log provides a critical security and observability layer for GitOps workflows. As implemented in the argoproj/argo-cd repository, this mechanism emits Kubernetes Events to track user actions and system operations, complementing the immutable Git commit history with a view of what was actually applied to the cluster.

How the Argo CD Audit Logger Works

The audit logging system centers on the AuditLogger struct in util/argo/audit_logger.go. This component filters, constructs, and persists operational events through six distinct phases:

  1. AuditLogger Creation – When the server, application controller, or ApplicationSet controller starts, it invokes argo.NewAuditLogger. This function receives a Kubernetes client, the Argo CD namespace, the component name (e.g., argocd-server), and a list of event reasons to enable (enableK8sEvent). The enabled reasons are stored in a map (enableEventLog) for fast lookup.

  2. Event Filtering – Before emitting an event, the logger checks enableK8sEventLog(info) (lines 15‑18 in audit_logger.go). If the event's Reason is not in the enabled list, nothing is logged. By default, DefaultEnableEventList returns ["all"], enabling every reason.

  3. Event Construction – The logEvent method builds a corev1.Event structure (lines 49‑106) containing:

    • Standard fields – type, reason, message, timestamps, and count
    • Object reference – Target resource's Kind, Name, Namespace, UID, and API version
    • Annotations – Acting user, destination server/namespace, and for non‑Application resources, the original namespace (resource‑namespace)
  4. Event Destination – For Application‑level events (Application, AppProject, ApplicationSet), the event is created in the resource's own namespace. For generic resources, the event is created in the Argo CD namespace to support multi‑cluster deployments (lines 68‑75).

  5. Persistence – The event is written to the Kubernetes API via l.kIf.CoreV1().Events(eventNamespace).Create. Operators can retain these events longer than the cluster's default TTL using tools like Event Exporter or Event Router (documented in security.md lines 100‑102).

  6. Visibility – Users can view audit events with kubectl get events. The events include the source.component (e.g., argocd-server) and a human‑readable message, making it easy to trace actions back to a specific user or automation token (see example output in security.md lines 84‑98).

Where the Audit Log is Used in the Codebase

The AuditLogger is integrated across multiple controllers and servers to ensure comprehensive coverage:

These calls funnel through the same AuditLogger implementation, ensuring consistent audit format across the entire stack.

Practical Implementation Examples

Creating an AuditLogger

During server initialization, components instantiate the logger with specific configuration:

import (
    "github.com/argoproj/argo-cd/util/argo"
    "k8s.io/client-go/kubernetes"
)

// kubeClient – a Kubernetes client‑go interface
// ns – the namespace where Argo CD is installed
// component – e.g. "argocd-server"
// enableK8sEvent – list of event reasons to enable (empty = default all)

auditLogger := argo.NewAuditLogger(kubeClient, ns, component, enableK8sEvent)

Logging an Application Event

To record a sync operation:

eventInfo := argo.EventInfo{
    Type:   "Normal",
    Reason: argo.EventReasonOperationStarted,
}
message := "admin initiated sync to HEAD (abc123)"
user := "admin@example.com"

auditLogger.LogAppEvent(myApp, eventInfo, message, user, nil)

This generates a Kubernetes Event resembling: guestbook.157f7c5f0f747acf Application Normal OperationStarted argocd-server admin initiated sync to HEAD (abc123).

Enabling Selective Event Logging

Filter events to reduce noise:

// Only log sync‑related events
auditLogger := argo.NewAuditLogger(kubeClient, ns, component, []string{
    argo.EventReasonOperationStarted,
    argo.EventReasonOperationCompleted,
})

Exporting Audit Events for Long‑Term Retention

Since Kubernetes events have a short TTL, export them for persistence:


# Example: forward all Argo CD events to a Google Cloud Pub/Sub topic

kubectl apply -f https://github.com/GoogleCloudPlatform/k8s-stackdriver/tree/master/event-exporter

See docs/operator-manual/security.md lines 100‑102 for additional export strategies.

Key Source Files

Understanding the audit log requires familiarity with these specific files in the argoproj/argo-cd repository:

Summary

  • Argo CD audit logs are implemented as native Kubernetes Events, not external log files.
  • The AuditLogger in util/argo/audit_logger.go filters events by reason and constructs detailed event objects with user annotations.
  • Events for Applications, AppProjects, and ApplicationSets are stored in their respective namespaces, while generic resource events go to the Argo CD namespace to support multi‑cluster deployments.
  • LogAppEvent and LogAppProjEvent are the primary methods used across controllers to emit audit events.
  • Events persist only for the cluster's default TTL unless exported using tools like Event Exporter or Event Router.
  • Query logs using standard kubectl get events commands, filtering by source.component (e.g., argocd-server).

Frequently Asked Questions

What is the Argo CD audit log?

The Argo CD audit log is a security feature that records operational activity as Kubernetes Events. It tracks who performed GitOps actions, what resources were modified, and why changes occurred, providing a searchable trail that complements the immutable Git history.

How do I view Argo CD audit logs?

You can view audit logs using standard Kubernetes tooling: kubectl get events --namespace argocd or kubectl get events --namespace <app-namespace>. The events include the component name in source.component (e.g., argocd-server) and a message field describing the action, allowing you to trace specific user or token activity.

How long are Argo CD audit events retained?

By default, Kubernetes events have a short TTL (typically 1 hour to 1 hour and 15 minutes depending on the cluster configuration). For long‑term retention, you must export events using tools like the Kubernetes Event Exporter or Event Router to external systems such as Elasticsearch, Cloud Pub/Sub, or Splunk.

Can I filter which events are logged?

Yes. When creating an AuditLogger via NewAuditLogger, you can pass a slice of enabled reasons (e.g., EventReasonOperationStarted, EventReasonOperationCompleted). If you pass an empty list or ["all"], the logger emits events for all reasons. This filtering occurs in the enableK8sEventLog function (lines 15‑18 of audit_logger.go).

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →