{"record":{"id":"ea552b3d374f23c0","repo":"kubernetes/kops","slug":"error-building-glance-client-w","errorCode":null,"errorMessage":"error building glance client: %w","messagePattern":"error building glance client: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"upup/pkg/fi/cloudup/openstack/cloud.go","lineNumber":412,"sourceCode":"\t\treturn nil, fmt.Errorf(\"error building neutron client: %w\", err)\n\t}\n\n\tnovaClient, err := openstack.NewComputeV2(provider, gophercloud.EndpointOpts{\n\t\tType:   \"compute\",\n\t\tRegion: region,\n\t})\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"error building nova client: %w\", err)\n\t}\n\t// 2.47 is the minimum version where the compute API /server/details returns flavor names\n\tnovaClient.Microversion = \"2.47\"\n\n\tglanceClient, err := openstack.NewImageV2(provider, gophercloud.EndpointOpts{\n\t\tType:   \"image\",\n\t\tRegion: region,\n\t})\n\tif err != nil {\n\t\treturn nil, fmt.Errorf(\"error building glance client: %w\", err)\n\t}\n\n\tvar dnsClient *gophercloud.ServiceClient\n\tif hasDNS {\n\t\tdnsClient, err = openstack.NewDNSV2(provider, gophercloud.EndpointOpts{\n\t\t\tType:   \"dns\",\n\t\t\tRegion: region,\n\t\t})\n\t\tif err != nil {\n\t\t\treturn nil, fmt.Errorf(\"error building dns client: %w\", err)\n\t\t}\n\t}\n\n\tc := &openstackCloud{\n\t\tcinderClient:  cinderClient,\n\t\tneutronClient: neutronClient,\n\t\tnovaClient:    novaClient,\n\t\tdnsClient:     dnsClient,","sourceCodeStart":394,"sourceCodeEnd":430,"githubUrl":"https://github.com/kubernetes/kops/blob/4c8573c808a73d578c5eadc86d410646ea0b0d73/upup/pkg/fi/cloudup/openstack/cloud.go#L394-L430","documentation":"buildClients (upup/pkg/fi/cloudup/openstack/cloud.go:412) builds the Glance image v2 client with openstack.NewImageV2 and EndpointOpts{Type: \"image\", Region: region}. It fails when the Keystone catalog has no image service v2 endpoint for that region. Wrapped with %w, so the underlying gophercloud error (usually ErrEndpointNotFound) is preserved for inspection.","triggerScenarios":"No 'image' type endpoint in the catalog for the region; only Glance v1 deployed (NewImageV2 requires v2); region mismatch between the configured region and the endpoint's region attribute; catalog entry disabled or interface unreachable.","commonSituations":"Legacy clouds still on Glance v1; multi-region deployments where the image service lives in a single region; region-name casing mismatch; restricted catalogs that hide the image service from the authenticating project.","solutions":["Check `openstack endpoint list --service image --region <region>` for a v2 (image) endpoint","Set OS_REGION_NAME to the region where Glance v2 is deployed","Register an image v2 endpoint or upgrade Glance from v1 if missing","Ensure the chosen endpoint interface (public/internal) is reachable from the machine running kops"],"exampleFix":null,"handlingStrategy":"validation","validationCode":"endpoints, err := catalogEndpoints(token, \"image\")\nif err != nil || len(endpoints) == 0 {\n    return fmt.Errorf(\"no image v2 endpoint for region %q\", region)\n}\nreturn nil","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Verify `openstack endpoint list --service image --region <region>` before kops","Upgrade Glance v1-only clouds to v2","Use exact region names from `openstack region list`","Confirm the image service is visible in the project's service catalog"],"tags":["openstack","glance","endpoint","service-catalog","gophercloud"],"backgroundTag":"endpoint-not-found","analyzedSha":"4c8573c808a73d578c5eadc86d410646ea0b0d73","analyzedAt":"2026-09-05T04:13:19.212Z","contentChangedAt":"2026-09-05T04:13:19.212Z","schemaVersion":2},"datasetVersion":"2026-09-12T12:17:11.808Z"}