Skip to main content
RunBook Academy

KubernetesCXV · Image Registry OperationsImage registry operations

imagePullSecrets and credential rotation — authentication to registries

Advanced⏱ ~17 minkubectl

What you'll learn

  • Use imagePullSecrets for registry authentication
  • Rotate credentials without downtime
  • Apply IRSA / Workload Identity for cloud registries
  • Apply the operational discipline of credential rotation

Prerequisites

Verified against Kubernetes 1.34.x · kubeadm 1.34.x · kubectl 1.34.x · etcd 3.6.x · CoreDNS 1.11.x · containerd 1.7.x / 2.x · 2026-08-16

Not yet marked complete on this device.

imagePullSecrets authenticate Pods to registries. This lesson walks the Secret types, the Pod integration, credential rotation, IRSA / Workload Identity, and the discipline.

The dockerconfigjson Secret

# Create a dockerconfigjson
echo '{"auths":{"registry.example.com":{"username":"ci","password":"***","auth":"***"}}}' | \
  base64 -w 0 > dockerconfig.base64
apiVersion: v1
kind: Secret
metadata:
  name: my-registry-creds
  namespace: prod-app
type: kubernetes.io/dockerconfigjson
data:
  .dockerconfigjson: <base64-encoded-docker-config>

The Secret contains a Docker-style config JSON with the registry credentials. The auth field is the base64-encoded username:password.

Per-namespace vs cluster-wide

flowchart LR
    A[imagePullSecrets] --> B[Per-namespace Secret]
    A --> C[Cluster-wide via service account]
    B --> B1[Each namespace has its own Secret]
    B --> B2[Credential isolation]
    C --> C1[Service account references Secret]
    C --> C2[All Pods in namespace share]

The two approaches:

  • Per-namespace Secret. Each namespace has its own Secret; isolation between namespaces.
  • Cluster-wide via ServiceAccount. The default ServiceAccount references a Secret; every Pod in the namespace uses it.

For production, per-namespace is preferred for isolation. Cluster-wide via ServiceAccount is simpler for small clusters.

ServiceAccount integration

apiVersion: v1
kind: ServiceAccount
metadata:
  name: prod-app
  namespace: prod-app
imagePullSecrets:
  - name: my-registry-creds
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: myapp
  namespace: prod-app
spec:
  template:
    spec:
      serviceAccountName: prod-app
      containers:
        - name: app
          image: registry.example.com/myapp:1.2.3

The ServiceAccount references the Secret. Pods that use the ServiceAccount inherit the imagePullSecrets.

Credential rotation

flowchart LR
    A[New credential] --> B[Create new Secret]
    B --> C[Replace existing Secret]
    C --> D[Existing Pods use old credential]
    D -->|kubelet refresh| E[New credential used]
    E -->|or restart| F[Immediate refresh]

The rotation:

  1. Create a new credential in the registry.
  2. Create a new Secret with the new credential.
  3. Replace the existing Secret (e.g., with kubectl create secret and a new name).
  4. New Pods use the new credential; existing Pods continue with the old until restart.
  5. Restart the Pods to use the new credential.

The kubelet does not actively refresh credentials; the credential is cached at Pod start.

IRSA / Workload Identity for cloud registries

apiVersion: v1
kind: ServiceAccount
metadata:
  name: prod-app
  namespace: prod-app
  annotations:
    eks.amazonaws.com/role-arn: arn:aws:iam::123:role/prod-app-ecr

IRSA (IAM Role for Service Accounts, AWS) or Workload Identity (GCP) or Managed Identity (Azure) provides cloud-native authentication:

  • No static credentials. The IAM role is assumed via OIDC token exchange.
  • No imagePullSecrets needed. The kubelet uses the IAM role to authenticate to ECR.
  • Automatic rotation. The IAM role’s credentials are rotated by AWS.

For cloud registries, IRSA / Workload Identity is preferred over static credentials.

Quiz

Knowledge check · 4 questions

  1. Q1. How can an imagePullSecret be applied to every Pod in a namespace without editing each one?

  2. Q2. Updating an imagePullSecret takes effect on running Pods without a restart.

  3. Q3. Finish a registry credential rotation that left three namespaces unable to pull images.

    The registry credential was rotated yesterday and a new Secret, `regcred-2026`, was created in all nine application namespaces. This morning 14 Pods across `prod-batch`, `prod-reports` and `prod-etl` are in `ImagePullBackOff` and `kubectl describe pod` shows `failed to authorize: 401 Unauthorized`. In those three namespaces `kubectl get sa default -o yaml` still lists `imagePullSecrets: [{name: regcred-2025}]`, and the old credential was revoked in the registry overnight.

  4. Q4. What `type` and data key does a registry credential Secret use, and what must the value inside it match for the pull to authenticate?

Passing score: 75%. Answers are checked in this browser.

The operational discipline

imagePullSecrets in production rest on five non-negotiable elements:

  • Use dockerconfigjson Secret type. Modern format.
  • Per-namespace Secrets. Credential isolation.
  • Rotate credentials quarterly. Update Secret, restart Pods.
  • Use IRSA / Workload Identity for cloud. No static credentials.
  • Document the rotation procedure. In the runbook.

imagePullSecrets are how Pods authenticate to registries. The discipline is per-namespace Secrets, rotation, and cloud-native identity where possible.