kubernetes/kops · error
discoveryService URL must be specified
Error message
discoveryService URL must be specified
What it means
When ServiceAccountIssuerDiscovery.DiscoveryService is set, its URL field is used verbatim as the service account issuer/discovery URL. If the URL is empty, kOps cannot construct the issuer and returns this validation error.
Source
Thrown at pkg/model/components/discovery.go:83
serviceAccountIssuer, err = base.GetHTTPsUrl()
if err != nil {
return err
}
case *vfs.MemFSPath:
if !base.IsClusterReadable() {
// If this _is_ a test, we should call MarkClusterReadable
return fmt.Errorf("locationStore=%q is only supported in tests", store)
}
serviceAccountIssuer = strings.Replace(base.Path(), "memfs://", "https://", 1)
default:
return fmt.Errorf("locationStore=%q is of unexpected type %T", store, base)
}
} else if said != nil && said.DiscoveryService != nil {
discoveryService := said.DiscoveryService
serviceAccountIssuer = discoveryService.URL
if serviceAccountIssuer == "" {
return fmt.Errorf("discoveryService URL must be specified")
}
} else {
if supportsPublicJWKS(clusterSpec) && clusterSpec.API.PublicName != "" {
serviceAccountIssuer = "https://" + clusterSpec.API.PublicName
} else {
serviceAccountIssuer = "https://api.internal." + b.ClusterName
}
}
kubeAPIServer.ServiceAccountIssuer = &serviceAccountIssuer
}
kubeAPIServer.ServiceAccountJWKSURI = new(*kubeAPIServer.ServiceAccountIssuer + "/openid/v1/jwks")
// We set apiserver ServiceAccountKey and ServiceAccountSigningKeyFile in nodeup
return nil
}
func supportsPublicJWKS(clusterSpec *kops.ClusterSpec) bool {
if !fi.ValueOf(clusterSpec.KubeAPIServer.AnonymousAuth) {View on GitHub (pinned to 4c8573c808)
Solutions
- Set discoveryService.url to the HTTPS URL serving OIDC discovery (/.well-known/openid-configuration and jwks)
- Remove the empty discoveryService block so the default issuer logic is used instead
- Validate the cluster spec with kops before applying
Example fix
// before
serviceAccountIssuerDiscovery:
discoveryService: {}
// after
serviceAccountIssuerDiscovery:
discoveryService:
url: "https://discovery.example.com" Defensive patterns
Strategy: validation
Validate before calling
if said := spec.ServiceAccountIssuerDiscovery; said != nil && said.DiscoveryService != nil && said.DiscoveryService.URL == "" {
return fmt.Errorf("discoveryService.url is required when discoveryService is set")
} Type guard
null
Try / catch
if err := buildOptions(); err != nil {
if strings.Contains(err.Error(), "discoveryService URL must be specified") {
// populate discoveryService.url in the spec
}
return err
} Prevention
- Validate required fields in cluster spec before apply
- Avoid templating that can render url empty
- Use kops editor/toolbox to verify the discovery block
When it happens
Trigger: Cluster spec defines serviceAccountIssuerDiscovery.discoveryService but leaves discoveryService.url unset (empty string) during BuildOptions.
Common situations: Partial YAML: discoveryService key added without url; templating variable that expanded to empty; copy-paste of a sample config missing the url field.
Understand the failure class
Background: "missing required argument" and "the following required arguments were not provided": what required-argument errors mean and how to fix them — this error's family across 20 libraries.
Related errors
- no keypair ID for %q
- error parsing locationStore=%q: %w
- locationStore=%q is only supported in tests
- locationStore=%q is of unexpected type %T
- Invalid service account email '%s'
AI-assisted analysis of kubernetes/kops@4c8573c808 (2026-09-05).
Data as JSON: /api/errors/20e338a815c7dd0d.
Report an issue: GitHub.