GoogleContainerTools/skaffold · error

creating container for %v: %v

Error message

creating container for %v: %v

What it means

CheckIfPullImgErr inspects a pod's container statuses and, when a container is stuck in a Waiting state whose reason is an image-pull error (ImagePullBackOff/ErrImagePull), returns this error naming the job. It surfaces Kubernetes' own pull failure as a Go error so callers can abort quickly instead of waiting for logs that will never arrive.

Source

Thrown at pkg/skaffold/k8sjob/util.go:194

		return true, err
	})
}

func isRetryableErr(k8sErr error) bool {
	isRetryable := false
	for _, checkIsRetryableErr := range retryableErrChecks {
		isRetryable = isRetryable || checkIsRetryableErr(k8sErr)
	}
	return isRetryable
}

func CheckIfPullImgErr(pod *corev1.Pod, jobName string) error {
	for _, cs := range pod.Status.ContainerStatuses {
		if cs.State.Waiting == nil {
			continue
		}
		if checkIsPullImgErr(cs.State.Waiting.Reason) {
			return fmt.Errorf("creating container for %v: %v", jobName, cs.State.Waiting.Reason)
		}
	}

	return nil
}

func checkIsPullImgErr(waitingReason string) bool {
	return validator.ImagePullBackOff == waitingReason ||
		validator.ErrImagePullBackOff == waitingReason ||
		validator.ImagePullErr == waitingReason
}

View on GitHub (pinned to a1189de023)

Solutions

  1. Verify the image exists: `docker pull <image>` locally or check the registry; fix the tag/name in the job manifest
  2. Attach registry credentials: create a secret and set imagePullSecrets on the pod/job spec
  3. If using a local image with kind/minikube, load it into the cluster (kind load docker-image / minikube image load) instead of expecting a pull
  4. Check `kubectl describe pod` events to confirm ImagePullBackOff and the exact registry error
  5. Handle registry rate limits by authenticating or using a mirror

Example fix

// before
image: myrepo/myimage:latst
// after
image: myrepo/myimage:latest
# plus, for private registries:
imagePullSecrets:
  - name: regcred
Defensive patterns

Strategy: try-catch

Validate before calling

// Pre-validate the image exists before applying the job
ref, _ := reference.ParseNormalizedNamed(imageTag)
// ensure tag is not :latest-accidental and image was pushed:
out, err := exec.Command("docker", "manifest", "inspect", imageTag).CombinedOutput()
if err != nil {
    return fmt.Errorf("image %s not found in registry: %s", imageTag, out)
}

Type guard

func hasPullErr(pod *corev1.Pod) (string, bool) {
    for _, cs := range pod.Status.ContainerStatuses {
        if cs.State.Waiting != nil &&
            (cs.State.Waiting.Reason == "ImagePullBackOff" || cs.State.Waiting.Reason == "ErrImagePull") {
            return cs.State.Waiting.Reason, true
        }
    }
    return "", false
}

Try / catch

if err := k8sjob.CheckIfPullImgErr(pod, jobName); err != nil {
    // image-pull failure is terminal; don't retry blind
    return fmt.Errorf("aborting: %w (check imagePullSecrets and tag)", err)
}

Prevention

When it happens

Trigger: A pod for the job has containerStatuses[].state.waiting.reason matching a pull-image error — wrong/misspelled image name or tag, private registry requiring credentials not present in the cluster, or the image does not exist in the registry.

Common situations: Pushing to a registry the cluster can't authenticate to (missing imagePullSecrets), typo'd image tag, referencing a locally-built image never pushed to the cluster, rate limiting from Docker Hub.

Related errors


AI-assisted analysis of GoogleContainerTools/skaffold@a1189de023 (2026-09-05). Data as JSON: /api/errors/b0b1422e3a2d3945. Report an issue: GitHub.