{"record":{"id":"ee68da56631f0f87","repo":"argoproj/argo-workflows","slug":"gcs-storage-newclient-w","errorCode":null,"errorMessage":"GCS storage.NewClient: %w","messagePattern":"GCS storage\\.NewClient: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"workflow/artifacts/gcs/gcs.go","lineNumber":98,"sourceCode":"\treturn newGCSClientDefault(ctx)\n}\n\nfunc newGCSClientWithCredential(ctx context.Context, serviceAccountJSON string) (*storage.Client, error) {\n\tcreds, err := google.CredentialsFromJSONWithType(ctx, []byte(serviceAccountJSON), google.ServiceAccount, storage.ScopeReadWrite)\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"GCS client CredentialsFromJSONWithType: %w\", err)\n\t}\n\tclient, err := storage.NewClient(ctx, option.WithCredentials(creds))\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"GCS storage.NewClient with credential: %w\", err)\n\t}\n\treturn client, nil\n}\n\nfunc newGCSClientDefault(ctx context.Context) (*storage.Client, error) {\n\tclient, err := storage.NewClient(ctx)\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"GCS storage.NewClient: %w\", err)\n\t}\n\treturn client, nil\n}\n\n// Load function downloads objects from GCS\nfunc (h *ArtifactDriver) Load(ctx context.Context, inputArtifact *wfv1.Artifact, path string) error {\n\terr := waitutil.Backoff(defaultRetry,\n\t\tfunc() (bool, error) {\n\t\t\tkey := filepath.Clean(inputArtifact.GCS.Key)\n\t\t\tlogger := logging.RequireLoggerFromContext(ctx)\n\t\t\tlogger.WithFields(logging.Fields{\"path\": path, \"key\": key}).Info(ctx, \"GCS Load\")\n\t\t\tgcsClient, err := h.newGCSClient(ctx)\n\t\t\tif err != nil {\n\t\t\t\tlogger.WithError(err).Warn(ctx, \"Failed to create new GCS client\")\n\t\t\t\treturn !isTransientGCSErr(ctx, err), err\n\t\t\t}\n\t\t\tdefer gcsClient.Close()\n\t\t\terr = downloadObjects(ctx, gcsClient, inputArtifact.GCS.Bucket, key, path)","sourceCodeStart":80,"sourceCodeEnd":116,"githubUrl":"https://github.com/argoproj/argo-workflows/blob/35bff19146f5a6ada77468c431f2624bd577e373/workflow/artifacts/gcs/gcs.go#L80-L116","documentation":"newGCSClientDefault builds a storage.Client using Application Default Credentials (metadata server / GOOGLE_APPLICATION_CREDENTIALS). This error wraps any failure from that constructor, meaning the driver could not even create the client — almost always an ADC discovery problem in the environment, since no explicit credentials are passed.","triggerScenarios":"Any GCS artifact operation when neither workload identity nor GOOGLE_APPLICATION_CREDENTIALS is available: the GCE/GKE metadata server is unreachable (non-GCP node), workload identity is not enabled on the node pool/namespace, or the ADC env var points at a missing file.","commonSituations":"Running Argo on non-GCP clusters (k3d/EKS) without serviceAccountKeySecret on the artifact; GKE Autopilot namespace without the Workload Identity binding (iam.gke.io/gcp-service-account annotation); metadata server blocked by NetworkPolicy.","solutions":["Attach serviceAccountKeySecret with a valid service-account key to the artifact","Configure GKE Workload Identity: enable on node pool, bind the KSA to a GSA (annotation iam.gke.io/gcp-service-account + roles/storage.objectAdmin)","If relying on ADC, set GOOGLE_APPLICATION_CREDENTIALS to a mounted key file","Verify network access to metadata.google.internal from workflow pods"],"exampleFix":"// before: artifact with no credentials on a non-GKE cluster\nartifacts: [{name: out, path: /out, gcs: {bucket: my-bucket, key: dir}}]\n// after\nartifacts: [{name: out, path: /out, gcs: {bucket: my-bucket, key: dir, serviceAccountKeySecret: {name: gcs-creds, key: serviceAccountKey}}}]\n// kubectl create secret generic gcs-creds --from-file=serviceAccountKey=key.json","handlingStrategy":"validation","validationCode":"// before running GCS artifact workflows, verify ADC works in the same pod identity:\n// kubectl run test-adc --serviceaccount=<ksa> --image=gcr.io/google.com/cloudsdktool/cloud-sdk \\\n//   -- gcloud storage ls gs://my-bucket\n// success implies workload identity/ADC is wired correctly","typeGuard":null,"tryCatchPattern":"client, err := storage.NewClient(ctx)\nif err != nil {\n\t// ADC unavailable: fall back to explicit key\n\tif keyJSON := os.Getenv(\"GCS_SA_KEY\"); keyJSON != \"\" {\n\t\treturn newGCSClientWithCredential(ctx, keyJSON)\n\t}\n\treturn err\n}","preventionTips":["Always configure either workload identity or serviceAccountKeySecret before first use","Annotate KSAs with iam.gke.io/gcp-service-account and bind workloadIdentityUser","Enable Private Google Access on subnets that run workflow nodes"],"tags":["gcs","gcp","adc","authentication"],"backgroundTag":"application-default-credentials-not-found","analyzedSha":"35bff19146f5a6ada77468c431f2624bd577e373","analyzedAt":"2026-09-03T19:34:35.908Z","contentChangedAt":"2026-09-03T19:34:35.908Z","schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}