From e23d1e1ce8f99b8035ad6e3dadb0d8b0dc45df37 Mon Sep 17 00:00:00 2001 From: Gondermann Date: Tue, 10 Mar 2026 15:59:57 +0100 Subject: [PATCH 01/10] Scaffolding for the ApplicationCredential controller $ go run ./cmd/scaffold-controller -interactive=false \ -kind=ApplicationCredential \ -gophercloud-client=NewIdentityV3 \ -gophercloud-module=github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials \ -gophercloud-type=ApplicationCredential \ -openstack-json-object=application_credentials \ -required-create-dependency=User \ -import-dependency=User On-behalf-of: SAP nils.gondermann@sap.com --- api/v1alpha1/applicationcredential_types.go | 88 +++ api/v1alpha1/zz_generated.deepcopy.go | 70 +++ cmd/models-schema/zz_generated.openapi.go | 564 +++++++++++------- config/rbac/role.yaml | 2 + ...nstack_v1alpha1_applicationcredential.yaml | 14 + .../applicationcredential/actuator.go | 271 +++++++++ .../applicationcredential/actuator_test.go | 119 ++++ .../applicationcredential/controller.go | 114 ++++ .../applicationcredential/status.go | 64 ++ .../00-assert.yaml | 33 + .../00-create-resource.yaml | 29 + .../00-secret.yaml | 6 + .../README.md | 11 + .../00-assert.yaml | 32 + .../00-create-resource.yaml | 28 + .../00-secret.yaml | 6 + .../01-assert.yaml | 11 + .../01-delete-secret.yaml | 7 + .../README.md | 15 + .../00-assert.yaml | 30 + .../00-create-resources-missing-deps.yaml | 42 ++ .../00-secret.yaml | 6 + .../01-assert.yaml | 30 + .../01-create-dependencies.yaml | 19 + .../02-assert.yaml | 17 + .../02-delete-dependencies.yaml | 9 + .../03-assert.yaml | 9 + .../03-delete-resources.yaml | 10 + .../README.md | 21 + .../00-assert.yaml | 17 + .../00-import-resource.yaml | 26 + .../00-secret.yaml | 6 + .../01-assert.yaml | 32 + .../01-create-trap-resource.yaml | 28 + .../02-assert.yaml | 34 ++ .../02-create-resource.yaml | 27 + .../03-assert.yaml | 6 + .../03-delete-import-dependencies.yaml | 7 + .../04-assert.yaml | 6 + .../04-delete-resource.yaml | 7 + .../README.md | 29 + .../00-assert.yaml | 30 + .../00-create-resources.yaml | 43 ++ .../00-secret.yaml | 6 + .../01-assert.yaml | 15 + .../01-import-resource.yaml | 13 + .../README.md | 13 + .../00-assert.yaml | 15 + .../00-import-resource.yaml | 15 + .../00-secret.yaml | 6 + .../01-assert.yaml | 34 ++ .../01-create-trap-resource.yaml | 31 + .../02-assert.yaml | 33 + .../02-create-resource.yaml | 28 + .../applicationcredential-import/README.md | 18 + .../00-assert.yaml | 26 + .../00-minimal-resource.yaml | 28 + .../00-secret.yaml | 6 + .../01-assert.yaml | 17 + .../01-updated-resource.yaml | 10 + .../02-assert.yaml | 26 + .../02-reverted-resource.yaml | 7 + .../applicationcredential-update/README.md | 17 + internal/osclients/applicationcredential.go | 104 ++++ website/docs/crd-reference.md | 10 + 65 files changed, 2224 insertions(+), 229 deletions(-) create mode 100644 api/v1alpha1/applicationcredential_types.go create mode 100644 config/samples/openstack_v1alpha1_applicationcredential.yaml create mode 100644 internal/controllers/applicationcredential/actuator.go create mode 100644 internal/controllers/applicationcredential/actuator_test.go create mode 100644 internal/controllers/applicationcredential/controller.go create mode 100644 internal/controllers/applicationcredential/status.go create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-create-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-secret.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-create-full/README.md create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-create-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-secret.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-delete-secret.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/README.md create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-create-resources-missing-deps.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-secret.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-create-dependencies.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-dependency/02-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-dependency/02-delete-dependencies.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-delete-resources.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-dependency/README.md create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-import-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-secret.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-create-trap-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-create-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/03-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/03-delete-import-dependencies.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/04-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/04-delete-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/README.md create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-create-resources.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-secret.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-import-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import-error/README.md create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import/00-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import/00-import-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import/00-secret.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import/01-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import/01-create-trap-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import/02-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import/02-create-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-import/README.md create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/00-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/00-minimal-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/00-secret.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/01-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/01-updated-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/02-assert.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/02-reverted-resource.yaml create mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/README.md create mode 100644 internal/osclients/applicationcredential.go diff --git a/api/v1alpha1/applicationcredential_types.go b/api/v1alpha1/applicationcredential_types.go new file mode 100644 index 000000000..07e3889cc --- /dev/null +++ b/api/v1alpha1/applicationcredential_types.go @@ -0,0 +1,88 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package v1alpha1 + +// ApplicationCredentialResourceSpec contains the desired state of the resource. +type ApplicationCredentialResourceSpec struct { + // name will be the name of the created resource. If not specified, the + // name of the ORC object will be used. + // +optional + Name *OpenStackName `json:"name,omitempty"` + + // description is a human-readable description for the resource. + // +kubebuilder:validation:MinLength:=1 + // +kubebuilder:validation:MaxLength:=255 + // +optional + Description *string `json:"description,omitempty"` + + // userRef is a reference to the ORC User which this resource is associated with. + // +required + // +kubebuilder:validation:XValidation:rule="self == oldSelf",message="userRef is immutable" + UserRef KubernetesNameRef `json:"userRef,omitempty"` + + // TODO(scaffolding): Add more types. + // To see what is supported, you can take inspiration from the CreateOpts structure from + // github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials + // + // Until you have implemented mutability for the field, you must add a CEL validation + // preventing the field being modified: + // `// +kubebuilder:validation:XValidation:rule="self == oldSelf",message=" is immutable"` +} + +// ApplicationCredentialFilter defines an existing resource by its properties +// +kubebuilder:validation:MinProperties:=1 +type ApplicationCredentialFilter struct { + // name of the existing resource + // +optional + Name *OpenStackName `json:"name,omitempty"` + + // description of the existing resource + // +kubebuilder:validation:MinLength:=1 + // +kubebuilder:validation:MaxLength:=255 + // +optional + Description *string `json:"description,omitempty"` + + // userRef is a reference to the ORC User which this resource is associated with. + // +optional + UserRef *KubernetesNameRef `json:"userRef,omitempty"` + + // TODO(scaffolding): Add more types. + // To see what is supported, you can take inspiration from the ListOpts structure from + // github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials +} + +// ApplicationCredentialResourceStatus represents the observed state of the resource. +type ApplicationCredentialResourceStatus struct { + // name is a Human-readable name for the resource. Might not be unique. + // +kubebuilder:validation:MaxLength=1024 + // +optional + Name string `json:"name,omitempty"` + + // description is a human-readable description for the resource. + // +kubebuilder:validation:MaxLength=1024 + // +optional + Description string `json:"description,omitempty"` + + // userID is the ID of the User to which the resource is associated. + // +kubebuilder:validation:MaxLength=1024 + // +optional + UserID string `json:"userID,omitempty"` + + // TODO(scaffolding): Add more types. + // To see what is supported, you can take inspiration from the ApplicationCredential structure from + // github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials +} diff --git a/api/v1alpha1/zz_generated.deepcopy.go b/api/v1alpha1/zz_generated.deepcopy.go index 4bd75eca4..019340172 100644 --- a/api/v1alpha1/zz_generated.deepcopy.go +++ b/api/v1alpha1/zz_generated.deepcopy.go @@ -337,6 +337,76 @@ func (in *AllowedAddressPairStatus) DeepCopy() *AllowedAddressPairStatus { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ApplicationCredentialFilter) DeepCopyInto(out *ApplicationCredentialFilter) { + *out = *in + if in.Name != nil { + in, out := &in.Name, &out.Name + *out = new(OpenStackName) + **out = **in + } + if in.Description != nil { + in, out := &in.Description, &out.Description + *out = new(string) + **out = **in + } + if in.UserRef != nil { + in, out := &in.UserRef, &out.UserRef + *out = new(KubernetesNameRef) + **out = **in + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialFilter. +func (in *ApplicationCredentialFilter) DeepCopy() *ApplicationCredentialFilter { + if in == nil { + return nil + } + out := new(ApplicationCredentialFilter) + in.DeepCopyInto(out) + return out +} + +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ApplicationCredentialResourceSpec) DeepCopyInto(out *ApplicationCredentialResourceSpec) { + *out = *in + if in.Name != nil { + in, out := &in.Name, &out.Name + *out = new(OpenStackName) + **out = **in + } + if in.Description != nil { + in, out := &in.Description, &out.Description + *out = new(string) + **out = **in + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialResourceSpec. +func (in *ApplicationCredentialResourceSpec) DeepCopy() *ApplicationCredentialResourceSpec { + if in == nil { + return nil + } + out := new(ApplicationCredentialResourceSpec) + in.DeepCopyInto(out) + return out +} + +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ApplicationCredentialResourceStatus) DeepCopyInto(out *ApplicationCredentialResourceStatus) { + *out = *in +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialResourceStatus. +func (in *ApplicationCredentialResourceStatus) DeepCopy() *ApplicationCredentialResourceStatus { + if in == nil { + return nil + } + out := new(ApplicationCredentialResourceStatus) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *CloudCredentialsReference) DeepCopyInto(out *CloudCredentialsReference) { *out = *in diff --git a/cmd/models-schema/zz_generated.openapi.go b/cmd/models-schema/zz_generated.openapi.go index 9250f4e36..33c043d59 100644 --- a/cmd/models-schema/zz_generated.openapi.go +++ b/cmd/models-schema/zz_generated.openapi.go @@ -30,235 +30,238 @@ import ( func GetOpenAPIDefinitions(ref common.ReferenceCallback) map[string]common.OpenAPIDefinition { return map[string]common.OpenAPIDefinition{ - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Address": schema_openstack_resource_controller_v2_api_v1alpha1_Address(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScope": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScope(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeImport": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeList": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllocationPool": schema_openstack_resource_controller_v2_api_v1alpha1_AllocationPool(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllocationPoolStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AllocationPoolStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllowedAddressPair": schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPair(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllowedAddressPairStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPairStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.CloudCredentialsReference": schema_openstack_resource_controller_v2_api_v1alpha1_CloudCredentialsReference(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Domain": schema_openstack_resource_controller_v2_api_v1alpha1_Domain(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainFilter": schema_openstack_resource_controller_v2_api_v1alpha1_DomainFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainImport": schema_openstack_resource_controller_v2_api_v1alpha1_DomainImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainList": schema_openstack_resource_controller_v2_api_v1alpha1_DomainList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_DomainResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_DomainResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainSpec": schema_openstack_resource_controller_v2_api_v1alpha1_DomainSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainStatus": schema_openstack_resource_controller_v2_api_v1alpha1_DomainStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Endpoint": schema_openstack_resource_controller_v2_api_v1alpha1_Endpoint(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointFilter": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointImport": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointList": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointSpec": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointStatus": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ExternalGateway": schema_openstack_resource_controller_v2_api_v1alpha1_ExternalGateway(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ExternalGatewayStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ExternalGatewayStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByKeystoneTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByKeystoneTags(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByNeutronTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByNeutronTags(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByServerTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByServerTags(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FixedIPStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FixedIPStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Flavor": schema_openstack_resource_controller_v2_api_v1alpha1_Flavor(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorFilter": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorImport": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorList": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIP": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIP(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPFilter": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPImport": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPList": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Group": schema_openstack_resource_controller_v2_api_v1alpha1_Group(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_GroupFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_GroupImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupList": schema_openstack_resource_controller_v2_api_v1alpha1_GroupList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_GroupResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_GroupResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_GroupSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_GroupStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostID": schema_openstack_resource_controller_v2_api_v1alpha1_HostID(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostRoute": schema_openstack_resource_controller_v2_api_v1alpha1_HostRoute(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostRouteStatus": schema_openstack_resource_controller_v2_api_v1alpha1_HostRouteStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.IPv6Options": schema_openstack_resource_controller_v2_api_v1alpha1_IPv6Options(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Image": schema_openstack_resource_controller_v2_api_v1alpha1_Image(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageContent": schema_openstack_resource_controller_v2_api_v1alpha1_ImageContent(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageContentSourceDownload": schema_openstack_resource_controller_v2_api_v1alpha1_ImageContentSourceDownload(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ImageFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageHash": schema_openstack_resource_controller_v2_api_v1alpha1_ImageHash(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageImport": schema_openstack_resource_controller_v2_api_v1alpha1_ImageImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageList": schema_openstack_resource_controller_v2_api_v1alpha1_ImageList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageProperties": schema_openstack_resource_controller_v2_api_v1alpha1_ImageProperties(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImagePropertiesHardware": schema_openstack_resource_controller_v2_api_v1alpha1_ImagePropertiesHardware(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImagePropertiesOperatingSystem": schema_openstack_resource_controller_v2_api_v1alpha1_ImagePropertiesOperatingSystem(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ImageResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ImageResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ImageSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ImageStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageStatusExtra": schema_openstack_resource_controller_v2_api_v1alpha1_ImageStatusExtra(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPair": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPair(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairFilter": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairImport": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairList": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairSpec": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairStatus": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ManagedOptions": schema_openstack_resource_controller_v2_api_v1alpha1_ManagedOptions(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Network": schema_openstack_resource_controller_v2_api_v1alpha1_Network(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkFilter": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkImport": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkList": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkSpec": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkStatus": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NeutronStatusMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_NeutronStatusMetadata(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Port": schema_openstack_resource_controller_v2_api_v1alpha1_Port(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortFilter": schema_openstack_resource_controller_v2_api_v1alpha1_PortFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortImport": schema_openstack_resource_controller_v2_api_v1alpha1_PortImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortList": schema_openstack_resource_controller_v2_api_v1alpha1_PortList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortRangeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortRangeSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortRangeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortRangeStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Project": schema_openstack_resource_controller_v2_api_v1alpha1_Project(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectImport": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectList": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProviderPropertiesStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProviderPropertiesStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Role": schema_openstack_resource_controller_v2_api_v1alpha1_Role(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleFilter": schema_openstack_resource_controller_v2_api_v1alpha1_RoleFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleImport": schema_openstack_resource_controller_v2_api_v1alpha1_RoleImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleList": schema_openstack_resource_controller_v2_api_v1alpha1_RoleList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RoleResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RoleResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RoleSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RoleStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Router": schema_openstack_resource_controller_v2_api_v1alpha1_Router(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterFilter": schema_openstack_resource_controller_v2_api_v1alpha1_RouterFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterImport": schema_openstack_resource_controller_v2_api_v1alpha1_RouterImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterface": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterface(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceList": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterList": schema_openstack_resource_controller_v2_api_v1alpha1_RouterList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroup": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroup(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupList": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupRule": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupRule(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupRuleStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupRuleStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Server": schema_openstack_resource_controller_v2_api_v1alpha1_Server(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServerFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroup": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroup(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupList": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupRules": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupRules(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupRulesStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupRulesStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServerImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerInterfaceFixedIP": schema_openstack_resource_controller_v2_api_v1alpha1_ServerInterfaceFixedIP(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerInterfaceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerInterfaceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerList": schema_openstack_resource_controller_v2_api_v1alpha1_ServerList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_ServerMetadata(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerMetadataStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerMetadataStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerPortSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerPortSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerVolumeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerVolumeSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerVolumeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerVolumeStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Service": schema_openstack_resource_controller_v2_api_v1alpha1_Service(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceList": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Subnet": schema_openstack_resource_controller_v2_api_v1alpha1_Subnet(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetFilter": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetGateway": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetGateway(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetImport": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetList": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Trunk": schema_openstack_resource_controller_v2_api_v1alpha1_Trunk(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkFilter": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkImport": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkList": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSubportSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSubportSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSubportStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSubportStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.User": schema_openstack_resource_controller_v2_api_v1alpha1_User(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserDataSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserDataSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserFilter": schema_openstack_resource_controller_v2_api_v1alpha1_UserFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserImport": schema_openstack_resource_controller_v2_api_v1alpha1_UserImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserList": schema_openstack_resource_controller_v2_api_v1alpha1_UserList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_UserResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserStatus": schema_openstack_resource_controller_v2_api_v1alpha1_UserStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Volume": schema_openstack_resource_controller_v2_api_v1alpha1_Volume(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeAttachmentStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeAttachmentStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeImport": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeList": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeMetadata(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeMetadataStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeMetadataStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeType": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeType(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeExtraSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeExtraSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeExtraSpecStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeExtraSpecStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeImport": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeList": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeStatus(ref), - "k8s.io/api/core/v1.AWSElasticBlockStoreVolumeSource": schema_k8sio_api_core_v1_AWSElasticBlockStoreVolumeSource(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Address": schema_openstack_resource_controller_v2_api_v1alpha1_Address(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScope": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScope(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeImport": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeList": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllocationPool": schema_openstack_resource_controller_v2_api_v1alpha1_AllocationPool(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllocationPoolStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AllocationPoolStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllowedAddressPair": schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPair(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllowedAddressPairStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPairStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.CloudCredentialsReference": schema_openstack_resource_controller_v2_api_v1alpha1_CloudCredentialsReference(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Domain": schema_openstack_resource_controller_v2_api_v1alpha1_Domain(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainFilter": schema_openstack_resource_controller_v2_api_v1alpha1_DomainFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainImport": schema_openstack_resource_controller_v2_api_v1alpha1_DomainImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainList": schema_openstack_resource_controller_v2_api_v1alpha1_DomainList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_DomainResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_DomainResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainSpec": schema_openstack_resource_controller_v2_api_v1alpha1_DomainSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainStatus": schema_openstack_resource_controller_v2_api_v1alpha1_DomainStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Endpoint": schema_openstack_resource_controller_v2_api_v1alpha1_Endpoint(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointFilter": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointImport": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointList": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointSpec": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointStatus": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ExternalGateway": schema_openstack_resource_controller_v2_api_v1alpha1_ExternalGateway(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ExternalGatewayStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ExternalGatewayStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByKeystoneTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByKeystoneTags(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByNeutronTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByNeutronTags(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByServerTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByServerTags(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FixedIPStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FixedIPStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Flavor": schema_openstack_resource_controller_v2_api_v1alpha1_Flavor(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorFilter": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorImport": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorList": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIP": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIP(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPFilter": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPImport": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPList": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Group": schema_openstack_resource_controller_v2_api_v1alpha1_Group(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_GroupFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_GroupImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupList": schema_openstack_resource_controller_v2_api_v1alpha1_GroupList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_GroupResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_GroupResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_GroupSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_GroupStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostID": schema_openstack_resource_controller_v2_api_v1alpha1_HostID(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostRoute": schema_openstack_resource_controller_v2_api_v1alpha1_HostRoute(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostRouteStatus": schema_openstack_resource_controller_v2_api_v1alpha1_HostRouteStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.IPv6Options": schema_openstack_resource_controller_v2_api_v1alpha1_IPv6Options(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Image": schema_openstack_resource_controller_v2_api_v1alpha1_Image(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageContent": schema_openstack_resource_controller_v2_api_v1alpha1_ImageContent(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageContentSourceDownload": schema_openstack_resource_controller_v2_api_v1alpha1_ImageContentSourceDownload(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ImageFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageHash": schema_openstack_resource_controller_v2_api_v1alpha1_ImageHash(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageImport": schema_openstack_resource_controller_v2_api_v1alpha1_ImageImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageList": schema_openstack_resource_controller_v2_api_v1alpha1_ImageList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageProperties": schema_openstack_resource_controller_v2_api_v1alpha1_ImageProperties(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImagePropertiesHardware": schema_openstack_resource_controller_v2_api_v1alpha1_ImagePropertiesHardware(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImagePropertiesOperatingSystem": schema_openstack_resource_controller_v2_api_v1alpha1_ImagePropertiesOperatingSystem(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ImageResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ImageResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ImageSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ImageStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageStatusExtra": schema_openstack_resource_controller_v2_api_v1alpha1_ImageStatusExtra(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPair": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPair(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairFilter": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairImport": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairList": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairSpec": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairStatus": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ManagedOptions": schema_openstack_resource_controller_v2_api_v1alpha1_ManagedOptions(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Network": schema_openstack_resource_controller_v2_api_v1alpha1_Network(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkFilter": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkImport": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkList": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkSpec": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkStatus": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NeutronStatusMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_NeutronStatusMetadata(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Port": schema_openstack_resource_controller_v2_api_v1alpha1_Port(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortFilter": schema_openstack_resource_controller_v2_api_v1alpha1_PortFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortImport": schema_openstack_resource_controller_v2_api_v1alpha1_PortImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortList": schema_openstack_resource_controller_v2_api_v1alpha1_PortList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortRangeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortRangeSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortRangeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortRangeStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Project": schema_openstack_resource_controller_v2_api_v1alpha1_Project(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectImport": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectList": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProviderPropertiesStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProviderPropertiesStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Role": schema_openstack_resource_controller_v2_api_v1alpha1_Role(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleFilter": schema_openstack_resource_controller_v2_api_v1alpha1_RoleFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleImport": schema_openstack_resource_controller_v2_api_v1alpha1_RoleImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleList": schema_openstack_resource_controller_v2_api_v1alpha1_RoleList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RoleResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RoleResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RoleSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RoleStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Router": schema_openstack_resource_controller_v2_api_v1alpha1_Router(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterFilter": schema_openstack_resource_controller_v2_api_v1alpha1_RouterFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterImport": schema_openstack_resource_controller_v2_api_v1alpha1_RouterImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterface": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterface(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceList": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterList": schema_openstack_resource_controller_v2_api_v1alpha1_RouterList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroup": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroup(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupList": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupRule": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupRule(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupRuleStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupRuleStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Server": schema_openstack_resource_controller_v2_api_v1alpha1_Server(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServerFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroup": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroup(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupList": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupRules": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupRules(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupRulesStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupRulesStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServerImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerInterfaceFixedIP": schema_openstack_resource_controller_v2_api_v1alpha1_ServerInterfaceFixedIP(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerInterfaceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerInterfaceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerList": schema_openstack_resource_controller_v2_api_v1alpha1_ServerList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_ServerMetadata(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerMetadataStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerMetadataStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerPortSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerPortSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerVolumeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerVolumeSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerVolumeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerVolumeStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Service": schema_openstack_resource_controller_v2_api_v1alpha1_Service(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceList": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Subnet": schema_openstack_resource_controller_v2_api_v1alpha1_Subnet(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetFilter": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetGateway": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetGateway(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetImport": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetList": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Trunk": schema_openstack_resource_controller_v2_api_v1alpha1_Trunk(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkFilter": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkImport": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkList": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSubportSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSubportSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSubportStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSubportStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.User": schema_openstack_resource_controller_v2_api_v1alpha1_User(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserDataSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserDataSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserFilter": schema_openstack_resource_controller_v2_api_v1alpha1_UserFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserImport": schema_openstack_resource_controller_v2_api_v1alpha1_UserImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserList": schema_openstack_resource_controller_v2_api_v1alpha1_UserList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_UserResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserStatus": schema_openstack_resource_controller_v2_api_v1alpha1_UserStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Volume": schema_openstack_resource_controller_v2_api_v1alpha1_Volume(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeAttachmentStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeAttachmentStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeImport": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeList": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeMetadata(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeMetadataStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeMetadataStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeType": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeType(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeExtraSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeExtraSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeExtraSpecStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeExtraSpecStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeImport": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeList": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeStatus(ref), + "k8s.io/api/core/v1.AWSElasticBlockStoreVolumeSource": schema_k8sio_api_core_v1_AWSElasticBlockStoreVolumeSource(ref), "k8s.io/api/core/v1.Affinity": schema_k8sio_api_core_v1_Affinity(ref), "k8s.io/api/core/v1.AppArmorProfile": schema_k8sio_api_core_v1_AppArmorProfile(ref), "k8s.io/api/core/v1.AttachedVolume": schema_k8sio_api_core_v1_AttachedVolume(ref), @@ -1038,6 +1041,109 @@ func schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPairStat } } +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialFilter(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "ApplicationCredentialFilter defines an existing resource by its properties", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "name": { + SchemaProps: spec.SchemaProps{ + Description: "name of the existing resource", + Type: []string{"string"}, + Format: "", + }, + }, + "description": { + SchemaProps: spec.SchemaProps{ + Description: "description of the existing resource", + Type: []string{"string"}, + Format: "", + }, + }, + "userRef": { + SchemaProps: spec.SchemaProps{ + Description: "userRef is a reference to the ORC User which this resource is associated with.", + Type: []string{"string"}, + Format: "", + }, + }, + }, + }, + }, + } +} + +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialResourceSpec(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "ApplicationCredentialResourceSpec contains the desired state of the resource.", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "name": { + SchemaProps: spec.SchemaProps{ + Description: "name will be the name of the created resource. If not specified, the name of the ORC object will be used.", + Type: []string{"string"}, + Format: "", + }, + }, + "description": { + SchemaProps: spec.SchemaProps{ + Description: "description is a human-readable description for the resource.", + Type: []string{"string"}, + Format: "", + }, + }, + "userRef": { + SchemaProps: spec.SchemaProps{ + Description: "userRef is a reference to the ORC User which this resource is associated with.", + Type: []string{"string"}, + Format: "", + }, + }, + }, + Required: []string{"userRef"}, + }, + }, + } +} + +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialResourceStatus(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "ApplicationCredentialResourceStatus represents the observed state of the resource.", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "name": { + SchemaProps: spec.SchemaProps{ + Description: "name is a Human-readable name for the resource. Might not be unique.", + Type: []string{"string"}, + Format: "", + }, + }, + "description": { + SchemaProps: spec.SchemaProps{ + Description: "description is a human-readable description for the resource.", + Type: []string{"string"}, + Format: "", + }, + }, + "userID": { + SchemaProps: spec.SchemaProps{ + Description: "userID is the ID of the User to which the resource is associated.", + Type: []string{"string"}, + Format: "", + }, + }, + }, + }, + }, + } +} + func schema_openstack_resource_controller_v2_api_v1alpha1_CloudCredentialsReference(ref common.ReferenceCallback) common.OpenAPIDefinition { return common.OpenAPIDefinition{ Schema: spec.Schema{ diff --git a/config/rbac/role.yaml b/config/rbac/role.yaml index dbadb7068..3b67eb9fa 100644 --- a/config/rbac/role.yaml +++ b/config/rbac/role.yaml @@ -18,6 +18,7 @@ rules: - openstack.k-orc.cloud resources: - addressscopes + - applicationcredentials - domains - endpoints - flavors @@ -52,6 +53,7 @@ rules: - openstack.k-orc.cloud resources: - addressscopes/status + - applicationcredentials/status - domains/status - endpoints/status - flavors/status diff --git a/config/samples/openstack_v1alpha1_applicationcredential.yaml b/config/samples/openstack_v1alpha1_applicationcredential.yaml new file mode 100644 index 000000000..8edc2aba1 --- /dev/null +++ b/config/samples/openstack_v1alpha1_applicationcredential.yaml @@ -0,0 +1,14 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-sample +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + resource: + description: Sample ApplicationCredential + # TODO(scaffolding): Add all fields the resource supports diff --git a/internal/controllers/applicationcredential/actuator.go b/internal/controllers/applicationcredential/actuator.go new file mode 100644 index 000000000..1b3ad3efc --- /dev/null +++ b/internal/controllers/applicationcredential/actuator.go @@ -0,0 +1,271 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package applicationcredential + +import ( + "context" + "iter" + + "github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials" + corev1 "k8s.io/api/core/v1" + "k8s.io/utils/ptr" + ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/client" + + orcv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" + "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/generic/interfaces" + "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/generic/progress" + "github.com/k-orc/openstack-resource-controller/v2/internal/logging" + "github.com/k-orc/openstack-resource-controller/v2/internal/osclients" + "github.com/k-orc/openstack-resource-controller/v2/internal/util/dependency" + orcerrors "github.com/k-orc/openstack-resource-controller/v2/internal/util/errors" +) + +// OpenStack resource types +type ( + osResourceT = applicationcredentials.ApplicationCredential + + createResourceActuator = interfaces.CreateResourceActuator[orcObjectPT, orcObjectT, filterT, osResourceT] + deleteResourceActuator = interfaces.DeleteResourceActuator[orcObjectPT, orcObjectT, osResourceT] + resourceReconciler = interfaces.ResourceReconciler[orcObjectPT, osResourceT] + helperFactory = interfaces.ResourceHelperFactory[orcObjectPT, orcObjectT, resourceSpecT, filterT, osResourceT] +) + +type applicationcredentialActuator struct { + osClient osclients.ApplicationCredentialClient + k8sClient client.Client +} + +var _ createResourceActuator = applicationcredentialActuator{} +var _ deleteResourceActuator = applicationcredentialActuator{} + +func (applicationcredentialActuator) GetResourceID(osResource *osResourceT) string { + return osResource.ID +} + +func (actuator applicationcredentialActuator) GetOSResourceByID(ctx context.Context, id string) (*osResourceT, progress.ReconcileStatus) { + resource, err := actuator.osClient.GetApplicationCredential(ctx, id) + if err != nil { + return nil, progress.WrapError(err) + } + return resource, nil +} + +func (actuator applicationcredentialActuator) ListOSResourcesForAdoption(ctx context.Context, orcObject orcObjectPT) (iter.Seq2[*osResourceT, error], bool) { + resourceSpec := orcObject.Spec.Resource + if resourceSpec == nil { + return nil, false + } + + // TODO(scaffolding) If you need to filter resources on fields that the List() function + // of gophercloud does not support, it's possible to perform client-side filtering. + // Check osclients.ResourceFilter + + listOpts := applicationcredentials.ListOpts{ + Name: getResourceName(orcObject), + Description: ptr.Deref(resourceSpec.Description, ""), + } + + return actuator.osClient.ListApplicationCredentials(ctx, listOpts), true +} + +func (actuator applicationcredentialActuator) ListOSResourcesForImport(ctx context.Context, obj orcObjectPT, filter filterT) (iter.Seq2[*osResourceT, error], progress.ReconcileStatus) { + // TODO(scaffolding) If you need to filter resources on fields that the List() function + // of gophercloud does not support, it's possible to perform client-side filtering. + // Check osclients.ResourceFilter + var reconcileStatus progress.ReconcileStatus + + user, rs := dependency.FetchDependency( + ctx, actuator.k8sClient, obj.Namespace, + filter.UserRef, "User", + func(dep *orcv1alpha1.User) bool { return orcv1alpha1.IsAvailable(dep) && dep.Status.ID != nil }, + ) + reconcileStatus = reconcileStatus.WithReconcileStatus(rs) + + if needsReschedule, _ := reconcileStatus.NeedsReschedule(); needsReschedule { + return nil, reconcileStatus + } + + listOpts := applicationcredentials.ListOpts{ + Name: string(ptr.Deref(filter.Name, "")), + Description: string(ptr.Deref(filter.Description, "")), + UserID: ptr.Deref(user.Status.ID, ""), + // TODO(scaffolding): Add more import filters + } + + return actuator.osClient.ListApplicationCredentials(ctx, listOpts), reconcileStatus +} + +func (actuator applicationcredentialActuator) CreateResource(ctx context.Context, obj orcObjectPT) (*osResourceT, progress.ReconcileStatus) { + resource := obj.Spec.Resource + + if resource == nil { + // Should have been caught by API validation + return nil, progress.WrapError( + orcerrors.Terminal(orcv1alpha1.ConditionReasonInvalidConfiguration, "Creation requested, but spec.resource is not set")) + } + var reconcileStatus progress.ReconcileStatus + + var userID string + user, userDepRS := userDependency.GetDependency( + ctx, actuator.k8sClient, obj, func(dep *orcv1alpha1.User) bool { + return orcv1alpha1.IsAvailable(dep) && dep.Status.ID != nil + }, + ) + reconcileStatus = reconcileStatus.WithReconcileStatus(userDepRS) + if user != nil { + userID = ptr.Deref(user.Status.ID, "") + } + if needsReschedule, _ := reconcileStatus.NeedsReschedule(); needsReschedule { + return nil, reconcileStatus + } + createOpts := applicationcredentials.CreateOpts{ + Name: getResourceName(obj), + Description: ptr.Deref(resource.Description, ""), + UserID: userID, + // TODO(scaffolding): Add more fields + } + + osResource, err := actuator.osClient.CreateApplicationCredential(ctx, createOpts) + if err != nil { + // We should require the spec to be updated before retrying a create which returned a conflict + if !orcerrors.IsRetryable(err) { + err = orcerrors.Terminal(orcv1alpha1.ConditionReasonInvalidConfiguration, "invalid configuration creating resource: "+err.Error(), err) + } + return nil, progress.WrapError(err) + } + + return osResource, nil +} + +func (actuator applicationcredentialActuator) DeleteResource(ctx context.Context, _ orcObjectPT, resource *osResourceT) progress.ReconcileStatus { + return progress.WrapError(actuator.osClient.DeleteApplicationCredential(ctx, resource.ID)) +} + +func (actuator applicationcredentialActuator) updateResource(ctx context.Context, obj orcObjectPT, osResource *osResourceT) progress.ReconcileStatus { + log := ctrl.LoggerFrom(ctx) + resource := obj.Spec.Resource + if resource == nil { + // Should have been caught by API validation + return progress.WrapError( + orcerrors.Terminal(orcv1alpha1.ConditionReasonInvalidConfiguration, "Update requested, but spec.resource is not set")) + } + + updateOpts := applicationcredentials.UpdateOpts{} + + handleNameUpdate(&updateOpts, obj, osResource) + handleDescriptionUpdate(&updateOpts, resource, osResource) + + // TODO(scaffolding): add handler for all fields supporting mutability + + needsUpdate, err := needsUpdate(updateOpts) + if err != nil { + return progress.WrapError( + orcerrors.Terminal(orcv1alpha1.ConditionReasonInvalidConfiguration, "invalid configuration updating resource: "+err.Error(), err)) + } + if !needsUpdate { + log.V(logging.Debug).Info("No changes") + return nil + } + + _, err = actuator.osClient.UpdateApplicationCredential(ctx, osResource.ID, updateOpts) + + // We should require the spec to be updated before retrying an update which returned a conflict + if orcerrors.IsConflict(err) { + err = orcerrors.Terminal(orcv1alpha1.ConditionReasonInvalidConfiguration, "invalid configuration updating resource: "+err.Error(), err) + } + + if err != nil { + return progress.WrapError(err) + } + + return progress.NeedsRefresh() +} + +func needsUpdate(updateOpts applicationcredentials.UpdateOpts) (bool, error) { + updateOptsMap, err := updateOpts.ToApplicationCredentialUpdateMap() + if err != nil { + return false, err + } + + updateMap, ok := updateOptsMap["application_credentials"].(map[string]any) + if !ok { + updateMap = make(map[string]any) + } + + return len(updateMap) > 0, nil +} + +func handleNameUpdate(updateOpts *applicationcredentials.UpdateOpts, obj orcObjectPT, osResource *osResourceT) { + name := getResourceName(obj) + if osResource.Name != name { + updateOpts.Name = &name + } +} + +func handleDescriptionUpdate(updateOpts *applicationcredentials.UpdateOpts, resource *resourceSpecT, osResource *osResourceT) { + description := ptr.Deref(resource.Description, "") + if osResource.Description != description { + updateOpts.Description = &description + } +} + +func (actuator applicationcredentialActuator) GetResourceReconcilers(ctx context.Context, orcObject orcObjectPT, osResource *osResourceT, controller interfaces.ResourceController) ([]resourceReconciler, progress.ReconcileStatus) { + return []resourceReconciler{ + actuator.updateResource, + }, nil +} + +type applicationcredentialHelperFactory struct{} + +var _ helperFactory = applicationcredentialHelperFactory{} + +func newActuator(ctx context.Context, orcObject *orcv1alpha1.ApplicationCredential, controller interfaces.ResourceController) (applicationcredentialActuator, progress.ReconcileStatus) { + log := ctrl.LoggerFrom(ctx) + + // Ensure credential secrets exist and have our finalizer + _, reconcileStatus := credentialsDependency.GetDependencies(ctx, controller.GetK8sClient(), orcObject, func(*corev1.Secret) bool { return true }) + if needsReschedule, _ := reconcileStatus.NeedsReschedule(); needsReschedule { + return applicationcredentialActuator{}, reconcileStatus + } + + clientScope, err := controller.GetScopeFactory().NewClientScopeFromObject(ctx, controller.GetK8sClient(), log, orcObject) + if err != nil { + return applicationcredentialActuator{}, progress.WrapError(err) + } + osClient, err := clientScope.NewApplicationCredentialClient() + if err != nil { + return applicationcredentialActuator{}, progress.WrapError(err) + } + + return applicationcredentialActuator{ + osClient: osClient, + k8sClient: controller.GetK8sClient(), + }, nil +} + +func (applicationcredentialHelperFactory) NewAPIObjectAdapter(obj orcObjectPT) adapterI { + return applicationcredentialAdapter{obj} +} + +func (applicationcredentialHelperFactory) NewCreateActuator(ctx context.Context, orcObject orcObjectPT, controller interfaces.ResourceController) (createResourceActuator, progress.ReconcileStatus) { + return newActuator(ctx, orcObject, controller) +} + +func (applicationcredentialHelperFactory) NewDeleteActuator(ctx context.Context, orcObject orcObjectPT, controller interfaces.ResourceController) (deleteResourceActuator, progress.ReconcileStatus) { + return newActuator(ctx, orcObject, controller) +} diff --git a/internal/controllers/applicationcredential/actuator_test.go b/internal/controllers/applicationcredential/actuator_test.go new file mode 100644 index 000000000..1a8015f89 --- /dev/null +++ b/internal/controllers/applicationcredential/actuator_test.go @@ -0,0 +1,119 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package applicationcredential + +import ( + "testing" + + "github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials" + orcv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" + "k8s.io/utils/ptr" +) + +func TestNeedsUpdate(t *testing.T) { + testCases := []struct { + name string + updateOpts applicationcredentials.UpdateOpts + expectChange bool + }{ + { + name: "Empty base opts", + updateOpts: applicationcredentials.UpdateOpts{}, + expectChange: false, + }, + { + name: "Updated opts", + updateOpts: applicationcredentials.UpdateOpts{Name: ptr.To("updated")}, + expectChange: true, + }, + } + + for _, tt := range testCases { + t.Run(tt.name, func(t *testing.T) { + got, _ := needsUpdate(tt.updateOpts) + if got != tt.expectChange { + t.Errorf("Expected change: %v, got: %v", tt.expectChange, got) + } + }) + } +} + +func TestHandleNameUpdate(t *testing.T) { + ptrToName := ptr.To[orcv1alpha1.OpenStackName] + testCases := []struct { + name string + newValue *orcv1alpha1.OpenStackName + existingValue string + expectChange bool + }{ + {name: "Identical", newValue: ptrToName("name"), existingValue: "name", expectChange: false}, + {name: "Different", newValue: ptrToName("new-name"), existingValue: "name", expectChange: true}, + {name: "No value provided, existing is identical to object name", newValue: nil, existingValue: "object-name", expectChange: false}, + {name: "No value provided, existing is different from object name", newValue: nil, existingValue: "different-from-object-name", expectChange: true}, + } + + for _, tt := range testCases { + t.Run(tt.name, func(t *testing.T) { + resource := &orcv1alpha1.ApplicationCredential{} + resource.Name = "object-name" + resource.Spec = orcv1alpha1.ApplicationCredentialSpec{ + Resource: &orcv1alpha1.ApplicationCredentialResourceSpec{Name: tt.newValue}, + } + osResource := &osResourceT{Name: tt.existingValue} + + updateOpts := applicationcredentials.UpdateOpts{} + handleNameUpdate(&updateOpts, resource, osResource) + + got, _ := needsUpdate(updateOpts) + if got != tt.expectChange { + t.Errorf("Expected change: %v, got: %v", tt.expectChange, got) + } + }) + + } +} + +func TestHandleDescriptionUpdate(t *testing.T) { + ptrToDescription := ptr.To[string] + testCases := []struct { + name string + newValue *string + existingValue string + expectChange bool + }{ + {name: "Identical", newValue: ptrToDescription("desc"), existingValue: "desc", expectChange: false}, + {name: "Different", newValue: ptrToDescription("new-desc"), existingValue: "desc", expectChange: true}, + {name: "No value provided, existing is set", newValue: nil, existingValue: "desc", expectChange: true}, + {name: "No value provided, existing is empty", newValue: nil, existingValue: "", expectChange: false}, + } + + for _, tt := range testCases { + t.Run(tt.name, func(t *testing.T) { + resource := &orcv1alpha1.ApplicationCredentialResourceSpec{Description: tt.newValue} + osResource := &osResourceT{Description: tt.existingValue} + + updateOpts := applicationcredentials.UpdateOpts{} + handleDescriptionUpdate(&updateOpts, resource, osResource) + + got, _ := needsUpdate(updateOpts) + if got != tt.expectChange { + t.Errorf("Expected change: %v, got: %v", tt.expectChange, got) + } + }) + + } +} diff --git a/internal/controllers/applicationcredential/controller.go b/internal/controllers/applicationcredential/controller.go new file mode 100644 index 000000000..34a86a51e --- /dev/null +++ b/internal/controllers/applicationcredential/controller.go @@ -0,0 +1,114 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package applicationcredential + +import ( + "context" + "errors" + + ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/builder" + "sigs.k8s.io/controller-runtime/pkg/controller" + + orcv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" + + "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/generic/interfaces" + "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/generic/reconciler" + "github.com/k-orc/openstack-resource-controller/v2/internal/scope" + "github.com/k-orc/openstack-resource-controller/v2/internal/util/credentials" + "github.com/k-orc/openstack-resource-controller/v2/internal/util/dependency" + "github.com/k-orc/openstack-resource-controller/v2/pkg/predicates" +) + +const controllerName = "applicationcredential" + +// +kubebuilder:rbac:groups=openstack.k-orc.cloud,resources=applicationcredentials,verbs=get;list;watch;create;update;patch;delete +// +kubebuilder:rbac:groups=openstack.k-orc.cloud,resources=applicationcredentials/status,verbs=get;update;patch + +type applicationcredentialReconcilerConstructor struct { + scopeFactory scope.Factory +} + +func New(scopeFactory scope.Factory) interfaces.Controller { + return applicationcredentialReconcilerConstructor{scopeFactory: scopeFactory} +} + +func (applicationcredentialReconcilerConstructor) GetName() string { + return controllerName +} + +var userDependency = dependency.NewDeletionGuardDependency[*orcv1alpha1.ApplicationCredentialList, *orcv1alpha1.User]( + "spec.resource.userRef", + func(applicationcredential *orcv1alpha1.ApplicationCredential) []string { + resource := applicationcredential.Spec.Resource + if resource == nil { + return nil + } + return []string{string(resource.UserRef)} + }, + finalizer, externalObjectFieldOwner, +) + +var userImportDependency = dependency.NewDependency[*orcv1alpha1.ApplicationCredentialList, *orcv1alpha1.User]( + "spec.import.filter.userRef", + func(applicationcredential *orcv1alpha1.ApplicationCredential) []string { + resource := applicationcredential.Spec.Import + if resource == nil || resource.Filter == nil || resource.Filter.UserRef == nil { + return nil + } + return []string{string(*resource.Filter.UserRef)} + }, +) + +// SetupWithManager sets up the controller with the Manager. +func (c applicationcredentialReconcilerConstructor) SetupWithManager(ctx context.Context, mgr ctrl.Manager, options controller.Options) error { + log := ctrl.LoggerFrom(ctx) + k8sClient := mgr.GetClient() + + userWatchEventHandler, err := userDependency.WatchEventHandler(log, k8sClient) + if err != nil { + return err + } + + userImportWatchEventHandler, err := userImportDependency.WatchEventHandler(log, k8sClient) + if err != nil { + return err + } + + builder := ctrl.NewControllerManagedBy(mgr). + WithOptions(options). + Watches(&orcv1alpha1.User{}, userWatchEventHandler, + builder.WithPredicates(predicates.NewBecameAvailable(log, &orcv1alpha1.User{})), + ). + // A second watch is necessary because we need a different handler that omits deletion guards + Watches(&orcv1alpha1.User{}, userImportWatchEventHandler, + builder.WithPredicates(predicates.NewBecameAvailable(log, &orcv1alpha1.User{})), + ). + For(&orcv1alpha1.ApplicationCredential{}) + + if err := errors.Join( + userDependency.AddToManager(ctx, mgr), + userImportDependency.AddToManager(ctx, mgr), + credentialsDependency.AddToManager(ctx, mgr), + credentials.AddCredentialsWatch(log, mgr.GetClient(), builder, credentialsDependency), + ); err != nil { + return err + } + + r := reconciler.NewController(controllerName, mgr.GetClient(), c.scopeFactory, applicationcredentialHelperFactory{}, applicationcredentialStatusWriter{}) + return builder.Complete(&r) +} diff --git a/internal/controllers/applicationcredential/status.go b/internal/controllers/applicationcredential/status.go new file mode 100644 index 000000000..34141fd33 --- /dev/null +++ b/internal/controllers/applicationcredential/status.go @@ -0,0 +1,64 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package applicationcredential + +import ( + "github.com/go-logr/logr" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + + orcv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" + "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/generic/interfaces" + "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/generic/progress" + orcapplyconfigv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/pkg/clients/applyconfiguration/api/v1alpha1" +) + +type applicationcredentialStatusWriter struct{} + +type objectApplyT = orcapplyconfigv1alpha1.ApplicationCredentialApplyConfiguration +type statusApplyT = orcapplyconfigv1alpha1.ApplicationCredentialStatusApplyConfiguration + +var _ interfaces.ResourceStatusWriter[*orcv1alpha1.ApplicationCredential, *osResourceT, *objectApplyT, *statusApplyT] = applicationcredentialStatusWriter{} + +func (applicationcredentialStatusWriter) GetApplyConfig(name, namespace string) *objectApplyT { + return orcapplyconfigv1alpha1.ApplicationCredential(name, namespace) +} + +func (applicationcredentialStatusWriter) ResourceAvailableStatus(orcObject *orcv1alpha1.ApplicationCredential, osResource *osResourceT) (metav1.ConditionStatus, progress.ReconcileStatus) { + if osResource == nil { + if orcObject.Status.ID == nil { + return metav1.ConditionFalse, nil + } else { + return metav1.ConditionUnknown, nil + } + } + return metav1.ConditionTrue, nil +} + +func (applicationcredentialStatusWriter) ApplyResourceStatus(log logr.Logger, osResource *osResourceT, statusApply *statusApplyT) { + resourceStatus := orcapplyconfigv1alpha1.ApplicationCredentialResourceStatus(). + WithUserID(osResource.UserID). + WithName(osResource.Name) + + // TODO(scaffolding): add all of the fields supported in the ApplicationCredentialResourceStatus struct + // If a zero-value isn't expected in the response, place it behind a conditional + + if osResource.Description != "" { + resourceStatus.WithDescription(osResource.Description) + } + + statusApply.WithResource(resourceStatus) +} diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-assert.yaml new file mode 100644 index 000000000..709036a53 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-assert.yaml @@ -0,0 +1,33 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-create-full +status: + resource: + name: applicationcredential-create-full-override + description: ApplicationCredential from "create full" test + # TODO(scaffolding): Add all fields the resource supports + conditions: + - type: Available + status: "True" + reason: Success + - type: Progressing + status: "False" + reason: Success +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestAssert +resourceRefs: + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-create-full + ref: applicationcredential + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: User + name: applicationcredential-create-full + ref: user +assertAll: + - celExpr: "applicationcredential.status.id != ''" + - celExpr: "applicationcredential.status.resource.userID == user.status.id" + # TODO(scaffolding): Add more checks diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-create-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-create-resource.yaml new file mode 100644 index 000000000..b95030658 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-create-resource.yaml @@ -0,0 +1,29 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-create-full +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Add the necessary fields to create the resource + resource: {} +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-create-full +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + resource: + name: applicationcredential-create-full-override + description: ApplicationCredential from "create full" test + userRef: applicationcredential-create-full + # TODO(scaffolding): Add all fields the resource supports diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-secret.yaml new file mode 100644 index 000000000..045711ee7 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-secret.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-full/README.md b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/README.md new file mode 100644 index 000000000..77afac10d --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/README.md @@ -0,0 +1,11 @@ +# Create a ApplicationCredential with all the options + +## Step 00 + +Create a ApplicationCredential using all available fields, and verify that the observed state corresponds to the spec. + +Also validate that the OpenStack resource uses the name from the spec when it is specified. + +## Reference + +https://k-orc.cloud/development/writing-tests/#create-full diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-assert.yaml new file mode 100644 index 000000000..0e6d4d81f --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-assert.yaml @@ -0,0 +1,32 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-create-minimal +status: + resource: + name: applicationcredential-create-minimal + # TODO(scaffolding): Add all fields the resource supports + conditions: + - type: Available + status: "True" + reason: Success + - type: Progressing + status: "False" + reason: Success +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestAssert +resourceRefs: + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-create-minimal + ref: applicationcredential + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: User + name: applicationcredential-create-minimal + ref: user +assertAll: + - celExpr: "applicationcredential.status.id != ''" + - celExpr: "applicationcredential.status.resource.userID == user.status.id" + # TODO(scaffolding): Add more checks diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-create-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-create-resource.yaml new file mode 100644 index 000000000..f62a6c7b3 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-create-resource.yaml @@ -0,0 +1,28 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-create-minimal +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Add the necessary fields to create the resource + resource: {} +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-create-minimal +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Only add the mandatory fields. It's possible the resource + # doesn't have mandatory fields, in that case, leave it empty. + resource: + userRef: applicationcredential-create-minimal diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-secret.yaml new file mode 100644 index 000000000..045711ee7 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-secret.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-assert.yaml new file mode 100644 index 000000000..6362f0b10 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-assert.yaml @@ -0,0 +1,11 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestAssert +resourceRefs: + - apiVersion: v1 + kind: Secret + name: openstack-clouds + ref: secret +assertAll: + - celExpr: "secret.metadata.deletionTimestamp != 0" + - celExpr: "'openstack.k-orc.cloud/applicationcredential' in secret.metadata.finalizers" diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-delete-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-delete-secret.yaml new file mode 100644 index 000000000..1620791b9 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-delete-secret.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + # We expect the deletion to hang due to the finalizer, so use --wait=false + - command: kubectl delete secret openstack-clouds --wait=false + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/README.md b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/README.md new file mode 100644 index 000000000..79cd913b3 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/README.md @@ -0,0 +1,15 @@ +# Create a ApplicationCredential with the minimum options + +## Step 00 + +Create a minimal ApplicationCredential, that sets only the required fields, and verify that the observed state corresponds to the spec. + +Also validate that the OpenStack resource uses the name of the ORC object when no name is explicitly specified. + +## Step 01 + +Try deleting the secret and ensure that it is not deleted thanks to the finalizer. + +## Reference + +https://k-orc.cloud/development/writing-tests/#create-minimal diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-assert.yaml new file mode 100644 index 000000000..a4c40956e --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-assert.yaml @@ -0,0 +1,30 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-dependency-no-secret +status: + conditions: + - type: Available + message: Waiting for Secret/applicationcredential-dependency to be created + status: "False" + reason: Progressing + - type: Progressing + message: Waiting for Secret/applicationcredential-dependency to be created + status: "True" + reason: Progressing +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-dependency-no-user +status: + conditions: + - type: Available + message: Waiting for User/applicationcredential-dependency-pending to be created + status: "False" + reason: Progressing + - type: Progressing + message: Waiting for User/applicationcredential-dependency-pending to be created + status: "True" + reason: Progressing diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-create-resources-missing-deps.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-create-resources-missing-deps.yaml new file mode 100644 index 000000000..3fec6964c --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-create-resources-missing-deps.yaml @@ -0,0 +1,42 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-dependency +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Add the necessary fields to create the resource + resource: {} +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-dependency-no-user +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + resource: + userRef: applicationcredential-dependency-pending + # TODO(scaffolding): Add the necessary fields to create the resource + +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-dependency-no-secret +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: applicationcredential-dependency + managementPolicy: managed + # TODO(scaffolding): Add the necessary fields to create the resource + resource: + userRef: applicationcredential-dependency diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-secret.yaml new file mode 100644 index 000000000..045711ee7 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-secret.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-assert.yaml new file mode 100644 index 000000000..89e29a72d --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-assert.yaml @@ -0,0 +1,30 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-dependency-no-secret +status: + conditions: + - type: Available + message: OpenStack resource is available + status: "True" + reason: Success + - type: Progressing + message: OpenStack resource is up to date + status: "False" + reason: Success +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-dependency-no-user +status: + conditions: + - type: Available + message: OpenStack resource is available + status: "True" + reason: Success + - type: Progressing + message: OpenStack resource is up to date + status: "False" + reason: Success diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-create-dependencies.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-create-dependencies.yaml new file mode 100644 index 000000000..75e318e17 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-create-dependencies.yaml @@ -0,0 +1,19 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + - command: kubectl create secret generic applicationcredential-dependency --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} + namespaced: true +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-dependency-pending +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Add the necessary fields to create the resource + resource: {} diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/02-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/02-assert.yaml new file mode 100644 index 000000000..3c90253ef --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/02-assert.yaml @@ -0,0 +1,17 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestAssert +resourceRefs: + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: User + name: applicationcredential-dependency + ref: user + - apiVersion: v1 + kind: Secret + name: applicationcredential-dependency + ref: secret +assertAll: + - celExpr: "user.metadata.deletionTimestamp != 0" + - celExpr: "'openstack.k-orc.cloud/applicationcredential' in user.metadata.finalizers" + - celExpr: "secret.metadata.deletionTimestamp != 0" + - celExpr: "'openstack.k-orc.cloud/applicationcredential' in secret.metadata.finalizers" diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/02-delete-dependencies.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/02-delete-dependencies.yaml new file mode 100644 index 000000000..8ff104281 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/02-delete-dependencies.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + # We expect the deletion to hang due to the finalizer, so use --wait=false + - command: kubectl delete user.openstack.k-orc.cloud applicationcredential-dependency --wait=false + namespaced: true + - command: kubectl delete secret applicationcredential-dependency --wait=false + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-assert.yaml new file mode 100644 index 000000000..4d6be7f09 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-assert.yaml @@ -0,0 +1,9 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestAssert +commands: +# Dependencies that were prevented deletion before should now be gone +- script: "! kubectl get user.openstack.k-orc.cloud applicationcredential-dependency --namespace $NAMESPACE" + skipLogOutput: true +- script: "! kubectl get secret applicationcredential-dependency --namespace $NAMESPACE" + skipLogOutput: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-delete-resources.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-delete-resources.yaml new file mode 100644 index 000000000..bed278a33 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-delete-resources.yaml @@ -0,0 +1,10 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +delete: +- apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-dependency-no-secret +- apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-dependency-no-user diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/README.md b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/README.md new file mode 100644 index 000000000..9d26de6a7 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/README.md @@ -0,0 +1,21 @@ +# Creation and deletion dependencies + +## Step 00 + +Create ApplicationCredentials referencing non-existing resources. Each ApplicationCredential is dependent on other non-existing resource. Verify that the ApplicationCredentials are waiting for the needed resources to be created externally. + +## Step 01 + +Create the missing dependencies and verify all the ApplicationCredentials are available. + +## Step 02 + +Delete all the dependencies and check that ORC prevents deletion since there is still a resource that depends on them. + +## Step 03 + +Delete the ApplicationCredentials and validate that all resources are gone. + +## Reference + +https://k-orc.cloud/development/writing-tests/#dependency diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-assert.yaml new file mode 100644 index 000000000..c9a2e3f75 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-assert.yaml @@ -0,0 +1,17 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-dependency +status: + conditions: + - type: Available + message: |- + Waiting for User/applicationcredential-import-dependency to be ready + status: "False" + reason: Progressing + - type: Progressing + message: |- + Waiting for User/applicationcredential-import-dependency to be ready + status: "True" + reason: Progressing diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-import-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-import-resource.yaml new file mode 100644 index 000000000..8877b2e99 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-import-resource.yaml @@ -0,0 +1,26 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-import-dependency +spec: + cloudCredentialsRef: + cloudName: openstack + secretName: openstack-clouds + managementPolicy: unmanaged + import: + filter: + name: applicationcredential-import-dependency-external +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-dependency +spec: + cloudCredentialsRef: + cloudName: openstack + secretName: openstack-clouds + managementPolicy: unmanaged + import: + filter: + userRef: applicationcredential-import-dependency diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-secret.yaml new file mode 100644 index 000000000..045711ee7 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-secret.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-assert.yaml new file mode 100644 index 000000000..483ed5c58 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-assert.yaml @@ -0,0 +1,32 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-dependency-not-this-one +status: + conditions: + - type: Available + message: OpenStack resource is available + status: "True" + reason: Success + - type: Progressing + message: OpenStack resource is up to date + status: "False" + reason: Success +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-dependency +status: + conditions: + - type: Available + message: |- + Waiting for User/applicationcredential-import-dependency to be ready + status: "False" + reason: Progressing + - type: Progressing + message: |- + Waiting for User/applicationcredential-import-dependency to be ready + status: "True" + reason: Progressing diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-create-trap-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-create-trap-resource.yaml new file mode 100644 index 000000000..d3fc3873a --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-create-trap-resource.yaml @@ -0,0 +1,28 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-import-dependency-not-this-one +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Add the necessary fields to create the resource + resource: {} +--- +# This `applicationcredential-import-dependency-not-this-one` should not be picked by the import filter +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-dependency-not-this-one +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + resource: + userRef: applicationcredential-import-dependency-not-this-one + # TODO(scaffolding): Add the necessary fields to create the resource diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-assert.yaml new file mode 100644 index 000000000..318452565 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-assert.yaml @@ -0,0 +1,34 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestAssert +resourceRefs: + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-import-dependency + ref: applicationcredential1 + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-import-dependency-not-this-one + ref: applicationcredential2 + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: User + name: applicationcredential-import-dependency + ref: user +assertAll: + - celExpr: "applicationcredential1.status.id != applicationcredential2.status.id" + - celExpr: "applicationcredential1.status.resource.userID == user.status.id" +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-dependency +status: + conditions: + - type: Available + message: OpenStack resource is available + status: "True" + reason: Success + - type: Progressing + message: OpenStack resource is up to date + status: "False" + reason: Success diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-create-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-create-resource.yaml new file mode 100644 index 000000000..2f9738f37 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-create-resource.yaml @@ -0,0 +1,27 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-import-dependency-external +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Add the necessary fields to create the resource + resource: {} +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-dependency-external +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + resource: + userRef: applicationcredential-import-dependency-external + # TODO(scaffolding): Add the necessary fields to create the resource diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/03-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/03-assert.yaml new file mode 100644 index 000000000..d74971a73 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/03-assert.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestAssert +commands: +- script: "! kubectl get user.openstack.k-orc.cloud applicationcredential-import-dependency --namespace $NAMESPACE" + skipLogOutput: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/03-delete-import-dependencies.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/03-delete-import-dependencies.yaml new file mode 100644 index 000000000..cc650c8c4 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/03-delete-import-dependencies.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + # We should be able to delete the import dependencies + - command: kubectl delete user.openstack.k-orc.cloud applicationcredential-import-dependency + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/04-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/04-assert.yaml new file mode 100644 index 000000000..4639c46a8 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/04-assert.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestAssert +commands: +- script: "! kubectl get applicationcredential.openstack.k-orc.cloud applicationcredential-import-dependency --namespace $NAMESPACE" + skipLogOutput: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/04-delete-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/04-delete-resource.yaml new file mode 100644 index 000000000..5a0b676bb --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/04-delete-resource.yaml @@ -0,0 +1,7 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +delete: + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-import-dependency diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/README.md b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/README.md new file mode 100644 index 000000000..2be49341d --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/README.md @@ -0,0 +1,29 @@ +# Check dependency handling for imported ApplicationCredential + +## Step 00 + +Import a ApplicationCredential that references other imported resources. The referenced imported resources have no matching resources yet. +Verify the ApplicationCredential is waiting for the dependency to be ready. + +## Step 01 + +Create a ApplicationCredential matching the import filter, except for referenced resources, and verify that it's not being imported. + +## Step 02 + +Create the referenced resources and a ApplicationCredential matching the import filters. + +Verify that the observed status on the imported ApplicationCredential corresponds to the spec of the created ApplicationCredential. + +## Step 03 + +Delete the referenced resources and check that ORC does not prevent deletion. The OpenStack resources still exist because they +were imported resources and we only deleted the ORC representation of it. + +## Step 04 + +Delete the ApplicationCredential and validate that all resources are gone. + +## Reference + +https://k-orc.cloud/development/writing-tests/#import-dependency diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-assert.yaml new file mode 100644 index 000000000..00afbdf41 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-assert.yaml @@ -0,0 +1,30 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-error-external-1 +status: + conditions: + - type: Available + message: OpenStack resource is available + status: "True" + reason: Success + - type: Progressing + message: OpenStack resource is up to date + status: "False" + reason: Success +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-error-external-2 +status: + conditions: + - type: Available + message: OpenStack resource is available + status: "True" + reason: Success + - type: Progressing + message: OpenStack resource is up to date + status: "False" + reason: Success diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-create-resources.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-create-resources.yaml new file mode 100644 index 000000000..611b974e8 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-create-resources.yaml @@ -0,0 +1,43 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-import-error +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Add the necessary fields to create the resource + resource: {} +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-error-external-1 +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + resource: + description: ApplicationCredential from "import error" test + userRef: applicationcredential-import-error + # TODO(scaffolding): add any required field +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-error-external-2 +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + resource: + description: ApplicationCredential from "import error" test + userRef: applicationcredential-import-error + # TODO(scaffolding): add any required field diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-secret.yaml new file mode 100644 index 000000000..045711ee7 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-secret.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-assert.yaml new file mode 100644 index 000000000..e97dd9774 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-assert.yaml @@ -0,0 +1,15 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-error +status: + conditions: + - type: Available + message: found more than one matching OpenStack resource during import + status: "False" + reason: InvalidConfiguration + - type: Progressing + message: found more than one matching OpenStack resource during import + status: "False" + reason: InvalidConfiguration diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-import-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-import-resource.yaml new file mode 100644 index 000000000..e70ca24b4 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-import-resource.yaml @@ -0,0 +1,13 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-error +spec: + cloudCredentialsRef: + cloudName: openstack + secretName: openstack-clouds + managementPolicy: unmanaged + import: + filter: + description: ApplicationCredential from "import error" test diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/README.md b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/README.md new file mode 100644 index 000000000..acd794097 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/README.md @@ -0,0 +1,13 @@ +# Import ApplicationCredential with more than one matching resources + +## Step 00 + +Create two ApplicationCredentials with identical specs. + +## Step 01 + +Ensure that an imported ApplicationCredential with a filter matching the resources returns an error. + +## Reference + +https://k-orc.cloud/development/writing-tests/#import-error diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/00-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/00-assert.yaml new file mode 100644 index 000000000..53ef7ac86 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/00-assert.yaml @@ -0,0 +1,15 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import +status: + conditions: + - type: Available + message: Waiting for OpenStack resource to be created externally + status: "False" + reason: Progressing + - type: Progressing + message: Waiting for OpenStack resource to be created externally + status: "True" + reason: Progressing diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/00-import-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/00-import-resource.yaml new file mode 100644 index 000000000..f000ecfd5 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/00-import-resource.yaml @@ -0,0 +1,15 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import +spec: + cloudCredentialsRef: + cloudName: openstack + secretName: openstack-clouds + managementPolicy: unmanaged + import: + filter: + name: applicationcredential-import-external + description: ApplicationCredential applicationcredential-import-external from "applicationcredential-import" test + # TODO(scaffolding): Add all fields supported by the filter diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/00-secret.yaml new file mode 100644 index 000000000..045711ee7 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/00-secret.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/01-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/01-assert.yaml new file mode 100644 index 000000000..3e0618259 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/01-assert.yaml @@ -0,0 +1,34 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-external-not-this-one +status: + conditions: + - type: Available + message: OpenStack resource is available + status: "True" + reason: Success + - type: Progressing + message: OpenStack resource is up to date + status: "False" + reason: Success + resource: + name: applicationcredential-import-external-not-this-one + description: ApplicationCredential applicationcredential-import-external from "applicationcredential-import" test + # TODO(scaffolding): Add fields necessary to match filter +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import +status: + conditions: + - type: Available + message: Waiting for OpenStack resource to be created externally + status: "False" + reason: Progressing + - type: Progressing + message: Waiting for OpenStack resource to be created externally + status: "True" + reason: Progressing diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/01-create-trap-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/01-create-trap-resource.yaml new file mode 100644 index 000000000..66edf6003 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/01-create-trap-resource.yaml @@ -0,0 +1,31 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-import-external-not-this-one +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Add the necessary fields to create the resource + resource: {} +--- +# This `applicationcredential-import-external-not-this-one` resource serves two purposes: +# - ensure that we can successfully create another resource which name is a substring of it (i.e. it's not being adopted) +# - ensure that importing a resource which name is a substring of it will not pick this one. +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-external-not-this-one +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + resource: + description: ApplicationCredential applicationcredential-import-external from "applicationcredential-import" test + userRef: applicationcredential-import-external-not-this-one + # TODO(scaffolding): Add fields necessary to match filter diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/02-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/02-assert.yaml new file mode 100644 index 000000000..7412f2324 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/02-assert.yaml @@ -0,0 +1,33 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestAssert +resourceRefs: + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-import-external + ref: applicationcredential1 + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-import-external-not-this-one + ref: applicationcredential2 +assertAll: + - celExpr: "applicationcredential1.status.id != applicationcredential2.status.id" +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import +status: + conditions: + - type: Available + message: OpenStack resource is available + status: "True" + reason: Success + - type: Progressing + message: OpenStack resource is up to date + status: "False" + reason: Success + resource: + name: applicationcredential-import-external + description: ApplicationCredential applicationcredential-import-external from "applicationcredential-import" test + # TODO(scaffolding): Add all fields the resource supports diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/02-create-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/02-create-resource.yaml new file mode 100644 index 000000000..c82fab8b5 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/02-create-resource.yaml @@ -0,0 +1,28 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-import +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Add the necessary fields to create the resource + resource: {} +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-import-external +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + resource: + description: ApplicationCredential applicationcredential-import-external from "applicationcredential-import" test + userRef: applicationcredential-import + # TODO(scaffolding): Add fields necessary to match filter diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/README.md b/internal/controllers/applicationcredential/tests/applicationcredential-import/README.md new file mode 100644 index 000000000..36422d1a4 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/README.md @@ -0,0 +1,18 @@ +# Import ApplicationCredential + +## Step 00 + +Import a applicationcredential that matches all fields in the filter, and verify it is waiting for the external resource to be created. + +## Step 01 + +Create a applicationcredential whose name is a superstring of the one specified in the import filter, otherwise matching the filter, and verify that it's not being imported. + +## Step 02 + +Create a applicationcredential matching the filter and verify that the observed status on the imported applicationcredential corresponds to the spec of the created applicationcredential. +Also, confirm that it does not adopt any applicationcredential whose name is a superstring of its own. + +## Reference + +https://k-orc.cloud/development/writing-tests/#import diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/00-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/00-assert.yaml new file mode 100644 index 000000000..fc2cfc9b5 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-update/00-assert.yaml @@ -0,0 +1,26 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestAssert +resourceRefs: + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-update + ref: applicationcredential +assertAll: + - celExpr: "!has(applicationcredential.status.resource.description)" +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-update +status: + resource: + name: applicationcredential-update + # TODO(scaffolding): Add matches for more fields + conditions: + - type: Available + status: "True" + reason: Success + - type: Progressing + status: "False" + reason: Success diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/00-minimal-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/00-minimal-resource.yaml new file mode 100644 index 000000000..b391c1818 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-update/00-minimal-resource.yaml @@ -0,0 +1,28 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-update +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Add the necessary fields to create the resource + resource: {} +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-update +spec: + cloudCredentialsRef: + # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created or updated + cloudName: openstack + secretName: openstack-clouds + managementPolicy: managed + # TODO(scaffolding): Only add the mandatory fields. It's possible the resource + # doesn't have mandatory fields, in that case, leave it empty. + resource: + userRef: applicationcredential-update diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/00-secret.yaml new file mode 100644 index 000000000..045711ee7 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-update/00-secret.yaml @@ -0,0 +1,6 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/01-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/01-assert.yaml new file mode 100644 index 000000000..bb022f746 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-update/01-assert.yaml @@ -0,0 +1,17 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-update +status: + resource: + name: applicationcredential-update-updated + description: applicationcredential-update-updated + # TODO(scaffolding): match all fields that were modified + conditions: + - type: Available + status: "True" + reason: Success + - type: Progressing + status: "False" + reason: Success diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/01-updated-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/01-updated-resource.yaml new file mode 100644 index 000000000..ad1de371a --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-update/01-updated-resource.yaml @@ -0,0 +1,10 @@ +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-update +spec: + resource: + name: applicationcredential-update-updated + description: applicationcredential-update-updated + # TODO(scaffolding): update all mutable fields diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/02-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/02-assert.yaml new file mode 100644 index 000000000..ec6e12d54 --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-update/02-assert.yaml @@ -0,0 +1,26 @@ +--- +apiVersion: kuttl.dev/v1beta1 +kind: TestAssert +resourceRefs: + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-update + ref: applicationcredential +assertAll: + - celExpr: "!has(applicationcredential.status.resource.description)" +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-update +status: + resource: + name: applicationcredential-update + # TODO(scaffolding): validate that updated fields were all reverted to their original value + conditions: + - type: Available + status: "True" + reason: Success + - type: Progressing + status: "False" + reason: Success diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/02-reverted-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/02-reverted-resource.yaml new file mode 100644 index 000000000..2c6c253ff --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-update/02-reverted-resource.yaml @@ -0,0 +1,7 @@ +# NOTE: kuttl only does patch updates, which means we can't delete a field. +# We have to use a kubectl apply command instead. +apiVersion: kuttl.dev/v1beta1 +kind: TestStep +commands: + - command: kubectl replace -f 00-minimal-resource.yaml + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/README.md b/internal/controllers/applicationcredential/tests/applicationcredential-update/README.md new file mode 100644 index 000000000..020723c0e --- /dev/null +++ b/internal/controllers/applicationcredential/tests/applicationcredential-update/README.md @@ -0,0 +1,17 @@ +# Update ApplicationCredential + +## Step 00 + +Create a ApplicationCredential using only mandatory fields. + +## Step 01 + +Update all mutable fields. + +## Step 02 + +Revert the resource to its original value and verify that the resulting object matches its state when first created. + +## Reference + +https://k-orc.cloud/development/writing-tests/#update diff --git a/internal/osclients/applicationcredential.go b/internal/osclients/applicationcredential.go new file mode 100644 index 000000000..1dcda69a9 --- /dev/null +++ b/internal/osclients/applicationcredential.go @@ -0,0 +1,104 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package osclients + +import ( + "context" + "fmt" + "iter" + + "github.com/gophercloud/gophercloud/v2" + "github.com/gophercloud/gophercloud/v2/openstack" + "github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials" + "github.com/gophercloud/utils/v2/openstack/clientconfig" +) + +type ApplicationCredentialClient interface { + ListApplicationCredentials(ctx context.Context, listOpts applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] + CreateApplicationCredential(ctx context.Context, opts applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) + DeleteApplicationCredential(ctx context.Context, resourceID string) error + GetApplicationCredential(ctx context.Context, resourceID string) (*applicationcredentials.ApplicationCredential, error) + UpdateApplicationCredential(ctx context.Context, id string, opts applicationcredentials.UpdateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) +} + +type applicationcredentialClient struct{ client *gophercloud.ServiceClient } + +// NewApplicationCredentialClient returns a new OpenStack client. +func NewApplicationCredentialClient(providerClient *gophercloud.ProviderClient, providerClientOpts *clientconfig.ClientOpts) (ApplicationCredentialClient, error) { + client, err := openstack.NewIdentityV3(providerClient, gophercloud.EndpointOpts{ + Region: providerClientOpts.RegionName, + Availability: clientconfig.GetEndpointType(providerClientOpts.EndpointType), + }) + + if err != nil { + return nil, fmt.Errorf("failed to create applicationcredential service client: %v", err) + } + + return &applicationcredentialClient{client}, nil +} + +func (c applicationcredentialClient) ListApplicationCredentials(ctx context.Context, listOpts applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] { + pager := applicationcredentials.List(c.client, listOpts) + return func(yield func(*applicationcredentials.ApplicationCredential, error) bool) { + _ = pager.EachPage(ctx, yieldPage(applicationcredentials.ExtractApplicationCredentials, yield)) + } +} + +func (c applicationcredentialClient) CreateApplicationCredential(ctx context.Context, opts applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { + return applicationcredentials.Create(ctx, c.client, opts).Extract() +} + +func (c applicationcredentialClient) DeleteApplicationCredential(ctx context.Context, resourceID string) error { + return applicationcredentials.Delete(ctx, c.client, resourceID).ExtractErr() +} + +func (c applicationcredentialClient) GetApplicationCredential(ctx context.Context, resourceID string) (*applicationcredentials.ApplicationCredential, error) { + return applicationcredentials.Get(ctx, c.client, resourceID).Extract() +} + +func (c applicationcredentialClient) UpdateApplicationCredential(ctx context.Context, id string, opts applicationcredentials.UpdateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { + return applicationcredentials.Update(ctx, c.client, id, opts).Extract() +} + +type applicationcredentialErrorClient struct{ error } + +// NewApplicationCredentialErrorClient returns a ApplicationCredentialClient in which every method returns the given error. +func NewApplicationCredentialErrorClient(e error) ApplicationCredentialClient { + return applicationcredentialErrorClient{e} +} + +func (e applicationcredentialErrorClient) ListApplicationCredentials(_ context.Context, _ applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] { + return func(yield func(*applicationcredentials.ApplicationCredential, error) bool) { + yield(nil, e.error) + } +} + +func (e applicationcredentialErrorClient) CreateApplicationCredential(_ context.Context, _ applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { + return nil, e.error +} + +func (e applicationcredentialErrorClient) DeleteApplicationCredential(_ context.Context, _ string) error { + return e.error +} + +func (e applicationcredentialErrorClient) GetApplicationCredential(_ context.Context, _ string) (*applicationcredentials.ApplicationCredential, error) { + return nil, e.error +} + +func (e applicationcredentialErrorClient) UpdateApplicationCredential(_ context.Context, _ string, _ applicationcredentials.UpdateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { + return nil, e.error +} diff --git a/website/docs/crd-reference.md b/website/docs/crd-reference.md index 8d22de9fc..bfbe25d70 100644 --- a/website/docs/crd-reference.md +++ b/website/docs/crd-reference.md @@ -256,6 +256,12 @@ _Appears in:_ | `mac` _string_ | mac contains a MAC address which a server connected to the port can
send packets with. | | MaxLength: 1024
Optional: \{\}
| + + + + + + #### AvailabilityZoneHint _Underlying type:_ _string_ @@ -1915,6 +1921,8 @@ _Appears in:_ - [Address](#address) - [AddressScopeFilter](#addressscopefilter) - [AddressScopeResourceSpec](#addressscoperesourcespec) +- [ApplicationCredentialFilter](#applicationcredentialfilter) +- [ApplicationCredentialResourceSpec](#applicationcredentialresourcespec) - [EndpointFilter](#endpointfilter) - [EndpointResourceSpec](#endpointresourcespec) - [ExternalGateway](#externalgateway) @@ -2330,6 +2338,8 @@ _Validation:_ _Appears in:_ - [AddressScopeFilter](#addressscopefilter) - [AddressScopeResourceSpec](#addressscoperesourcespec) +- [ApplicationCredentialFilter](#applicationcredentialfilter) +- [ApplicationCredentialResourceSpec](#applicationcredentialresourcespec) - [FlavorFilter](#flavorfilter) - [FlavorResourceSpec](#flavorresourcespec) - [ImageFilter](#imagefilter) From f90c3d2dd0c0544fbc0003c5dcc9b35757928fbc Mon Sep 17 00:00:00 2001 From: Gondermann Date: Tue, 10 Mar 2026 16:09:23 +0100 Subject: [PATCH 02/10] Scaffolding for the ApplicationCredential controller Register with the resource generator On-behalf-of: SAP nils.gondermann@sap.com --- PROJECT | 8 + ...enerated.applicationcredential-resource.go | 179 ++++++++++ api/v1alpha1/zz_generated.deepcopy.go | 147 +++++++++ cmd/models-schema/zz_generated.openapi.go | 235 +++++++++++++ cmd/resource-generator/main.go | 3 + ...ck.k-orc.cloud_applicationcredentials.yaml | 311 ++++++++++++++++++ config/crd/kustomization.yaml | 1 + config/samples/kustomization.yaml | 1 + .../zz_generated.adapter.go | 88 +++++ .../zz_generated.controller.go | 45 +++ .../osclients/mock/applicationcredential.go | 131 ++++++++ internal/osclients/mock/doc.go | 3 + kuttl-test.yaml | 1 + .../api/v1alpha1/applicationcredential.go | 281 ++++++++++++++++ .../v1alpha1/applicationcredentialfilter.go | 61 ++++ .../v1alpha1/applicationcredentialimport.go | 48 +++ .../applicationcredentialresourcespec.go | 61 ++++ .../applicationcredentialresourcestatus.go | 57 ++++ .../api/v1alpha1/applicationcredentialspec.go | 79 +++++ .../v1alpha1/applicationcredentialstatus.go | 66 ++++ .../applyconfiguration/internal/internal.go | 102 ++++++ pkg/clients/applyconfiguration/utils.go | 14 + .../typed/api/v1alpha1/api_client.go | 5 + .../api/v1alpha1/applicationcredential.go | 74 +++++ .../api/v1alpha1/fake/fake_api_client.go | 4 + .../fake/fake_applicationcredential.go | 53 +++ .../typed/api/v1alpha1/generated_expansion.go | 2 + .../api/v1alpha1/applicationcredential.go | 102 ++++++ .../api/v1alpha1/interface.go | 7 + .../informers/externalversions/generic.go | 2 + .../api/v1alpha1/applicationcredential.go | 70 ++++ .../api/v1alpha1/expansion_generated.go | 8 + website/docs/crd-reference.md | 130 ++++++++ 33 files changed, 2379 insertions(+) create mode 100644 api/v1alpha1/zz_generated.applicationcredential-resource.go create mode 100644 config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml create mode 100644 internal/controllers/applicationcredential/zz_generated.adapter.go create mode 100644 internal/controllers/applicationcredential/zz_generated.controller.go create mode 100644 internal/osclients/mock/applicationcredential.go create mode 100644 pkg/clients/applyconfiguration/api/v1alpha1/applicationcredential.go create mode 100644 pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialfilter.go create mode 100644 pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialimport.go create mode 100644 pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcespec.go create mode 100644 pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcestatus.go create mode 100644 pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialspec.go create mode 100644 pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialstatus.go create mode 100644 pkg/clients/clientset/clientset/typed/api/v1alpha1/applicationcredential.go create mode 100644 pkg/clients/clientset/clientset/typed/api/v1alpha1/fake/fake_applicationcredential.go create mode 100644 pkg/clients/informers/externalversions/api/v1alpha1/applicationcredential.go create mode 100644 pkg/clients/listers/api/v1alpha1/applicationcredential.go diff --git a/PROJECT b/PROJECT index b3181e74c..73daa42d0 100644 --- a/PROJECT +++ b/PROJECT @@ -16,6 +16,14 @@ resources: kind: AddressScope path: github.com/k-orc/openstack-resource-controller/api/v1alpha1 version: v1alpha1 +- api: + crdVersion: v1 + namespaced: true + domain: k-orc.cloud + group: openstack + kind: ApplicationCredential + path: github.com/k-orc/openstack-resource-controller/api/v1alpha1 + version: v1alpha1 - api: crdVersion: v1 namespaced: true diff --git a/api/v1alpha1/zz_generated.applicationcredential-resource.go b/api/v1alpha1/zz_generated.applicationcredential-resource.go new file mode 100644 index 000000000..d949c84d0 --- /dev/null +++ b/api/v1alpha1/zz_generated.applicationcredential-resource.go @@ -0,0 +1,179 @@ +// Code generated by resource-generator. DO NOT EDIT. +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package v1alpha1 + +import ( + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" +) + +// ApplicationCredentialImport specifies an existing resource which will be imported instead of +// creating a new one +// +kubebuilder:validation:MinProperties:=1 +// +kubebuilder:validation:MaxProperties:=1 +type ApplicationCredentialImport struct { + // id contains the unique identifier of an existing OpenStack resource. Note + // that when specifying an import by ID, the resource MUST already exist. + // The ORC object will enter an error state if the resource does not exist. + // +kubebuilder:validation:Format:=uuid + // +kubebuilder:validation:MaxLength:=36 + // +optional + ID *string `json:"id,omitempty"` //nolint:kubeapilinter + + // filter contains a resource query which is expected to return a single + // result. The controller will continue to retry if filter returns no + // results. If filter returns multiple results the controller will set an + // error state and will not continue to retry. + // +optional + Filter *ApplicationCredentialFilter `json:"filter,omitempty"` +} + +// ApplicationCredentialSpec defines the desired state of an ORC object. +// +kubebuilder:validation:XValidation:rule="self.managementPolicy == 'managed' ? has(self.resource) : true",message="resource must be specified when policy is managed" +// +kubebuilder:validation:XValidation:rule="self.managementPolicy == 'managed' ? !has(self.__import__) : true",message="import may not be specified when policy is managed" +// +kubebuilder:validation:XValidation:rule="self.managementPolicy == 'unmanaged' ? !has(self.resource) : true",message="resource may not be specified when policy is unmanaged" +// +kubebuilder:validation:XValidation:rule="self.managementPolicy == 'unmanaged' ? has(self.__import__) : true",message="import must be specified when policy is unmanaged" +// +kubebuilder:validation:XValidation:rule="has(self.managedOptions) ? self.managementPolicy == 'managed' : true",message="managedOptions may only be provided when policy is managed" +type ApplicationCredentialSpec struct { + // import refers to an existing OpenStack resource which will be imported instead of + // creating a new one. + // +optional + Import *ApplicationCredentialImport `json:"import,omitempty"` + + // resource specifies the desired state of the resource. + // + // resource may not be specified if the management policy is `unmanaged`. + // + // resource must be specified if the management policy is `managed`. + // +optional + Resource *ApplicationCredentialResourceSpec `json:"resource,omitempty"` + + // managementPolicy defines how ORC will treat the object. Valid values are + // `managed`: ORC will create, update, and delete the resource; `unmanaged`: + // ORC will import an existing resource, and will not apply updates to it or + // delete it. + // +kubebuilder:validation:XValidation:rule="self == oldSelf",message="managementPolicy is immutable" + // +kubebuilder:default:=managed + // +optional + ManagementPolicy ManagementPolicy `json:"managementPolicy,omitempty"` + + // managedOptions specifies options which may be applied to managed objects. + // +optional + ManagedOptions *ManagedOptions `json:"managedOptions,omitempty"` + + // cloudCredentialsRef points to a secret containing OpenStack credentials + // +required + CloudCredentialsRef CloudCredentialsReference `json:"cloudCredentialsRef,omitzero"` +} + +// ApplicationCredentialStatus defines the observed state of an ORC resource. +type ApplicationCredentialStatus struct { + // conditions represents the observed status of the object. + // Known .status.conditions.type are: "Available", "Progressing" + // + // Available represents the availability of the OpenStack resource. If it is + // true then the resource is ready for use. + // + // Progressing indicates whether the controller is still attempting to + // reconcile the current state of the OpenStack resource to the desired + // state. Progressing will be False either because the desired state has + // been achieved, or because some terminal error prevents it from ever being + // achieved and the controller is no longer attempting to reconcile. If + // Progressing is True, an observer waiting on the resource should continue + // to wait. + // + // +kubebuilder:validation:MaxItems:=32 + // +patchMergeKey=type + // +patchStrategy=merge + // +listType=map + // +listMapKey=type + // +optional + Conditions []metav1.Condition `json:"conditions,omitempty" patchStrategy:"merge" patchMergeKey:"type"` + + // id is the unique identifier of the OpenStack resource. + // +kubebuilder:validation:MaxLength:=1024 + // +optional + ID *string `json:"id,omitempty"` + + // resource contains the observed state of the OpenStack resource. + // +optional + Resource *ApplicationCredentialResourceStatus `json:"resource,omitempty"` +} + +var _ ObjectWithConditions = &ApplicationCredential{} + +func (i *ApplicationCredential) GetConditions() []metav1.Condition { + return i.Status.Conditions +} + +// +genclient +// +kubebuilder:object:root=true +// +kubebuilder:resource:categories=openstack +// +kubebuilder:subresource:status +// +kubebuilder:printcolumn:name="ID",type="string",JSONPath=".status.id",description="Resource ID" +// +kubebuilder:printcolumn:name="Available",type="string",JSONPath=".status.conditions[?(@.type=='Available')].status",description="Availability status of resource" +// +kubebuilder:printcolumn:name="Message",type="string",JSONPath=".status.conditions[?(@.type=='Progressing')].message",description="Message describing current progress status" + +// ApplicationCredential is the Schema for an ORC resource. +type ApplicationCredential struct { + metav1.TypeMeta `json:",inline"` + + // metadata contains the object metadata + // +optional + metav1.ObjectMeta `json:"metadata,omitempty"` + + // spec specifies the desired state of the resource. + // +required + Spec ApplicationCredentialSpec `json:"spec,omitzero"` + + // status defines the observed state of the resource. + // +optional + Status ApplicationCredentialStatus `json:"status,omitempty"` +} + +// +kubebuilder:object:root=true + +// ApplicationCredentialList contains a list of ApplicationCredential. +type ApplicationCredentialList struct { + metav1.TypeMeta `json:",inline"` + + // metadata contains the list metadata + // +optional + metav1.ListMeta `json:"metadata,omitempty"` + + // items contains a list of ApplicationCredential. + // +required + Items []ApplicationCredential `json:"items"` +} + +func (l *ApplicationCredentialList) GetItems() []ApplicationCredential { + return l.Items +} + +func init() { + SchemeBuilder.Register(&ApplicationCredential{}, &ApplicationCredentialList{}) +} + +func (i *ApplicationCredential) GetCloudCredentialsRef() (*string, *CloudCredentialsReference) { + if i == nil { + return nil, nil + } + + return &i.Namespace, &i.Spec.CloudCredentialsRef +} + +var _ CloudCredentialsRefProvider = &ApplicationCredential{} diff --git a/api/v1alpha1/zz_generated.deepcopy.go b/api/v1alpha1/zz_generated.deepcopy.go index 019340172..91bbfa4e3 100644 --- a/api/v1alpha1/zz_generated.deepcopy.go +++ b/api/v1alpha1/zz_generated.deepcopy.go @@ -337,6 +337,33 @@ func (in *AllowedAddressPairStatus) DeepCopy() *AllowedAddressPairStatus { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ApplicationCredential) DeepCopyInto(out *ApplicationCredential) { + *out = *in + out.TypeMeta = in.TypeMeta + in.ObjectMeta.DeepCopyInto(&out.ObjectMeta) + in.Spec.DeepCopyInto(&out.Spec) + in.Status.DeepCopyInto(&out.Status) +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredential. +func (in *ApplicationCredential) DeepCopy() *ApplicationCredential { + if in == nil { + return nil + } + out := new(ApplicationCredential) + in.DeepCopyInto(out) + return out +} + +// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object. +func (in *ApplicationCredential) DeepCopyObject() runtime.Object { + if c := in.DeepCopy(); c != nil { + return c + } + return nil +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ApplicationCredentialFilter) DeepCopyInto(out *ApplicationCredentialFilter) { *out = *in @@ -367,6 +394,63 @@ func (in *ApplicationCredentialFilter) DeepCopy() *ApplicationCredentialFilter { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ApplicationCredentialImport) DeepCopyInto(out *ApplicationCredentialImport) { + *out = *in + if in.ID != nil { + in, out := &in.ID, &out.ID + *out = new(string) + **out = **in + } + if in.Filter != nil { + in, out := &in.Filter, &out.Filter + *out = new(ApplicationCredentialFilter) + (*in).DeepCopyInto(*out) + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialImport. +func (in *ApplicationCredentialImport) DeepCopy() *ApplicationCredentialImport { + if in == nil { + return nil + } + out := new(ApplicationCredentialImport) + in.DeepCopyInto(out) + return out +} + +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ApplicationCredentialList) DeepCopyInto(out *ApplicationCredentialList) { + *out = *in + out.TypeMeta = in.TypeMeta + in.ListMeta.DeepCopyInto(&out.ListMeta) + if in.Items != nil { + in, out := &in.Items, &out.Items + *out = make([]ApplicationCredential, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialList. +func (in *ApplicationCredentialList) DeepCopy() *ApplicationCredentialList { + if in == nil { + return nil + } + out := new(ApplicationCredentialList) + in.DeepCopyInto(out) + return out +} + +// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object. +func (in *ApplicationCredentialList) DeepCopyObject() runtime.Object { + if c := in.DeepCopy(); c != nil { + return c + } + return nil +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ApplicationCredentialResourceSpec) DeepCopyInto(out *ApplicationCredentialResourceSpec) { *out = *in @@ -407,6 +491,69 @@ func (in *ApplicationCredentialResourceStatus) DeepCopy() *ApplicationCredential return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ApplicationCredentialSpec) DeepCopyInto(out *ApplicationCredentialSpec) { + *out = *in + if in.Import != nil { + in, out := &in.Import, &out.Import + *out = new(ApplicationCredentialImport) + (*in).DeepCopyInto(*out) + } + if in.Resource != nil { + in, out := &in.Resource, &out.Resource + *out = new(ApplicationCredentialResourceSpec) + (*in).DeepCopyInto(*out) + } + if in.ManagedOptions != nil { + in, out := &in.ManagedOptions, &out.ManagedOptions + *out = new(ManagedOptions) + **out = **in + } + out.CloudCredentialsRef = in.CloudCredentialsRef +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialSpec. +func (in *ApplicationCredentialSpec) DeepCopy() *ApplicationCredentialSpec { + if in == nil { + return nil + } + out := new(ApplicationCredentialSpec) + in.DeepCopyInto(out) + return out +} + +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ApplicationCredentialStatus) DeepCopyInto(out *ApplicationCredentialStatus) { + *out = *in + if in.Conditions != nil { + in, out := &in.Conditions, &out.Conditions + *out = make([]v1.Condition, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } + if in.ID != nil { + in, out := &in.ID, &out.ID + *out = new(string) + **out = **in + } + if in.Resource != nil { + in, out := &in.Resource, &out.Resource + *out = new(ApplicationCredentialResourceStatus) + **out = **in + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialStatus. +func (in *ApplicationCredentialStatus) DeepCopy() *ApplicationCredentialStatus { + if in == nil { + return nil + } + out := new(ApplicationCredentialStatus) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *CloudCredentialsReference) DeepCopyInto(out *CloudCredentialsReference) { *out = *in diff --git a/cmd/models-schema/zz_generated.openapi.go b/cmd/models-schema/zz_generated.openapi.go index 33c043d59..e00660aa9 100644 --- a/cmd/models-schema/zz_generated.openapi.go +++ b/cmd/models-schema/zz_generated.openapi.go @@ -43,9 +43,14 @@ func GetOpenAPIDefinitions(ref common.ReferenceCallback) map[string]common.OpenA "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllocationPoolStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AllocationPoolStatus(ref), "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllowedAddressPair": schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPair(ref), "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllowedAddressPairStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPairStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredential": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredential(ref), "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialImport": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialList": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialList(ref), "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialResourceSpec(ref), "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialStatus(ref), "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.CloudCredentialsReference": schema_openstack_resource_controller_v2_api_v1alpha1_CloudCredentialsReference(ref), "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Domain": schema_openstack_resource_controller_v2_api_v1alpha1_Domain(ref), "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainFilter": schema_openstack_resource_controller_v2_api_v1alpha1_DomainFilter(ref), @@ -1041,6 +1046,57 @@ func schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPairStat } } +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredential(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "ApplicationCredential is the Schema for an ORC resource.", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "kind": { + SchemaProps: spec.SchemaProps{ + Description: "Kind is a string value representing the REST resource this object represents. Servers may infer this from the endpoint the client submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds", + Type: []string{"string"}, + Format: "", + }, + }, + "apiVersion": { + SchemaProps: spec.SchemaProps{ + Description: "APIVersion defines the versioned schema of this representation of an object. Servers should convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources", + Type: []string{"string"}, + Format: "", + }, + }, + "metadata": { + SchemaProps: spec.SchemaProps{ + Description: "metadata contains the object metadata", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"), + }, + }, + "spec": { + SchemaProps: spec.SchemaProps{ + Description: "spec specifies the desired state of the resource.", + Default: map[string]interface{}{}, + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialSpec"), + }, + }, + "status": { + SchemaProps: spec.SchemaProps{ + Description: "status defines the observed state of the resource.", + Default: map[string]interface{}{}, + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialStatus"), + }, + }, + }, + Required: []string{"spec"}, + }, + }, + Dependencies: []string{ + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialSpec", "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialStatus", "k8s.io/apimachinery/pkg/apis/meta/v1.ObjectMeta"}, + } +} + func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialFilter(ref common.ReferenceCallback) common.OpenAPIDefinition { return common.OpenAPIDefinition{ Schema: spec.Schema{ @@ -1075,6 +1131,85 @@ func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialF } } +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialImport(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "ApplicationCredentialImport specifies an existing resource which will be imported instead of creating a new one", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "id": { + SchemaProps: spec.SchemaProps{ + Description: "id contains the unique identifier of an existing OpenStack resource. Note that when specifying an import by ID, the resource MUST already exist. The ORC object will enter an error state if the resource does not exist.", + Type: []string{"string"}, + Format: "", + }, + }, + "filter": { + SchemaProps: spec.SchemaProps{ + Description: "filter contains a resource query which is expected to return a single result. The controller will continue to retry if filter returns no results. If filter returns multiple results the controller will set an error state and will not continue to retry.", + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialFilter"), + }, + }, + }, + }, + }, + Dependencies: []string{ + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialFilter"}, + } +} + +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialList(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "ApplicationCredentialList contains a list of ApplicationCredential.", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "kind": { + SchemaProps: spec.SchemaProps{ + Description: "Kind is a string value representing the REST resource this object represents. Servers may infer this from the endpoint the client submits requests to. Cannot be updated. In CamelCase. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds", + Type: []string{"string"}, + Format: "", + }, + }, + "apiVersion": { + SchemaProps: spec.SchemaProps{ + Description: "APIVersion defines the versioned schema of this representation of an object. Servers should convert recognized schemas to the latest internal value, and may reject unrecognized values. More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources", + Type: []string{"string"}, + Format: "", + }, + }, + "metadata": { + SchemaProps: spec.SchemaProps{ + Description: "metadata contains the list metadata", + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"), + }, + }, + "items": { + SchemaProps: spec.SchemaProps{ + Description: "items contains a list of ApplicationCredential.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredential"), + }, + }, + }, + }, + }, + }, + Required: []string{"items"}, + }, + }, + Dependencies: []string{ + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredential", "k8s.io/apimachinery/pkg/apis/meta/v1.ListMeta"}, + } +} + func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialResourceSpec(ref common.ReferenceCallback) common.OpenAPIDefinition { return common.OpenAPIDefinition{ Schema: spec.Schema{ @@ -1144,6 +1279,106 @@ func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialR } } +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialSpec(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "ApplicationCredentialSpec defines the desired state of an ORC object.", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "import": { + SchemaProps: spec.SchemaProps{ + Description: "import refers to an existing OpenStack resource which will be imported instead of creating a new one.", + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialImport"), + }, + }, + "resource": { + SchemaProps: spec.SchemaProps{ + Description: "resource specifies the desired state of the resource.\n\nresource may not be specified if the management policy is `unmanaged`.\n\nresource must be specified if the management policy is `managed`.", + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceSpec"), + }, + }, + "managementPolicy": { + SchemaProps: spec.SchemaProps{ + Description: "managementPolicy defines how ORC will treat the object. Valid values are `managed`: ORC will create, update, and delete the resource; `unmanaged`: ORC will import an existing resource, and will not apply updates to it or delete it.", + Type: []string{"string"}, + Format: "", + }, + }, + "managedOptions": { + SchemaProps: spec.SchemaProps{ + Description: "managedOptions specifies options which may be applied to managed objects.", + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ManagedOptions"), + }, + }, + "cloudCredentialsRef": { + SchemaProps: spec.SchemaProps{ + Description: "cloudCredentialsRef points to a secret containing OpenStack credentials", + Default: map[string]interface{}{}, + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.CloudCredentialsReference"), + }, + }, + }, + Required: []string{"cloudCredentialsRef"}, + }, + }, + Dependencies: []string{ + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialImport", "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceSpec", "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.CloudCredentialsReference", "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ManagedOptions"}, + } +} + +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialStatus(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "ApplicationCredentialStatus defines the observed state of an ORC resource.", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "conditions": { + VendorExtensible: spec.VendorExtensible{ + Extensions: spec.Extensions{ + "x-kubernetes-list-map-keys": []interface{}{ + "type", + }, + "x-kubernetes-list-type": "map", + "x-kubernetes-patch-merge-key": "type", + "x-kubernetes-patch-strategy": "merge", + }, + }, + SchemaProps: spec.SchemaProps{ + Description: "conditions represents the observed status of the object. Known .status.conditions.type are: \"Available\", \"Progressing\"\n\nAvailable represents the availability of the OpenStack resource. If it is true then the resource is ready for use.\n\nProgressing indicates whether the controller is still attempting to reconcile the current state of the OpenStack resource to the desired state. Progressing will be False either because the desired state has been achieved, or because some terminal error prevents it from ever being achieved and the controller is no longer attempting to reconcile. If Progressing is True, an observer waiting on the resource should continue to wait.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.Condition"), + }, + }, + }, + }, + }, + "id": { + SchemaProps: spec.SchemaProps{ + Description: "id is the unique identifier of the OpenStack resource.", + Type: []string{"string"}, + Format: "", + }, + }, + "resource": { + SchemaProps: spec.SchemaProps{ + Description: "resource contains the observed state of the OpenStack resource.", + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceStatus"), + }, + }, + }, + }, + }, + Dependencies: []string{ + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceStatus", "k8s.io/apimachinery/pkg/apis/meta/v1.Condition"}, + } +} + func schema_openstack_resource_controller_v2_api_v1alpha1_CloudCredentialsReference(ref common.ReferenceCallback) common.OpenAPIDefinition { return common.OpenAPIDefinition{ Schema: spec.Schema{ diff --git a/cmd/resource-generator/main.go b/cmd/resource-generator/main.go index 37c577523..2ff83df6e 100644 --- a/cmd/resource-generator/main.go +++ b/cmd/resource-generator/main.go @@ -174,6 +174,9 @@ var resources []templateFields = []templateFields{ { Name: "AddressScope", }, + { + Name: "ApplicationCredential", + }, } // These resources won't be generated diff --git a/config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml b/config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml new file mode 100644 index 000000000..449790ab8 --- /dev/null +++ b/config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml @@ -0,0 +1,311 @@ +--- +apiVersion: apiextensions.k8s.io/v1 +kind: CustomResourceDefinition +metadata: + annotations: + controller-gen.kubebuilder.io/version: v0.17.1 + name: applicationcredentials.openstack.k-orc.cloud +spec: + group: openstack.k-orc.cloud + names: + categories: + - openstack + kind: ApplicationCredential + listKind: ApplicationCredentialList + plural: applicationcredentials + singular: applicationcredential + scope: Namespaced + versions: + - additionalPrinterColumns: + - description: Resource ID + jsonPath: .status.id + name: ID + type: string + - description: Availability status of resource + jsonPath: .status.conditions[?(@.type=='Available')].status + name: Available + type: string + - description: Message describing current progress status + jsonPath: .status.conditions[?(@.type=='Progressing')].message + name: Message + type: string + name: v1alpha1 + schema: + openAPIV3Schema: + description: ApplicationCredential is the Schema for an ORC resource. + properties: + apiVersion: + description: |- + APIVersion defines the versioned schema of this representation of an object. + Servers should convert recognized schemas to the latest internal value, and + may reject unrecognized values. + More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#resources + type: string + kind: + description: |- + Kind is a string value representing the REST resource this object represents. + Servers may infer this from the endpoint the client submits requests to. + Cannot be updated. + In CamelCase. + More info: https://git.k8s.io/community/contributors/devel/sig-architecture/api-conventions.md#types-kinds + type: string + metadata: + type: object + spec: + description: spec specifies the desired state of the resource. + properties: + cloudCredentialsRef: + description: cloudCredentialsRef points to a secret containing OpenStack + credentials + properties: + cloudName: + description: cloudName specifies the name of the entry in the + clouds.yaml file to use. + maxLength: 256 + minLength: 1 + type: string + secretName: + description: |- + secretName is the name of a secret in the same namespace as the resource being provisioned. + The secret must contain a key named `clouds.yaml` which contains an OpenStack clouds.yaml file. + The secret may optionally contain a key named `cacert` containing a PEM-encoded CA certificate. + maxLength: 253 + minLength: 1 + type: string + required: + - cloudName + - secretName + type: object + import: + description: |- + import refers to an existing OpenStack resource which will be imported instead of + creating a new one. + maxProperties: 1 + minProperties: 1 + properties: + filter: + description: |- + filter contains a resource query which is expected to return a single + result. The controller will continue to retry if filter returns no + results. If filter returns multiple results the controller will set an + error state and will not continue to retry. + minProperties: 1 + properties: + description: + description: description of the existing resource + maxLength: 255 + minLength: 1 + type: string + name: + description: name of the existing resource + maxLength: 255 + minLength: 1 + pattern: ^[^,]+$ + type: string + userRef: + description: userRef is a reference to the ORC User which + this resource is associated with. + maxLength: 253 + minLength: 1 + type: string + type: object + id: + description: |- + id contains the unique identifier of an existing OpenStack resource. Note + that when specifying an import by ID, the resource MUST already exist. + The ORC object will enter an error state if the resource does not exist. + format: uuid + maxLength: 36 + type: string + type: object + managedOptions: + description: managedOptions specifies options which may be applied + to managed objects. + properties: + onDelete: + default: delete + description: |- + onDelete specifies the behaviour of the controller when the ORC + object is deleted. Options are `delete` - delete the OpenStack resource; + `detach` - do not delete the OpenStack resource. If not specified, the + default is `delete`. + enum: + - delete + - detach + type: string + type: object + managementPolicy: + default: managed + description: |- + managementPolicy defines how ORC will treat the object. Valid values are + `managed`: ORC will create, update, and delete the resource; `unmanaged`: + ORC will import an existing resource, and will not apply updates to it or + delete it. + enum: + - managed + - unmanaged + type: string + x-kubernetes-validations: + - message: managementPolicy is immutable + rule: self == oldSelf + resource: + description: |- + resource specifies the desired state of the resource. + + resource may not be specified if the management policy is `unmanaged`. + + resource must be specified if the management policy is `managed`. + properties: + description: + description: description is a human-readable description for the + resource. + maxLength: 255 + minLength: 1 + type: string + name: + description: |- + name will be the name of the created resource. If not specified, the + name of the ORC object will be used. + maxLength: 255 + minLength: 1 + pattern: ^[^,]+$ + type: string + userRef: + description: userRef is a reference to the ORC User which this + resource is associated with. + maxLength: 253 + minLength: 1 + type: string + x-kubernetes-validations: + - message: userRef is immutable + rule: self == oldSelf + required: + - userRef + type: object + required: + - cloudCredentialsRef + type: object + x-kubernetes-validations: + - message: resource must be specified when policy is managed + rule: 'self.managementPolicy == ''managed'' ? has(self.resource) : true' + - message: import may not be specified when policy is managed + rule: 'self.managementPolicy == ''managed'' ? !has(self.__import__) + : true' + - message: resource may not be specified when policy is unmanaged + rule: 'self.managementPolicy == ''unmanaged'' ? !has(self.resource) + : true' + - message: import must be specified when policy is unmanaged + rule: 'self.managementPolicy == ''unmanaged'' ? has(self.__import__) + : true' + - message: managedOptions may only be provided when policy is managed + rule: 'has(self.managedOptions) ? self.managementPolicy == ''managed'' + : true' + status: + description: status defines the observed state of the resource. + properties: + conditions: + description: |- + conditions represents the observed status of the object. + Known .status.conditions.type are: "Available", "Progressing" + + Available represents the availability of the OpenStack resource. If it is + true then the resource is ready for use. + + Progressing indicates whether the controller is still attempting to + reconcile the current state of the OpenStack resource to the desired + state. Progressing will be False either because the desired state has + been achieved, or because some terminal error prevents it from ever being + achieved and the controller is no longer attempting to reconcile. If + Progressing is True, an observer waiting on the resource should continue + to wait. + items: + description: Condition contains details for one aspect of the current + state of this API Resource. + properties: + lastTransitionTime: + description: |- + lastTransitionTime is the last time the condition transitioned from one status to another. + This should be when the underlying condition changed. If that is not known, then using the time when the API field changed is acceptable. + format: date-time + type: string + message: + description: |- + message is a human readable message indicating details about the transition. + This may be an empty string. + maxLength: 32768 + type: string + observedGeneration: + description: |- + observedGeneration represents the .metadata.generation that the condition was set based upon. + For instance, if .metadata.generation is currently 12, but the .status.conditions[x].observedGeneration is 9, the condition is out of date + with respect to the current state of the instance. + format: int64 + minimum: 0 + type: integer + reason: + description: |- + reason contains a programmatic identifier indicating the reason for the condition's last transition. + Producers of specific condition types may define expected values and meanings for this field, + and whether the values are considered a guaranteed API. + The value should be a CamelCase string. + This field may not be empty. + maxLength: 1024 + minLength: 1 + pattern: ^[A-Za-z]([A-Za-z0-9_,:]*[A-Za-z0-9_])?$ + type: string + status: + description: status of the condition, one of True, False, Unknown. + enum: + - "True" + - "False" + - Unknown + type: string + type: + description: type of condition in CamelCase or in foo.example.com/CamelCase. + maxLength: 316 + pattern: ^([a-z0-9]([-a-z0-9]*[a-z0-9])?(\.[a-z0-9]([-a-z0-9]*[a-z0-9])?)*/)?(([A-Za-z0-9][-A-Za-z0-9_.]*)?[A-Za-z0-9])$ + type: string + required: + - lastTransitionTime + - message + - reason + - status + - type + type: object + maxItems: 32 + type: array + x-kubernetes-list-map-keys: + - type + x-kubernetes-list-type: map + id: + description: id is the unique identifier of the OpenStack resource. + maxLength: 1024 + type: string + resource: + description: resource contains the observed state of the OpenStack + resource. + properties: + description: + description: description is a human-readable description for the + resource. + maxLength: 1024 + type: string + name: + description: name is a Human-readable name for the resource. Might + not be unique. + maxLength: 1024 + type: string + userID: + description: userID is the ID of the User to which the resource + is associated. + maxLength: 1024 + type: string + type: object + type: object + required: + - spec + type: object + served: true + storage: true + subresources: + status: {} diff --git a/config/crd/kustomization.yaml b/config/crd/kustomization.yaml index 592ed3b14..85a318b42 100644 --- a/config/crd/kustomization.yaml +++ b/config/crd/kustomization.yaml @@ -4,6 +4,7 @@ # It should be run by config/default resources: - bases/openstack.k-orc.cloud_addressscopes.yaml +- bases/openstack.k-orc.cloud_applicationcredentials.yaml - bases/openstack.k-orc.cloud_domains.yaml - bases/openstack.k-orc.cloud_endpoints.yaml - bases/openstack.k-orc.cloud_flavors.yaml diff --git a/config/samples/kustomization.yaml b/config/samples/kustomization.yaml index eb819d448..4b86755db 100644 --- a/config/samples/kustomization.yaml +++ b/config/samples/kustomization.yaml @@ -2,6 +2,7 @@ ## Append samples of your project ## resources: - openstack_v1alpha1_addressscope.yaml +- openstack_v1alpha1_applicationcredential.yaml - openstack_v1alpha1_domain.yaml - openstack_v1alpha1_endpoint.yaml - openstack_v1alpha1_flavor.yaml diff --git a/internal/controllers/applicationcredential/zz_generated.adapter.go b/internal/controllers/applicationcredential/zz_generated.adapter.go new file mode 100644 index 000000000..55f0b5346 --- /dev/null +++ b/internal/controllers/applicationcredential/zz_generated.adapter.go @@ -0,0 +1,88 @@ +// Code generated by resource-generator. DO NOT EDIT. +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package applicationcredential + +import ( + orcv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" + "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/generic/interfaces" +) + +// Fundamental types +type ( + orcObjectT = orcv1alpha1.ApplicationCredential + orcObjectListT = orcv1alpha1.ApplicationCredentialList + resourceSpecT = orcv1alpha1.ApplicationCredentialResourceSpec + filterT = orcv1alpha1.ApplicationCredentialFilter +) + +// Derived types +type ( + orcObjectPT = *orcObjectT + adapterI = interfaces.APIObjectAdapter[orcObjectPT, resourceSpecT, filterT] + adapterT = applicationcredentialAdapter +) + +type applicationcredentialAdapter struct { + *orcv1alpha1.ApplicationCredential +} + +var _ adapterI = &adapterT{} + +func (f adapterT) GetObject() orcObjectPT { + return f.ApplicationCredential +} + +func (f adapterT) GetManagementPolicy() orcv1alpha1.ManagementPolicy { + return f.Spec.ManagementPolicy +} + +func (f adapterT) GetManagedOptions() *orcv1alpha1.ManagedOptions { + return f.Spec.ManagedOptions +} + +func (f adapterT) GetStatusID() *string { + return f.Status.ID +} + +func (f adapterT) GetResourceSpec() *resourceSpecT { + return f.Spec.Resource +} + +func (f adapterT) GetImportID() *string { + if f.Spec.Import == nil { + return nil + } + return f.Spec.Import.ID +} + +func (f adapterT) GetImportFilter() *filterT { + if f.Spec.Import == nil { + return nil + } + return f.Spec.Import.Filter +} + +// getResourceName returns the name of the OpenStack resource we should use. +// This method is not implemented as part of APIObjectAdapter as it is intended +// to be used by resource actuators, which don't use the adapter. +func getResourceName(orcObject orcObjectPT) string { + if orcObject.Spec.Resource.Name != nil { + return string(*orcObject.Spec.Resource.Name) + } + return orcObject.Name +} diff --git a/internal/controllers/applicationcredential/zz_generated.controller.go b/internal/controllers/applicationcredential/zz_generated.controller.go new file mode 100644 index 000000000..09ae74111 --- /dev/null +++ b/internal/controllers/applicationcredential/zz_generated.controller.go @@ -0,0 +1,45 @@ +// Code generated by resource-generator. DO NOT EDIT. +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +package applicationcredential + +import ( + corev1 "k8s.io/api/core/v1" + + "github.com/k-orc/openstack-resource-controller/v2/internal/util/dependency" + orcstrings "github.com/k-orc/openstack-resource-controller/v2/internal/util/strings" +) + +var ( + // NOTE: controllerName must be defined in any controller using this template + + // finalizer is the string this controller adds to an object's Finalizers + finalizer = orcstrings.GetFinalizerName(controllerName) + + // externalObjectFieldOwner is the field owner we use when using + // server-side-apply on objects we don't control + externalObjectFieldOwner = orcstrings.GetSSAFieldOwner(controllerName) + + credentialsDependency = dependency.NewDeletionGuardDependency[*orcObjectListT, *corev1.Secret]( + "spec.cloudCredentialsRef.secretName", + func(obj orcObjectPT) []string { + return []string{obj.Spec.CloudCredentialsRef.SecretName} + }, + finalizer, externalObjectFieldOwner, + dependency.OverrideDependencyName("credentials"), + ) +) diff --git a/internal/osclients/mock/applicationcredential.go b/internal/osclients/mock/applicationcredential.go new file mode 100644 index 000000000..194a49a2f --- /dev/null +++ b/internal/osclients/mock/applicationcredential.go @@ -0,0 +1,131 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ +// Code generated by MockGen. DO NOT EDIT. +// Source: ../applicationcredential.go +// +// Generated by this command: +// +// mockgen -package mock -destination=applicationcredential.go -source=../applicationcredential.go github.com/k-orc/openstack-resource-controller/internal/osclients/mock ApplicationCredentialClient +// + +// Package mock is a generated GoMock package. +package mock + +import ( + context "context" + iter "iter" + reflect "reflect" + + applicationcredentials "github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials" + gomock "go.uber.org/mock/gomock" +) + +// MockApplicationCredentialClient is a mock of ApplicationCredentialClient interface. +type MockApplicationCredentialClient struct { + ctrl *gomock.Controller + recorder *MockApplicationCredentialClientMockRecorder + isgomock struct{} +} + +// MockApplicationCredentialClientMockRecorder is the mock recorder for MockApplicationCredentialClient. +type MockApplicationCredentialClientMockRecorder struct { + mock *MockApplicationCredentialClient +} + +// NewMockApplicationCredentialClient creates a new mock instance. +func NewMockApplicationCredentialClient(ctrl *gomock.Controller) *MockApplicationCredentialClient { + mock := &MockApplicationCredentialClient{ctrl: ctrl} + mock.recorder = &MockApplicationCredentialClientMockRecorder{mock} + return mock +} + +// EXPECT returns an object that allows the caller to indicate expected use. +func (m *MockApplicationCredentialClient) EXPECT() *MockApplicationCredentialClientMockRecorder { + return m.recorder +} + +// CreateApplicationCredential mocks base method. +func (m *MockApplicationCredentialClient) CreateApplicationCredential(ctx context.Context, opts applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "CreateApplicationCredential", ctx, opts) + ret0, _ := ret[0].(*applicationcredentials.ApplicationCredential) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// CreateApplicationCredential indicates an expected call of CreateApplicationCredential. +func (mr *MockApplicationCredentialClientMockRecorder) CreateApplicationCredential(ctx, opts any) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateApplicationCredential", reflect.TypeOf((*MockApplicationCredentialClient)(nil).CreateApplicationCredential), ctx, opts) +} + +// DeleteApplicationCredential mocks base method. +func (m *MockApplicationCredentialClient) DeleteApplicationCredential(ctx context.Context, resourceID string) error { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "DeleteApplicationCredential", ctx, resourceID) + ret0, _ := ret[0].(error) + return ret0 +} + +// DeleteApplicationCredential indicates an expected call of DeleteApplicationCredential. +func (mr *MockApplicationCredentialClientMockRecorder) DeleteApplicationCredential(ctx, resourceID any) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DeleteApplicationCredential", reflect.TypeOf((*MockApplicationCredentialClient)(nil).DeleteApplicationCredential), ctx, resourceID) +} + +// GetApplicationCredential mocks base method. +func (m *MockApplicationCredentialClient) GetApplicationCredential(ctx context.Context, resourceID string) (*applicationcredentials.ApplicationCredential, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "GetApplicationCredential", ctx, resourceID) + ret0, _ := ret[0].(*applicationcredentials.ApplicationCredential) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// GetApplicationCredential indicates an expected call of GetApplicationCredential. +func (mr *MockApplicationCredentialClientMockRecorder) GetApplicationCredential(ctx, resourceID any) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetApplicationCredential", reflect.TypeOf((*MockApplicationCredentialClient)(nil).GetApplicationCredential), ctx, resourceID) +} + +// ListApplicationCredentials mocks base method. +func (m *MockApplicationCredentialClient) ListApplicationCredentials(ctx context.Context, listOpts applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "ListApplicationCredentials", ctx, listOpts) + ret0, _ := ret[0].(iter.Seq2[*applicationcredentials.ApplicationCredential, error]) + return ret0 +} + +// ListApplicationCredentials indicates an expected call of ListApplicationCredentials. +func (mr *MockApplicationCredentialClientMockRecorder) ListApplicationCredentials(ctx, listOpts any) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "ListApplicationCredentials", reflect.TypeOf((*MockApplicationCredentialClient)(nil).ListApplicationCredentials), ctx, listOpts) +} + +// UpdateApplicationCredential mocks base method. +func (m *MockApplicationCredentialClient) UpdateApplicationCredential(ctx context.Context, id string, opts applicationcredentials.UpdateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "UpdateApplicationCredential", ctx, id, opts) + ret0, _ := ret[0].(*applicationcredentials.ApplicationCredential) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// UpdateApplicationCredential indicates an expected call of UpdateApplicationCredential. +func (mr *MockApplicationCredentialClientMockRecorder) UpdateApplicationCredential(ctx, id, opts any) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateApplicationCredential", reflect.TypeOf((*MockApplicationCredentialClient)(nil).UpdateApplicationCredential), ctx, id, opts) +} diff --git a/internal/osclients/mock/doc.go b/internal/osclients/mock/doc.go index 71870a3a7..766500c8f 100644 --- a/internal/osclients/mock/doc.go +++ b/internal/osclients/mock/doc.go @@ -38,6 +38,9 @@ import ( //go:generate mockgen -package mock -destination=addressscope.go -source=../addressscope.go github.com/k-orc/openstack-resource-controller/internal/osclients/mock AddressScopeClient //go:generate /usr/bin/env bash -c "cat ../../../hack/boilerplate.go.txt addressscope.go > _addressscope.go && mv _addressscope.go addressscope.go" +//go:generate mockgen -package mock -destination=applicationcredential.go -source=../applicationcredential.go github.com/k-orc/openstack-resource-controller/internal/osclients/mock ApplicationCredentialClient +//go:generate /usr/bin/env bash -c "cat ../../../hack/boilerplate.go.txt applicationcredential.go > _applicationcredential.go && mv _applicationcredential.go applicationcredential.go" + //go:generate mockgen -package mock -destination=domain.go -source=../domain.go github.com/k-orc/openstack-resource-controller/internal/osclients/mock DomainClient //go:generate /usr/bin/env bash -c "cat ../../../hack/boilerplate.go.txt domain.go > _domain.go && mv _domain.go domain.go" diff --git a/kuttl-test.yaml b/kuttl-test.yaml index a6384f50d..d58526493 100644 --- a/kuttl-test.yaml +++ b/kuttl-test.yaml @@ -3,6 +3,7 @@ apiVersion: kuttl.dev/v1beta1 kind: TestSuite testDirs: - ./internal/controllers/addressscope/tests/ +- ./internal/controllers/applicationcredential/tests/ - ./internal/controllers/domain/tests/ - ./internal/controllers/endpoint/tests/ - ./internal/controllers/flavor/tests/ diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredential.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredential.go new file mode 100644 index 000000000..db5eb36e8 --- /dev/null +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredential.go @@ -0,0 +1,281 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by applyconfiguration-gen. DO NOT EDIT. + +package v1alpha1 + +import ( + apiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" + internal "github.com/k-orc/openstack-resource-controller/v2/pkg/clients/applyconfiguration/internal" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + types "k8s.io/apimachinery/pkg/types" + managedfields "k8s.io/apimachinery/pkg/util/managedfields" + v1 "k8s.io/client-go/applyconfigurations/meta/v1" +) + +// ApplicationCredentialApplyConfiguration represents a declarative configuration of the ApplicationCredential type for use +// with apply. +type ApplicationCredentialApplyConfiguration struct { + v1.TypeMetaApplyConfiguration `json:",inline"` + *v1.ObjectMetaApplyConfiguration `json:"metadata,omitempty"` + Spec *ApplicationCredentialSpecApplyConfiguration `json:"spec,omitempty"` + Status *ApplicationCredentialStatusApplyConfiguration `json:"status,omitempty"` +} + +// ApplicationCredential constructs a declarative configuration of the ApplicationCredential type for use with +// apply. +func ApplicationCredential(name, namespace string) *ApplicationCredentialApplyConfiguration { + b := &ApplicationCredentialApplyConfiguration{} + b.WithName(name) + b.WithNamespace(namespace) + b.WithKind("ApplicationCredential") + b.WithAPIVersion("openstack.k-orc.cloud/v1alpha1") + return b +} + +// ExtractApplicationCredential extracts the applied configuration owned by fieldManager from +// applicationCredential. If no managedFields are found in applicationCredential for fieldManager, a +// ApplicationCredentialApplyConfiguration is returned with only the Name, Namespace (if applicable), +// APIVersion and Kind populated. It is possible that no managed fields were found for because other +// field managers have taken ownership of all the fields previously owned by fieldManager, or because +// the fieldManager never owned fields any fields. +// applicationCredential must be a unmodified ApplicationCredential API object that was retrieved from the Kubernetes API. +// ExtractApplicationCredential provides a way to perform a extract/modify-in-place/apply workflow. +// Note that an extracted apply configuration will contain fewer fields than what the fieldManager previously +// applied if another fieldManager has updated or force applied any of the previously applied fields. +// Experimental! +func ExtractApplicationCredential(applicationCredential *apiv1alpha1.ApplicationCredential, fieldManager string) (*ApplicationCredentialApplyConfiguration, error) { + return extractApplicationCredential(applicationCredential, fieldManager, "") +} + +// ExtractApplicationCredentialStatus is the same as ExtractApplicationCredential except +// that it extracts the status subresource applied configuration. +// Experimental! +func ExtractApplicationCredentialStatus(applicationCredential *apiv1alpha1.ApplicationCredential, fieldManager string) (*ApplicationCredentialApplyConfiguration, error) { + return extractApplicationCredential(applicationCredential, fieldManager, "status") +} + +func extractApplicationCredential(applicationCredential *apiv1alpha1.ApplicationCredential, fieldManager string, subresource string) (*ApplicationCredentialApplyConfiguration, error) { + b := &ApplicationCredentialApplyConfiguration{} + err := managedfields.ExtractInto(applicationCredential, internal.Parser().Type("com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredential"), fieldManager, b, subresource) + if err != nil { + return nil, err + } + b.WithName(applicationCredential.Name) + b.WithNamespace(applicationCredential.Namespace) + + b.WithKind("ApplicationCredential") + b.WithAPIVersion("openstack.k-orc.cloud/v1alpha1") + return b, nil +} +func (b ApplicationCredentialApplyConfiguration) IsApplyConfiguration() {} + +// WithKind sets the Kind field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Kind field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithKind(value string) *ApplicationCredentialApplyConfiguration { + b.TypeMetaApplyConfiguration.Kind = &value + return b +} + +// WithAPIVersion sets the APIVersion field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the APIVersion field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithAPIVersion(value string) *ApplicationCredentialApplyConfiguration { + b.TypeMetaApplyConfiguration.APIVersion = &value + return b +} + +// WithName sets the Name field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Name field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithName(value string) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + b.ObjectMetaApplyConfiguration.Name = &value + return b +} + +// WithGenerateName sets the GenerateName field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the GenerateName field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithGenerateName(value string) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + b.ObjectMetaApplyConfiguration.GenerateName = &value + return b +} + +// WithNamespace sets the Namespace field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Namespace field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithNamespace(value string) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + b.ObjectMetaApplyConfiguration.Namespace = &value + return b +} + +// WithUID sets the UID field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the UID field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithUID(value types.UID) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + b.ObjectMetaApplyConfiguration.UID = &value + return b +} + +// WithResourceVersion sets the ResourceVersion field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the ResourceVersion field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithResourceVersion(value string) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + b.ObjectMetaApplyConfiguration.ResourceVersion = &value + return b +} + +// WithGeneration sets the Generation field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Generation field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithGeneration(value int64) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + b.ObjectMetaApplyConfiguration.Generation = &value + return b +} + +// WithCreationTimestamp sets the CreationTimestamp field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the CreationTimestamp field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithCreationTimestamp(value metav1.Time) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + b.ObjectMetaApplyConfiguration.CreationTimestamp = &value + return b +} + +// WithDeletionTimestamp sets the DeletionTimestamp field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the DeletionTimestamp field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithDeletionTimestamp(value metav1.Time) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + b.ObjectMetaApplyConfiguration.DeletionTimestamp = &value + return b +} + +// WithDeletionGracePeriodSeconds sets the DeletionGracePeriodSeconds field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the DeletionGracePeriodSeconds field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithDeletionGracePeriodSeconds(value int64) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + b.ObjectMetaApplyConfiguration.DeletionGracePeriodSeconds = &value + return b +} + +// WithLabels puts the entries into the Labels field in the declarative configuration +// and returns the receiver, so that objects can be build by chaining "With" function invocations. +// If called multiple times, the entries provided by each call will be put on the Labels field, +// overwriting an existing map entries in Labels field with the same key. +func (b *ApplicationCredentialApplyConfiguration) WithLabels(entries map[string]string) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + if b.ObjectMetaApplyConfiguration.Labels == nil && len(entries) > 0 { + b.ObjectMetaApplyConfiguration.Labels = make(map[string]string, len(entries)) + } + for k, v := range entries { + b.ObjectMetaApplyConfiguration.Labels[k] = v + } + return b +} + +// WithAnnotations puts the entries into the Annotations field in the declarative configuration +// and returns the receiver, so that objects can be build by chaining "With" function invocations. +// If called multiple times, the entries provided by each call will be put on the Annotations field, +// overwriting an existing map entries in Annotations field with the same key. +func (b *ApplicationCredentialApplyConfiguration) WithAnnotations(entries map[string]string) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + if b.ObjectMetaApplyConfiguration.Annotations == nil && len(entries) > 0 { + b.ObjectMetaApplyConfiguration.Annotations = make(map[string]string, len(entries)) + } + for k, v := range entries { + b.ObjectMetaApplyConfiguration.Annotations[k] = v + } + return b +} + +// WithOwnerReferences adds the given value to the OwnerReferences field in the declarative configuration +// and returns the receiver, so that objects can be build by chaining "With" function invocations. +// If called multiple times, values provided by each call will be appended to the OwnerReferences field. +func (b *ApplicationCredentialApplyConfiguration) WithOwnerReferences(values ...*v1.OwnerReferenceApplyConfiguration) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + for i := range values { + if values[i] == nil { + panic("nil value passed to WithOwnerReferences") + } + b.ObjectMetaApplyConfiguration.OwnerReferences = append(b.ObjectMetaApplyConfiguration.OwnerReferences, *values[i]) + } + return b +} + +// WithFinalizers adds the given value to the Finalizers field in the declarative configuration +// and returns the receiver, so that objects can be build by chaining "With" function invocations. +// If called multiple times, values provided by each call will be appended to the Finalizers field. +func (b *ApplicationCredentialApplyConfiguration) WithFinalizers(values ...string) *ApplicationCredentialApplyConfiguration { + b.ensureObjectMetaApplyConfigurationExists() + for i := range values { + b.ObjectMetaApplyConfiguration.Finalizers = append(b.ObjectMetaApplyConfiguration.Finalizers, values[i]) + } + return b +} + +func (b *ApplicationCredentialApplyConfiguration) ensureObjectMetaApplyConfigurationExists() { + if b.ObjectMetaApplyConfiguration == nil { + b.ObjectMetaApplyConfiguration = &v1.ObjectMetaApplyConfiguration{} + } +} + +// WithSpec sets the Spec field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Spec field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithSpec(value *ApplicationCredentialSpecApplyConfiguration) *ApplicationCredentialApplyConfiguration { + b.Spec = value + return b +} + +// WithStatus sets the Status field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Status field is set to the value of the last call. +func (b *ApplicationCredentialApplyConfiguration) WithStatus(value *ApplicationCredentialStatusApplyConfiguration) *ApplicationCredentialApplyConfiguration { + b.Status = value + return b +} + +// GetKind retrieves the value of the Kind field in the declarative configuration. +func (b *ApplicationCredentialApplyConfiguration) GetKind() *string { + return b.TypeMetaApplyConfiguration.Kind +} + +// GetAPIVersion retrieves the value of the APIVersion field in the declarative configuration. +func (b *ApplicationCredentialApplyConfiguration) GetAPIVersion() *string { + return b.TypeMetaApplyConfiguration.APIVersion +} + +// GetName retrieves the value of the Name field in the declarative configuration. +func (b *ApplicationCredentialApplyConfiguration) GetName() *string { + b.ensureObjectMetaApplyConfigurationExists() + return b.ObjectMetaApplyConfiguration.Name +} + +// GetNamespace retrieves the value of the Namespace field in the declarative configuration. +func (b *ApplicationCredentialApplyConfiguration) GetNamespace() *string { + b.ensureObjectMetaApplyConfigurationExists() + return b.ObjectMetaApplyConfiguration.Namespace +} diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialfilter.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialfilter.go new file mode 100644 index 000000000..6a7b1e7be --- /dev/null +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialfilter.go @@ -0,0 +1,61 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by applyconfiguration-gen. DO NOT EDIT. + +package v1alpha1 + +import ( + apiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" +) + +// ApplicationCredentialFilterApplyConfiguration represents a declarative configuration of the ApplicationCredentialFilter type for use +// with apply. +type ApplicationCredentialFilterApplyConfiguration struct { + Name *apiv1alpha1.OpenStackName `json:"name,omitempty"` + Description *string `json:"description,omitempty"` + UserRef *apiv1alpha1.KubernetesNameRef `json:"userRef,omitempty"` +} + +// ApplicationCredentialFilterApplyConfiguration constructs a declarative configuration of the ApplicationCredentialFilter type for use with +// apply. +func ApplicationCredentialFilter() *ApplicationCredentialFilterApplyConfiguration { + return &ApplicationCredentialFilterApplyConfiguration{} +} + +// WithName sets the Name field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Name field is set to the value of the last call. +func (b *ApplicationCredentialFilterApplyConfiguration) WithName(value apiv1alpha1.OpenStackName) *ApplicationCredentialFilterApplyConfiguration { + b.Name = &value + return b +} + +// WithDescription sets the Description field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Description field is set to the value of the last call. +func (b *ApplicationCredentialFilterApplyConfiguration) WithDescription(value string) *ApplicationCredentialFilterApplyConfiguration { + b.Description = &value + return b +} + +// WithUserRef sets the UserRef field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the UserRef field is set to the value of the last call. +func (b *ApplicationCredentialFilterApplyConfiguration) WithUserRef(value apiv1alpha1.KubernetesNameRef) *ApplicationCredentialFilterApplyConfiguration { + b.UserRef = &value + return b +} diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialimport.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialimport.go new file mode 100644 index 000000000..b84df0314 --- /dev/null +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialimport.go @@ -0,0 +1,48 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by applyconfiguration-gen. DO NOT EDIT. + +package v1alpha1 + +// ApplicationCredentialImportApplyConfiguration represents a declarative configuration of the ApplicationCredentialImport type for use +// with apply. +type ApplicationCredentialImportApplyConfiguration struct { + ID *string `json:"id,omitempty"` + Filter *ApplicationCredentialFilterApplyConfiguration `json:"filter,omitempty"` +} + +// ApplicationCredentialImportApplyConfiguration constructs a declarative configuration of the ApplicationCredentialImport type for use with +// apply. +func ApplicationCredentialImport() *ApplicationCredentialImportApplyConfiguration { + return &ApplicationCredentialImportApplyConfiguration{} +} + +// WithID sets the ID field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the ID field is set to the value of the last call. +func (b *ApplicationCredentialImportApplyConfiguration) WithID(value string) *ApplicationCredentialImportApplyConfiguration { + b.ID = &value + return b +} + +// WithFilter sets the Filter field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Filter field is set to the value of the last call. +func (b *ApplicationCredentialImportApplyConfiguration) WithFilter(value *ApplicationCredentialFilterApplyConfiguration) *ApplicationCredentialImportApplyConfiguration { + b.Filter = value + return b +} diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcespec.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcespec.go new file mode 100644 index 000000000..f070d2766 --- /dev/null +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcespec.go @@ -0,0 +1,61 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by applyconfiguration-gen. DO NOT EDIT. + +package v1alpha1 + +import ( + apiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" +) + +// ApplicationCredentialResourceSpecApplyConfiguration represents a declarative configuration of the ApplicationCredentialResourceSpec type for use +// with apply. +type ApplicationCredentialResourceSpecApplyConfiguration struct { + Name *apiv1alpha1.OpenStackName `json:"name,omitempty"` + Description *string `json:"description,omitempty"` + UserRef *apiv1alpha1.KubernetesNameRef `json:"userRef,omitempty"` +} + +// ApplicationCredentialResourceSpecApplyConfiguration constructs a declarative configuration of the ApplicationCredentialResourceSpec type for use with +// apply. +func ApplicationCredentialResourceSpec() *ApplicationCredentialResourceSpecApplyConfiguration { + return &ApplicationCredentialResourceSpecApplyConfiguration{} +} + +// WithName sets the Name field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Name field is set to the value of the last call. +func (b *ApplicationCredentialResourceSpecApplyConfiguration) WithName(value apiv1alpha1.OpenStackName) *ApplicationCredentialResourceSpecApplyConfiguration { + b.Name = &value + return b +} + +// WithDescription sets the Description field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Description field is set to the value of the last call. +func (b *ApplicationCredentialResourceSpecApplyConfiguration) WithDescription(value string) *ApplicationCredentialResourceSpecApplyConfiguration { + b.Description = &value + return b +} + +// WithUserRef sets the UserRef field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the UserRef field is set to the value of the last call. +func (b *ApplicationCredentialResourceSpecApplyConfiguration) WithUserRef(value apiv1alpha1.KubernetesNameRef) *ApplicationCredentialResourceSpecApplyConfiguration { + b.UserRef = &value + return b +} diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcestatus.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcestatus.go new file mode 100644 index 000000000..ce52d9d53 --- /dev/null +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcestatus.go @@ -0,0 +1,57 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by applyconfiguration-gen. DO NOT EDIT. + +package v1alpha1 + +// ApplicationCredentialResourceStatusApplyConfiguration represents a declarative configuration of the ApplicationCredentialResourceStatus type for use +// with apply. +type ApplicationCredentialResourceStatusApplyConfiguration struct { + Name *string `json:"name,omitempty"` + Description *string `json:"description,omitempty"` + UserID *string `json:"userID,omitempty"` +} + +// ApplicationCredentialResourceStatusApplyConfiguration constructs a declarative configuration of the ApplicationCredentialResourceStatus type for use with +// apply. +func ApplicationCredentialResourceStatus() *ApplicationCredentialResourceStatusApplyConfiguration { + return &ApplicationCredentialResourceStatusApplyConfiguration{} +} + +// WithName sets the Name field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Name field is set to the value of the last call. +func (b *ApplicationCredentialResourceStatusApplyConfiguration) WithName(value string) *ApplicationCredentialResourceStatusApplyConfiguration { + b.Name = &value + return b +} + +// WithDescription sets the Description field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Description field is set to the value of the last call. +func (b *ApplicationCredentialResourceStatusApplyConfiguration) WithDescription(value string) *ApplicationCredentialResourceStatusApplyConfiguration { + b.Description = &value + return b +} + +// WithUserID sets the UserID field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the UserID field is set to the value of the last call. +func (b *ApplicationCredentialResourceStatusApplyConfiguration) WithUserID(value string) *ApplicationCredentialResourceStatusApplyConfiguration { + b.UserID = &value + return b +} diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialspec.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialspec.go new file mode 100644 index 000000000..d73e0886b --- /dev/null +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialspec.go @@ -0,0 +1,79 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by applyconfiguration-gen. DO NOT EDIT. + +package v1alpha1 + +import ( + apiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" +) + +// ApplicationCredentialSpecApplyConfiguration represents a declarative configuration of the ApplicationCredentialSpec type for use +// with apply. +type ApplicationCredentialSpecApplyConfiguration struct { + Import *ApplicationCredentialImportApplyConfiguration `json:"import,omitempty"` + Resource *ApplicationCredentialResourceSpecApplyConfiguration `json:"resource,omitempty"` + ManagementPolicy *apiv1alpha1.ManagementPolicy `json:"managementPolicy,omitempty"` + ManagedOptions *ManagedOptionsApplyConfiguration `json:"managedOptions,omitempty"` + CloudCredentialsRef *CloudCredentialsReferenceApplyConfiguration `json:"cloudCredentialsRef,omitempty"` +} + +// ApplicationCredentialSpecApplyConfiguration constructs a declarative configuration of the ApplicationCredentialSpec type for use with +// apply. +func ApplicationCredentialSpec() *ApplicationCredentialSpecApplyConfiguration { + return &ApplicationCredentialSpecApplyConfiguration{} +} + +// WithImport sets the Import field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Import field is set to the value of the last call. +func (b *ApplicationCredentialSpecApplyConfiguration) WithImport(value *ApplicationCredentialImportApplyConfiguration) *ApplicationCredentialSpecApplyConfiguration { + b.Import = value + return b +} + +// WithResource sets the Resource field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Resource field is set to the value of the last call. +func (b *ApplicationCredentialSpecApplyConfiguration) WithResource(value *ApplicationCredentialResourceSpecApplyConfiguration) *ApplicationCredentialSpecApplyConfiguration { + b.Resource = value + return b +} + +// WithManagementPolicy sets the ManagementPolicy field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the ManagementPolicy field is set to the value of the last call. +func (b *ApplicationCredentialSpecApplyConfiguration) WithManagementPolicy(value apiv1alpha1.ManagementPolicy) *ApplicationCredentialSpecApplyConfiguration { + b.ManagementPolicy = &value + return b +} + +// WithManagedOptions sets the ManagedOptions field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the ManagedOptions field is set to the value of the last call. +func (b *ApplicationCredentialSpecApplyConfiguration) WithManagedOptions(value *ManagedOptionsApplyConfiguration) *ApplicationCredentialSpecApplyConfiguration { + b.ManagedOptions = value + return b +} + +// WithCloudCredentialsRef sets the CloudCredentialsRef field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the CloudCredentialsRef field is set to the value of the last call. +func (b *ApplicationCredentialSpecApplyConfiguration) WithCloudCredentialsRef(value *CloudCredentialsReferenceApplyConfiguration) *ApplicationCredentialSpecApplyConfiguration { + b.CloudCredentialsRef = value + return b +} diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialstatus.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialstatus.go new file mode 100644 index 000000000..2dc54e77a --- /dev/null +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialstatus.go @@ -0,0 +1,66 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by applyconfiguration-gen. DO NOT EDIT. + +package v1alpha1 + +import ( + v1 "k8s.io/client-go/applyconfigurations/meta/v1" +) + +// ApplicationCredentialStatusApplyConfiguration represents a declarative configuration of the ApplicationCredentialStatus type for use +// with apply. +type ApplicationCredentialStatusApplyConfiguration struct { + Conditions []v1.ConditionApplyConfiguration `json:"conditions,omitempty"` + ID *string `json:"id,omitempty"` + Resource *ApplicationCredentialResourceStatusApplyConfiguration `json:"resource,omitempty"` +} + +// ApplicationCredentialStatusApplyConfiguration constructs a declarative configuration of the ApplicationCredentialStatus type for use with +// apply. +func ApplicationCredentialStatus() *ApplicationCredentialStatusApplyConfiguration { + return &ApplicationCredentialStatusApplyConfiguration{} +} + +// WithConditions adds the given value to the Conditions field in the declarative configuration +// and returns the receiver, so that objects can be build by chaining "With" function invocations. +// If called multiple times, values provided by each call will be appended to the Conditions field. +func (b *ApplicationCredentialStatusApplyConfiguration) WithConditions(values ...*v1.ConditionApplyConfiguration) *ApplicationCredentialStatusApplyConfiguration { + for i := range values { + if values[i] == nil { + panic("nil value passed to WithConditions") + } + b.Conditions = append(b.Conditions, *values[i]) + } + return b +} + +// WithID sets the ID field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the ID field is set to the value of the last call. +func (b *ApplicationCredentialStatusApplyConfiguration) WithID(value string) *ApplicationCredentialStatusApplyConfiguration { + b.ID = &value + return b +} + +// WithResource sets the Resource field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Resource field is set to the value of the last call. +func (b *ApplicationCredentialStatusApplyConfiguration) WithResource(value *ApplicationCredentialResourceStatusApplyConfiguration) *ApplicationCredentialStatusApplyConfiguration { + b.Resource = value + return b +} diff --git a/pkg/clients/applyconfiguration/internal/internal.go b/pkg/clients/applyconfiguration/internal/internal.go index 216436517..fa4338589 100644 --- a/pkg/clients/applyconfiguration/internal/internal.go +++ b/pkg/clients/applyconfiguration/internal/internal.go @@ -196,6 +196,108 @@ var schemaYAML = typed.YAMLObject(`types: - name: mac type: scalar: string +- name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredential + map: + fields: + - name: apiVersion + type: + scalar: string + - name: kind + type: + scalar: string + - name: metadata + type: + namedType: io.k8s.apimachinery.pkg.apis.meta.v1.ObjectMeta + default: {} + - name: spec + type: + namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialSpec + default: {} + - name: status + type: + namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialStatus + default: {} +- name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialFilter + map: + fields: + - name: description + type: + scalar: string + - name: name + type: + scalar: string + - name: userRef + type: + scalar: string +- name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialImport + map: + fields: + - name: filter + type: + namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialFilter + - name: id + type: + scalar: string +- name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialResourceSpec + map: + fields: + - name: description + type: + scalar: string + - name: name + type: + scalar: string + - name: userRef + type: + scalar: string +- name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialResourceStatus + map: + fields: + - name: description + type: + scalar: string + - name: name + type: + scalar: string + - name: userID + type: + scalar: string +- name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialSpec + map: + fields: + - name: cloudCredentialsRef + type: + namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.CloudCredentialsReference + default: {} + - name: import + type: + namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialImport + - name: managedOptions + type: + namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ManagedOptions + - name: managementPolicy + type: + scalar: string + - name: resource + type: + namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialResourceSpec +- name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialStatus + map: + fields: + - name: conditions + type: + list: + elementType: + namedType: io.k8s.apimachinery.pkg.apis.meta.v1.Condition + elementRelationship: associative + keys: + - type + - name: id + type: + scalar: string + - name: resource + type: + namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialResourceStatus - name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.CloudCredentialsReference map: fields: diff --git a/pkg/clients/applyconfiguration/utils.go b/pkg/clients/applyconfiguration/utils.go index bb76ee624..373bc2636 100644 --- a/pkg/clients/applyconfiguration/utils.go +++ b/pkg/clients/applyconfiguration/utils.go @@ -56,6 +56,20 @@ func ForKind(kind schema.GroupVersionKind) interface{} { return &apiv1alpha1.AllowedAddressPairApplyConfiguration{} case v1alpha1.SchemeGroupVersion.WithKind("AllowedAddressPairStatus"): return &apiv1alpha1.AllowedAddressPairStatusApplyConfiguration{} + case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredential"): + return &apiv1alpha1.ApplicationCredentialApplyConfiguration{} + case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialFilter"): + return &apiv1alpha1.ApplicationCredentialFilterApplyConfiguration{} + case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialImport"): + return &apiv1alpha1.ApplicationCredentialImportApplyConfiguration{} + case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialResourceSpec"): + return &apiv1alpha1.ApplicationCredentialResourceSpecApplyConfiguration{} + case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialResourceStatus"): + return &apiv1alpha1.ApplicationCredentialResourceStatusApplyConfiguration{} + case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialSpec"): + return &apiv1alpha1.ApplicationCredentialSpecApplyConfiguration{} + case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialStatus"): + return &apiv1alpha1.ApplicationCredentialStatusApplyConfiguration{} case v1alpha1.SchemeGroupVersion.WithKind("CloudCredentialsReference"): return &apiv1alpha1.CloudCredentialsReferenceApplyConfiguration{} case v1alpha1.SchemeGroupVersion.WithKind("Domain"): diff --git a/pkg/clients/clientset/clientset/typed/api/v1alpha1/api_client.go b/pkg/clients/clientset/clientset/typed/api/v1alpha1/api_client.go index 78e698815..a145cab6f 100644 --- a/pkg/clients/clientset/clientset/typed/api/v1alpha1/api_client.go +++ b/pkg/clients/clientset/clientset/typed/api/v1alpha1/api_client.go @@ -29,6 +29,7 @@ import ( type OpenstackV1alpha1Interface interface { RESTClient() rest.Interface AddressScopesGetter + ApplicationCredentialsGetter DomainsGetter EndpointsGetter FlavorsGetter @@ -62,6 +63,10 @@ func (c *OpenstackV1alpha1Client) AddressScopes(namespace string) AddressScopeIn return newAddressScopes(c, namespace) } +func (c *OpenstackV1alpha1Client) ApplicationCredentials(namespace string) ApplicationCredentialInterface { + return newApplicationCredentials(c, namespace) +} + func (c *OpenstackV1alpha1Client) Domains(namespace string) DomainInterface { return newDomains(c, namespace) } diff --git a/pkg/clients/clientset/clientset/typed/api/v1alpha1/applicationcredential.go b/pkg/clients/clientset/clientset/typed/api/v1alpha1/applicationcredential.go new file mode 100644 index 000000000..f3f3411c5 --- /dev/null +++ b/pkg/clients/clientset/clientset/typed/api/v1alpha1/applicationcredential.go @@ -0,0 +1,74 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by client-gen. DO NOT EDIT. + +package v1alpha1 + +import ( + context "context" + + apiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" + applyconfigurationapiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/pkg/clients/applyconfiguration/api/v1alpha1" + scheme "github.com/k-orc/openstack-resource-controller/v2/pkg/clients/clientset/clientset/scheme" + v1 "k8s.io/apimachinery/pkg/apis/meta/v1" + types "k8s.io/apimachinery/pkg/types" + watch "k8s.io/apimachinery/pkg/watch" + gentype "k8s.io/client-go/gentype" +) + +// ApplicationCredentialsGetter has a method to return a ApplicationCredentialInterface. +// A group's client should implement this interface. +type ApplicationCredentialsGetter interface { + ApplicationCredentials(namespace string) ApplicationCredentialInterface +} + +// ApplicationCredentialInterface has methods to work with ApplicationCredential resources. +type ApplicationCredentialInterface interface { + Create(ctx context.Context, applicationCredential *apiv1alpha1.ApplicationCredential, opts v1.CreateOptions) (*apiv1alpha1.ApplicationCredential, error) + Update(ctx context.Context, applicationCredential *apiv1alpha1.ApplicationCredential, opts v1.UpdateOptions) (*apiv1alpha1.ApplicationCredential, error) + // Add a +genclient:noStatus comment above the type to avoid generating UpdateStatus(). + UpdateStatus(ctx context.Context, applicationCredential *apiv1alpha1.ApplicationCredential, opts v1.UpdateOptions) (*apiv1alpha1.ApplicationCredential, error) + Delete(ctx context.Context, name string, opts v1.DeleteOptions) error + DeleteCollection(ctx context.Context, opts v1.DeleteOptions, listOpts v1.ListOptions) error + Get(ctx context.Context, name string, opts v1.GetOptions) (*apiv1alpha1.ApplicationCredential, error) + List(ctx context.Context, opts v1.ListOptions) (*apiv1alpha1.ApplicationCredentialList, error) + Watch(ctx context.Context, opts v1.ListOptions) (watch.Interface, error) + Patch(ctx context.Context, name string, pt types.PatchType, data []byte, opts v1.PatchOptions, subresources ...string) (result *apiv1alpha1.ApplicationCredential, err error) + Apply(ctx context.Context, applicationCredential *applyconfigurationapiv1alpha1.ApplicationCredentialApplyConfiguration, opts v1.ApplyOptions) (result *apiv1alpha1.ApplicationCredential, err error) + // Add a +genclient:noStatus comment above the type to avoid generating ApplyStatus(). + ApplyStatus(ctx context.Context, applicationCredential *applyconfigurationapiv1alpha1.ApplicationCredentialApplyConfiguration, opts v1.ApplyOptions) (result *apiv1alpha1.ApplicationCredential, err error) + ApplicationCredentialExpansion +} + +// applicationCredentials implements ApplicationCredentialInterface +type applicationCredentials struct { + *gentype.ClientWithListAndApply[*apiv1alpha1.ApplicationCredential, *apiv1alpha1.ApplicationCredentialList, *applyconfigurationapiv1alpha1.ApplicationCredentialApplyConfiguration] +} + +// newApplicationCredentials returns a ApplicationCredentials +func newApplicationCredentials(c *OpenstackV1alpha1Client, namespace string) *applicationCredentials { + return &applicationCredentials{ + gentype.NewClientWithListAndApply[*apiv1alpha1.ApplicationCredential, *apiv1alpha1.ApplicationCredentialList, *applyconfigurationapiv1alpha1.ApplicationCredentialApplyConfiguration]( + "applicationcredentials", + c.RESTClient(), + scheme.ParameterCodec, + namespace, + func() *apiv1alpha1.ApplicationCredential { return &apiv1alpha1.ApplicationCredential{} }, + func() *apiv1alpha1.ApplicationCredentialList { return &apiv1alpha1.ApplicationCredentialList{} }, + ), + } +} diff --git a/pkg/clients/clientset/clientset/typed/api/v1alpha1/fake/fake_api_client.go b/pkg/clients/clientset/clientset/typed/api/v1alpha1/fake/fake_api_client.go index 4f4334818..87bc2b39d 100644 --- a/pkg/clients/clientset/clientset/typed/api/v1alpha1/fake/fake_api_client.go +++ b/pkg/clients/clientset/clientset/typed/api/v1alpha1/fake/fake_api_client.go @@ -32,6 +32,10 @@ func (c *FakeOpenstackV1alpha1) AddressScopes(namespace string) v1alpha1.Address return newFakeAddressScopes(c, namespace) } +func (c *FakeOpenstackV1alpha1) ApplicationCredentials(namespace string) v1alpha1.ApplicationCredentialInterface { + return newFakeApplicationCredentials(c, namespace) +} + func (c *FakeOpenstackV1alpha1) Domains(namespace string) v1alpha1.DomainInterface { return newFakeDomains(c, namespace) } diff --git a/pkg/clients/clientset/clientset/typed/api/v1alpha1/fake/fake_applicationcredential.go b/pkg/clients/clientset/clientset/typed/api/v1alpha1/fake/fake_applicationcredential.go new file mode 100644 index 000000000..c093e7c28 --- /dev/null +++ b/pkg/clients/clientset/clientset/typed/api/v1alpha1/fake/fake_applicationcredential.go @@ -0,0 +1,53 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by client-gen. DO NOT EDIT. + +package fake + +import ( + v1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" + apiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/pkg/clients/applyconfiguration/api/v1alpha1" + typedapiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/pkg/clients/clientset/clientset/typed/api/v1alpha1" + gentype "k8s.io/client-go/gentype" +) + +// fakeApplicationCredentials implements ApplicationCredentialInterface +type fakeApplicationCredentials struct { + *gentype.FakeClientWithListAndApply[*v1alpha1.ApplicationCredential, *v1alpha1.ApplicationCredentialList, *apiv1alpha1.ApplicationCredentialApplyConfiguration] + Fake *FakeOpenstackV1alpha1 +} + +func newFakeApplicationCredentials(fake *FakeOpenstackV1alpha1, namespace string) typedapiv1alpha1.ApplicationCredentialInterface { + return &fakeApplicationCredentials{ + gentype.NewFakeClientWithListAndApply[*v1alpha1.ApplicationCredential, *v1alpha1.ApplicationCredentialList, *apiv1alpha1.ApplicationCredentialApplyConfiguration]( + fake.Fake, + namespace, + v1alpha1.SchemeGroupVersion.WithResource("applicationcredentials"), + v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredential"), + func() *v1alpha1.ApplicationCredential { return &v1alpha1.ApplicationCredential{} }, + func() *v1alpha1.ApplicationCredentialList { return &v1alpha1.ApplicationCredentialList{} }, + func(dst, src *v1alpha1.ApplicationCredentialList) { dst.ListMeta = src.ListMeta }, + func(list *v1alpha1.ApplicationCredentialList) []*v1alpha1.ApplicationCredential { + return gentype.ToPointerSlice(list.Items) + }, + func(list *v1alpha1.ApplicationCredentialList, items []*v1alpha1.ApplicationCredential) { + list.Items = gentype.FromPointerSlice(items) + }, + ), + fake, + } +} diff --git a/pkg/clients/clientset/clientset/typed/api/v1alpha1/generated_expansion.go b/pkg/clients/clientset/clientset/typed/api/v1alpha1/generated_expansion.go index fa80c4303..de60388f2 100644 --- a/pkg/clients/clientset/clientset/typed/api/v1alpha1/generated_expansion.go +++ b/pkg/clients/clientset/clientset/typed/api/v1alpha1/generated_expansion.go @@ -20,6 +20,8 @@ package v1alpha1 type AddressScopeExpansion interface{} +type ApplicationCredentialExpansion interface{} + type DomainExpansion interface{} type EndpointExpansion interface{} diff --git a/pkg/clients/informers/externalversions/api/v1alpha1/applicationcredential.go b/pkg/clients/informers/externalversions/api/v1alpha1/applicationcredential.go new file mode 100644 index 000000000..a728706a7 --- /dev/null +++ b/pkg/clients/informers/externalversions/api/v1alpha1/applicationcredential.go @@ -0,0 +1,102 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by informer-gen. DO NOT EDIT. + +package v1alpha1 + +import ( + context "context" + time "time" + + v2apiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" + clientset "github.com/k-orc/openstack-resource-controller/v2/pkg/clients/clientset/clientset" + internalinterfaces "github.com/k-orc/openstack-resource-controller/v2/pkg/clients/informers/externalversions/internalinterfaces" + apiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/pkg/clients/listers/api/v1alpha1" + v1 "k8s.io/apimachinery/pkg/apis/meta/v1" + runtime "k8s.io/apimachinery/pkg/runtime" + watch "k8s.io/apimachinery/pkg/watch" + cache "k8s.io/client-go/tools/cache" +) + +// ApplicationCredentialInformer provides access to a shared informer and lister for +// ApplicationCredentials. +type ApplicationCredentialInformer interface { + Informer() cache.SharedIndexInformer + Lister() apiv1alpha1.ApplicationCredentialLister +} + +type applicationCredentialInformer struct { + factory internalinterfaces.SharedInformerFactory + tweakListOptions internalinterfaces.TweakListOptionsFunc + namespace string +} + +// NewApplicationCredentialInformer constructs a new informer for ApplicationCredential type. +// Always prefer using an informer factory to get a shared informer instead of getting an independent +// one. This reduces memory footprint and number of connections to the server. +func NewApplicationCredentialInformer(client clientset.Interface, namespace string, resyncPeriod time.Duration, indexers cache.Indexers) cache.SharedIndexInformer { + return NewFilteredApplicationCredentialInformer(client, namespace, resyncPeriod, indexers, nil) +} + +// NewFilteredApplicationCredentialInformer constructs a new informer for ApplicationCredential type. +// Always prefer using an informer factory to get a shared informer instead of getting an independent +// one. This reduces memory footprint and number of connections to the server. +func NewFilteredApplicationCredentialInformer(client clientset.Interface, namespace string, resyncPeriod time.Duration, indexers cache.Indexers, tweakListOptions internalinterfaces.TweakListOptionsFunc) cache.SharedIndexInformer { + return cache.NewSharedIndexInformer( + &cache.ListWatch{ + ListFunc: func(options v1.ListOptions) (runtime.Object, error) { + if tweakListOptions != nil { + tweakListOptions(&options) + } + return client.OpenstackV1alpha1().ApplicationCredentials(namespace).List(context.Background(), options) + }, + WatchFunc: func(options v1.ListOptions) (watch.Interface, error) { + if tweakListOptions != nil { + tweakListOptions(&options) + } + return client.OpenstackV1alpha1().ApplicationCredentials(namespace).Watch(context.Background(), options) + }, + ListWithContextFunc: func(ctx context.Context, options v1.ListOptions) (runtime.Object, error) { + if tweakListOptions != nil { + tweakListOptions(&options) + } + return client.OpenstackV1alpha1().ApplicationCredentials(namespace).List(ctx, options) + }, + WatchFuncWithContext: func(ctx context.Context, options v1.ListOptions) (watch.Interface, error) { + if tweakListOptions != nil { + tweakListOptions(&options) + } + return client.OpenstackV1alpha1().ApplicationCredentials(namespace).Watch(ctx, options) + }, + }, + &v2apiv1alpha1.ApplicationCredential{}, + resyncPeriod, + indexers, + ) +} + +func (f *applicationCredentialInformer) defaultInformer(client clientset.Interface, resyncPeriod time.Duration) cache.SharedIndexInformer { + return NewFilteredApplicationCredentialInformer(client, f.namespace, resyncPeriod, cache.Indexers{cache.NamespaceIndex: cache.MetaNamespaceIndexFunc}, f.tweakListOptions) +} + +func (f *applicationCredentialInformer) Informer() cache.SharedIndexInformer { + return f.factory.InformerFor(&v2apiv1alpha1.ApplicationCredential{}, f.defaultInformer) +} + +func (f *applicationCredentialInformer) Lister() apiv1alpha1.ApplicationCredentialLister { + return apiv1alpha1.NewApplicationCredentialLister(f.Informer().GetIndexer()) +} diff --git a/pkg/clients/informers/externalversions/api/v1alpha1/interface.go b/pkg/clients/informers/externalversions/api/v1alpha1/interface.go index 13fa48405..b9b415243 100644 --- a/pkg/clients/informers/externalversions/api/v1alpha1/interface.go +++ b/pkg/clients/informers/externalversions/api/v1alpha1/interface.go @@ -26,6 +26,8 @@ import ( type Interface interface { // AddressScopes returns a AddressScopeInformer. AddressScopes() AddressScopeInformer + // ApplicationCredentials returns a ApplicationCredentialInformer. + ApplicationCredentials() ApplicationCredentialInformer // Domains returns a DomainInformer. Domains() DomainInformer // Endpoints returns a EndpointInformer. @@ -88,6 +90,11 @@ func (v *version) AddressScopes() AddressScopeInformer { return &addressScopeInformer{factory: v.factory, namespace: v.namespace, tweakListOptions: v.tweakListOptions} } +// ApplicationCredentials returns a ApplicationCredentialInformer. +func (v *version) ApplicationCredentials() ApplicationCredentialInformer { + return &applicationCredentialInformer{factory: v.factory, namespace: v.namespace, tweakListOptions: v.tweakListOptions} +} + // Domains returns a DomainInformer. func (v *version) Domains() DomainInformer { return &domainInformer{factory: v.factory, namespace: v.namespace, tweakListOptions: v.tweakListOptions} diff --git a/pkg/clients/informers/externalversions/generic.go b/pkg/clients/informers/externalversions/generic.go index 40c16cf12..99f589164 100644 --- a/pkg/clients/informers/externalversions/generic.go +++ b/pkg/clients/informers/externalversions/generic.go @@ -55,6 +55,8 @@ func (f *sharedInformerFactory) ForResource(resource schema.GroupVersionResource // Group=openstack.k-orc.cloud, Version=v1alpha1 case v1alpha1.SchemeGroupVersion.WithResource("addressscopes"): return &genericInformer{resource: resource.GroupResource(), informer: f.Openstack().V1alpha1().AddressScopes().Informer()}, nil + case v1alpha1.SchemeGroupVersion.WithResource("applicationcredentials"): + return &genericInformer{resource: resource.GroupResource(), informer: f.Openstack().V1alpha1().ApplicationCredentials().Informer()}, nil case v1alpha1.SchemeGroupVersion.WithResource("domains"): return &genericInformer{resource: resource.GroupResource(), informer: f.Openstack().V1alpha1().Domains().Informer()}, nil case v1alpha1.SchemeGroupVersion.WithResource("endpoints"): diff --git a/pkg/clients/listers/api/v1alpha1/applicationcredential.go b/pkg/clients/listers/api/v1alpha1/applicationcredential.go new file mode 100644 index 000000000..559f9b947 --- /dev/null +++ b/pkg/clients/listers/api/v1alpha1/applicationcredential.go @@ -0,0 +1,70 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by lister-gen. DO NOT EDIT. + +package v1alpha1 + +import ( + apiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" + labels "k8s.io/apimachinery/pkg/labels" + listers "k8s.io/client-go/listers" + cache "k8s.io/client-go/tools/cache" +) + +// ApplicationCredentialLister helps list ApplicationCredentials. +// All objects returned here must be treated as read-only. +type ApplicationCredentialLister interface { + // List lists all ApplicationCredentials in the indexer. + // Objects returned here must be treated as read-only. + List(selector labels.Selector) (ret []*apiv1alpha1.ApplicationCredential, err error) + // ApplicationCredentials returns an object that can list and get ApplicationCredentials. + ApplicationCredentials(namespace string) ApplicationCredentialNamespaceLister + ApplicationCredentialListerExpansion +} + +// applicationCredentialLister implements the ApplicationCredentialLister interface. +type applicationCredentialLister struct { + listers.ResourceIndexer[*apiv1alpha1.ApplicationCredential] +} + +// NewApplicationCredentialLister returns a new ApplicationCredentialLister. +func NewApplicationCredentialLister(indexer cache.Indexer) ApplicationCredentialLister { + return &applicationCredentialLister{listers.New[*apiv1alpha1.ApplicationCredential](indexer, apiv1alpha1.Resource("applicationcredential"))} +} + +// ApplicationCredentials returns an object that can list and get ApplicationCredentials. +func (s *applicationCredentialLister) ApplicationCredentials(namespace string) ApplicationCredentialNamespaceLister { + return applicationCredentialNamespaceLister{listers.NewNamespaced[*apiv1alpha1.ApplicationCredential](s.ResourceIndexer, namespace)} +} + +// ApplicationCredentialNamespaceLister helps list and get ApplicationCredentials. +// All objects returned here must be treated as read-only. +type ApplicationCredentialNamespaceLister interface { + // List lists all ApplicationCredentials in the indexer for a given namespace. + // Objects returned here must be treated as read-only. + List(selector labels.Selector) (ret []*apiv1alpha1.ApplicationCredential, err error) + // Get retrieves the ApplicationCredential from the indexer for a given namespace and name. + // Objects returned here must be treated as read-only. + Get(name string) (*apiv1alpha1.ApplicationCredential, error) + ApplicationCredentialNamespaceListerExpansion +} + +// applicationCredentialNamespaceLister implements the ApplicationCredentialNamespaceLister +// interface. +type applicationCredentialNamespaceLister struct { + listers.ResourceIndexer[*apiv1alpha1.ApplicationCredential] +} diff --git a/pkg/clients/listers/api/v1alpha1/expansion_generated.go b/pkg/clients/listers/api/v1alpha1/expansion_generated.go index 5328b091b..98590bb01 100644 --- a/pkg/clients/listers/api/v1alpha1/expansion_generated.go +++ b/pkg/clients/listers/api/v1alpha1/expansion_generated.go @@ -26,6 +26,14 @@ type AddressScopeListerExpansion interface{} // AddressScopeNamespaceLister. type AddressScopeNamespaceListerExpansion interface{} +// ApplicationCredentialListerExpansion allows custom methods to be added to +// ApplicationCredentialLister. +type ApplicationCredentialListerExpansion interface{} + +// ApplicationCredentialNamespaceListerExpansion allows custom methods to be added to +// ApplicationCredentialNamespaceLister. +type ApplicationCredentialNamespaceListerExpansion interface{} + // DomainListerExpansion allows custom methods to be added to // DomainLister. type DomainListerExpansion interface{} diff --git a/website/docs/crd-reference.md b/website/docs/crd-reference.md index bfbe25d70..884240fe6 100644 --- a/website/docs/crd-reference.md +++ b/website/docs/crd-reference.md @@ -11,6 +11,7 @@ Package v1alpha1 contains API Schema definitions for the openstack v1alpha1 API ### Resource Types - [AddressScope](#addressscope) +- [ApplicationCredential](#applicationcredential) - [Domain](#domain) - [Endpoint](#endpoint) - [Flavor](#flavor) @@ -256,12 +257,138 @@ _Appears in:_ | `mac` _string_ | mac contains a MAC address which a server connected to the port can
send packets with. | | MaxLength: 1024
Optional: \{\}
| +#### ApplicationCredential +ApplicationCredential is the Schema for an ORC resource. + + +| Field | Description | Default | Validation | +| --- | --- | --- | --- | +| `apiVersion` _string_ | `openstack.k-orc.cloud/v1alpha1` | | | +| `kind` _string_ | `ApplicationCredential` | | | +| `metadata` _[ObjectMeta](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.29/#objectmeta-v1-meta)_ | Refer to Kubernetes API documentation for fields of `metadata`. | | | +| `spec` _[ApplicationCredentialSpec](#applicationcredentialspec)_ | spec specifies the desired state of the resource. | | | +| `status` _[ApplicationCredentialStatus](#applicationcredentialstatus)_ | status defines the observed state of the resource. | | | + + +#### ApplicationCredentialFilter + + + +ApplicationCredentialFilter defines an existing resource by its properties + +_Validation:_ +- MinProperties: 1 + +_Appears in:_ +- [ApplicationCredentialImport](#applicationcredentialimport) + +| Field | Description | Default | Validation | +| --- | --- | --- | --- | +| `name` _[OpenStackName](#openstackname)_ | name of the existing resource | | MaxLength: 255
MinLength: 1
Pattern: `^[^,]+$`
| +| `description` _string_ | description of the existing resource | | MaxLength: 255
MinLength: 1
| +| `userRef` _[KubernetesNameRef](#kubernetesnameref)_ | userRef is a reference to the ORC User which this resource is associated with. | | MaxLength: 253
MinLength: 1
| + + +#### ApplicationCredentialImport + + + +ApplicationCredentialImport specifies an existing resource which will be imported instead of +creating a new one + +_Validation:_ +- MaxProperties: 1 +- MinProperties: 1 + +_Appears in:_ +- [ApplicationCredentialSpec](#applicationcredentialspec) + +| Field | Description | Default | Validation | +| --- | --- | --- | --- | +| `id` _string_ | id contains the unique identifier of an existing OpenStack resource. Note
that when specifying an import by ID, the resource MUST already exist.
The ORC object will enter an error state if the resource does not exist. | | Format: uuid
MaxLength: 36
| +| `filter` _[ApplicationCredentialFilter](#applicationcredentialfilter)_ | filter contains a resource query which is expected to return a single
result. The controller will continue to retry if filter returns no
results. If filter returns multiple results the controller will set an
error state and will not continue to retry. | | MinProperties: 1
| + + +#### ApplicationCredentialResourceSpec + + + +ApplicationCredentialResourceSpec contains the desired state of the resource. + + + +_Appears in:_ +- [ApplicationCredentialSpec](#applicationcredentialspec) + +| Field | Description | Default | Validation | +| --- | --- | --- | --- | +| `name` _[OpenStackName](#openstackname)_ | name will be the name of the created resource. If not specified, the
name of the ORC object will be used. | | MaxLength: 255
MinLength: 1
Pattern: `^[^,]+$`
| +| `description` _string_ | description is a human-readable description for the resource. | | MaxLength: 255
MinLength: 1
| +| `userRef` _[KubernetesNameRef](#kubernetesnameref)_ | userRef is a reference to the ORC User which this resource is associated with. | | MaxLength: 253
MinLength: 1
| + + +#### ApplicationCredentialResourceStatus + + + +ApplicationCredentialResourceStatus represents the observed state of the resource. + + + +_Appears in:_ +- [ApplicationCredentialStatus](#applicationcredentialstatus) + +| Field | Description | Default | Validation | +| --- | --- | --- | --- | +| `name` _string_ | name is a Human-readable name for the resource. Might not be unique. | | MaxLength: 1024
| +| `description` _string_ | description is a human-readable description for the resource. | | MaxLength: 1024
| +| `userID` _string_ | userID is the ID of the User to which the resource is associated. | | MaxLength: 1024
| + + +#### ApplicationCredentialSpec + + + +ApplicationCredentialSpec defines the desired state of an ORC object. + + + +_Appears in:_ +- [ApplicationCredential](#applicationcredential) + +| Field | Description | Default | Validation | +| --- | --- | --- | --- | +| `import` _[ApplicationCredentialImport](#applicationcredentialimport)_ | import refers to an existing OpenStack resource which will be imported instead of
creating a new one. | | MaxProperties: 1
MinProperties: 1
| +| `resource` _[ApplicationCredentialResourceSpec](#applicationcredentialresourcespec)_ | resource specifies the desired state of the resource.
resource may not be specified if the management policy is `unmanaged`.
resource must be specified if the management policy is `managed`. | | | +| `managementPolicy` _[ManagementPolicy](#managementpolicy)_ | managementPolicy defines how ORC will treat the object. Valid values are
`managed`: ORC will create, update, and delete the resource; `unmanaged`:
ORC will import an existing resource, and will not apply updates to it or
delete it. | managed | Enum: [managed unmanaged]
| +| `managedOptions` _[ManagedOptions](#managedoptions)_ | managedOptions specifies options which may be applied to managed objects. | | | +| `cloudCredentialsRef` _[CloudCredentialsReference](#cloudcredentialsreference)_ | cloudCredentialsRef points to a secret containing OpenStack credentials | | | + + +#### ApplicationCredentialStatus + + + +ApplicationCredentialStatus defines the observed state of an ORC resource. + + + +_Appears in:_ +- [ApplicationCredential](#applicationcredential) + +| Field | Description | Default | Validation | +| --- | --- | --- | --- | +| `conditions` _[Condition](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.29/#condition-v1-meta) array_ | conditions represents the observed status of the object.
Known .status.conditions.type are: "Available", "Progressing"
Available represents the availability of the OpenStack resource. If it is
true then the resource is ready for use.
Progressing indicates whether the controller is still attempting to
reconcile the current state of the OpenStack resource to the desired
state. Progressing will be False either because the desired state has
been achieved, or because some terminal error prevents it from ever being
achieved and the controller is no longer attempting to reconcile. If
Progressing is True, an observer waiting on the resource should continue
to wait. | | MaxItems: 32
| +| `id` _string_ | id is the unique identifier of the OpenStack resource. | | MaxLength: 1024
| +| `resource` _[ApplicationCredentialResourceStatus](#applicationcredentialresourcestatus)_ | resource contains the observed state of the OpenStack resource. | | | + + #### AvailabilityZoneHint _Underlying type:_ _string_ @@ -309,6 +436,7 @@ CloudCredentialsReference is a reference to a secret containing OpenStack creden _Appears in:_ - [AddressScopeSpec](#addressscopespec) +- [ApplicationCredentialSpec](#applicationcredentialspec) - [DomainSpec](#domainspec) - [EndpointSpec](#endpointspec) - [FlavorSpec](#flavorspec) @@ -1997,6 +2125,7 @@ _Appears in:_ _Appears in:_ - [AddressScopeSpec](#addressscopespec) +- [ApplicationCredentialSpec](#applicationcredentialspec) - [DomainSpec](#domainspec) - [EndpointSpec](#endpointspec) - [FlavorSpec](#flavorspec) @@ -2035,6 +2164,7 @@ _Validation:_ _Appears in:_ - [AddressScopeSpec](#addressscopespec) +- [ApplicationCredentialSpec](#applicationcredentialspec) - [DomainSpec](#domainspec) - [EndpointSpec](#endpointspec) - [FlavorSpec](#flavorspec) From d3af13f96b4f92c138929cf385f3ade0731e8507 Mon Sep 17 00:00:00 2001 From: Gondermann Date: Wed, 4 Feb 2026 14:36:40 +0100 Subject: [PATCH 03/10] Scaffolding for the ApplicationCredential controller Add the OpenStack client to scope On-behalf-of: SAP nils.gondermann@sap.com --- internal/scope/mock.go | 63 +++++++++++++++++++++----------------- internal/scope/provider.go | 4 +++ internal/scope/scope.go | 1 + 3 files changed, 40 insertions(+), 28 deletions(-) diff --git a/internal/scope/mock.go b/internal/scope/mock.go index 71bd8d8e6..256fa2e1d 100644 --- a/internal/scope/mock.go +++ b/internal/scope/mock.go @@ -34,26 +34,28 @@ import ( // MockScopeFactory implements both the ScopeFactory and ClientScope interfaces. It can be used in place of the default ProviderScopeFactory // when we want to use mocked service clients which do not attempt to connect to a running OpenStack cloud. type MockScopeFactory struct { - AddressScope *mock.MockAddressScopeClient - ComputeClient *mock.MockComputeClient - DomainClient *mock.MockDomainClient - EndpointClient *mock.MockEndpointClient - GroupClient *mock.MockGroupClient - IdentityClient *mock.MockIdentityClient - ImageClient *mock.MockImageClient - KeyPairClient *mock.MockKeyPairClient - NetworkClient *mock.MockNetworkClient - RoleClient *mock.MockRoleClient - ServiceClient *mock.MockServiceClient - UserClient *mock.MockUserClient - VolumeClient *mock.MockVolumeClient - VolumeTypeClient *mock.MockVolumeTypeClient + AddressScope *mock.MockAddressScopeClient + ApplicationCredentialClient *mock.MockApplicationCredentialClient + ComputeClient *mock.MockComputeClient + DomainClient *mock.MockDomainClient + EndpointClient *mock.MockEndpointClient + GroupClient *mock.MockGroupClient + IdentityClient *mock.MockIdentityClient + ImageClient *mock.MockImageClient + KeyPairClient *mock.MockKeyPairClient + NetworkClient *mock.MockNetworkClient + RoleClient *mock.MockRoleClient + ServiceClient *mock.MockServiceClient + UserClient *mock.MockUserClient + VolumeClient *mock.MockVolumeClient + VolumeTypeClient *mock.MockVolumeTypeClient clientScopeCreateError error } func NewMockScopeFactory(mockCtrl *gomock.Controller) *MockScopeFactory { addressScope := mock.NewMockAddressScopeClient(mockCtrl) + applicationcredentialClient := mock.NewMockApplicationCredentialClient(mockCtrl) computeClient := mock.NewMockComputeClient(mockCtrl) domainClient := mock.NewMockDomainClient(mockCtrl) endpointClient := mock.NewMockEndpointClient(mockCtrl) @@ -69,20 +71,21 @@ func NewMockScopeFactory(mockCtrl *gomock.Controller) *MockScopeFactory { volumetypeClient := mock.NewMockVolumeTypeClient(mockCtrl) return &MockScopeFactory{ - AddressScope: addressScope, - ComputeClient: computeClient, - DomainClient: domainClient, - EndpointClient: endpointClient, - GroupClient: groupClient, - IdentityClient: identityClient, - ImageClient: imageClient, - KeyPairClient: keypairClient, - NetworkClient: networkClient, - RoleClient: roleClient, - ServiceClient: serviceClient, - UserClient: userClient, - VolumeClient: volumeClient, - VolumeTypeClient: volumetypeClient, + AddressScope: addressScope, + ApplicationCredentialClient: applicationcredentialClient, + ComputeClient: computeClient, + DomainClient: domainClient, + EndpointClient: endpointClient, + GroupClient: groupClient, + IdentityClient: identityClient, + ImageClient: imageClient, + KeyPairClient: keypairClient, + NetworkClient: networkClient, + RoleClient: roleClient, + ServiceClient: serviceClient, + UserClient: userClient, + VolumeClient: volumeClient, + VolumeTypeClient: volumetypeClient, } } @@ -153,6 +156,10 @@ func (f *MockScopeFactory) NewEndpointClient() (osclients.EndpointClient, error) return f.EndpointClient, nil } +func (f *MockScopeFactory) NewApplicationCredentialClient() (osclients.ApplicationCredentialClient, error) { + return f.ApplicationCredentialClient, nil +} + func (f *MockScopeFactory) ExtractToken() (*tokens.Token, error) { return &tokens.Token{ExpiresAt: time.Now().Add(24 * time.Hour)}, nil } diff --git a/internal/scope/provider.go b/internal/scope/provider.go index 6f9902c39..aadd5c5ff 100644 --- a/internal/scope/provider.go +++ b/internal/scope/provider.go @@ -141,6 +141,10 @@ func (s *providerScope) NewAddressScopeClient() (clients.AddressScopeClient, err return clients.NewAddressScopeClient(s.providerClient, s.providerClientOpts) } +func (s *providerScope) NewApplicationCredentialClient() (clients.ApplicationCredentialClient, error) { + return clients.NewApplicationCredentialClient(s.providerClient, s.providerClientOpts) +} + func (s *providerScope) NewComputeClient() (clients.ComputeClient, error) { return clients.NewComputeClient(s.providerClient, s.providerClientOpts) } diff --git a/internal/scope/scope.go b/internal/scope/scope.go index 6ed103308..d8426fd62 100644 --- a/internal/scope/scope.go +++ b/internal/scope/scope.go @@ -49,6 +49,7 @@ type Factory interface { // Scope contains arguments common to most operations. type Scope interface { NewAddressScopeClient() (osclients.AddressScopeClient, error) + NewApplicationCredentialClient() (osclients.ApplicationCredentialClient, error) NewComputeClient() (osclients.ComputeClient, error) NewDomainClient() (osclients.DomainClient, error) NewEndpointClient() (osclients.EndpointClient, error) From 2d5c9cd6445427db180f9923ce3e5b371dd06987 Mon Sep 17 00:00:00 2001 From: Gondermann Date: Wed, 4 Feb 2026 14:38:40 +0100 Subject: [PATCH 04/10] Scaffolding for the ApplicationCredential controller Register the controller On-behalf-of: SAP nils.gondermann@sap.com --- cmd/manager/main.go | 2 ++ 1 file changed, 2 insertions(+) diff --git a/cmd/manager/main.go b/cmd/manager/main.go index 25eae08f3..c8a624acc 100644 --- a/cmd/manager/main.go +++ b/cmd/manager/main.go @@ -28,6 +28,7 @@ import ( "sigs.k8s.io/controller-runtime/pkg/log/zap" "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/addressscope" + "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/applicationcredential" "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/domain" "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/endpoint" "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/flavor" @@ -112,6 +113,7 @@ func main() { controllers := []interfaces.Controller{ addressscope.New(scopeFactory), + applicationcredential.New(scopeFactory), endpoint.New(scopeFactory), image.New(scopeFactory), network.New(scopeFactory), From 48e2373267e8bd6119470c10ee08ffc6120197db Mon Sep 17 00:00:00 2001 From: Gondermann Date: Wed, 4 Feb 2026 16:02:59 +0100 Subject: [PATCH 05/10] ApplicationCredential Type Declaration On-behalf-of: SAP nils.gondermann@sap.com --- api/v1alpha1/applicationcredential_types.go | 142 +++++++++++++++++--- 1 file changed, 121 insertions(+), 21 deletions(-) diff --git a/api/v1alpha1/applicationcredential_types.go b/api/v1alpha1/applicationcredential_types.go index 07e3889cc..a45805710 100644 --- a/api/v1alpha1/applicationcredential_types.go +++ b/api/v1alpha1/applicationcredential_types.go @@ -16,7 +16,42 @@ limitations under the License. package v1alpha1 +import metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + +// +kubebuilder:validation:Enum:=CONNECT;DELETE;GET;HEAD;OPTIONS;PATCH;POST;PUT;TRACE +type HTTPMethod string + +const ( + HTTPMethodCONNECT HTTPMethod = "CONNECT" + HTTPMethodDELETE HTTPMethod = "DELETE" + HTTPMethodGET HTTPMethod = "GET" + HTTPMethodHEAD HTTPMethod = "HEAD" + HTTPMethodOPTIONS HTTPMethod = "OPTIONS" + HTTPMethodPATCH HTTPMethod = "PATCH" + HTTPMethodPOST HTTPMethod = "POST" + HTTPMethodPUT HTTPMethod = "PUT" + HTTPMethodTRACE HTTPMethod = "TRACE" +) + +// ApplicationCredentialAccessRule defines an access rule +// +kubebuilder:validation:MinProperties:=1 +type ApplicationCredentialAccessRule struct { + // path that the application credential is permitted to access + // +kubebuilder:validation:MaxLength=1024 + // +optional + Path *string `json:"path,omitempty"` + + // method that the application credential is permitted to use for a given API endpoint + // +optional + Method *HTTPMethod `json:"method,omitempty"` + + // serviceRef identifier for the service that the application credential is permitted to access + // +optional + ServiceRef *KubernetesNameRef `json:"serviceRef,omitempty"` +} + // ApplicationCredentialResourceSpec contains the desired state of the resource. +// +kubebuilder:validation:XValidation:rule="self == oldSelf",message="ApplicationCredentialResourceSpec is immutable" type ApplicationCredentialResourceSpec struct { // name will be the name of the created resource. If not specified, the // name of the ORC object will be used. @@ -31,38 +66,87 @@ type ApplicationCredentialResourceSpec struct { // userRef is a reference to the ORC User which this resource is associated with. // +required - // +kubebuilder:validation:XValidation:rule="self == oldSelf",message="userRef is immutable" UserRef KubernetesNameRef `json:"userRef,omitempty"` - // TODO(scaffolding): Add more types. - // To see what is supported, you can take inspiration from the CreateOpts structure from - // github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials - // - // Until you have implemented mutability for the field, you must add a CEL validation - // preventing the field being modified: - // `// +kubebuilder:validation:XValidation:rule="self == oldSelf",message=" is immutable"` + // unrestricted is a flag indicating whether the application credential may be used for creation or destruction of other application credentials or trusts + // +optional + Unrestricted *bool `json:"unrestricted,omitempty"` + + // secretRef is a reference to a Secret containing the application credential secret + // +required + SecretRef KubernetesNameRef `json:"secretRef,omitempty"` + + // roleRefs may only contain roles that the user has assigned on the project. If not provided, the roles assigned to the application credential will be the same as the roles in the current token. + // +kubebuilder:validation:MaxItems:=256 + // +listType=atomic + // +optional + RoleRefs []KubernetesNameRef `json:"roleRefs,omitempty"` + + // accessRules is a list of fine grained access control rules + // +kubebuilder:validation:MaxItems:=256 + // +listType=atomic + // +optional + AccessRules []ApplicationCredentialAccessRule `json:"accessRules,omitempty"` + + // expiresAt is the time of expiration for the application credential. If unset, the application credential does not expire. + // +optional + ExpiresAt *metav1.Time `json:"expiresAt,omitempty"` } // ApplicationCredentialFilter defines an existing resource by its properties -// +kubebuilder:validation:MinProperties:=1 +// +kubebuilder:validation:MinProperties:=2 type ApplicationCredentialFilter struct { + // userRef is a reference to the ORC User which this resource is associated with. + // +required + UserRef KubernetesNameRef `json:"userRef,omitempty"` + // name of the existing resource // +optional Name *OpenStackName `json:"name,omitempty"` // description of the existing resource - // +kubebuilder:validation:MinLength:=1 - // +kubebuilder:validation:MaxLength:=255 + // +kubebuilder:validation:MaxLength:=1024 // +optional Description *string `json:"description,omitempty"` +} - // userRef is a reference to the ORC User which this resource is associated with. +type ApplicationCredentialRoleStatus struct { + // name of an existing role + // +kubebuilder:validation:MaxLength:=1024 + // +optional + Name *string `json:"name,omitempty"` + + // id is the ID of a role + // +kubebuilder:validation:MaxLength:=1024 // +optional - UserRef *KubernetesNameRef `json:"userRef,omitempty"` + ID *string `json:"id,omitempty"` - // TODO(scaffolding): Add more types. - // To see what is supported, you can take inspiration from the ListOpts structure from - // github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials + // domainID of the domain of this role + // +kubebuilder:validation:MaxLength:=1024 + // +optional + DomainID *string `json:"domainID,omitempty"` +} + +type ApplicationCredentialAccessRuleStatus struct { + // id is the ID of this access rule + // +kubebuilder:validation:MaxLength:=1024 + // +optional + ID *string `json:"id,omitempty"` + + // path that the application credential is permitted to access + // +kubebuilder:validation:MaxLength:=1024 + // +optional + Path *string `json:"path,omitempty"` + + // method that the application credential is permitted to use for a given API endpoint + // +kubebuilder:validation:MaxLength=32 + // +optional + Method *string `json:"method,omitempty"` + + // service type identifier for the service that the application credential is permitted to access + // +kubebuilder:validation:MaxLength:=1024 + // +optional + Service *string `json:"service,omitempty"` } // ApplicationCredentialResourceStatus represents the observed state of the resource. @@ -77,12 +161,28 @@ type ApplicationCredentialResourceStatus struct { // +optional Description string `json:"description,omitempty"` - // userID is the ID of the User to which the resource is associated. + // unrestricted is a flag indicating whether the application credential may be used for creation or destruction of other application credentials or trusts + // +optional + Unrestricted bool `json:"unrestricted,omitempty"` + + // projectID of the project the application credential was created for and that authentication requests using this application credential will be scoped to. // +kubebuilder:validation:MaxLength=1024 // +optional - UserID string `json:"userID,omitempty"` + ProjectID string `json:"projectID,omitempty"` - // TODO(scaffolding): Add more types. - // To see what is supported, you can take inspiration from the ApplicationCredential structure from - // github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials + // roles is a list of role objects may only contain roles that the user has assigned on the project + // +kubebuilder:validation:MaxItems:=64 + // +listType=atomic + // +optional + Roles []ApplicationCredentialRoleStatus `json:"roles"` + + // expiresAt is the time of expiration for the application credential. If unset, the application credential does not expire. + // +optional + ExpiresAt *metav1.Time `json:"expiresAt"` + + // accessRules is a list of fine grained access control rules + // +kubebuilder:validation:MaxItems:=64 + // +listType=atomic + // +optional + AccessRules []ApplicationCredentialAccessRuleStatus `json:"accessRules,omitempty"` } From 2eb472419394fc7eb4ea8c3cf8a5fb13d8dde943 Mon Sep 17 00:00:00 2001 From: Gondermann Date: Tue, 10 Feb 2026 12:19:18 +0100 Subject: [PATCH 06/10] ApplicationCredential Workaround for userID requirement in OpenStack API On-behalf-of: SAP nils.gondermann@sap.com --- internal/osclients/applicationcredential.go | 67 ++++++++++++++++++++- 1 file changed, 64 insertions(+), 3 deletions(-) diff --git a/internal/osclients/applicationcredential.go b/internal/osclients/applicationcredential.go index 1dcda69a9..2742093fa 100644 --- a/internal/osclients/applicationcredential.go +++ b/internal/osclients/applicationcredential.go @@ -18,12 +18,16 @@ package osclients import ( "context" + "errors" "fmt" "iter" + tokens3 "github.com/gophercloud/gophercloud/v2/openstack/identity/v3/tokens" + "github.com/gophercloud/gophercloud/v2" "github.com/gophercloud/gophercloud/v2/openstack" "github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials" + "github.com/gophercloud/gophercloud/v2/openstack/identity/v3/users" "github.com/gophercloud/utils/v2/openstack/clientconfig" ) @@ -66,12 +70,69 @@ func (c applicationcredentialClient) DeleteApplicationCredential(ctx context.Con return applicationcredentials.Delete(ctx, c.client, resourceID).ExtractErr() } +func (c applicationcredentialClient) UpdateApplicationCredential(ctx context.Context, id string, opts applicationcredentials.UpdateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { + return applicationcredentials.Update(ctx, c.client, id, opts).Extract() +} + func (c applicationcredentialClient) GetApplicationCredential(ctx context.Context, resourceID string) (*applicationcredentials.ApplicationCredential, error) { - return applicationcredentials.Get(ctx, c.client, resourceID).Extract() + // The unique ID of an application credential is not enough to query it from OpenStack + // OpenStack actually also requires a unique user ID. + // We can not provide the user ID here, as the function signatures of ORC interfaces + // expect us to return an OpenStack resource based on a single string. + + // To work around this, we first query ApplicationCredentials for the currently + // authenticated user which ORC is connected as. If that fails, we iterate over + // all users we have access to and query their ApplicationCredentials. + + // Currently authenticated user + userID, err := GetAuthenticatedUserID(c.client.ProviderClient) + if err == nil { + appCred, appCredErr := applicationcredentials.Get(ctx, c.client, userID, resourceID).Extract() + + if appCred != nil { + return appCred, appCredErr + } + } + + // If not found in currently authenticated user, try iterating over all users + userPager := users.List(c.client, nil) + userIterator := func(yield func(*users.User, error) bool) { + _ = userPager.EachPage(ctx, yieldPage(users.ExtractUsers, yield)) + } + + for user, userErr := range userIterator { + if userErr != nil { + continue + } + + appCred, appCredErr := applicationcredentials.Get(ctx, c.client, user.ID, resourceID).Extract() + + if appCred != nil { + return appCred, appCredErr + } + } + + return nil, gophercloud.ErrResourceNotFound{ + Name: resourceID, + ResourceType: "ApplicationCredential", + } } -func (c applicationcredentialClient) UpdateApplicationCredential(ctx context.Context, id string, opts applicationcredentials.UpdateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { - return applicationcredentials.Update(ctx, c.client, id, opts).Extract() +func GetAuthenticatedUserID(providerClient *gophercloud.ProviderClient) (string, error) { + r := providerClient.GetAuthResult() + if r == nil { + return "", errors.New("no AuthResult available") + } + switch r := r.(type) { + case tokens3.CreateResult: + u, err := r.ExtractUser() + if err != nil { + return "", err + } + return u.ID, nil + default: + return "", errors.New("wrong AuthResult version") + } } type applicationcredentialErrorClient struct{ error } From 07e206c1cd8bf229b94b381eeab64571a7911ede Mon Sep 17 00:00:00 2001 From: Gondermann Date: Wed, 4 Feb 2026 17:09:55 +0100 Subject: [PATCH 07/10] ApplicationCredential Actuator and Status On-behalf-of: SAP nils.gondermann@sap.com --- .../applicationcredential/actuator.go | 244 +++++++++++------- .../applicationcredential/actuator_test.go | 119 --------- .../applicationcredential/controller.go | 85 +++++- .../applicationcredential/status.go | 32 ++- internal/osclients/applicationcredential.go | 33 +-- 5 files changed, 267 insertions(+), 246 deletions(-) delete mode 100644 internal/controllers/applicationcredential/actuator_test.go diff --git a/internal/controllers/applicationcredential/actuator.go b/internal/controllers/applicationcredential/actuator.go index 1b3ad3efc..b079972ca 100644 --- a/internal/controllers/applicationcredential/actuator.go +++ b/internal/controllers/applicationcredential/actuator.go @@ -18,6 +18,7 @@ package applicationcredential import ( "context" + "fmt" "iter" "github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials" @@ -29,7 +30,6 @@ import ( orcv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/generic/interfaces" "github.com/k-orc/openstack-resource-controller/v2/internal/controllers/generic/progress" - "github.com/k-orc/openstack-resource-controller/v2/internal/logging" "github.com/k-orc/openstack-resource-controller/v2/internal/osclients" "github.com/k-orc/openstack-resource-controller/v2/internal/util/dependency" orcerrors "github.com/k-orc/openstack-resource-controller/v2/internal/util/errors" @@ -41,7 +41,6 @@ type ( createResourceActuator = interfaces.CreateResourceActuator[orcObjectPT, orcObjectT, filterT, osResourceT] deleteResourceActuator = interfaces.DeleteResourceActuator[orcObjectPT, orcObjectT, osResourceT] - resourceReconciler = interfaces.ResourceReconciler[orcObjectPT, osResourceT] helperFactory = interfaces.ResourceHelperFactory[orcObjectPT, orcObjectT, resourceSpecT, filterT, osResourceT] ) @@ -65,33 +64,54 @@ func (actuator applicationcredentialActuator) GetOSResourceByID(ctx context.Cont return resource, nil } +func (actuator applicationcredentialActuator) ResolveUserIDDependency(ctx context.Context, orcObject orcObjectPT) (*string, progress.ReconcileStatus) { + user, rs := userDependency.GetDependency( + ctx, actuator.k8sClient, orcObject, func(dep *orcv1alpha1.User) bool { + return orcv1alpha1.IsAvailable(dep) && dep.Status.ID != nil + }, + ) + + if user == nil { + return nil, rs + } + + return user.Status.ID, rs +} + func (actuator applicationcredentialActuator) ListOSResourcesForAdoption(ctx context.Context, orcObject orcObjectPT) (iter.Seq2[*osResourceT, error], bool) { resourceSpec := orcObject.Spec.Resource if resourceSpec == nil { return nil, false } - // TODO(scaffolding) If you need to filter resources on fields that the List() function - // of gophercloud does not support, it's possible to perform client-side filtering. - // Check osclients.ResourceFilter + user, _ := dependency.FetchDependency( + ctx, actuator.k8sClient, orcObject.Namespace, + &resourceSpec.UserRef, "User", + func(dep *orcv1alpha1.User) bool { return orcv1alpha1.IsAvailable(dep) && dep.Status.ID != nil }, + ) + + var filters []osclients.ResourceFilter[osResourceT] + + // Add client-side filters + if resourceSpec.Description != nil { + filters = append(filters, func(f *applicationcredentials.ApplicationCredential) bool { + return f.Description == *resourceSpec.Description + }) + } listOpts := applicationcredentials.ListOpts{ - Name: getResourceName(orcObject), - Description: ptr.Deref(resourceSpec.Description, ""), + Name: getResourceName(orcObject), } - return actuator.osClient.ListApplicationCredentials(ctx, listOpts), true + return actuator.listOSResources(ctx, ptr.Deref(user.Status.ID, ""), filters, listOpts), true } func (actuator applicationcredentialActuator) ListOSResourcesForImport(ctx context.Context, obj orcObjectPT, filter filterT) (iter.Seq2[*osResourceT, error], progress.ReconcileStatus) { - // TODO(scaffolding) If you need to filter resources on fields that the List() function - // of gophercloud does not support, it's possible to perform client-side filtering. - // Check osclients.ResourceFilter var reconcileStatus progress.ReconcileStatus user, rs := dependency.FetchDependency( ctx, actuator.k8sClient, obj.Namespace, - filter.UserRef, "User", + &filter.UserRef, "User", func(dep *orcv1alpha1.User) bool { return orcv1alpha1.IsAvailable(dep) && dep.Status.ID != nil }, ) reconcileStatus = reconcileStatus.WithReconcileStatus(rs) @@ -100,14 +120,25 @@ func (actuator applicationcredentialActuator) ListOSResourcesForImport(ctx conte return nil, reconcileStatus } + var filters []osclients.ResourceFilter[osResourceT] + + // Add client-side filters + if filter.Description != nil { + filters = append(filters, func(f *applicationcredentials.ApplicationCredential) bool { + return f.Description == *filter.Description + }) + } + listOpts := applicationcredentials.ListOpts{ - Name: string(ptr.Deref(filter.Name, "")), - Description: string(ptr.Deref(filter.Description, "")), - UserID: ptr.Deref(user.Status.ID, ""), - // TODO(scaffolding): Add more import filters + Name: string(ptr.Deref(filter.Name, "")), } - return actuator.osClient.ListApplicationCredentials(ctx, listOpts), reconcileStatus + return actuator.listOSResources(ctx, ptr.Deref(user.Status.ID, ""), filters, listOpts), nil +} + +func (actuator applicationcredentialActuator) listOSResources(ctx context.Context, userID string, filters []osclients.ResourceFilter[osResourceT], listOpts applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] { + applicationCredentials := actuator.osClient.ListApplicationCredentials(ctx, userID, listOpts) + return osclients.Filter(applicationCredentials, filters...) } func (actuator applicationcredentialActuator) CreateResource(ctx context.Context, obj orcObjectPT) (*osResourceT, progress.ReconcileStatus) { @@ -118,116 +149,129 @@ func (actuator applicationcredentialActuator) CreateResource(ctx context.Context return nil, progress.WrapError( orcerrors.Terminal(orcv1alpha1.ConditionReasonInvalidConfiguration, "Creation requested, but spec.resource is not set")) } + var reconcileStatus progress.ReconcileStatus - var userID string - user, userDepRS := userDependency.GetDependency( - ctx, actuator.k8sClient, obj, func(dep *orcv1alpha1.User) bool { - return orcv1alpha1.IsAvailable(dep) && dep.Status.ID != nil - }, - ) - reconcileStatus = reconcileStatus.WithReconcileStatus(userDepRS) - if user != nil { - userID = ptr.Deref(user.Status.ID, "") - } - if needsReschedule, _ := reconcileStatus.NeedsReschedule(); needsReschedule { - return nil, reconcileStatus - } - createOpts := applicationcredentials.CreateOpts{ - Name: getResourceName(obj), - Description: ptr.Deref(resource.Description, ""), - UserID: userID, - // TODO(scaffolding): Add more fields - } + user, userDepRS := userDependency.GetDependency( + ctx, actuator.k8sClient, obj, func(dep *orcv1alpha1.User) bool { + return orcv1alpha1.IsAvailable(dep) && dep.Status.ID != nil + }, + ) - osResource, err := actuator.osClient.CreateApplicationCredential(ctx, createOpts) - if err != nil { - // We should require the spec to be updated before retrying a create which returned a conflict - if !orcerrors.IsRetryable(err) { - err = orcerrors.Terminal(orcv1alpha1.ConditionReasonInvalidConfiguration, "invalid configuration creating resource: "+err.Error(), err) + rolesMap, roleDepRs := roleDependency.GetDependencies( + ctx, actuator.k8sClient, obj, func(dep *orcv1alpha1.Role) bool { + return orcv1alpha1.IsAvailable(dep) && dep.Status.ID != nil + }, + ) + + serviceMap, serviceDepRS := serviceDependency.GetDependencies( + ctx, actuator.k8sClient, obj, func(dep *orcv1alpha1.Service) bool { + return orcv1alpha1.IsAvailable(dep) && dep.Status.ID != nil + }, + ) + + secret, secretReconcileStatus := dependency.FetchDependency( + ctx, actuator.k8sClient, obj.Namespace, + &resource.SecretRef, "Secret", + func(*corev1.Secret) bool { return true }, // Secrets don't have availability status + ) + + var secretData []byte + if secretReconcileStatus == nil { + var ok bool + secretData, ok = secret.Data["value"] + if !ok { + reconcileStatus = reconcileStatus.WithReconcileStatus( + progress.NewReconcileStatus().WithProgressMessage("Application credential secret does not contain \"value\" key")) } - return nil, progress.WrapError(err) } - return osResource, nil -} - -func (actuator applicationcredentialActuator) DeleteResource(ctx context.Context, _ orcObjectPT, resource *osResourceT) progress.ReconcileStatus { - return progress.WrapError(actuator.osClient.DeleteApplicationCredential(ctx, resource.ID)) -} + reconcileStatus = reconcileStatus. + WithReconcileStatus(userDepRS). + WithReconcileStatus(roleDepRs). + WithReconcileStatus(serviceDepRS). + WithReconcileStatus(secretReconcileStatus) -func (actuator applicationcredentialActuator) updateResource(ctx context.Context, obj orcObjectPT, osResource *osResourceT) progress.ReconcileStatus { - log := ctrl.LoggerFrom(ctx) - resource := obj.Spec.Resource - if resource == nil { - // Should have been caught by API validation - return progress.WrapError( - orcerrors.Terminal(orcv1alpha1.ConditionReasonInvalidConfiguration, "Update requested, but spec.resource is not set")) + if needsReschedule, _ := reconcileStatus.NeedsReschedule(); needsReschedule { + return nil, reconcileStatus } - updateOpts := applicationcredentials.UpdateOpts{} + roleList := make([]applicationcredentials.Role, len(resource.RoleRefs)) + for i := range resource.RoleRefs { + roleName := string(resource.RoleRefs[i]) + role, ok := rolesMap[roleName] + if !ok { + // Programming error + return nil, progress.WrapError(fmt.Errorf("role %s was not returned by GetDependencies", roleName)) + } + roleList[i].ID = *role.Status.ID + } - handleNameUpdate(&updateOpts, obj, osResource) - handleDescriptionUpdate(&updateOpts, resource, osResource) + accessRuleList := make([]applicationcredentials.AccessRule, len(resource.AccessRules)) + for i := range resource.AccessRules { + accessRuleSpec := &resource.AccessRules[i] + accessRule := &accessRuleList[i] + + if accessRuleSpec.ServiceRef != nil { + serviceName := string(*accessRuleSpec.ServiceRef) + service, ok := serviceMap[serviceName] + if !ok { + // Programming error + return nil, progress.WrapError(fmt.Errorf("service %s was not returned by GetDependencies", serviceName)) + } + accessRule.Service = service.Status.Resource.Type + } - // TODO(scaffolding): add handler for all fields supporting mutability + if accessRuleSpec.Path != nil { + accessRule.Path = *accessRuleSpec.Path + } - needsUpdate, err := needsUpdate(updateOpts) - if err != nil { - return progress.WrapError( - orcerrors.Terminal(orcv1alpha1.ConditionReasonInvalidConfiguration, "invalid configuration updating resource: "+err.Error(), err)) - } - if !needsUpdate { - log.V(logging.Debug).Info("No changes") - return nil + if accessRuleSpec.Method != nil { + accessRule.Method = string(*accessRuleSpec.Method) + } } - _, err = actuator.osClient.UpdateApplicationCredential(ctx, osResource.ID, updateOpts) + createOpts := applicationcredentials.CreateOpts{ + Name: getResourceName(obj), + Description: ptr.Deref(resource.Description, ""), + Unrestricted: ptr.Deref(resource.Unrestricted, false), + Secret: string(secretData), + Roles: roleList, + AccessRules: accessRuleList, + } - // We should require the spec to be updated before retrying an update which returned a conflict - if orcerrors.IsConflict(err) { - err = orcerrors.Terminal(orcv1alpha1.ConditionReasonInvalidConfiguration, "invalid configuration updating resource: "+err.Error(), err) + if resource.ExpiresAt != nil { + createOpts.ExpiresAt = &resource.ExpiresAt.Time } + osResource, err := actuator.osClient.CreateApplicationCredential(ctx, ptr.Deref(user.Status.ID, ""), createOpts) if err != nil { - return progress.WrapError(err) + // We should require the spec to be updated before retrying a create which returned a conflict + if !orcerrors.IsRetryable(err) { + err = orcerrors.Terminal(orcv1alpha1.ConditionReasonInvalidConfiguration, "invalid configuration creating resource: "+err.Error(), err) + } + return nil, progress.WrapError(err) } - return progress.NeedsRefresh() + return osResource, nil } -func needsUpdate(updateOpts applicationcredentials.UpdateOpts) (bool, error) { - updateOptsMap, err := updateOpts.ToApplicationCredentialUpdateMap() - if err != nil { - return false, err - } - - updateMap, ok := updateOptsMap["application_credentials"].(map[string]any) - if !ok { - updateMap = make(map[string]any) - } +func (actuator applicationcredentialActuator) DeleteResource(ctx context.Context, orcObject orcObjectPT, resource *osResourceT) progress.ReconcileStatus { + var reconcileStatus progress.ReconcileStatus - return len(updateMap) > 0, nil -} + user, userDepRS := userDependency.GetDependency( + ctx, actuator.k8sClient, orcObject, func(dep *orcv1alpha1.User) bool { + return orcv1alpha1.IsAvailable(dep) && dep.Status.ID != nil + }, + ) -func handleNameUpdate(updateOpts *applicationcredentials.UpdateOpts, obj orcObjectPT, osResource *osResourceT) { - name := getResourceName(obj) - if osResource.Name != name { - updateOpts.Name = &name - } -} + reconcileStatus = reconcileStatus.WithReconcileStatus(userDepRS) -func handleDescriptionUpdate(updateOpts *applicationcredentials.UpdateOpts, resource *resourceSpecT, osResource *osResourceT) { - description := ptr.Deref(resource.Description, "") - if osResource.Description != description { - updateOpts.Description = &description + if needsReschedule, _ := reconcileStatus.NeedsReschedule(); needsReschedule { + return reconcileStatus } -} -func (actuator applicationcredentialActuator) GetResourceReconcilers(ctx context.Context, orcObject orcObjectPT, osResource *osResourceT, controller interfaces.ResourceController) ([]resourceReconciler, progress.ReconcileStatus) { - return []resourceReconciler{ - actuator.updateResource, - }, nil + return progress.WrapError(actuator.osClient.DeleteApplicationCredential(ctx, ptr.Deref(user.Status.ID, ""), resource.ID)) } type applicationcredentialHelperFactory struct{} diff --git a/internal/controllers/applicationcredential/actuator_test.go b/internal/controllers/applicationcredential/actuator_test.go deleted file mode 100644 index 1a8015f89..000000000 --- a/internal/controllers/applicationcredential/actuator_test.go +++ /dev/null @@ -1,119 +0,0 @@ -/* -Copyright The ORC Authors. - -Licensed under the Apache License, Version 2.0 (the "License"); -you may not use this file except in compliance with the License. -You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - -Unless required by applicable law or agreed to in writing, software -distributed under the License is distributed on an "AS IS" BASIS, -WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -See the License for the specific language governing permissions and -limitations under the License. -*/ - -package applicationcredential - -import ( - "testing" - - "github.com/gophercloud/gophercloud/v2/openstack/identity/v3/applicationcredentials" - orcv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" - "k8s.io/utils/ptr" -) - -func TestNeedsUpdate(t *testing.T) { - testCases := []struct { - name string - updateOpts applicationcredentials.UpdateOpts - expectChange bool - }{ - { - name: "Empty base opts", - updateOpts: applicationcredentials.UpdateOpts{}, - expectChange: false, - }, - { - name: "Updated opts", - updateOpts: applicationcredentials.UpdateOpts{Name: ptr.To("updated")}, - expectChange: true, - }, - } - - for _, tt := range testCases { - t.Run(tt.name, func(t *testing.T) { - got, _ := needsUpdate(tt.updateOpts) - if got != tt.expectChange { - t.Errorf("Expected change: %v, got: %v", tt.expectChange, got) - } - }) - } -} - -func TestHandleNameUpdate(t *testing.T) { - ptrToName := ptr.To[orcv1alpha1.OpenStackName] - testCases := []struct { - name string - newValue *orcv1alpha1.OpenStackName - existingValue string - expectChange bool - }{ - {name: "Identical", newValue: ptrToName("name"), existingValue: "name", expectChange: false}, - {name: "Different", newValue: ptrToName("new-name"), existingValue: "name", expectChange: true}, - {name: "No value provided, existing is identical to object name", newValue: nil, existingValue: "object-name", expectChange: false}, - {name: "No value provided, existing is different from object name", newValue: nil, existingValue: "different-from-object-name", expectChange: true}, - } - - for _, tt := range testCases { - t.Run(tt.name, func(t *testing.T) { - resource := &orcv1alpha1.ApplicationCredential{} - resource.Name = "object-name" - resource.Spec = orcv1alpha1.ApplicationCredentialSpec{ - Resource: &orcv1alpha1.ApplicationCredentialResourceSpec{Name: tt.newValue}, - } - osResource := &osResourceT{Name: tt.existingValue} - - updateOpts := applicationcredentials.UpdateOpts{} - handleNameUpdate(&updateOpts, resource, osResource) - - got, _ := needsUpdate(updateOpts) - if got != tt.expectChange { - t.Errorf("Expected change: %v, got: %v", tt.expectChange, got) - } - }) - - } -} - -func TestHandleDescriptionUpdate(t *testing.T) { - ptrToDescription := ptr.To[string] - testCases := []struct { - name string - newValue *string - existingValue string - expectChange bool - }{ - {name: "Identical", newValue: ptrToDescription("desc"), existingValue: "desc", expectChange: false}, - {name: "Different", newValue: ptrToDescription("new-desc"), existingValue: "desc", expectChange: true}, - {name: "No value provided, existing is set", newValue: nil, existingValue: "desc", expectChange: true}, - {name: "No value provided, existing is empty", newValue: nil, existingValue: "", expectChange: false}, - } - - for _, tt := range testCases { - t.Run(tt.name, func(t *testing.T) { - resource := &orcv1alpha1.ApplicationCredentialResourceSpec{Description: tt.newValue} - osResource := &osResourceT{Description: tt.existingValue} - - updateOpts := applicationcredentials.UpdateOpts{} - handleDescriptionUpdate(&updateOpts, resource, osResource) - - got, _ := needsUpdate(updateOpts) - if got != tt.expectChange { - t.Errorf("Expected change: %v, got: %v", tt.expectChange, got) - } - }) - - } -} diff --git a/internal/controllers/applicationcredential/controller.go b/internal/controllers/applicationcredential/controller.go index 34a86a51e..9bb6f283f 100644 --- a/internal/controllers/applicationcredential/controller.go +++ b/internal/controllers/applicationcredential/controller.go @@ -20,6 +20,7 @@ import ( "context" "errors" + corev1 "k8s.io/api/core/v1" ctrl "sigs.k8s.io/controller-runtime" "sigs.k8s.io/controller-runtime/pkg/builder" "sigs.k8s.io/controller-runtime/pkg/controller" @@ -39,6 +40,54 @@ const controllerName = "applicationcredential" // +kubebuilder:rbac:groups=openstack.k-orc.cloud,resources=applicationcredentials,verbs=get;list;watch;create;update;patch;delete // +kubebuilder:rbac:groups=openstack.k-orc.cloud,resources=applicationcredentials/status,verbs=get;update;patch +var ( + // We don't need a deletion guard on the application credential secret because it's only + // used on creation. + secretDependency = dependency.NewDependency[*orcv1alpha1.ApplicationCredentialList, *corev1.Secret]( + "spec.resource.secretRef", + func(applicationcredential *orcv1alpha1.ApplicationCredential) []string { + resource := applicationcredential.Spec.Resource + if resource == nil { + return nil + } + + return []string{string(resource.SecretRef)} + }, + ) + + roleDependency = dependency.NewDeletionGuardDependency[*orcv1alpha1.ApplicationCredentialList, *orcv1alpha1.Role]( + "spec.resource.roleRefs", + func(port *orcv1alpha1.ApplicationCredential) []string { + if port.Spec.Resource == nil { + return nil + } + roles := make([]string, len(port.Spec.Resource.RoleRefs)) + for i := range port.Spec.Resource.RoleRefs { + roles[i] = string(port.Spec.Resource.RoleRefs[i]) + } + return roles + }, + finalizer, externalObjectFieldOwner, + ) + + serviceDependency = dependency.NewDeletionGuardDependency[*orcv1alpha1.ApplicationCredentialList, *orcv1alpha1.Service]( + "spec.resource.accessRules[].serviceRef", + func(router *orcv1alpha1.ApplicationCredential) []string { + resource := router.Spec.Resource + if resource == nil { + return nil + } + + services := make([]string, len(resource.AccessRules)) + for i := range resource.AccessRules { + services[i] = string(*resource.AccessRules[i].ServiceRef) + } + return services + }, + finalizer, externalObjectFieldOwner, + ) +) + type applicationcredentialReconcilerConstructor struct { scopeFactory scope.Factory } @@ -67,10 +116,10 @@ var userImportDependency = dependency.NewDependency[*orcv1alpha1.ApplicationCred "spec.import.filter.userRef", func(applicationcredential *orcv1alpha1.ApplicationCredential) []string { resource := applicationcredential.Spec.Import - if resource == nil || resource.Filter == nil || resource.Filter.UserRef == nil { + if resource == nil || resource.Filter == nil { return nil } - return []string{string(*resource.Filter.UserRef)} + return []string{string(resource.Filter.UserRef)} }, ) @@ -89,6 +138,21 @@ func (c applicationcredentialReconcilerConstructor) SetupWithManager(ctx context return err } + secretWatchEventHandler, err := secretDependency.WatchEventHandler(log, k8sClient) + if err != nil { + return err + } + + roleWatchEventHandler, err := roleDependency.WatchEventHandler(log, k8sClient) + if err != nil { + return err + } + + serviceWatchEventHandler, err := serviceDependency.WatchEventHandler(log, k8sClient) + if err != nil { + return err + } + builder := ctrl.NewControllerManagedBy(mgr). WithOptions(options). Watches(&orcv1alpha1.User{}, userWatchEventHandler, @@ -98,12 +162,29 @@ func (c applicationcredentialReconcilerConstructor) SetupWithManager(ctx context Watches(&orcv1alpha1.User{}, userImportWatchEventHandler, builder.WithPredicates(predicates.NewBecameAvailable(log, &orcv1alpha1.User{})), ). + // XXX: This is a general watch on secrets. A general watch on secrets + // is undesirable because: + // - It requires problematic RBAC + // - Secrets are arbitrarily large, and we don't want to cache their contents + // + // These will require separate solutions. For the latter we should + // probably use a MetadataOnly watch only secrets. + Watches(&corev1.Secret{}, secretWatchEventHandler). + Watches(&orcv1alpha1.Role{}, roleWatchEventHandler, + builder.WithPredicates(predicates.NewBecameAvailable(log, &orcv1alpha1.Role{})), + ). + Watches(&orcv1alpha1.Service{}, serviceWatchEventHandler, + builder.WithPredicates(predicates.NewBecameAvailable(log, &orcv1alpha1.Service{})), + ). For(&orcv1alpha1.ApplicationCredential{}) if err := errors.Join( userDependency.AddToManager(ctx, mgr), userImportDependency.AddToManager(ctx, mgr), credentialsDependency.AddToManager(ctx, mgr), + secretDependency.AddToManager(ctx, mgr), + roleDependency.AddToManager(ctx, mgr), + serviceDependency.AddToManager(ctx, mgr), credentials.AddCredentialsWatch(log, mgr.GetClient(), builder, credentialsDependency), ); err != nil { return err diff --git a/internal/controllers/applicationcredential/status.go b/internal/controllers/applicationcredential/status.go index 34141fd33..2530a65e9 100644 --- a/internal/controllers/applicationcredential/status.go +++ b/internal/controllers/applicationcredential/status.go @@ -50,15 +50,39 @@ func (applicationcredentialStatusWriter) ResourceAvailableStatus(orcObject *orcv func (applicationcredentialStatusWriter) ApplyResourceStatus(log logr.Logger, osResource *osResourceT, statusApply *statusApplyT) { resourceStatus := orcapplyconfigv1alpha1.ApplicationCredentialResourceStatus(). - WithUserID(osResource.UserID). - WithName(osResource.Name) + WithName(osResource.Name). + WithUnrestricted(osResource.Unrestricted). + WithProjectID(osResource.ProjectID) - // TODO(scaffolding): add all of the fields supported in the ApplicationCredentialResourceStatus struct - // If a zero-value isn't expected in the response, place it behind a conditional + if !osResource.ExpiresAt.IsZero() { + resourceStatus.WithExpiresAt(metav1.NewTime(osResource.ExpiresAt)) + } if osResource.Description != "" { resourceStatus.WithDescription(osResource.Description) } + for i := range osResource.Roles { + roleStatus := orcapplyconfigv1alpha1.ApplicationCredentialRoleStatus(). + WithID(osResource.Roles[i].ID). + WithName(osResource.Roles[i].Name) + + if osResource.Roles[i].DomainID != "" { + roleStatus.WithDomainID(osResource.Roles[i].DomainID) + } + + resourceStatus.WithRoles(roleStatus) + } + + for i := range osResource.AccessRules { + accessRuleStatus := orcapplyconfigv1alpha1.ApplicationCredentialAccessRuleStatus(). + WithID(osResource.AccessRules[i].ID). + WithPath(osResource.AccessRules[i].Path). + WithMethod(osResource.AccessRules[i].Method). + WithService(osResource.AccessRules[i].Service) + + resourceStatus.WithAccessRules(accessRuleStatus) + } + statusApply.WithResource(resourceStatus) } diff --git a/internal/osclients/applicationcredential.go b/internal/osclients/applicationcredential.go index 2742093fa..30c63adad 100644 --- a/internal/osclients/applicationcredential.go +++ b/internal/osclients/applicationcredential.go @@ -32,11 +32,10 @@ import ( ) type ApplicationCredentialClient interface { - ListApplicationCredentials(ctx context.Context, listOpts applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] - CreateApplicationCredential(ctx context.Context, opts applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) - DeleteApplicationCredential(ctx context.Context, resourceID string) error + ListApplicationCredentials(ctx context.Context, userID string, listOpts applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] + CreateApplicationCredential(ctx context.Context, userID string, opts applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) + DeleteApplicationCredential(ctx context.Context, userID string, resourceID string) error GetApplicationCredential(ctx context.Context, resourceID string) (*applicationcredentials.ApplicationCredential, error) - UpdateApplicationCredential(ctx context.Context, id string, opts applicationcredentials.UpdateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) } type applicationcredentialClient struct{ client *gophercloud.ServiceClient } @@ -55,23 +54,19 @@ func NewApplicationCredentialClient(providerClient *gophercloud.ProviderClient, return &applicationcredentialClient{client}, nil } -func (c applicationcredentialClient) ListApplicationCredentials(ctx context.Context, listOpts applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] { - pager := applicationcredentials.List(c.client, listOpts) +func (c applicationcredentialClient) ListApplicationCredentials(ctx context.Context, userID string, listOpts applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] { + pager := applicationcredentials.List(c.client, userID, listOpts) return func(yield func(*applicationcredentials.ApplicationCredential, error) bool) { _ = pager.EachPage(ctx, yieldPage(applicationcredentials.ExtractApplicationCredentials, yield)) } } -func (c applicationcredentialClient) CreateApplicationCredential(ctx context.Context, opts applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { - return applicationcredentials.Create(ctx, c.client, opts).Extract() +func (c applicationcredentialClient) CreateApplicationCredential(ctx context.Context, userID string, opts applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { + return applicationcredentials.Create(ctx, c.client, userID, opts).Extract() } -func (c applicationcredentialClient) DeleteApplicationCredential(ctx context.Context, resourceID string) error { - return applicationcredentials.Delete(ctx, c.client, resourceID).ExtractErr() -} - -func (c applicationcredentialClient) UpdateApplicationCredential(ctx context.Context, id string, opts applicationcredentials.UpdateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { - return applicationcredentials.Update(ctx, c.client, id, opts).Extract() +func (c applicationcredentialClient) DeleteApplicationCredential(ctx context.Context, userID string, resourceID string) error { + return applicationcredentials.Delete(ctx, c.client, userID, resourceID).ExtractErr() } func (c applicationcredentialClient) GetApplicationCredential(ctx context.Context, resourceID string) (*applicationcredentials.ApplicationCredential, error) { @@ -142,24 +137,20 @@ func NewApplicationCredentialErrorClient(e error) ApplicationCredentialClient { return applicationcredentialErrorClient{e} } -func (e applicationcredentialErrorClient) ListApplicationCredentials(_ context.Context, _ applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] { +func (e applicationcredentialErrorClient) ListApplicationCredentials(_ context.Context, _ string, _ applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] { return func(yield func(*applicationcredentials.ApplicationCredential, error) bool) { yield(nil, e.error) } } -func (e applicationcredentialErrorClient) CreateApplicationCredential(_ context.Context, _ applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { +func (e applicationcredentialErrorClient) CreateApplicationCredential(_ context.Context, _ string, _ applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { return nil, e.error } -func (e applicationcredentialErrorClient) DeleteApplicationCredential(_ context.Context, _ string) error { +func (e applicationcredentialErrorClient) DeleteApplicationCredential(_ context.Context, _ string, _ string) error { return e.error } func (e applicationcredentialErrorClient) GetApplicationCredential(_ context.Context, _ string) (*applicationcredentials.ApplicationCredential, error) { return nil, e.error } - -func (e applicationcredentialErrorClient) UpdateApplicationCredential(_ context.Context, _ string, _ applicationcredentials.UpdateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { - return nil, e.error -} From db95c8ee1cb9901d0c962c1c352ad68daacaf144 Mon Sep 17 00:00:00 2001 From: Gondermann Date: Tue, 17 Mar 2026 12:17:59 +0100 Subject: [PATCH 08/10] ApplicationCredential Regenerate Interfaces On-behalf-of: SAP nils.gondermann@sap.com --- api/v1alpha1/zz_generated.deepcopy.go | 141 +++- cmd/models-schema/zz_generated.openapi.go | 717 ++++++++++++------ ...ck.k-orc.cloud_applicationcredentials.yaml | 147 +++- .../osclients/mock/applicationcredential.go | 39 +- .../applicationcredentialaccessrule.go | 61 ++ .../applicationcredentialaccessrulestatus.go | 66 ++ .../v1alpha1/applicationcredentialfilter.go | 18 +- .../applicationcredentialresourcespec.go | 59 +- .../applicationcredentialresourcestatus.go | 64 +- .../applicationcredentialrolestatus.go | 57 ++ .../applyconfiguration/internal/internal.go | 80 +- pkg/clients/applyconfiguration/utils.go | 6 + website/docs/crd-reference.md | 137 +++- 13 files changed, 1260 insertions(+), 332 deletions(-) create mode 100644 pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialaccessrule.go create mode 100644 pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialaccessrulestatus.go create mode 100644 pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialrolestatus.go diff --git a/api/v1alpha1/zz_generated.deepcopy.go b/api/v1alpha1/zz_generated.deepcopy.go index 91bbfa4e3..4cb24d60f 100644 --- a/api/v1alpha1/zz_generated.deepcopy.go +++ b/api/v1alpha1/zz_generated.deepcopy.go @@ -364,6 +364,71 @@ func (in *ApplicationCredential) DeepCopyObject() runtime.Object { return nil } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ApplicationCredentialAccessRule) DeepCopyInto(out *ApplicationCredentialAccessRule) { + *out = *in + if in.Path != nil { + in, out := &in.Path, &out.Path + *out = new(string) + **out = **in + } + if in.Method != nil { + in, out := &in.Method, &out.Method + *out = new(HTTPMethod) + **out = **in + } + if in.ServiceRef != nil { + in, out := &in.ServiceRef, &out.ServiceRef + *out = new(KubernetesNameRef) + **out = **in + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialAccessRule. +func (in *ApplicationCredentialAccessRule) DeepCopy() *ApplicationCredentialAccessRule { + if in == nil { + return nil + } + out := new(ApplicationCredentialAccessRule) + in.DeepCopyInto(out) + return out +} + +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ApplicationCredentialAccessRuleStatus) DeepCopyInto(out *ApplicationCredentialAccessRuleStatus) { + *out = *in + if in.ID != nil { + in, out := &in.ID, &out.ID + *out = new(string) + **out = **in + } + if in.Path != nil { + in, out := &in.Path, &out.Path + *out = new(string) + **out = **in + } + if in.Method != nil { + in, out := &in.Method, &out.Method + *out = new(string) + **out = **in + } + if in.Service != nil { + in, out := &in.Service, &out.Service + *out = new(string) + **out = **in + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialAccessRuleStatus. +func (in *ApplicationCredentialAccessRuleStatus) DeepCopy() *ApplicationCredentialAccessRuleStatus { + if in == nil { + return nil + } + out := new(ApplicationCredentialAccessRuleStatus) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ApplicationCredentialFilter) DeepCopyInto(out *ApplicationCredentialFilter) { *out = *in @@ -377,11 +442,6 @@ func (in *ApplicationCredentialFilter) DeepCopyInto(out *ApplicationCredentialFi *out = new(string) **out = **in } - if in.UserRef != nil { - in, out := &in.UserRef, &out.UserRef - *out = new(KubernetesNameRef) - **out = **in - } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialFilter. @@ -464,6 +524,27 @@ func (in *ApplicationCredentialResourceSpec) DeepCopyInto(out *ApplicationCreden *out = new(string) **out = **in } + if in.Unrestricted != nil { + in, out := &in.Unrestricted, &out.Unrestricted + *out = new(bool) + **out = **in + } + if in.RoleRefs != nil { + in, out := &in.RoleRefs, &out.RoleRefs + *out = make([]KubernetesNameRef, len(*in)) + copy(*out, *in) + } + if in.AccessRules != nil { + in, out := &in.AccessRules, &out.AccessRules + *out = make([]ApplicationCredentialAccessRule, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } + if in.ExpiresAt != nil { + in, out := &in.ExpiresAt, &out.ExpiresAt + *out = (*in).DeepCopy() + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialResourceSpec. @@ -479,6 +560,24 @@ func (in *ApplicationCredentialResourceSpec) DeepCopy() *ApplicationCredentialRe // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ApplicationCredentialResourceStatus) DeepCopyInto(out *ApplicationCredentialResourceStatus) { *out = *in + if in.Roles != nil { + in, out := &in.Roles, &out.Roles + *out = make([]ApplicationCredentialRoleStatus, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } + if in.ExpiresAt != nil { + in, out := &in.ExpiresAt, &out.ExpiresAt + *out = (*in).DeepCopy() + } + if in.AccessRules != nil { + in, out := &in.AccessRules, &out.AccessRules + *out = make([]ApplicationCredentialAccessRuleStatus, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } } // DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialResourceStatus. @@ -491,6 +590,36 @@ func (in *ApplicationCredentialResourceStatus) DeepCopy() *ApplicationCredential return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ApplicationCredentialRoleStatus) DeepCopyInto(out *ApplicationCredentialRoleStatus) { + *out = *in + if in.Name != nil { + in, out := &in.Name, &out.Name + *out = new(string) + **out = **in + } + if in.ID != nil { + in, out := &in.ID, &out.ID + *out = new(string) + **out = **in + } + if in.DomainID != nil { + in, out := &in.DomainID, &out.DomainID + *out = new(string) + **out = **in + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ApplicationCredentialRoleStatus. +func (in *ApplicationCredentialRoleStatus) DeepCopy() *ApplicationCredentialRoleStatus { + if in == nil { + return nil + } + out := new(ApplicationCredentialRoleStatus) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ApplicationCredentialSpec) DeepCopyInto(out *ApplicationCredentialSpec) { *out = *in @@ -540,7 +669,7 @@ func (in *ApplicationCredentialStatus) DeepCopyInto(out *ApplicationCredentialSt if in.Resource != nil { in, out := &in.Resource, &out.Resource *out = new(ApplicationCredentialResourceStatus) - **out = **in + (*in).DeepCopyInto(*out) } } diff --git a/cmd/models-schema/zz_generated.openapi.go b/cmd/models-schema/zz_generated.openapi.go index e00660aa9..cd6d6186d 100644 --- a/cmd/models-schema/zz_generated.openapi.go +++ b/cmd/models-schema/zz_generated.openapi.go @@ -30,243 +30,246 @@ import ( func GetOpenAPIDefinitions(ref common.ReferenceCallback) map[string]common.OpenAPIDefinition { return map[string]common.OpenAPIDefinition{ - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Address": schema_openstack_resource_controller_v2_api_v1alpha1_Address(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScope": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScope(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeImport": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeList": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllocationPool": schema_openstack_resource_controller_v2_api_v1alpha1_AllocationPool(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllocationPoolStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AllocationPoolStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllowedAddressPair": schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPair(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllowedAddressPairStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPairStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredential": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredential(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialImport": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialList": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.CloudCredentialsReference": schema_openstack_resource_controller_v2_api_v1alpha1_CloudCredentialsReference(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Domain": schema_openstack_resource_controller_v2_api_v1alpha1_Domain(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainFilter": schema_openstack_resource_controller_v2_api_v1alpha1_DomainFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainImport": schema_openstack_resource_controller_v2_api_v1alpha1_DomainImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainList": schema_openstack_resource_controller_v2_api_v1alpha1_DomainList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_DomainResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_DomainResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainSpec": schema_openstack_resource_controller_v2_api_v1alpha1_DomainSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainStatus": schema_openstack_resource_controller_v2_api_v1alpha1_DomainStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Endpoint": schema_openstack_resource_controller_v2_api_v1alpha1_Endpoint(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointFilter": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointImport": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointList": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointSpec": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointStatus": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ExternalGateway": schema_openstack_resource_controller_v2_api_v1alpha1_ExternalGateway(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ExternalGatewayStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ExternalGatewayStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByKeystoneTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByKeystoneTags(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByNeutronTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByNeutronTags(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByServerTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByServerTags(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FixedIPStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FixedIPStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Flavor": schema_openstack_resource_controller_v2_api_v1alpha1_Flavor(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorFilter": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorImport": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorList": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIP": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIP(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPFilter": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPImport": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPList": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Group": schema_openstack_resource_controller_v2_api_v1alpha1_Group(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_GroupFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_GroupImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupList": schema_openstack_resource_controller_v2_api_v1alpha1_GroupList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_GroupResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_GroupResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_GroupSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_GroupStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostID": schema_openstack_resource_controller_v2_api_v1alpha1_HostID(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostRoute": schema_openstack_resource_controller_v2_api_v1alpha1_HostRoute(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostRouteStatus": schema_openstack_resource_controller_v2_api_v1alpha1_HostRouteStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.IPv6Options": schema_openstack_resource_controller_v2_api_v1alpha1_IPv6Options(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Image": schema_openstack_resource_controller_v2_api_v1alpha1_Image(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageContent": schema_openstack_resource_controller_v2_api_v1alpha1_ImageContent(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageContentSourceDownload": schema_openstack_resource_controller_v2_api_v1alpha1_ImageContentSourceDownload(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ImageFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageHash": schema_openstack_resource_controller_v2_api_v1alpha1_ImageHash(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageImport": schema_openstack_resource_controller_v2_api_v1alpha1_ImageImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageList": schema_openstack_resource_controller_v2_api_v1alpha1_ImageList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageProperties": schema_openstack_resource_controller_v2_api_v1alpha1_ImageProperties(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImagePropertiesHardware": schema_openstack_resource_controller_v2_api_v1alpha1_ImagePropertiesHardware(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImagePropertiesOperatingSystem": schema_openstack_resource_controller_v2_api_v1alpha1_ImagePropertiesOperatingSystem(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ImageResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ImageResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ImageSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ImageStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageStatusExtra": schema_openstack_resource_controller_v2_api_v1alpha1_ImageStatusExtra(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPair": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPair(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairFilter": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairImport": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairList": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairSpec": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairStatus": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ManagedOptions": schema_openstack_resource_controller_v2_api_v1alpha1_ManagedOptions(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Network": schema_openstack_resource_controller_v2_api_v1alpha1_Network(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkFilter": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkImport": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkList": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkSpec": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkStatus": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NeutronStatusMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_NeutronStatusMetadata(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Port": schema_openstack_resource_controller_v2_api_v1alpha1_Port(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortFilter": schema_openstack_resource_controller_v2_api_v1alpha1_PortFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortImport": schema_openstack_resource_controller_v2_api_v1alpha1_PortImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortList": schema_openstack_resource_controller_v2_api_v1alpha1_PortList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortRangeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortRangeSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortRangeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortRangeStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Project": schema_openstack_resource_controller_v2_api_v1alpha1_Project(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectImport": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectList": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProviderPropertiesStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProviderPropertiesStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Role": schema_openstack_resource_controller_v2_api_v1alpha1_Role(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleFilter": schema_openstack_resource_controller_v2_api_v1alpha1_RoleFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleImport": schema_openstack_resource_controller_v2_api_v1alpha1_RoleImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleList": schema_openstack_resource_controller_v2_api_v1alpha1_RoleList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RoleResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RoleResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RoleSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RoleStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Router": schema_openstack_resource_controller_v2_api_v1alpha1_Router(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterFilter": schema_openstack_resource_controller_v2_api_v1alpha1_RouterFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterImport": schema_openstack_resource_controller_v2_api_v1alpha1_RouterImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterface": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterface(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceList": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterList": schema_openstack_resource_controller_v2_api_v1alpha1_RouterList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroup": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroup(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupList": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupRule": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupRule(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupRuleStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupRuleStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Server": schema_openstack_resource_controller_v2_api_v1alpha1_Server(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServerFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroup": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroup(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupList": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupRules": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupRules(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupRulesStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupRulesStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServerImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerInterfaceFixedIP": schema_openstack_resource_controller_v2_api_v1alpha1_ServerInterfaceFixedIP(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerInterfaceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerInterfaceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerList": schema_openstack_resource_controller_v2_api_v1alpha1_ServerList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_ServerMetadata(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerMetadataStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerMetadataStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerPortSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerPortSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerVolumeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerVolumeSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerVolumeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerVolumeStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Service": schema_openstack_resource_controller_v2_api_v1alpha1_Service(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceList": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Subnet": schema_openstack_resource_controller_v2_api_v1alpha1_Subnet(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetFilter": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetGateway": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetGateway(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetImport": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetList": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Trunk": schema_openstack_resource_controller_v2_api_v1alpha1_Trunk(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkFilter": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkImport": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkList": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSubportSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSubportSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSubportStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSubportStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.User": schema_openstack_resource_controller_v2_api_v1alpha1_User(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserDataSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserDataSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserFilter": schema_openstack_resource_controller_v2_api_v1alpha1_UserFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserImport": schema_openstack_resource_controller_v2_api_v1alpha1_UserImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserList": schema_openstack_resource_controller_v2_api_v1alpha1_UserList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_UserResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserStatus": schema_openstack_resource_controller_v2_api_v1alpha1_UserStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Volume": schema_openstack_resource_controller_v2_api_v1alpha1_Volume(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeAttachmentStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeAttachmentStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeImport": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeList": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeMetadata(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeMetadataStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeMetadataStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeType": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeType(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeExtraSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeExtraSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeExtraSpecStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeExtraSpecStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeFilter(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeImport": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeImport(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeList": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeList(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeResourceSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeResourceStatus(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeSpec(ref), - "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeStatus(ref), - "k8s.io/api/core/v1.AWSElasticBlockStoreVolumeSource": schema_k8sio_api_core_v1_AWSElasticBlockStoreVolumeSource(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Address": schema_openstack_resource_controller_v2_api_v1alpha1_Address(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScope": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScope(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeImport": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeList": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AddressScopeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AddressScopeStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllocationPool": schema_openstack_resource_controller_v2_api_v1alpha1_AllocationPool(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllocationPoolStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AllocationPoolStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllowedAddressPair": schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPair(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.AllowedAddressPairStatus": schema_openstack_resource_controller_v2_api_v1alpha1_AllowedAddressPairStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredential": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredential(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialAccessRule": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialAccessRule(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialAccessRuleStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialAccessRuleStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialImport": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialList": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialRoleStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialRoleStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.CloudCredentialsReference": schema_openstack_resource_controller_v2_api_v1alpha1_CloudCredentialsReference(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Domain": schema_openstack_resource_controller_v2_api_v1alpha1_Domain(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainFilter": schema_openstack_resource_controller_v2_api_v1alpha1_DomainFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainImport": schema_openstack_resource_controller_v2_api_v1alpha1_DomainImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainList": schema_openstack_resource_controller_v2_api_v1alpha1_DomainList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_DomainResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_DomainResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainSpec": schema_openstack_resource_controller_v2_api_v1alpha1_DomainSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.DomainStatus": schema_openstack_resource_controller_v2_api_v1alpha1_DomainStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Endpoint": schema_openstack_resource_controller_v2_api_v1alpha1_Endpoint(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointFilter": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointImport": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointList": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointSpec": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.EndpointStatus": schema_openstack_resource_controller_v2_api_v1alpha1_EndpointStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ExternalGateway": schema_openstack_resource_controller_v2_api_v1alpha1_ExternalGateway(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ExternalGatewayStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ExternalGatewayStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByKeystoneTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByKeystoneTags(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByNeutronTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByNeutronTags(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FilterByServerTags": schema_openstack_resource_controller_v2_api_v1alpha1_FilterByServerTags(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FixedIPStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FixedIPStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Flavor": schema_openstack_resource_controller_v2_api_v1alpha1_Flavor(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorFilter": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorImport": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorList": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FlavorStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FlavorStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIP": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIP(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPFilter": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPImport": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPList": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPSpec": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.FloatingIPStatus": schema_openstack_resource_controller_v2_api_v1alpha1_FloatingIPStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Group": schema_openstack_resource_controller_v2_api_v1alpha1_Group(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_GroupFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_GroupImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupList": schema_openstack_resource_controller_v2_api_v1alpha1_GroupList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_GroupResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_GroupResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_GroupSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.GroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_GroupStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostID": schema_openstack_resource_controller_v2_api_v1alpha1_HostID(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostRoute": schema_openstack_resource_controller_v2_api_v1alpha1_HostRoute(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.HostRouteStatus": schema_openstack_resource_controller_v2_api_v1alpha1_HostRouteStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.IPv6Options": schema_openstack_resource_controller_v2_api_v1alpha1_IPv6Options(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Image": schema_openstack_resource_controller_v2_api_v1alpha1_Image(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageContent": schema_openstack_resource_controller_v2_api_v1alpha1_ImageContent(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageContentSourceDownload": schema_openstack_resource_controller_v2_api_v1alpha1_ImageContentSourceDownload(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ImageFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageHash": schema_openstack_resource_controller_v2_api_v1alpha1_ImageHash(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageImport": schema_openstack_resource_controller_v2_api_v1alpha1_ImageImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageList": schema_openstack_resource_controller_v2_api_v1alpha1_ImageList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageProperties": schema_openstack_resource_controller_v2_api_v1alpha1_ImageProperties(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImagePropertiesHardware": schema_openstack_resource_controller_v2_api_v1alpha1_ImagePropertiesHardware(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImagePropertiesOperatingSystem": schema_openstack_resource_controller_v2_api_v1alpha1_ImagePropertiesOperatingSystem(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ImageResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ImageResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ImageSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ImageStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ImageStatusExtra": schema_openstack_resource_controller_v2_api_v1alpha1_ImageStatusExtra(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPair": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPair(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairFilter": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairImport": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairList": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairSpec": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.KeyPairStatus": schema_openstack_resource_controller_v2_api_v1alpha1_KeyPairStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ManagedOptions": schema_openstack_resource_controller_v2_api_v1alpha1_ManagedOptions(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Network": schema_openstack_resource_controller_v2_api_v1alpha1_Network(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkFilter": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkImport": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkList": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkSpec": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NetworkStatus": schema_openstack_resource_controller_v2_api_v1alpha1_NetworkStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.NeutronStatusMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_NeutronStatusMetadata(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Port": schema_openstack_resource_controller_v2_api_v1alpha1_Port(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortFilter": schema_openstack_resource_controller_v2_api_v1alpha1_PortFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortImport": schema_openstack_resource_controller_v2_api_v1alpha1_PortImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortList": schema_openstack_resource_controller_v2_api_v1alpha1_PortList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortRangeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortRangeSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortRangeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortRangeStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortSpec": schema_openstack_resource_controller_v2_api_v1alpha1_PortSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.PortStatus": schema_openstack_resource_controller_v2_api_v1alpha1_PortStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Project": schema_openstack_resource_controller_v2_api_v1alpha1_Project(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectImport": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectList": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProjectStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProjectStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ProviderPropertiesStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ProviderPropertiesStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Role": schema_openstack_resource_controller_v2_api_v1alpha1_Role(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleFilter": schema_openstack_resource_controller_v2_api_v1alpha1_RoleFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleImport": schema_openstack_resource_controller_v2_api_v1alpha1_RoleImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleList": schema_openstack_resource_controller_v2_api_v1alpha1_RoleList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RoleResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RoleResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RoleSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RoleStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RoleStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Router": schema_openstack_resource_controller_v2_api_v1alpha1_Router(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterFilter": schema_openstack_resource_controller_v2_api_v1alpha1_RouterFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterImport": schema_openstack_resource_controller_v2_api_v1alpha1_RouterImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterface": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterface(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceList": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterInterfaceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterInterfaceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterList": schema_openstack_resource_controller_v2_api_v1alpha1_RouterList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterSpec": schema_openstack_resource_controller_v2_api_v1alpha1_RouterSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.RouterStatus": schema_openstack_resource_controller_v2_api_v1alpha1_RouterStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroup": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroup(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupList": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupRule": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupRule(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupRuleStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupRuleStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SecurityGroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SecurityGroupStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Server": schema_openstack_resource_controller_v2_api_v1alpha1_Server(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServerFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroup": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroup(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupList": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupRules": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupRules(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupRulesStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupRulesStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerGroupStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerGroupStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServerImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerInterfaceFixedIP": schema_openstack_resource_controller_v2_api_v1alpha1_ServerInterfaceFixedIP(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerInterfaceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerInterfaceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerList": schema_openstack_resource_controller_v2_api_v1alpha1_ServerList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_ServerMetadata(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerMetadataStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerMetadataStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerPortSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerPortSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerVolumeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServerVolumeSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServerVolumeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServerVolumeStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Service": schema_openstack_resource_controller_v2_api_v1alpha1_Service(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceFilter": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceImport": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceList": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ServiceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_ServiceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Subnet": schema_openstack_resource_controller_v2_api_v1alpha1_Subnet(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetFilter": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetGateway": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetGateway(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetImport": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetList": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetSpec": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.SubnetStatus": schema_openstack_resource_controller_v2_api_v1alpha1_SubnetStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Trunk": schema_openstack_resource_controller_v2_api_v1alpha1_Trunk(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkFilter": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkImport": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkList": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSubportSpec": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSubportSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.TrunkSubportStatus": schema_openstack_resource_controller_v2_api_v1alpha1_TrunkSubportStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.User": schema_openstack_resource_controller_v2_api_v1alpha1_User(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserDataSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserDataSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserFilter": schema_openstack_resource_controller_v2_api_v1alpha1_UserFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserImport": schema_openstack_resource_controller_v2_api_v1alpha1_UserImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserList": schema_openstack_resource_controller_v2_api_v1alpha1_UserList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_UserResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserSpec": schema_openstack_resource_controller_v2_api_v1alpha1_UserSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.UserStatus": schema_openstack_resource_controller_v2_api_v1alpha1_UserStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.Volume": schema_openstack_resource_controller_v2_api_v1alpha1_Volume(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeAttachmentStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeAttachmentStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeImport": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeList": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeMetadata": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeMetadata(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeMetadataStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeMetadataStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeType": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeType(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeExtraSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeExtraSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeExtraSpecStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeExtraSpecStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeFilter": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeFilter(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeImport": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeImport(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeList": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeList(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeResourceSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeResourceSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeResourceStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeResourceStatus(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeSpec": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeSpec(ref), + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.VolumeTypeStatus": schema_openstack_resource_controller_v2_api_v1alpha1_VolumeTypeStatus(ref), + "k8s.io/api/core/v1.AWSElasticBlockStoreVolumeSource": schema_k8sio_api_core_v1_AWSElasticBlockStoreVolumeSource(ref), "k8s.io/api/core/v1.Affinity": schema_k8sio_api_core_v1_Affinity(ref), "k8s.io/api/core/v1.AppArmorProfile": schema_k8sio_api_core_v1_AppArmorProfile(ref), "k8s.io/api/core/v1.AttachedVolume": schema_k8sio_api_core_v1_AttachedVolume(ref), @@ -1097,27 +1100,87 @@ func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredential( } } -func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialFilter(ref common.ReferenceCallback) common.OpenAPIDefinition { +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialAccessRule(ref common.ReferenceCallback) common.OpenAPIDefinition { return common.OpenAPIDefinition{ Schema: spec.Schema{ SchemaProps: spec.SchemaProps{ - Description: "ApplicationCredentialFilter defines an existing resource by its properties", + Description: "ApplicationCredentialAccessRule defines an access rule", Type: []string{"object"}, Properties: map[string]spec.Schema{ - "name": { + "path": { SchemaProps: spec.SchemaProps{ - Description: "name of the existing resource", + Description: "path that the application credential is permitted to access", Type: []string{"string"}, Format: "", }, }, - "description": { + "method": { SchemaProps: spec.SchemaProps{ - Description: "description of the existing resource", + Description: "method that the application credential is permitted to use for a given API endpoint", + Type: []string{"string"}, + Format: "", + }, + }, + "serviceRef": { + SchemaProps: spec.SchemaProps{ + Description: "serviceRef identifier for the service that the application credential is permitted to access", + Type: []string{"string"}, + Format: "", + }, + }, + }, + }, + }, + } +} + +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialAccessRuleStatus(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "id": { + SchemaProps: spec.SchemaProps{ + Description: "id is the ID of this access rule", Type: []string{"string"}, Format: "", }, }, + "path": { + SchemaProps: spec.SchemaProps{ + Description: "path that the application credential is permitted to access", + Type: []string{"string"}, + Format: "", + }, + }, + "method": { + SchemaProps: spec.SchemaProps{ + Description: "method that the application credential is permitted to use for a given API endpoint", + Type: []string{"string"}, + Format: "", + }, + }, + "service": { + SchemaProps: spec.SchemaProps{ + Description: "service type identifier for the service that the application credential is permitted to access", + Type: []string{"string"}, + Format: "", + }, + }, + }, + }, + }, + } +} + +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialFilter(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Description: "ApplicationCredentialFilter defines an existing resource by its properties", + Type: []string{"object"}, + Properties: map[string]spec.Schema{ "userRef": { SchemaProps: spec.SchemaProps{ Description: "userRef is a reference to the ORC User which this resource is associated with.", @@ -1125,7 +1188,22 @@ func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialF Format: "", }, }, + "name": { + SchemaProps: spec.SchemaProps{ + Description: "name of the existing resource", + Type: []string{"string"}, + Format: "", + }, + }, + "description": { + SchemaProps: spec.SchemaProps{ + Description: "description of the existing resource", + Type: []string{"string"}, + Format: "", + }, + }, }, + Required: []string{"userRef"}, }, }, } @@ -1238,10 +1316,71 @@ func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialR Format: "", }, }, + "unrestricted": { + SchemaProps: spec.SchemaProps{ + Description: "unrestricted is a flag indicating whether the application credential may be used for creation or destruction of other application credentials or trusts", + Type: []string{"boolean"}, + Format: "", + }, + }, + "secretRef": { + SchemaProps: spec.SchemaProps{ + Description: "secretRef is a reference to a Secret containing the application credential secret", + Type: []string{"string"}, + Format: "", + }, + }, + "roleRefs": { + VendorExtensible: spec.VendorExtensible{ + Extensions: spec.Extensions{ + "x-kubernetes-list-type": "atomic", + }, + }, + SchemaProps: spec.SchemaProps{ + Description: "roleRefs may only contain roles that the user has assigned on the project. If not provided, the roles assigned to the application credential will be the same as the roles in the current token.", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: "", + Type: []string{"string"}, + Format: "", + }, + }, + }, + }, + }, + "accessRules": { + VendorExtensible: spec.VendorExtensible{ + Extensions: spec.Extensions{ + "x-kubernetes-list-type": "atomic", + }, + }, + SchemaProps: spec.SchemaProps{ + Description: "accessRules is a list of fine grained access control rules", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialAccessRule"), + }, + }, + }, + }, + }, + "expiresAt": { + SchemaProps: spec.SchemaProps{ + Description: "expiresAt is the time of expiration for the application credential. If unset, the application credential does not expire.", + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.Time"), + }, + }, }, - Required: []string{"userRef"}, + Required: []string{"userRef", "secretRef"}, }, }, + Dependencies: []string{ + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialAccessRule", "k8s.io/apimachinery/pkg/apis/meta/v1.Time"}, } } @@ -1266,9 +1405,95 @@ func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialR Format: "", }, }, - "userID": { + "unrestricted": { + SchemaProps: spec.SchemaProps{ + Description: "unrestricted is a flag indicating whether the application credential may be used for creation or destruction of other application credentials or trusts", + Type: []string{"boolean"}, + Format: "", + }, + }, + "projectID": { + SchemaProps: spec.SchemaProps{ + Description: "projectID of the project the application credential was created for and that authentication requests using this application credential will be scoped to.", + Type: []string{"string"}, + Format: "", + }, + }, + "roles": { + VendorExtensible: spec.VendorExtensible{ + Extensions: spec.Extensions{ + "x-kubernetes-list-type": "atomic", + }, + }, + SchemaProps: spec.SchemaProps{ + Description: "roles is a list of role objects may only contain roles that the user has assigned on the project", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialRoleStatus"), + }, + }, + }, + }, + }, + "expiresAt": { + SchemaProps: spec.SchemaProps{ + Description: "expiresAt is the time of expiration for the application credential. If unset, the application credential does not expire.", + Ref: ref("k8s.io/apimachinery/pkg/apis/meta/v1.Time"), + }, + }, + "accessRules": { + VendorExtensible: spec.VendorExtensible{ + Extensions: spec.Extensions{ + "x-kubernetes-list-type": "atomic", + }, + }, + SchemaProps: spec.SchemaProps{ + Description: "accessRules is a list of fine grained access control rules", + Type: []string{"array"}, + Items: &spec.SchemaOrArray{ + Schema: &spec.Schema{ + SchemaProps: spec.SchemaProps{ + Default: map[string]interface{}{}, + Ref: ref("github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialAccessRuleStatus"), + }, + }, + }, + }, + }, + }, + }, + }, + Dependencies: []string{ + "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialAccessRuleStatus", "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1.ApplicationCredentialRoleStatus", "k8s.io/apimachinery/pkg/apis/meta/v1.Time"}, + } +} + +func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialRoleStatus(ref common.ReferenceCallback) common.OpenAPIDefinition { + return common.OpenAPIDefinition{ + Schema: spec.Schema{ + SchemaProps: spec.SchemaProps{ + Type: []string{"object"}, + Properties: map[string]spec.Schema{ + "name": { + SchemaProps: spec.SchemaProps{ + Description: "name of an existing role", + Type: []string{"string"}, + Format: "", + }, + }, + "id": { + SchemaProps: spec.SchemaProps{ + Description: "id is the ID of a role", + Type: []string{"string"}, + Format: "", + }, + }, + "domainID": { SchemaProps: spec.SchemaProps{ - Description: "userID is the ID of the User to which the resource is associated.", + Description: "domainID of the domain of this role", Type: []string{"string"}, Format: "", }, diff --git a/config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml b/config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml index 449790ab8..f16fe117f 100644 --- a/config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml +++ b/config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml @@ -3,7 +3,7 @@ apiVersion: apiextensions.k8s.io/v1 kind: CustomResourceDefinition metadata: annotations: - controller-gen.kubebuilder.io/version: v0.17.1 + controller-gen.kubebuilder.io/version: v0.20.1 name: applicationcredentials.openstack.k-orc.cloud spec: group: openstack.k-orc.cloud @@ -89,12 +89,11 @@ spec: result. The controller will continue to retry if filter returns no results. If filter returns multiple results the controller will set an error state and will not continue to retry. - minProperties: 1 + minProperties: 2 properties: description: description: description of the existing resource - maxLength: 255 - minLength: 1 + maxLength: 1024 type: string name: description: name of the existing resource @@ -108,6 +107,8 @@ spec: maxLength: 253 minLength: 1 type: string + required: + - userRef type: object id: description: |- @@ -156,12 +157,54 @@ spec: resource must be specified if the management policy is `managed`. properties: + accessRules: + description: accessRules is a list of fine grained access control + rules + items: + description: ApplicationCredentialAccessRule defines an access + rule + minProperties: 1 + properties: + method: + description: method that the application credential is permitted + to use for a given API endpoint + enum: + - CONNECT + - DELETE + - GET + - HEAD + - OPTIONS + - PATCH + - POST + - PUT + - TRACE + type: string + path: + description: path that the application credential is permitted + to access + maxLength: 1024 + type: string + serviceRef: + description: serviceRef identifier for the service that + the application credential is permitted to access + maxLength: 253 + minLength: 1 + type: string + type: object + maxItems: 256 + type: array + x-kubernetes-list-type: atomic description: description: description is a human-readable description for the resource. maxLength: 255 minLength: 1 type: string + expiresAt: + description: expiresAt is the time of expiration for the application + credential. If unset, the application credential does not expire. + format: date-time + type: string name: description: |- name will be the name of the created resource. If not specified, the @@ -170,18 +213,42 @@ spec: minLength: 1 pattern: ^[^,]+$ type: string + roleRefs: + description: roleRefs may only contain roles that the user has + assigned on the project. If not provided, the roles assigned + to the application credential will be the same as the roles + in the current token. + items: + maxLength: 253 + minLength: 1 + type: string + maxItems: 256 + type: array + x-kubernetes-list-type: atomic + secretRef: + description: secretRef is a reference to a Secret containing the + application credential secret + maxLength: 253 + minLength: 1 + type: string + unrestricted: + description: unrestricted is a flag indicating whether the application + credential may be used for creation or destruction of other + application credentials or trusts + type: boolean userRef: description: userRef is a reference to the ORC User which this resource is associated with. maxLength: 253 minLength: 1 type: string - x-kubernetes-validations: - - message: userRef is immutable - rule: self == oldSelf required: + - secretRef - userRef type: object + x-kubernetes-validations: + - message: ApplicationCredentialResourceSpec is immutable + rule: self == oldSelf required: - cloudCredentialsRef type: object @@ -285,21 +352,81 @@ spec: description: resource contains the observed state of the OpenStack resource. properties: + accessRules: + description: accessRules is a list of fine grained access control + rules + items: + properties: + id: + description: id is the ID of this access rule + maxLength: 1024 + type: string + method: + description: method that the application credential is permitted + to use for a given API endpoint + maxLength: 32 + type: string + path: + description: path that the application credential is permitted + to access + maxLength: 1024 + type: string + service: + description: service type identifier for the service that + the application credential is permitted to access + maxLength: 1024 + type: string + type: object + maxItems: 64 + type: array + x-kubernetes-list-type: atomic description: description: description is a human-readable description for the resource. maxLength: 1024 type: string + expiresAt: + description: expiresAt is the time of expiration for the application + credential. If unset, the application credential does not expire. + format: date-time + type: string name: description: name is a Human-readable name for the resource. Might not be unique. maxLength: 1024 type: string - userID: - description: userID is the ID of the User to which the resource - is associated. + projectID: + description: projectID of the project the application credential + was created for and that authentication requests using this + application credential will be scoped to. maxLength: 1024 type: string + roles: + description: roles is a list of role objects may only contain + roles that the user has assigned on the project + items: + properties: + domainID: + description: domainID of the domain of this role + maxLength: 1024 + type: string + id: + description: id is the ID of a role + maxLength: 1024 + type: string + name: + description: name of an existing role + maxLength: 1024 + type: string + type: object + maxItems: 64 + type: array + x-kubernetes-list-type: atomic + unrestricted: + description: unrestricted is a flag indicating whether the application + credential may be used for creation or destruction of other + application credentials or trusts + type: boolean type: object type: object required: diff --git a/internal/osclients/mock/applicationcredential.go b/internal/osclients/mock/applicationcredential.go index 194a49a2f..cecd4726e 100644 --- a/internal/osclients/mock/applicationcredential.go +++ b/internal/osclients/mock/applicationcredential.go @@ -58,32 +58,32 @@ func (m *MockApplicationCredentialClient) EXPECT() *MockApplicationCredentialCli } // CreateApplicationCredential mocks base method. -func (m *MockApplicationCredentialClient) CreateApplicationCredential(ctx context.Context, opts applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { +func (m *MockApplicationCredentialClient) CreateApplicationCredential(ctx context.Context, userID string, opts applicationcredentials.CreateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "CreateApplicationCredential", ctx, opts) + ret := m.ctrl.Call(m, "CreateApplicationCredential", ctx, userID, opts) ret0, _ := ret[0].(*applicationcredentials.ApplicationCredential) ret1, _ := ret[1].(error) return ret0, ret1 } // CreateApplicationCredential indicates an expected call of CreateApplicationCredential. -func (mr *MockApplicationCredentialClientMockRecorder) CreateApplicationCredential(ctx, opts any) *gomock.Call { +func (mr *MockApplicationCredentialClientMockRecorder) CreateApplicationCredential(ctx, userID, opts any) *gomock.Call { mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateApplicationCredential", reflect.TypeOf((*MockApplicationCredentialClient)(nil).CreateApplicationCredential), ctx, opts) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "CreateApplicationCredential", reflect.TypeOf((*MockApplicationCredentialClient)(nil).CreateApplicationCredential), ctx, userID, opts) } // DeleteApplicationCredential mocks base method. -func (m *MockApplicationCredentialClient) DeleteApplicationCredential(ctx context.Context, resourceID string) error { +func (m *MockApplicationCredentialClient) DeleteApplicationCredential(ctx context.Context, userID, resourceID string) error { m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "DeleteApplicationCredential", ctx, resourceID) + ret := m.ctrl.Call(m, "DeleteApplicationCredential", ctx, userID, resourceID) ret0, _ := ret[0].(error) return ret0 } // DeleteApplicationCredential indicates an expected call of DeleteApplicationCredential. -func (mr *MockApplicationCredentialClientMockRecorder) DeleteApplicationCredential(ctx, resourceID any) *gomock.Call { +func (mr *MockApplicationCredentialClientMockRecorder) DeleteApplicationCredential(ctx, userID, resourceID any) *gomock.Call { mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DeleteApplicationCredential", reflect.TypeOf((*MockApplicationCredentialClient)(nil).DeleteApplicationCredential), ctx, resourceID) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "DeleteApplicationCredential", reflect.TypeOf((*MockApplicationCredentialClient)(nil).DeleteApplicationCredential), ctx, userID, resourceID) } // GetApplicationCredential mocks base method. @@ -102,30 +102,15 @@ func (mr *MockApplicationCredentialClientMockRecorder) GetApplicationCredential( } // ListApplicationCredentials mocks base method. -func (m *MockApplicationCredentialClient) ListApplicationCredentials(ctx context.Context, listOpts applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] { +func (m *MockApplicationCredentialClient) ListApplicationCredentials(ctx context.Context, userID string, listOpts applicationcredentials.ListOptsBuilder) iter.Seq2[*applicationcredentials.ApplicationCredential, error] { m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "ListApplicationCredentials", ctx, listOpts) + ret := m.ctrl.Call(m, "ListApplicationCredentials", ctx, userID, listOpts) ret0, _ := ret[0].(iter.Seq2[*applicationcredentials.ApplicationCredential, error]) return ret0 } // ListApplicationCredentials indicates an expected call of ListApplicationCredentials. -func (mr *MockApplicationCredentialClientMockRecorder) ListApplicationCredentials(ctx, listOpts any) *gomock.Call { +func (mr *MockApplicationCredentialClientMockRecorder) ListApplicationCredentials(ctx, userID, listOpts any) *gomock.Call { mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "ListApplicationCredentials", reflect.TypeOf((*MockApplicationCredentialClient)(nil).ListApplicationCredentials), ctx, listOpts) -} - -// UpdateApplicationCredential mocks base method. -func (m *MockApplicationCredentialClient) UpdateApplicationCredential(ctx context.Context, id string, opts applicationcredentials.UpdateOptsBuilder) (*applicationcredentials.ApplicationCredential, error) { - m.ctrl.T.Helper() - ret := m.ctrl.Call(m, "UpdateApplicationCredential", ctx, id, opts) - ret0, _ := ret[0].(*applicationcredentials.ApplicationCredential) - ret1, _ := ret[1].(error) - return ret0, ret1 -} - -// UpdateApplicationCredential indicates an expected call of UpdateApplicationCredential. -func (mr *MockApplicationCredentialClientMockRecorder) UpdateApplicationCredential(ctx, id, opts any) *gomock.Call { - mr.mock.ctrl.T.Helper() - return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "UpdateApplicationCredential", reflect.TypeOf((*MockApplicationCredentialClient)(nil).UpdateApplicationCredential), ctx, id, opts) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "ListApplicationCredentials", reflect.TypeOf((*MockApplicationCredentialClient)(nil).ListApplicationCredentials), ctx, userID, listOpts) } diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialaccessrule.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialaccessrule.go new file mode 100644 index 000000000..4b485c5cb --- /dev/null +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialaccessrule.go @@ -0,0 +1,61 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by applyconfiguration-gen. DO NOT EDIT. + +package v1alpha1 + +import ( + apiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" +) + +// ApplicationCredentialAccessRuleApplyConfiguration represents a declarative configuration of the ApplicationCredentialAccessRule type for use +// with apply. +type ApplicationCredentialAccessRuleApplyConfiguration struct { + Path *string `json:"path,omitempty"` + Method *apiv1alpha1.HTTPMethod `json:"method,omitempty"` + ServiceRef *apiv1alpha1.KubernetesNameRef `json:"serviceRef,omitempty"` +} + +// ApplicationCredentialAccessRuleApplyConfiguration constructs a declarative configuration of the ApplicationCredentialAccessRule type for use with +// apply. +func ApplicationCredentialAccessRule() *ApplicationCredentialAccessRuleApplyConfiguration { + return &ApplicationCredentialAccessRuleApplyConfiguration{} +} + +// WithPath sets the Path field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Path field is set to the value of the last call. +func (b *ApplicationCredentialAccessRuleApplyConfiguration) WithPath(value string) *ApplicationCredentialAccessRuleApplyConfiguration { + b.Path = &value + return b +} + +// WithMethod sets the Method field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Method field is set to the value of the last call. +func (b *ApplicationCredentialAccessRuleApplyConfiguration) WithMethod(value apiv1alpha1.HTTPMethod) *ApplicationCredentialAccessRuleApplyConfiguration { + b.Method = &value + return b +} + +// WithServiceRef sets the ServiceRef field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the ServiceRef field is set to the value of the last call. +func (b *ApplicationCredentialAccessRuleApplyConfiguration) WithServiceRef(value apiv1alpha1.KubernetesNameRef) *ApplicationCredentialAccessRuleApplyConfiguration { + b.ServiceRef = &value + return b +} diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialaccessrulestatus.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialaccessrulestatus.go new file mode 100644 index 000000000..9624a3d3f --- /dev/null +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialaccessrulestatus.go @@ -0,0 +1,66 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by applyconfiguration-gen. DO NOT EDIT. + +package v1alpha1 + +// ApplicationCredentialAccessRuleStatusApplyConfiguration represents a declarative configuration of the ApplicationCredentialAccessRuleStatus type for use +// with apply. +type ApplicationCredentialAccessRuleStatusApplyConfiguration struct { + ID *string `json:"id,omitempty"` + Path *string `json:"path,omitempty"` + Method *string `json:"method,omitempty"` + Service *string `json:"service,omitempty"` +} + +// ApplicationCredentialAccessRuleStatusApplyConfiguration constructs a declarative configuration of the ApplicationCredentialAccessRuleStatus type for use with +// apply. +func ApplicationCredentialAccessRuleStatus() *ApplicationCredentialAccessRuleStatusApplyConfiguration { + return &ApplicationCredentialAccessRuleStatusApplyConfiguration{} +} + +// WithID sets the ID field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the ID field is set to the value of the last call. +func (b *ApplicationCredentialAccessRuleStatusApplyConfiguration) WithID(value string) *ApplicationCredentialAccessRuleStatusApplyConfiguration { + b.ID = &value + return b +} + +// WithPath sets the Path field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Path field is set to the value of the last call. +func (b *ApplicationCredentialAccessRuleStatusApplyConfiguration) WithPath(value string) *ApplicationCredentialAccessRuleStatusApplyConfiguration { + b.Path = &value + return b +} + +// WithMethod sets the Method field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Method field is set to the value of the last call. +func (b *ApplicationCredentialAccessRuleStatusApplyConfiguration) WithMethod(value string) *ApplicationCredentialAccessRuleStatusApplyConfiguration { + b.Method = &value + return b +} + +// WithService sets the Service field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Service field is set to the value of the last call. +func (b *ApplicationCredentialAccessRuleStatusApplyConfiguration) WithService(value string) *ApplicationCredentialAccessRuleStatusApplyConfiguration { + b.Service = &value + return b +} diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialfilter.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialfilter.go index 6a7b1e7be..d3d4a136b 100644 --- a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialfilter.go +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialfilter.go @@ -25,9 +25,9 @@ import ( // ApplicationCredentialFilterApplyConfiguration represents a declarative configuration of the ApplicationCredentialFilter type for use // with apply. type ApplicationCredentialFilterApplyConfiguration struct { + UserRef *apiv1alpha1.KubernetesNameRef `json:"userRef,omitempty"` Name *apiv1alpha1.OpenStackName `json:"name,omitempty"` Description *string `json:"description,omitempty"` - UserRef *apiv1alpha1.KubernetesNameRef `json:"userRef,omitempty"` } // ApplicationCredentialFilterApplyConfiguration constructs a declarative configuration of the ApplicationCredentialFilter type for use with @@ -36,6 +36,14 @@ func ApplicationCredentialFilter() *ApplicationCredentialFilterApplyConfiguratio return &ApplicationCredentialFilterApplyConfiguration{} } +// WithUserRef sets the UserRef field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the UserRef field is set to the value of the last call. +func (b *ApplicationCredentialFilterApplyConfiguration) WithUserRef(value apiv1alpha1.KubernetesNameRef) *ApplicationCredentialFilterApplyConfiguration { + b.UserRef = &value + return b +} + // WithName sets the Name field in the declarative configuration to the given value // and returns the receiver, so that objects can be built by chaining "With" function invocations. // If called multiple times, the Name field is set to the value of the last call. @@ -51,11 +59,3 @@ func (b *ApplicationCredentialFilterApplyConfiguration) WithDescription(value st b.Description = &value return b } - -// WithUserRef sets the UserRef field in the declarative configuration to the given value -// and returns the receiver, so that objects can be built by chaining "With" function invocations. -// If called multiple times, the UserRef field is set to the value of the last call. -func (b *ApplicationCredentialFilterApplyConfiguration) WithUserRef(value apiv1alpha1.KubernetesNameRef) *ApplicationCredentialFilterApplyConfiguration { - b.UserRef = &value - return b -} diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcespec.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcespec.go index f070d2766..fd1c8bc5c 100644 --- a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcespec.go +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcespec.go @@ -20,14 +20,20 @@ package v1alpha1 import ( apiv1alpha1 "github.com/k-orc/openstack-resource-controller/v2/api/v1alpha1" + v1 "k8s.io/apimachinery/pkg/apis/meta/v1" ) // ApplicationCredentialResourceSpecApplyConfiguration represents a declarative configuration of the ApplicationCredentialResourceSpec type for use // with apply. type ApplicationCredentialResourceSpecApplyConfiguration struct { - Name *apiv1alpha1.OpenStackName `json:"name,omitempty"` - Description *string `json:"description,omitempty"` - UserRef *apiv1alpha1.KubernetesNameRef `json:"userRef,omitempty"` + Name *apiv1alpha1.OpenStackName `json:"name,omitempty"` + Description *string `json:"description,omitempty"` + UserRef *apiv1alpha1.KubernetesNameRef `json:"userRef,omitempty"` + Unrestricted *bool `json:"unrestricted,omitempty"` + SecretRef *apiv1alpha1.KubernetesNameRef `json:"secretRef,omitempty"` + RoleRefs []apiv1alpha1.KubernetesNameRef `json:"roleRefs,omitempty"` + AccessRules []ApplicationCredentialAccessRuleApplyConfiguration `json:"accessRules,omitempty"` + ExpiresAt *v1.Time `json:"expiresAt,omitempty"` } // ApplicationCredentialResourceSpecApplyConfiguration constructs a declarative configuration of the ApplicationCredentialResourceSpec type for use with @@ -59,3 +65,50 @@ func (b *ApplicationCredentialResourceSpecApplyConfiguration) WithUserRef(value b.UserRef = &value return b } + +// WithUnrestricted sets the Unrestricted field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Unrestricted field is set to the value of the last call. +func (b *ApplicationCredentialResourceSpecApplyConfiguration) WithUnrestricted(value bool) *ApplicationCredentialResourceSpecApplyConfiguration { + b.Unrestricted = &value + return b +} + +// WithSecretRef sets the SecretRef field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the SecretRef field is set to the value of the last call. +func (b *ApplicationCredentialResourceSpecApplyConfiguration) WithSecretRef(value apiv1alpha1.KubernetesNameRef) *ApplicationCredentialResourceSpecApplyConfiguration { + b.SecretRef = &value + return b +} + +// WithRoleRefs adds the given value to the RoleRefs field in the declarative configuration +// and returns the receiver, so that objects can be build by chaining "With" function invocations. +// If called multiple times, values provided by each call will be appended to the RoleRefs field. +func (b *ApplicationCredentialResourceSpecApplyConfiguration) WithRoleRefs(values ...apiv1alpha1.KubernetesNameRef) *ApplicationCredentialResourceSpecApplyConfiguration { + for i := range values { + b.RoleRefs = append(b.RoleRefs, values[i]) + } + return b +} + +// WithAccessRules adds the given value to the AccessRules field in the declarative configuration +// and returns the receiver, so that objects can be build by chaining "With" function invocations. +// If called multiple times, values provided by each call will be appended to the AccessRules field. +func (b *ApplicationCredentialResourceSpecApplyConfiguration) WithAccessRules(values ...*ApplicationCredentialAccessRuleApplyConfiguration) *ApplicationCredentialResourceSpecApplyConfiguration { + for i := range values { + if values[i] == nil { + panic("nil value passed to WithAccessRules") + } + b.AccessRules = append(b.AccessRules, *values[i]) + } + return b +} + +// WithExpiresAt sets the ExpiresAt field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the ExpiresAt field is set to the value of the last call. +func (b *ApplicationCredentialResourceSpecApplyConfiguration) WithExpiresAt(value v1.Time) *ApplicationCredentialResourceSpecApplyConfiguration { + b.ExpiresAt = &value + return b +} diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcestatus.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcestatus.go index ce52d9d53..04e3eb95a 100644 --- a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcestatus.go +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialresourcestatus.go @@ -18,12 +18,20 @@ limitations under the License. package v1alpha1 +import ( + v1 "k8s.io/apimachinery/pkg/apis/meta/v1" +) + // ApplicationCredentialResourceStatusApplyConfiguration represents a declarative configuration of the ApplicationCredentialResourceStatus type for use // with apply. type ApplicationCredentialResourceStatusApplyConfiguration struct { - Name *string `json:"name,omitempty"` - Description *string `json:"description,omitempty"` - UserID *string `json:"userID,omitempty"` + Name *string `json:"name,omitempty"` + Description *string `json:"description,omitempty"` + Unrestricted *bool `json:"unrestricted,omitempty"` + ProjectID *string `json:"projectID,omitempty"` + Roles []ApplicationCredentialRoleStatusApplyConfiguration `json:"roles,omitempty"` + ExpiresAt *v1.Time `json:"expiresAt,omitempty"` + AccessRules []ApplicationCredentialAccessRuleStatusApplyConfiguration `json:"accessRules,omitempty"` } // ApplicationCredentialResourceStatusApplyConfiguration constructs a declarative configuration of the ApplicationCredentialResourceStatus type for use with @@ -48,10 +56,52 @@ func (b *ApplicationCredentialResourceStatusApplyConfiguration) WithDescription( return b } -// WithUserID sets the UserID field in the declarative configuration to the given value +// WithUnrestricted sets the Unrestricted field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Unrestricted field is set to the value of the last call. +func (b *ApplicationCredentialResourceStatusApplyConfiguration) WithUnrestricted(value bool) *ApplicationCredentialResourceStatusApplyConfiguration { + b.Unrestricted = &value + return b +} + +// WithProjectID sets the ProjectID field in the declarative configuration to the given value // and returns the receiver, so that objects can be built by chaining "With" function invocations. -// If called multiple times, the UserID field is set to the value of the last call. -func (b *ApplicationCredentialResourceStatusApplyConfiguration) WithUserID(value string) *ApplicationCredentialResourceStatusApplyConfiguration { - b.UserID = &value +// If called multiple times, the ProjectID field is set to the value of the last call. +func (b *ApplicationCredentialResourceStatusApplyConfiguration) WithProjectID(value string) *ApplicationCredentialResourceStatusApplyConfiguration { + b.ProjectID = &value + return b +} + +// WithRoles adds the given value to the Roles field in the declarative configuration +// and returns the receiver, so that objects can be build by chaining "With" function invocations. +// If called multiple times, values provided by each call will be appended to the Roles field. +func (b *ApplicationCredentialResourceStatusApplyConfiguration) WithRoles(values ...*ApplicationCredentialRoleStatusApplyConfiguration) *ApplicationCredentialResourceStatusApplyConfiguration { + for i := range values { + if values[i] == nil { + panic("nil value passed to WithRoles") + } + b.Roles = append(b.Roles, *values[i]) + } + return b +} + +// WithExpiresAt sets the ExpiresAt field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the ExpiresAt field is set to the value of the last call. +func (b *ApplicationCredentialResourceStatusApplyConfiguration) WithExpiresAt(value v1.Time) *ApplicationCredentialResourceStatusApplyConfiguration { + b.ExpiresAt = &value + return b +} + +// WithAccessRules adds the given value to the AccessRules field in the declarative configuration +// and returns the receiver, so that objects can be build by chaining "With" function invocations. +// If called multiple times, values provided by each call will be appended to the AccessRules field. +func (b *ApplicationCredentialResourceStatusApplyConfiguration) WithAccessRules(values ...*ApplicationCredentialAccessRuleStatusApplyConfiguration) *ApplicationCredentialResourceStatusApplyConfiguration { + for i := range values { + if values[i] == nil { + panic("nil value passed to WithAccessRules") + } + b.AccessRules = append(b.AccessRules, *values[i]) + } return b } diff --git a/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialrolestatus.go b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialrolestatus.go new file mode 100644 index 000000000..c3e88c115 --- /dev/null +++ b/pkg/clients/applyconfiguration/api/v1alpha1/applicationcredentialrolestatus.go @@ -0,0 +1,57 @@ +/* +Copyright The ORC Authors. + +Licensed under the Apache License, Version 2.0 (the "License"); +you may not use this file except in compliance with the License. +You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + +Unless required by applicable law or agreed to in writing, software +distributed under the License is distributed on an "AS IS" BASIS, +WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +See the License for the specific language governing permissions and +limitations under the License. +*/ + +// Code generated by applyconfiguration-gen. DO NOT EDIT. + +package v1alpha1 + +// ApplicationCredentialRoleStatusApplyConfiguration represents a declarative configuration of the ApplicationCredentialRoleStatus type for use +// with apply. +type ApplicationCredentialRoleStatusApplyConfiguration struct { + Name *string `json:"name,omitempty"` + ID *string `json:"id,omitempty"` + DomainID *string `json:"domainID,omitempty"` +} + +// ApplicationCredentialRoleStatusApplyConfiguration constructs a declarative configuration of the ApplicationCredentialRoleStatus type for use with +// apply. +func ApplicationCredentialRoleStatus() *ApplicationCredentialRoleStatusApplyConfiguration { + return &ApplicationCredentialRoleStatusApplyConfiguration{} +} + +// WithName sets the Name field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the Name field is set to the value of the last call. +func (b *ApplicationCredentialRoleStatusApplyConfiguration) WithName(value string) *ApplicationCredentialRoleStatusApplyConfiguration { + b.Name = &value + return b +} + +// WithID sets the ID field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the ID field is set to the value of the last call. +func (b *ApplicationCredentialRoleStatusApplyConfiguration) WithID(value string) *ApplicationCredentialRoleStatusApplyConfiguration { + b.ID = &value + return b +} + +// WithDomainID sets the DomainID field in the declarative configuration to the given value +// and returns the receiver, so that objects can be built by chaining "With" function invocations. +// If called multiple times, the DomainID field is set to the value of the last call. +func (b *ApplicationCredentialRoleStatusApplyConfiguration) WithDomainID(value string) *ApplicationCredentialRoleStatusApplyConfiguration { + b.DomainID = &value + return b +} diff --git a/pkg/clients/applyconfiguration/internal/internal.go b/pkg/clients/applyconfiguration/internal/internal.go index fa4338589..1db6b1e94 100644 --- a/pkg/clients/applyconfiguration/internal/internal.go +++ b/pkg/clients/applyconfiguration/internal/internal.go @@ -217,6 +217,33 @@ var schemaYAML = typed.YAMLObject(`types: type: namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialStatus default: {} +- name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialAccessRule + map: + fields: + - name: method + type: + scalar: string + - name: path + type: + scalar: string + - name: serviceRef + type: + scalar: string +- name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialAccessRuleStatus + map: + fields: + - name: id + type: + scalar: string + - name: method + type: + scalar: string + - name: path + type: + scalar: string + - name: service + type: + scalar: string - name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialFilter map: fields: @@ -241,25 +268,76 @@ var schemaYAML = typed.YAMLObject(`types: - name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialResourceSpec map: fields: + - name: accessRules + type: + list: + elementType: + namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialAccessRule + elementRelationship: atomic - name: description type: scalar: string + - name: expiresAt + type: + namedType: io.k8s.apimachinery.pkg.apis.meta.v1.Time - name: name type: scalar: string + - name: roleRefs + type: + list: + elementType: + scalar: string + elementRelationship: atomic + - name: secretRef + type: + scalar: string + - name: unrestricted + type: + scalar: boolean - name: userRef type: scalar: string - name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialResourceStatus map: fields: + - name: accessRules + type: + list: + elementType: + namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialAccessRuleStatus + elementRelationship: atomic - name: description type: scalar: string + - name: expiresAt + type: + namedType: io.k8s.apimachinery.pkg.apis.meta.v1.Time - name: name type: scalar: string - - name: userID + - name: projectID + type: + scalar: string + - name: roles + type: + list: + elementType: + namedType: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialRoleStatus + elementRelationship: atomic + - name: unrestricted + type: + scalar: boolean +- name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialRoleStatus + map: + fields: + - name: domainID + type: + scalar: string + - name: id + type: + scalar: string + - name: name type: scalar: string - name: com.github.k-orc.openstack-resource-controller.v2.api.v1alpha1.ApplicationCredentialSpec diff --git a/pkg/clients/applyconfiguration/utils.go b/pkg/clients/applyconfiguration/utils.go index 373bc2636..54b063b6d 100644 --- a/pkg/clients/applyconfiguration/utils.go +++ b/pkg/clients/applyconfiguration/utils.go @@ -58,6 +58,10 @@ func ForKind(kind schema.GroupVersionKind) interface{} { return &apiv1alpha1.AllowedAddressPairStatusApplyConfiguration{} case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredential"): return &apiv1alpha1.ApplicationCredentialApplyConfiguration{} + case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialAccessRule"): + return &apiv1alpha1.ApplicationCredentialAccessRuleApplyConfiguration{} + case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialAccessRuleStatus"): + return &apiv1alpha1.ApplicationCredentialAccessRuleStatusApplyConfiguration{} case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialFilter"): return &apiv1alpha1.ApplicationCredentialFilterApplyConfiguration{} case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialImport"): @@ -66,6 +70,8 @@ func ForKind(kind schema.GroupVersionKind) interface{} { return &apiv1alpha1.ApplicationCredentialResourceSpecApplyConfiguration{} case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialResourceStatus"): return &apiv1alpha1.ApplicationCredentialResourceStatusApplyConfiguration{} + case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialRoleStatus"): + return &apiv1alpha1.ApplicationCredentialRoleStatusApplyConfiguration{} case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialSpec"): return &apiv1alpha1.ApplicationCredentialSpecApplyConfiguration{} case v1alpha1.SchemeGroupVersion.WithKind("ApplicationCredentialStatus"): diff --git a/website/docs/crd-reference.md b/website/docs/crd-reference.md index 884240fe6..3ba3a5bda 100644 --- a/website/docs/crd-reference.md +++ b/website/docs/crd-reference.md @@ -271,9 +271,47 @@ ApplicationCredential is the Schema for an ORC resource. | --- | --- | --- | --- | | `apiVersion` _string_ | `openstack.k-orc.cloud/v1alpha1` | | | | `kind` _string_ | `ApplicationCredential` | | | -| `metadata` _[ObjectMeta](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.29/#objectmeta-v1-meta)_ | Refer to Kubernetes API documentation for fields of `metadata`. | | | -| `spec` _[ApplicationCredentialSpec](#applicationcredentialspec)_ | spec specifies the desired state of the resource. | | | -| `status` _[ApplicationCredentialStatus](#applicationcredentialstatus)_ | status defines the observed state of the resource. | | | +| `metadata` _[ObjectMeta](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.29/#objectmeta-v1-meta)_ | Refer to Kubernetes API documentation for fields of `metadata`. | | Optional: \{\}
| +| `spec` _[ApplicationCredentialSpec](#applicationcredentialspec)_ | spec specifies the desired state of the resource. | | Required: \{\}
| +| `status` _[ApplicationCredentialStatus](#applicationcredentialstatus)_ | status defines the observed state of the resource. | | Optional: \{\}
| + + +#### ApplicationCredentialAccessRule + + + +ApplicationCredentialAccessRule defines an access rule + +_Validation:_ +- MinProperties: 1 + +_Appears in:_ +- [ApplicationCredentialResourceSpec](#applicationcredentialresourcespec) + +| Field | Description | Default | Validation | +| --- | --- | --- | --- | +| `path` _string_ | path that the application credential is permitted to access | | MaxLength: 1024
Optional: \{\}
| +| `method` _[HTTPMethod](#httpmethod)_ | method that the application credential is permitted to use for a given API endpoint | | Enum: [CONNECT DELETE GET HEAD OPTIONS PATCH POST PUT TRACE]
Optional: \{\}
| +| `serviceRef` _[KubernetesNameRef](#kubernetesnameref)_ | serviceRef identifier for the service that the application credential is permitted to access | | MaxLength: 253
MinLength: 1
Optional: \{\}
| + + +#### ApplicationCredentialAccessRuleStatus + + + + + + + +_Appears in:_ +- [ApplicationCredentialResourceStatus](#applicationcredentialresourcestatus) + +| Field | Description | Default | Validation | +| --- | --- | --- | --- | +| `id` _string_ | id is the ID of this access rule | | MaxLength: 1024
Optional: \{\}
| +| `path` _string_ | path that the application credential is permitted to access | | MaxLength: 1024
Optional: \{\}
| +| `method` _string_ | method that the application credential is permitted to use for a given API endpoint | | MaxLength: 32
Optional: \{\}
| +| `service` _string_ | service type identifier for the service that the application credential is permitted to access | | MaxLength: 1024
Optional: \{\}
| #### ApplicationCredentialFilter @@ -283,16 +321,16 @@ ApplicationCredential is the Schema for an ORC resource. ApplicationCredentialFilter defines an existing resource by its properties _Validation:_ -- MinProperties: 1 +- MinProperties: 2 _Appears in:_ - [ApplicationCredentialImport](#applicationcredentialimport) | Field | Description | Default | Validation | | --- | --- | --- | --- | -| `name` _[OpenStackName](#openstackname)_ | name of the existing resource | | MaxLength: 255
MinLength: 1
Pattern: `^[^,]+$`
| -| `description` _string_ | description of the existing resource | | MaxLength: 255
MinLength: 1
| -| `userRef` _[KubernetesNameRef](#kubernetesnameref)_ | userRef is a reference to the ORC User which this resource is associated with. | | MaxLength: 253
MinLength: 1
| +| `userRef` _[KubernetesNameRef](#kubernetesnameref)_ | userRef is a reference to the ORC User which this resource is associated with. | | MaxLength: 253
MinLength: 1
Required: \{\}
| +| `name` _[OpenStackName](#openstackname)_ | name of the existing resource | | MaxLength: 255
MinLength: 1
Pattern: `^[^,]+$`
Optional: \{\}
| +| `description` _string_ | description of the existing resource | | MaxLength: 1024
Optional: \{\}
| #### ApplicationCredentialImport @@ -311,8 +349,8 @@ _Appears in:_ | Field | Description | Default | Validation | | --- | --- | --- | --- | -| `id` _string_ | id contains the unique identifier of an existing OpenStack resource. Note
that when specifying an import by ID, the resource MUST already exist.
The ORC object will enter an error state if the resource does not exist. | | Format: uuid
MaxLength: 36
| -| `filter` _[ApplicationCredentialFilter](#applicationcredentialfilter)_ | filter contains a resource query which is expected to return a single
result. The controller will continue to retry if filter returns no
results. If filter returns multiple results the controller will set an
error state and will not continue to retry. | | MinProperties: 1
| +| `id` _string_ | id contains the unique identifier of an existing OpenStack resource. Note
that when specifying an import by ID, the resource MUST already exist.
The ORC object will enter an error state if the resource does not exist. | | Format: uuid
MaxLength: 36
Optional: \{\}
| +| `filter` _[ApplicationCredentialFilter](#applicationcredentialfilter)_ | filter contains a resource query which is expected to return a single
result. The controller will continue to retry if filter returns no
results. If filter returns multiple results the controller will set an
error state and will not continue to retry. | | MinProperties: 2
Optional: \{\}
| #### ApplicationCredentialResourceSpec @@ -328,9 +366,14 @@ _Appears in:_ | Field | Description | Default | Validation | | --- | --- | --- | --- | -| `name` _[OpenStackName](#openstackname)_ | name will be the name of the created resource. If not specified, the
name of the ORC object will be used. | | MaxLength: 255
MinLength: 1
Pattern: `^[^,]+$`
| -| `description` _string_ | description is a human-readable description for the resource. | | MaxLength: 255
MinLength: 1
| -| `userRef` _[KubernetesNameRef](#kubernetesnameref)_ | userRef is a reference to the ORC User which this resource is associated with. | | MaxLength: 253
MinLength: 1
| +| `name` _[OpenStackName](#openstackname)_ | name will be the name of the created resource. If not specified, the
name of the ORC object will be used. | | MaxLength: 255
MinLength: 1
Pattern: `^[^,]+$`
Optional: \{\}
| +| `description` _string_ | description is a human-readable description for the resource. | | MaxLength: 255
MinLength: 1
Optional: \{\}
| +| `userRef` _[KubernetesNameRef](#kubernetesnameref)_ | userRef is a reference to the ORC User which this resource is associated with. | | MaxLength: 253
MinLength: 1
Required: \{\}
| +| `unrestricted` _boolean_ | unrestricted is a flag indicating whether the application credential may be used for creation or destruction of other application credentials or trusts | | Optional: \{\}
| +| `secretRef` _[KubernetesNameRef](#kubernetesnameref)_ | secretRef is a reference to a Secret containing the application credential secret | | MaxLength: 253
MinLength: 1
Required: \{\}
| +| `roleRefs` _[KubernetesNameRef](#kubernetesnameref) array_ | roleRefs may only contain roles that the user has assigned on the project. If not provided, the roles assigned to the application credential will be the same as the roles in the current token. | | MaxItems: 256
MaxLength: 253
MinLength: 1
Optional: \{\}
| +| `accessRules` _[ApplicationCredentialAccessRule](#applicationcredentialaccessrule) array_ | accessRules is a list of fine grained access control rules | | MaxItems: 256
MinProperties: 1
Optional: \{\}
| +| `expiresAt` _[Time](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.29/#time-v1-meta)_ | expiresAt is the time of expiration for the application credential. If unset, the application credential does not expire. | | Optional: \{\}
| #### ApplicationCredentialResourceStatus @@ -346,9 +389,31 @@ _Appears in:_ | Field | Description | Default | Validation | | --- | --- | --- | --- | -| `name` _string_ | name is a Human-readable name for the resource. Might not be unique. | | MaxLength: 1024
| -| `description` _string_ | description is a human-readable description for the resource. | | MaxLength: 1024
| -| `userID` _string_ | userID is the ID of the User to which the resource is associated. | | MaxLength: 1024
| +| `name` _string_ | name is a Human-readable name for the resource. Might not be unique. | | MaxLength: 1024
Optional: \{\}
| +| `description` _string_ | description is a human-readable description for the resource. | | MaxLength: 1024
Optional: \{\}
| +| `unrestricted` _boolean_ | unrestricted is a flag indicating whether the application credential may be used for creation or destruction of other application credentials or trusts | | Optional: \{\}
| +| `projectID` _string_ | projectID of the project the application credential was created for and that authentication requests using this application credential will be scoped to. | | MaxLength: 1024
Optional: \{\}
| +| `roles` _[ApplicationCredentialRoleStatus](#applicationcredentialrolestatus) array_ | roles is a list of role objects may only contain roles that the user has assigned on the project | | MaxItems: 64
Optional: \{\}
| +| `expiresAt` _[Time](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.29/#time-v1-meta)_ | expiresAt is the time of expiration for the application credential. If unset, the application credential does not expire. | | Optional: \{\}
| +| `accessRules` _[ApplicationCredentialAccessRuleStatus](#applicationcredentialaccessrulestatus) array_ | accessRules is a list of fine grained access control rules | | MaxItems: 64
Optional: \{\}
| + + +#### ApplicationCredentialRoleStatus + + + + + + + +_Appears in:_ +- [ApplicationCredentialResourceStatus](#applicationcredentialresourcestatus) + +| Field | Description | Default | Validation | +| --- | --- | --- | --- | +| `name` _string_ | name of an existing role | | MaxLength: 1024
Optional: \{\}
| +| `id` _string_ | id is the ID of a role | | MaxLength: 1024
Optional: \{\}
| +| `domainID` _string_ | domainID of the domain of this role | | MaxLength: 1024
Optional: \{\}
| #### ApplicationCredentialSpec @@ -364,11 +429,11 @@ _Appears in:_ | Field | Description | Default | Validation | | --- | --- | --- | --- | -| `import` _[ApplicationCredentialImport](#applicationcredentialimport)_ | import refers to an existing OpenStack resource which will be imported instead of
creating a new one. | | MaxProperties: 1
MinProperties: 1
| -| `resource` _[ApplicationCredentialResourceSpec](#applicationcredentialresourcespec)_ | resource specifies the desired state of the resource.
resource may not be specified if the management policy is `unmanaged`.
resource must be specified if the management policy is `managed`. | | | -| `managementPolicy` _[ManagementPolicy](#managementpolicy)_ | managementPolicy defines how ORC will treat the object. Valid values are
`managed`: ORC will create, update, and delete the resource; `unmanaged`:
ORC will import an existing resource, and will not apply updates to it or
delete it. | managed | Enum: [managed unmanaged]
| -| `managedOptions` _[ManagedOptions](#managedoptions)_ | managedOptions specifies options which may be applied to managed objects. | | | -| `cloudCredentialsRef` _[CloudCredentialsReference](#cloudcredentialsreference)_ | cloudCredentialsRef points to a secret containing OpenStack credentials | | | +| `import` _[ApplicationCredentialImport](#applicationcredentialimport)_ | import refers to an existing OpenStack resource which will be imported instead of
creating a new one. | | MaxProperties: 1
MinProperties: 1
Optional: \{\}
| +| `resource` _[ApplicationCredentialResourceSpec](#applicationcredentialresourcespec)_ | resource specifies the desired state of the resource.
resource may not be specified if the management policy is `unmanaged`.
resource must be specified if the management policy is `managed`. | | Optional: \{\}
| +| `managementPolicy` _[ManagementPolicy](#managementpolicy)_ | managementPolicy defines how ORC will treat the object. Valid values are
`managed`: ORC will create, update, and delete the resource; `unmanaged`:
ORC will import an existing resource, and will not apply updates to it or
delete it. | managed | Enum: [managed unmanaged]
Optional: \{\}
| +| `managedOptions` _[ManagedOptions](#managedoptions)_ | managedOptions specifies options which may be applied to managed objects. | | Optional: \{\}
| +| `cloudCredentialsRef` _[CloudCredentialsReference](#cloudcredentialsreference)_ | cloudCredentialsRef points to a secret containing OpenStack credentials | | Required: \{\}
| #### ApplicationCredentialStatus @@ -384,9 +449,9 @@ _Appears in:_ | Field | Description | Default | Validation | | --- | --- | --- | --- | -| `conditions` _[Condition](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.29/#condition-v1-meta) array_ | conditions represents the observed status of the object.
Known .status.conditions.type are: "Available", "Progressing"
Available represents the availability of the OpenStack resource. If it is
true then the resource is ready for use.
Progressing indicates whether the controller is still attempting to
reconcile the current state of the OpenStack resource to the desired
state. Progressing will be False either because the desired state has
been achieved, or because some terminal error prevents it from ever being
achieved and the controller is no longer attempting to reconcile. If
Progressing is True, an observer waiting on the resource should continue
to wait. | | MaxItems: 32
| -| `id` _string_ | id is the unique identifier of the OpenStack resource. | | MaxLength: 1024
| -| `resource` _[ApplicationCredentialResourceStatus](#applicationcredentialresourcestatus)_ | resource contains the observed state of the OpenStack resource. | | | +| `conditions` _[Condition](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.29/#condition-v1-meta) array_ | conditions represents the observed status of the object.
Known .status.conditions.type are: "Available", "Progressing"
Available represents the availability of the OpenStack resource. If it is
true then the resource is ready for use.
Progressing indicates whether the controller is still attempting to
reconcile the current state of the OpenStack resource to the desired
state. Progressing will be False either because the desired state has
been achieved, or because some terminal error prevents it from ever being
achieved and the controller is no longer attempting to reconcile. If
Progressing is True, an observer waiting on the resource should continue
to wait. | | MaxItems: 32
Optional: \{\}
| +| `id` _string_ | id is the unique identifier of the OpenStack resource. | | MaxLength: 1024
Optional: \{\}
| +| `resource` _[ApplicationCredentialResourceStatus](#applicationcredentialresourcestatus)_ | resource contains the observed state of the OpenStack resource. | | Optional: \{\}
| #### AvailabilityZoneHint @@ -1306,6 +1371,31 @@ _Appears in:_ | `resource` _[GroupResourceStatus](#groupresourcestatus)_ | resource contains the observed state of the OpenStack resource. | | Optional: \{\}
| +#### HTTPMethod + +_Underlying type:_ _string_ + + + +_Validation:_ +- Enum: [CONNECT DELETE GET HEAD OPTIONS PATCH POST PUT TRACE] + +_Appears in:_ +- [ApplicationCredentialAccessRule](#applicationcredentialaccessrule) + +| Field | Description | +| --- | --- | +| `CONNECT` | | +| `DELETE` | | +| `GET` | | +| `HEAD` | | +| `OPTIONS` | | +| `PATCH` | | +| `POST` | | +| `PUT` | | +| `TRACE` | | + + #### HostID @@ -2049,6 +2139,7 @@ _Appears in:_ - [Address](#address) - [AddressScopeFilter](#addressscopefilter) - [AddressScopeResourceSpec](#addressscoperesourcespec) +- [ApplicationCredentialAccessRule](#applicationcredentialaccessrule) - [ApplicationCredentialFilter](#applicationcredentialfilter) - [ApplicationCredentialResourceSpec](#applicationcredentialresourcespec) - [EndpointFilter](#endpointfilter) From 3e08cf46e4e9401d354f57b6f3b4212efc44d23b Mon Sep 17 00:00:00 2001 From: Gondermann Date: Thu, 12 Feb 2026 15:57:10 +0100 Subject: [PATCH 09/10] ApplicationCredential Tests and Config Samples On-behalf-of: SAP nils.gondermann@sap.com --- ...nstack_v1alpha1_applicationcredential.yaml | 55 ++++++++++++++-- .../00-assert.yaml | 20 +++++- .../00-create-resource.yaml | 49 +++++++++++--- .../00-secret.yaml | 2 + .../00-assert.yaml | 9 ++- .../00-create-resource.yaml | 16 ++--- .../00-secret.yaml | 2 + .../01-delete-secret.yaml | 2 + .../00-assert.yaml | 15 +++++ .../00-create-resources-missing-deps.yaml | 34 ++++++---- .../00-secret.yaml | 2 + .../01-assert.yaml | 15 +++++ .../01-create-dependencies.yaml | 12 ++-- .../03-delete-resources.yaml | 3 + .../00-import-resource.yaml | 5 +- .../00-secret.yaml | 4 ++ .../01-create-trap-resource.yaml | 16 ++--- .../02-assert.yaml | 66 +++++++++---------- .../02-create-resource.yaml | 14 ++-- .../00-create-resources.yaml | 20 +++--- .../00-secret.yaml | 2 + .../01-import-resource.yaml | 16 ++++- .../00-import-resource.yaml | 17 ++++- .../00-secret.yaml | 2 + .../01-assert.yaml | 1 - .../01-create-trap-resource.yaml | 15 ++--- .../02-assert.yaml | 1 - .../02-create-resource.yaml | 15 ++--- .../00-assert.yaml | 26 -------- .../00-minimal-resource.yaml | 28 -------- .../00-secret.yaml | 6 -- .../01-assert.yaml | 17 ----- .../01-updated-resource.yaml | 10 --- .../02-assert.yaml | 26 -------- .../02-reverted-resource.yaml | 7 -- .../applicationcredential-update/README.md | 17 ----- 36 files changed, 303 insertions(+), 264 deletions(-) delete mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/00-assert.yaml delete mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/00-minimal-resource.yaml delete mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/00-secret.yaml delete mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/01-assert.yaml delete mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/01-updated-resource.yaml delete mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/02-assert.yaml delete mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/02-reverted-resource.yaml delete mode 100644 internal/controllers/applicationcredential/tests/applicationcredential-update/README.md diff --git a/config/samples/openstack_v1alpha1_applicationcredential.yaml b/config/samples/openstack_v1alpha1_applicationcredential.yaml index 8edc2aba1..d2fca282b 100644 --- a/config/samples/openstack_v1alpha1_applicationcredential.yaml +++ b/config/samples/openstack_v1alpha1_applicationcredential.yaml @@ -1,14 +1,59 @@ --- apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: Role +metadata: + name: appcred-sample +spec: + cloudCredentialsRef: + cloudName: openstack-admin + secretName: openstack-clouds + managementPolicy: managed + resource: {} +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: appcred-sample +spec: + cloudCredentialsRef: + cloudName: openstack-admin + secretName: openstack-clouds + managementPolicy: unmanaged + import: + filter: + name: admin +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: Service +metadata: + name: appcred-sample +spec: + cloudCredentialsRef: + cloudName: openstack-admin + secretName: openstack-clouds + managementPolicy: unmanaged + import: + filter: + type: "compute" +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential metadata: - name: applicationcredential-sample + name: appcred-sample spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: managed resource: - description: Sample ApplicationCredential - # TODO(scaffolding): Add all fields the resource supports + description: Sample Application Credential + userRef: appcred-sample + unrestricted: true + secretRef: kubernetes-secret + roleRefs: + - appcred-sample + accessRules: + - method: "GET" + serviceRef: appcred-sample + path: "/v2.1/servers" + expiresAt: "2033-03-03T22:22:22Z" diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-assert.yaml index 709036a53..917806d94 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-assert.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-assert.yaml @@ -7,7 +7,12 @@ status: resource: name: applicationcredential-create-full-override description: ApplicationCredential from "create full" test - # TODO(scaffolding): Add all fields the resource supports + unrestricted: true + accessRules: + - method: "GET" + path: "/v2.1/servers" + service: "compute" + expiresAt: "2033-03-03T22:22:22Z" conditions: - type: Available status: "True" @@ -27,7 +32,16 @@ resourceRefs: kind: User name: applicationcredential-create-full ref: user + - apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: Role + name: applicationcredential-create-full + ref: role assertAll: - celExpr: "applicationcredential.status.id != ''" - - celExpr: "applicationcredential.status.resource.userID == user.status.id" - # TODO(scaffolding): Add more checks + - celExpr: "applicationcredential.status.resource.projectID != ''" + - celExpr: "applicationcredential.status.resource.accessRules.size() == 1" + - celExpr: "applicationcredential.status.resource.accessRules[0].id != ''" + - celExpr: "applicationcredential.status.resource.roles.size() == 1" + - celExpr: "applicationcredential.status.resource.roles[0].id == role.status.id" + - celExpr: "applicationcredential.status.resource.roles[0].name == role.status.resource.name" + - celExpr: "!has(applicationcredential.status.resource.roles[0].domainID)" diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-create-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-create-resource.yaml index b95030658..bd2b9c187 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-create-resource.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-create-resource.yaml @@ -1,16 +1,42 @@ --- apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: Role +metadata: + name: applicationcredential-create-full +spec: + cloudCredentialsRef: + cloudName: openstack-admin + secretName: openstack-clouds + managementPolicy: unmanaged + import: + filter: + name: reader +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 kind: User metadata: name: applicationcredential-create-full spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds - managementPolicy: managed - # TODO(scaffolding): Add the necessary fields to create the resource - resource: {} + managementPolicy: unmanaged + import: + filter: + name: admin +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: Service +metadata: + name: applicationcredential-create-full +spec: + cloudCredentialsRef: + cloudName: openstack-admin + secretName: openstack-clouds + managementPolicy: unmanaged + import: + filter: + type: "compute" --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential @@ -18,12 +44,19 @@ metadata: name: applicationcredential-create-full spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: managed resource: name: applicationcredential-create-full-override description: ApplicationCredential from "create full" test userRef: applicationcredential-create-full - # TODO(scaffolding): Add all fields the resource supports + unrestricted: true + secretRef: application-credential-secret + roleRefs: + - applicationcredential-create-full + accessRules: + - method: "GET" + serviceRef: applicationcredential-create-full + path: "/v2.1/servers" + expiresAt: "2033-03-03T22:22:22Z" diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-secret.yaml index 045711ee7..1c93df420 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-secret.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-full/00-secret.yaml @@ -4,3 +4,5 @@ kind: TestStep commands: - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} namespaced: true + - command: kubectl create secret generic application-credential-secret --from-literal=value=abc123 + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-assert.yaml index 0e6d4d81f..3111da88b 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-assert.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-assert.yaml @@ -5,8 +5,9 @@ metadata: name: applicationcredential-create-minimal status: resource: + # Name should default to object name name: applicationcredential-create-minimal - # TODO(scaffolding): Add all fields the resource supports + unrestricted: false conditions: - type: Available status: "True" @@ -28,5 +29,7 @@ resourceRefs: ref: user assertAll: - celExpr: "applicationcredential.status.id != ''" - - celExpr: "applicationcredential.status.resource.userID == user.status.id" - # TODO(scaffolding): Add more checks + - celExpr: "applicationcredential.status.resource.projectID != ''" + - celExpr: "!has(applicationcredential.status.resource.accessRules)" + - celExpr: "applicationcredential.status.resource.roles.size() > 0" + - celExpr: "!has(applicationcredential.status.resource.description)" diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-create-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-create-resource.yaml index f62a6c7b3..2bf956d7d 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-create-resource.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-create-resource.yaml @@ -5,12 +5,12 @@ metadata: name: applicationcredential-create-minimal spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds - managementPolicy: managed - # TODO(scaffolding): Add the necessary fields to create the resource - resource: {} + managementPolicy: unmanaged + import: + filter: + name: admin --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential @@ -18,11 +18,9 @@ metadata: name: applicationcredential-create-minimal spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: managed - # TODO(scaffolding): Only add the mandatory fields. It's possible the resource - # doesn't have mandatory fields, in that case, leave it empty. resource: userRef: applicationcredential-create-minimal + secretRef: application-credential-secret diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-secret.yaml index 045711ee7..1c93df420 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-secret.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/00-secret.yaml @@ -4,3 +4,5 @@ kind: TestStep commands: - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} namespaced: true + - command: kubectl create secret generic application-credential-secret --from-literal=value=abc123 + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-delete-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-delete-secret.yaml index 1620791b9..41677143a 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-delete-secret.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-create-minimal/01-delete-secret.yaml @@ -5,3 +5,5 @@ commands: # We expect the deletion to hang due to the finalizer, so use --wait=false - command: kubectl delete secret openstack-clouds --wait=false namespaced: true + - command: kubectl delete secret application-credential-secret --wait=false + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-assert.yaml index a4c40956e..a2d263694 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-assert.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-assert.yaml @@ -16,6 +16,21 @@ status: --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential +metadata: + name: applicationcredential-dependency-no-secret-ref +status: + conditions: + - type: Available + message: Waiting for Secret/applicationcredential-dependency-pending to be created + status: "False" + reason: Progressing + - type: Progressing + message: Waiting for Secret/applicationcredential-dependency-pending to be created + status: "True" + reason: Progressing +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential metadata: name: applicationcredential-dependency-no-user status: diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-create-resources-missing-deps.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-create-resources-missing-deps.yaml index 3fec6964c..b73db0f6e 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-create-resources-missing-deps.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-create-resources-missing-deps.yaml @@ -5,12 +5,12 @@ metadata: name: applicationcredential-dependency spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds - managementPolicy: managed - # TODO(scaffolding): Add the necessary fields to create the resource - resource: {} + managementPolicy: unmanaged + import: + filter: + name: admin --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential @@ -18,14 +18,12 @@ metadata: name: applicationcredential-dependency-no-user spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: managed resource: userRef: applicationcredential-dependency-pending - # TODO(scaffolding): Add the necessary fields to create the resource - + secretRef: application-credential-secret --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential @@ -33,10 +31,22 @@ metadata: name: applicationcredential-dependency-no-secret spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: applicationcredential-dependency managementPolicy: managed - # TODO(scaffolding): Add the necessary fields to create the resource resource: userRef: applicationcredential-dependency + secretRef: application-credential-secret +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential +metadata: + name: applicationcredential-dependency-no-secret-ref +spec: + cloudCredentialsRef: + cloudName: openstack-admin + secretName: openstack-clouds + managementPolicy: managed + resource: + userRef: applicationcredential-dependency + secretRef: applicationcredential-dependency-pending diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-secret.yaml index 045711ee7..1c93df420 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-secret.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/00-secret.yaml @@ -4,3 +4,5 @@ kind: TestStep commands: - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} namespaced: true + - command: kubectl create secret generic application-credential-secret --from-literal=value=abc123 + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-assert.yaml index 89e29a72d..0b9278c2c 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-assert.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-assert.yaml @@ -16,6 +16,21 @@ status: --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential +metadata: + name: applicationcredential-dependency-no-secret-ref +status: + conditions: + - type: Available + message: OpenStack resource is available + status: "True" + reason: Success + - type: Progressing + message: OpenStack resource is up to date + status: "False" + reason: Success +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: ApplicationCredential metadata: name: applicationcredential-dependency-no-user status: diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-create-dependencies.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-create-dependencies.yaml index 75e318e17..8e895a5ee 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-create-dependencies.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/01-create-dependencies.yaml @@ -4,6 +4,8 @@ kind: TestStep commands: - command: kubectl create secret generic applicationcredential-dependency --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} namespaced: true + - command: kubectl create secret generic applicationcredential-dependency-pending --from-literal=value=abc123 + namespaced: true --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: User @@ -11,9 +13,9 @@ metadata: name: applicationcredential-dependency-pending spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds - managementPolicy: managed - # TODO(scaffolding): Add the necessary fields to create the resource - resource: {} + managementPolicy: unmanaged + import: + filter: + name: admin diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-delete-resources.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-delete-resources.yaml index bed278a33..86a2f7362 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-delete-resources.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-dependency/03-delete-resources.yaml @@ -8,3 +8,6 @@ delete: - apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential name: applicationcredential-dependency-no-user +- apiVersion: openstack.k-orc.cloud/v1alpha1 + kind: ApplicationCredential + name: applicationcredential-dependency-no-secret-ref diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-import-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-import-resource.yaml index 8877b2e99..732cd584a 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-import-resource.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-import-resource.yaml @@ -5,7 +5,7 @@ metadata: name: applicationcredential-import-dependency spec: cloudCredentialsRef: - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: unmanaged import: @@ -18,9 +18,10 @@ metadata: name: applicationcredential-import-dependency spec: cloudCredentialsRef: - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: unmanaged import: filter: userRef: applicationcredential-import-dependency + description: application-credential-import-dependency-target diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-secret.yaml index 045711ee7..4efb5049c 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-secret.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/00-secret.yaml @@ -4,3 +4,7 @@ kind: TestStep commands: - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} namespaced: true + - command: kubectl create secret generic application-credential-secret --from-literal=value=abc123 + namespaced: true + - command: kubectl create secret generic application-credential-user-password --from-literal=password=abc123 + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-create-trap-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-create-trap-resource.yaml index d3fc3873a..1ccc8c3ee 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-create-trap-resource.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/01-create-trap-resource.yaml @@ -5,12 +5,12 @@ metadata: name: applicationcredential-import-dependency-not-this-one spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds - managementPolicy: managed - # TODO(scaffolding): Add the necessary fields to create the resource - resource: {} + managementPolicy: unmanaged + import: + filter: + name: admin --- # This `applicationcredential-import-dependency-not-this-one` should not be picked by the import filter apiVersion: openstack.k-orc.cloud/v1alpha1 @@ -19,10 +19,10 @@ metadata: name: applicationcredential-import-dependency-not-this-one spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: managed resource: + description: application-credential-import-dependency-target userRef: applicationcredential-import-dependency-not-this-one - # TODO(scaffolding): Add the necessary fields to create the resource + secretRef: application-credential-secret diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-assert.yaml index 318452565..3c96a9fae 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-assert.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-assert.yaml @@ -1,34 +1,34 @@ --- -apiVersion: kuttl.dev/v1beta1 -kind: TestAssert -resourceRefs: - - apiVersion: openstack.k-orc.cloud/v1alpha1 - kind: ApplicationCredential - name: applicationcredential-import-dependency - ref: applicationcredential1 - - apiVersion: openstack.k-orc.cloud/v1alpha1 - kind: ApplicationCredential - name: applicationcredential-import-dependency-not-this-one - ref: applicationcredential2 - - apiVersion: openstack.k-orc.cloud/v1alpha1 - kind: User - name: applicationcredential-import-dependency - ref: user -assertAll: - - celExpr: "applicationcredential1.status.id != applicationcredential2.status.id" - - celExpr: "applicationcredential1.status.resource.userID == user.status.id" ---- -apiVersion: openstack.k-orc.cloud/v1alpha1 -kind: ApplicationCredential -metadata: - name: applicationcredential-import-dependency -status: - conditions: - - type: Available - message: OpenStack resource is available - status: "True" - reason: Success - - type: Progressing - message: OpenStack resource is up to date - status: "False" - reason: Success +# FIXME: Need to be able to grant newly created external user permission to create application credentials +# apiVersion: kuttl.dev/v1beta1 +# kind: TestAssert +# resourceRefs: +# - apiVersion: openstack.k-orc.cloud/v1alpha1 +# kind: ApplicationCredential +# name: applicationcredential-import-dependency +# ref: applicationcredential1 +# - apiVersion: openstack.k-orc.cloud/v1alpha1 +# kind: ApplicationCredential +# name: applicationcredential-import-dependency-not-this-one +# ref: applicationcredential2 +# - apiVersion: openstack.k-orc.cloud/v1alpha1 +# kind: User +# name: applicationcredential-import-dependency +# ref: user +# assertAll: +# - celExpr: "applicationcredential1.status.id != applicationcredential2.status.id" +# # --- +# apiVersion: openstack.k-orc.cloud/v1alpha1 +# kind: ApplicationCredential +# metadata: +# name: applicationcredential-import-dependency +# status: +# conditions: +# - type: Available +# message: OpenStack resource is available +# status: "True" +# reason: Success +# - type: Progressing +# message: OpenStack resource is up to date +# status: "False" +# reason: Success diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-create-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-create-resource.yaml index 2f9738f37..5b8c1b547 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-create-resource.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-dependency/02-create-resource.yaml @@ -5,12 +5,12 @@ metadata: name: applicationcredential-import-dependency-external spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: managed - # TODO(scaffolding): Add the necessary fields to create the resource - resource: {} + resource: + description: application-credential external user + passwordRef: application-credential-user-password --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential @@ -18,10 +18,10 @@ metadata: name: applicationcredential-import-dependency-external spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: managed resource: + description: application-credential-import-dependency-target userRef: applicationcredential-import-dependency-external - # TODO(scaffolding): Add the necessary fields to create the resource + secretRef: application-credential-secret diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-create-resources.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-create-resources.yaml index 611b974e8..49f4ec091 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-create-resources.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-create-resources.yaml @@ -5,12 +5,12 @@ metadata: name: applicationcredential-import-error spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds - managementPolicy: managed - # TODO(scaffolding): Add the necessary fields to create the resource - resource: {} + managementPolicy: unmanaged + import: + filter: + name: admin --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential @@ -18,14 +18,13 @@ metadata: name: applicationcredential-import-error-external-1 spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: managed resource: description: ApplicationCredential from "import error" test userRef: applicationcredential-import-error - # TODO(scaffolding): add any required field + secretRef: application-credential-secret --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential @@ -33,11 +32,10 @@ metadata: name: applicationcredential-import-error-external-2 spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: managed resource: description: ApplicationCredential from "import error" test userRef: applicationcredential-import-error - # TODO(scaffolding): add any required field + secretRef: application-credential-secret diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-secret.yaml index 045711ee7..1c93df420 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-secret.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/00-secret.yaml @@ -4,3 +4,5 @@ kind: TestStep commands: - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} namespaced: true + - command: kubectl create secret generic application-credential-secret --from-literal=value=abc123 + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-import-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-import-resource.yaml index e70ca24b4..5cd837952 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-import-resource.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import-error/01-import-resource.yaml @@ -1,13 +1,27 @@ --- apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-import-error +spec: + cloudCredentialsRef: + cloudName: openstack-admin + secretName: openstack-clouds + managementPolicy: unmanaged + import: + filter: + name: admin +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential metadata: name: applicationcredential-import-error spec: cloudCredentialsRef: - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: unmanaged import: filter: description: ApplicationCredential from "import error" test + userRef: applicationcredential-import-error diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/00-import-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/00-import-resource.yaml index f000ecfd5..39fbd4468 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import/00-import-resource.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/00-import-resource.yaml @@ -1,15 +1,28 @@ --- apiVersion: openstack.k-orc.cloud/v1alpha1 +kind: User +metadata: + name: applicationcredential-import-external +spec: + cloudCredentialsRef: + cloudName: openstack-admin + secretName: openstack-clouds + managementPolicy: unmanaged + import: + filter: + name: admin +--- +apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential metadata: name: applicationcredential-import spec: cloudCredentialsRef: - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: unmanaged import: filter: name: applicationcredential-import-external description: ApplicationCredential applicationcredential-import-external from "applicationcredential-import" test - # TODO(scaffolding): Add all fields supported by the filter + userRef: applicationcredential-import-external diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/00-secret.yaml index 045711ee7..1c93df420 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import/00-secret.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/00-secret.yaml @@ -4,3 +4,5 @@ kind: TestStep commands: - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} namespaced: true + - command: kubectl create secret generic application-credential-secret --from-literal=value=abc123 + namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/01-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/01-assert.yaml index 3e0618259..1beb1c01c 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import/01-assert.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/01-assert.yaml @@ -16,7 +16,6 @@ status: resource: name: applicationcredential-import-external-not-this-one description: ApplicationCredential applicationcredential-import-external from "applicationcredential-import" test - # TODO(scaffolding): Add fields necessary to match filter --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/01-create-trap-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/01-create-trap-resource.yaml index 66edf6003..c459f8c1f 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import/01-create-trap-resource.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/01-create-trap-resource.yaml @@ -5,12 +5,12 @@ metadata: name: applicationcredential-import-external-not-this-one spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds - managementPolicy: managed - # TODO(scaffolding): Add the necessary fields to create the resource - resource: {} + managementPolicy: unmanaged + import: + filter: + name: admin --- # This `applicationcredential-import-external-not-this-one` resource serves two purposes: # - ensure that we can successfully create another resource which name is a substring of it (i.e. it's not being adopted) @@ -21,11 +21,10 @@ metadata: name: applicationcredential-import-external-not-this-one spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: managed resource: description: ApplicationCredential applicationcredential-import-external from "applicationcredential-import" test userRef: applicationcredential-import-external-not-this-one - # TODO(scaffolding): Add fields necessary to match filter + secretRef: application-credential-secret diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/02-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/02-assert.yaml index 7412f2324..7077e0834 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import/02-assert.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/02-assert.yaml @@ -30,4 +30,3 @@ status: resource: name: applicationcredential-import-external description: ApplicationCredential applicationcredential-import-external from "applicationcredential-import" test - # TODO(scaffolding): Add all fields the resource supports diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-import/02-create-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-import/02-create-resource.yaml index c82fab8b5..ee49595b2 100644 --- a/internal/controllers/applicationcredential/tests/applicationcredential-import/02-create-resource.yaml +++ b/internal/controllers/applicationcredential/tests/applicationcredential-import/02-create-resource.yaml @@ -5,12 +5,12 @@ metadata: name: applicationcredential-import spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds - managementPolicy: managed - # TODO(scaffolding): Add the necessary fields to create the resource - resource: {} + managementPolicy: unmanaged + import: + filter: + name: admin --- apiVersion: openstack.k-orc.cloud/v1alpha1 kind: ApplicationCredential @@ -18,11 +18,10 @@ metadata: name: applicationcredential-import-external spec: cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack + cloudName: openstack-admin secretName: openstack-clouds managementPolicy: managed resource: description: ApplicationCredential applicationcredential-import-external from "applicationcredential-import" test userRef: applicationcredential-import - # TODO(scaffolding): Add fields necessary to match filter + secretRef: application-credential-secret diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/00-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/00-assert.yaml deleted file mode 100644 index fc2cfc9b5..000000000 --- a/internal/controllers/applicationcredential/tests/applicationcredential-update/00-assert.yaml +++ /dev/null @@ -1,26 +0,0 @@ ---- -apiVersion: kuttl.dev/v1beta1 -kind: TestAssert -resourceRefs: - - apiVersion: openstack.k-orc.cloud/v1alpha1 - kind: ApplicationCredential - name: applicationcredential-update - ref: applicationcredential -assertAll: - - celExpr: "!has(applicationcredential.status.resource.description)" ---- -apiVersion: openstack.k-orc.cloud/v1alpha1 -kind: ApplicationCredential -metadata: - name: applicationcredential-update -status: - resource: - name: applicationcredential-update - # TODO(scaffolding): Add matches for more fields - conditions: - - type: Available - status: "True" - reason: Success - - type: Progressing - status: "False" - reason: Success diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/00-minimal-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/00-minimal-resource.yaml deleted file mode 100644 index b391c1818..000000000 --- a/internal/controllers/applicationcredential/tests/applicationcredential-update/00-minimal-resource.yaml +++ /dev/null @@ -1,28 +0,0 @@ ---- -apiVersion: openstack.k-orc.cloud/v1alpha1 -kind: User -metadata: - name: applicationcredential-update -spec: - cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created - cloudName: openstack - secretName: openstack-clouds - managementPolicy: managed - # TODO(scaffolding): Add the necessary fields to create the resource - resource: {} ---- -apiVersion: openstack.k-orc.cloud/v1alpha1 -kind: ApplicationCredential -metadata: - name: applicationcredential-update -spec: - cloudCredentialsRef: - # TODO(scaffolding): Use openstack-admin if the resource needs admin credentials to be created or updated - cloudName: openstack - secretName: openstack-clouds - managementPolicy: managed - # TODO(scaffolding): Only add the mandatory fields. It's possible the resource - # doesn't have mandatory fields, in that case, leave it empty. - resource: - userRef: applicationcredential-update diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/00-secret.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/00-secret.yaml deleted file mode 100644 index 045711ee7..000000000 --- a/internal/controllers/applicationcredential/tests/applicationcredential-update/00-secret.yaml +++ /dev/null @@ -1,6 +0,0 @@ ---- -apiVersion: kuttl.dev/v1beta1 -kind: TestStep -commands: - - command: kubectl create secret generic openstack-clouds --from-file=clouds.yaml=${E2E_KUTTL_OSCLOUDS} ${E2E_KUTTL_CACERT_OPT} - namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/01-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/01-assert.yaml deleted file mode 100644 index bb022f746..000000000 --- a/internal/controllers/applicationcredential/tests/applicationcredential-update/01-assert.yaml +++ /dev/null @@ -1,17 +0,0 @@ ---- -apiVersion: openstack.k-orc.cloud/v1alpha1 -kind: ApplicationCredential -metadata: - name: applicationcredential-update -status: - resource: - name: applicationcredential-update-updated - description: applicationcredential-update-updated - # TODO(scaffolding): match all fields that were modified - conditions: - - type: Available - status: "True" - reason: Success - - type: Progressing - status: "False" - reason: Success diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/01-updated-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/01-updated-resource.yaml deleted file mode 100644 index ad1de371a..000000000 --- a/internal/controllers/applicationcredential/tests/applicationcredential-update/01-updated-resource.yaml +++ /dev/null @@ -1,10 +0,0 @@ ---- -apiVersion: openstack.k-orc.cloud/v1alpha1 -kind: ApplicationCredential -metadata: - name: applicationcredential-update -spec: - resource: - name: applicationcredential-update-updated - description: applicationcredential-update-updated - # TODO(scaffolding): update all mutable fields diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/02-assert.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/02-assert.yaml deleted file mode 100644 index ec6e12d54..000000000 --- a/internal/controllers/applicationcredential/tests/applicationcredential-update/02-assert.yaml +++ /dev/null @@ -1,26 +0,0 @@ ---- -apiVersion: kuttl.dev/v1beta1 -kind: TestAssert -resourceRefs: - - apiVersion: openstack.k-orc.cloud/v1alpha1 - kind: ApplicationCredential - name: applicationcredential-update - ref: applicationcredential -assertAll: - - celExpr: "!has(applicationcredential.status.resource.description)" ---- -apiVersion: openstack.k-orc.cloud/v1alpha1 -kind: ApplicationCredential -metadata: - name: applicationcredential-update -status: - resource: - name: applicationcredential-update - # TODO(scaffolding): validate that updated fields were all reverted to their original value - conditions: - - type: Available - status: "True" - reason: Success - - type: Progressing - status: "False" - reason: Success diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/02-reverted-resource.yaml b/internal/controllers/applicationcredential/tests/applicationcredential-update/02-reverted-resource.yaml deleted file mode 100644 index 2c6c253ff..000000000 --- a/internal/controllers/applicationcredential/tests/applicationcredential-update/02-reverted-resource.yaml +++ /dev/null @@ -1,7 +0,0 @@ -# NOTE: kuttl only does patch updates, which means we can't delete a field. -# We have to use a kubectl apply command instead. -apiVersion: kuttl.dev/v1beta1 -kind: TestStep -commands: - - command: kubectl replace -f 00-minimal-resource.yaml - namespaced: true diff --git a/internal/controllers/applicationcredential/tests/applicationcredential-update/README.md b/internal/controllers/applicationcredential/tests/applicationcredential-update/README.md deleted file mode 100644 index 020723c0e..000000000 --- a/internal/controllers/applicationcredential/tests/applicationcredential-update/README.md +++ /dev/null @@ -1,17 +0,0 @@ -# Update ApplicationCredential - -## Step 00 - -Create a ApplicationCredential using only mandatory fields. - -## Step 01 - -Update all mutable fields. - -## Step 02 - -Revert the resource to its original value and verify that the resulting object matches its state when first created. - -## Reference - -https://k-orc.cloud/development/writing-tests/#update From da57e7bbe619e3e2638abcbbae2bfbdd3b1290d7 Mon Sep 17 00:00:00 2001 From: Gondermann Date: Mon, 23 Mar 2026 15:21:41 +0100 Subject: [PATCH 10/10] ApplicationCredential Additional Documentation On-behalf-of: SAP nils.gondermann@sap.com --- README.md | 1 + api/v1alpha1/applicationcredential_types.go | 2 ++ cmd/models-schema/zz_generated.openapi.go | 4 ++-- .../openstack.k-orc.cloud_applicationcredentials.yaml | 10 ++++++---- website/docs/crd-reference.md | 4 ++-- 5 files changed, 13 insertions(+), 8 deletions(-) diff --git a/README.md b/README.md index 6c343b281..47f14047d 100644 --- a/README.md +++ b/README.md @@ -73,6 +73,7 @@ kubectl delete -f $ORC_RELEASE | **controller** | **1.x** | **2.x** | **main** | |:---------------------------:|:-------:|:-------:|:--------:| +| application credential | | ◐ | ◐ | | addressscope | | ✔ | ✔ | | domain | | ✔ | ✔ | | endpoint | | ◐ | ◐ | diff --git a/api/v1alpha1/applicationcredential_types.go b/api/v1alpha1/applicationcredential_types.go index a45805710..bcb11a3dd 100644 --- a/api/v1alpha1/applicationcredential_types.go +++ b/api/v1alpha1/applicationcredential_types.go @@ -65,6 +65,7 @@ type ApplicationCredentialResourceSpec struct { Description *string `json:"description,omitempty"` // userRef is a reference to the ORC User which this resource is associated with. + // Note: Due to the nature of the OpenStack API, managing application credentials for a user different than the one ORC is authenticated against can be computationally expensive. In the worst case, all application credentials of all users have to be queried. // +required UserRef KubernetesNameRef `json:"userRef,omitempty"` @@ -97,6 +98,7 @@ type ApplicationCredentialResourceSpec struct { // +kubebuilder:validation:MinProperties:=2 type ApplicationCredentialFilter struct { // userRef is a reference to the ORC User which this resource is associated with. + // Note: Due to the nature of the OpenStack API, managing application credentials for a user different than the one ORC is authenticated against can be computationally expensive. In the worst case, all application credentials of all users have to be queried. // +required UserRef KubernetesNameRef `json:"userRef,omitempty"` diff --git a/cmd/models-schema/zz_generated.openapi.go b/cmd/models-schema/zz_generated.openapi.go index cd6d6186d..bd99a37f2 100644 --- a/cmd/models-schema/zz_generated.openapi.go +++ b/cmd/models-schema/zz_generated.openapi.go @@ -1183,7 +1183,7 @@ func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialF Properties: map[string]spec.Schema{ "userRef": { SchemaProps: spec.SchemaProps{ - Description: "userRef is a reference to the ORC User which this resource is associated with.", + Description: "userRef is a reference to the ORC User which this resource is associated with. Note: Due to the nature of the OpenStack API, managing application credentials for a user different than the one ORC is authenticated against can be computationally expensive. In the worst case, all application credentials of all users have to be queried.", Type: []string{"string"}, Format: "", }, @@ -1311,7 +1311,7 @@ func schema_openstack_resource_controller_v2_api_v1alpha1_ApplicationCredentialR }, "userRef": { SchemaProps: spec.SchemaProps{ - Description: "userRef is a reference to the ORC User which this resource is associated with.", + Description: "userRef is a reference to the ORC User which this resource is associated with. Note: Due to the nature of the OpenStack API, managing application credentials for a user different than the one ORC is authenticated against can be computationally expensive. In the worst case, all application credentials of all users have to be queried.", Type: []string{"string"}, Format: "", }, diff --git a/config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml b/config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml index f16fe117f..c3d4c5dce 100644 --- a/config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml +++ b/config/crd/bases/openstack.k-orc.cloud_applicationcredentials.yaml @@ -102,8 +102,9 @@ spec: pattern: ^[^,]+$ type: string userRef: - description: userRef is a reference to the ORC User which - this resource is associated with. + description: |- + userRef is a reference to the ORC User which this resource is associated with. + Note: Due to the nature of the OpenStack API, managing application credentials for a user different than the one ORC is authenticated against can be computationally expensive. In the worst case, all application credentials of all users have to be queried. maxLength: 253 minLength: 1 type: string @@ -237,8 +238,9 @@ spec: application credentials or trusts type: boolean userRef: - description: userRef is a reference to the ORC User which this - resource is associated with. + description: |- + userRef is a reference to the ORC User which this resource is associated with. + Note: Due to the nature of the OpenStack API, managing application credentials for a user different than the one ORC is authenticated against can be computationally expensive. In the worst case, all application credentials of all users have to be queried. maxLength: 253 minLength: 1 type: string diff --git a/website/docs/crd-reference.md b/website/docs/crd-reference.md index 3ba3a5bda..3f8e8abe7 100644 --- a/website/docs/crd-reference.md +++ b/website/docs/crd-reference.md @@ -328,7 +328,7 @@ _Appears in:_ | Field | Description | Default | Validation | | --- | --- | --- | --- | -| `userRef` _[KubernetesNameRef](#kubernetesnameref)_ | userRef is a reference to the ORC User which this resource is associated with. | | MaxLength: 253
MinLength: 1
Required: \{\}
| +| `userRef` _[KubernetesNameRef](#kubernetesnameref)_ | userRef is a reference to the ORC User which this resource is associated with.
Note: Due to the nature of the OpenStack API, managing application credentials for a user different than the one ORC is authenticated against can be computationally expensive. In the worst case, all application credentials of all users have to be queried. | | MaxLength: 253
MinLength: 1
Required: \{\}
| | `name` _[OpenStackName](#openstackname)_ | name of the existing resource | | MaxLength: 255
MinLength: 1
Pattern: `^[^,]+$`
Optional: \{\}
| | `description` _string_ | description of the existing resource | | MaxLength: 1024
Optional: \{\}
| @@ -368,7 +368,7 @@ _Appears in:_ | --- | --- | --- | --- | | `name` _[OpenStackName](#openstackname)_ | name will be the name of the created resource. If not specified, the
name of the ORC object will be used. | | MaxLength: 255
MinLength: 1
Pattern: `^[^,]+$`
Optional: \{\}
| | `description` _string_ | description is a human-readable description for the resource. | | MaxLength: 255
MinLength: 1
Optional: \{\}
| -| `userRef` _[KubernetesNameRef](#kubernetesnameref)_ | userRef is a reference to the ORC User which this resource is associated with. | | MaxLength: 253
MinLength: 1
Required: \{\}
| +| `userRef` _[KubernetesNameRef](#kubernetesnameref)_ | userRef is a reference to the ORC User which this resource is associated with.
Note: Due to the nature of the OpenStack API, managing application credentials for a user different than the one ORC is authenticated against can be computationally expensive. In the worst case, all application credentials of all users have to be queried. | | MaxLength: 253
MinLength: 1
Required: \{\}
| | `unrestricted` _boolean_ | unrestricted is a flag indicating whether the application credential may be used for creation or destruction of other application credentials or trusts | | Optional: \{\}
| | `secretRef` _[KubernetesNameRef](#kubernetesnameref)_ | secretRef is a reference to a Secret containing the application credential secret | | MaxLength: 253
MinLength: 1
Required: \{\}
| | `roleRefs` _[KubernetesNameRef](#kubernetesnameref) array_ | roleRefs may only contain roles that the user has assigned on the project. If not provided, the roles assigned to the application credential will be the same as the roles in the current token. | | MaxItems: 256
MaxLength: 253
MinLength: 1
Optional: \{\}
|