From cf8049e5e1eb34258dde6eab70ebb8cc244ba4dd Mon Sep 17 00:00:00 2001 From: Simon Murray Date: Thu, 8 Aug 2024 15:32:38 +0100 Subject: [PATCH] Identity Controller Boilerplate At present, when provisioning in a cluster, it blocks a long time waiting for OpenStack to do what it needs to do. This has a knock on effect for UX in that said delay is visible in the UI and CLI tools. This lays down the groundwork to make this asychronous so we don't hold up uer interaction, but we do cluster provisioning. This is a template also for phyiscal network provisioning that takes even longer, and causes request timeouts that need to be avoided. --- Makefile | 3 +- .../region.unikorn-cloud.org_identities.yaml | 50 +++++++++++++ charts/region/templates/_helpers.tpl | 4 + .../identity-controller/clusterrole.yaml | 30 ++++++++ .../clusterrolebinding.yaml | 14 ++++ .../identity-controller/deployment.yaml | 38 ++++++++++ .../templates/identity-controller/role.yaml | 23 ++++++ .../identity-controller/rolebinding.yaml | 14 ++++ .../identity-controller/serviceaccount.yaml | 10 +++ charts/region/values.yaml | 5 ++ cmd/unikorn-identity-controller/main.go | 27 +++++++ .../unikorn-identity-controller/.dockerignore | 2 + docker/unikorn-identity-controller/Dockerfile | 8 ++ .../unikorn-region-controller/.dockerignore | 1 - docker/unikorn-region-controller/Dockerfile | 1 - go.mod | 9 +++ go.sum | 2 + pkg/apis/unikorn/v1alpha1/helpers.go | 48 ++++++++++++ pkg/apis/unikorn/v1alpha1/types.go | 4 + .../unikorn/v1alpha1/zz_generated.deepcopy.go | 9 ++- pkg/managers/identity/manager.go | 74 +++++++++++++++++++ .../managers/identity/provisioner.go | 55 ++++++++++++++ 22 files changed, 427 insertions(+), 4 deletions(-) create mode 100644 charts/region/templates/identity-controller/clusterrole.yaml create mode 100644 charts/region/templates/identity-controller/clusterrolebinding.yaml create mode 100644 charts/region/templates/identity-controller/deployment.yaml create mode 100644 charts/region/templates/identity-controller/role.yaml create mode 100644 charts/region/templates/identity-controller/rolebinding.yaml create mode 100644 charts/region/templates/identity-controller/serviceaccount.yaml create mode 100644 cmd/unikorn-identity-controller/main.go create mode 100644 docker/unikorn-identity-controller/.dockerignore create mode 100644 docker/unikorn-identity-controller/Dockerfile create mode 100644 pkg/apis/unikorn/v1alpha1/helpers.go create mode 100644 pkg/managers/identity/manager.go create mode 100644 pkg/provisioners/managers/identity/provisioner.go diff --git a/Makefile b/Makefile index 6dde3bb..071c40e 100644 --- a/Makefile +++ b/Makefile @@ -11,7 +11,8 @@ REVISION := $(shell git rev-parse HEAD) # for your host's architecture. The latter are going to run in Kubernetes, so # want to be amd64. CONTROLLERS = \ - unikorn-region-controller + unikorn-region-controller \ + unikorn-identity-controller # Release will do cross compliation of all images for the 'all' target. # Note we aren't fucking about with docker here because that opens up a diff --git a/charts/region/crds/region.unikorn-cloud.org_identities.yaml b/charts/region/crds/region.unikorn-cloud.org_identities.yaml index 503b235..06b3e30 100644 --- a/charts/region/crds/region.unikorn-cloud.org_identities.yaml +++ b/charts/region/crds/region.unikorn-cloud.org_identities.yaml @@ -89,6 +89,9 @@ spec: - projectID - userID type: object + pause: + description: Pause, if true, will inhibit reconciliation. + type: boolean provider: description: Provider defines the provider type. enum: @@ -116,6 +119,53 @@ spec: - provider type: object status: + properties: + conditions: + description: Current service state of a cluster manager. + items: + description: |- + Condition is a generic condition type for use across all resource types. + It's generic so that the underlying controller-manager functionality can + be shared across all resources. + properties: + lastTransitionTime: + description: Last time the condition transitioned from one status + to another. + format: date-time + type: string + message: + description: Human-readable message indicating details about + last transition. + type: string + reason: + description: Unique, one-word, CamelCase reason for the condition's + last transition. + enum: + - Provisioning + - Provisioned + - Cancelled + - Errored + - Deprovisioning + - Deprovisioned + type: string + status: + description: |- + Status is the status of the condition. + Can be True, False, Unknown. + type: string + type: + description: Type is the type of the condition. + enum: + - Available + type: string + required: + - lastTransitionTime + - message + - reason + - status + - type + type: object + type: array type: object required: - spec diff --git a/charts/region/templates/_helpers.tpl b/charts/region/templates/_helpers.tpl index 78374be..18bf26d 100644 --- a/charts/region/templates/_helpers.tpl +++ b/charts/region/templates/_helpers.tpl @@ -5,6 +5,10 @@ Create the container images {{- .Values.image | default (printf "%s/unikorn-region-controller:%s" (include "unikorn.defaultRepositoryPath" .) (.Values.tag | default .Chart.Version)) }} {{- end }} +{{- define "unikorn.identityControllerImage" -}} +{{- .Values.identityController.image | default (printf "%s/unikorn-identity-controller:%s" (include "unikorn.defaultRepositoryPath" .) (.Values.tag | default .Chart.Version)) }} +{{- end }} + {{/* Create image pull secrets */}} diff --git a/charts/region/templates/identity-controller/clusterrole.yaml b/charts/region/templates/identity-controller/clusterrole.yaml new file mode 100644 index 0000000..47d97bf --- /dev/null +++ b/charts/region/templates/identity-controller/clusterrole.yaml @@ -0,0 +1,30 @@ +apiVersion: rbac.authorization.k8s.io/v1 +kind: ClusterRole +metadata: + name: unikorn-identity-controller + labels: + {{- include "unikorn.labels" . | nindent 4 }} +rules: +# Orchestrate Unikorn resources (my job). +- apiGroups: + - region.unikorn-cloud.org + resources: + - identities + verbs: + - list + - watch + - patch + - update +- apiGroups: + - region.unikorn-cloud.org + resources: + - identities/status + verbs: + - update +- apiGroups: + - "" + resources: + - secrets + verbs: + - list + - watch diff --git a/charts/region/templates/identity-controller/clusterrolebinding.yaml b/charts/region/templates/identity-controller/clusterrolebinding.yaml new file mode 100644 index 0000000..435c340 --- /dev/null +++ b/charts/region/templates/identity-controller/clusterrolebinding.yaml @@ -0,0 +1,14 @@ +apiVersion: rbac.authorization.k8s.io/v1 +kind: ClusterRoleBinding +metadata: + name: unikorn-identity-controller + labels: + {{- include "unikorn.labels" . | nindent 4 }} +subjects: +- kind: ServiceAccount + namespace: {{ .Release.Namespace }} + name: unikorn-identity-controller +roleRef: + apiGroup: rbac.authorization.k8s.io + kind: ClusterRole + name: unikorn-identity-controller diff --git a/charts/region/templates/identity-controller/deployment.yaml b/charts/region/templates/identity-controller/deployment.yaml new file mode 100644 index 0000000..505374a --- /dev/null +++ b/charts/region/templates/identity-controller/deployment.yaml @@ -0,0 +1,38 @@ +apiVersion: apps/v1 +kind: Deployment +metadata: + name: unikorn-identity-controller + labels: + {{- include "unikorn.labels" . | nindent 4 }} +spec: + replicas: 1 + selector: + matchLabels: + app: unikorn-identity-controller + template: + metadata: + labels: + app: unikorn-identity-controller + spec: + containers: + - name: unikorn-identity-controller + image: {{ include "unikorn.identityControllerImage" . }} + ports: + - name: http + containerPort: 6080 + - name: prometheus + containerPort: 8080 + - name: pprof + containerPort: 6060 + resources: + requests: + cpu: "50m" + memory: 50Mi + limits: + cpu: "100m" + memory: 100Mi + securityContext: + readOnlyRootFilesystem: true + serviceAccountName: unikorn-identity-controller + securityContext: + runAsNonRoot: true diff --git a/charts/region/templates/identity-controller/role.yaml b/charts/region/templates/identity-controller/role.yaml new file mode 100644 index 0000000..0ab2e24 --- /dev/null +++ b/charts/region/templates/identity-controller/role.yaml @@ -0,0 +1,23 @@ +apiVersion: rbac.authorization.k8s.io/v1 +kind: Role +metadata: + name: unikorn-identity-controller + labels: + {{- include "unikorn.labels" . | nindent 4 }} +rules: +# Controller prerequisites. +- apiGroups: + - coordination.k8s.io + resources: + - leases + verbs: + - create + - get + - update +- apiGroups: + - "" + resources: + - events + verbs: + - create + - update diff --git a/charts/region/templates/identity-controller/rolebinding.yaml b/charts/region/templates/identity-controller/rolebinding.yaml new file mode 100644 index 0000000..462ba73 --- /dev/null +++ b/charts/region/templates/identity-controller/rolebinding.yaml @@ -0,0 +1,14 @@ +apiVersion: rbac.authorization.k8s.io/v1 +kind: RoleBinding +metadata: + name: unikorn-identity-controller + labels: + {{- include "unikorn.labels" . | nindent 4 }} +subjects: +- kind: ServiceAccount + namespace: {{ .Release.Namespace }} + name: unikorn-identity-controller +roleRef: + apiGroup: rbac.authorization.k8s.io + kind: Role + name: unikorn-identity-controller diff --git a/charts/region/templates/identity-controller/serviceaccount.yaml b/charts/region/templates/identity-controller/serviceaccount.yaml new file mode 100644 index 0000000..0a61c88 --- /dev/null +++ b/charts/region/templates/identity-controller/serviceaccount.yaml @@ -0,0 +1,10 @@ +apiVersion: v1 +kind: ServiceAccount +metadata: + name: unikorn-identity-controller + labels: + {{- include "unikorn.labels" . | nindent 4 }} +{{- with ( include "unikorn.imagePullSecrets" . ) }} +imagePullSecrets: +{{ . }} +{{- end }} diff --git a/charts/region/values.yaml b/charts/region/values.yaml index 9d9277d..64c49d5 100644 --- a/charts/region/values.yaml +++ b/charts/region/values.yaml @@ -101,6 +101,11 @@ organization: unikorn-cloud # Allows override of the global default image. # image: +# Identity controller configuration. +identityController: + # Allow override of the identity controller image. + image: + # Sets the DNS hosts/X.509 Certs. region: host: region.unikorn-cloud.org diff --git a/cmd/unikorn-identity-controller/main.go b/cmd/unikorn-identity-controller/main.go new file mode 100644 index 0000000..35fbc3a --- /dev/null +++ b/cmd/unikorn-identity-controller/main.go @@ -0,0 +1,27 @@ +/* +Copyright 2022-2024 EscherCloud. +Copyright 2024 the Unikorn 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 main + +import ( + "github.com/unikorn-cloud/core/pkg/manager" + "github.com/unikorn-cloud/region/pkg/managers/identity" +) + +func main() { + manager.Run(&identity.Factory{}) +} diff --git a/docker/unikorn-identity-controller/.dockerignore b/docker/unikorn-identity-controller/.dockerignore new file mode 100644 index 0000000..c5a52a1 --- /dev/null +++ b/docker/unikorn-identity-controller/.dockerignore @@ -0,0 +1,2 @@ +* +!bin/*-linux-gnu/unikorn-identity-controller diff --git a/docker/unikorn-identity-controller/Dockerfile b/docker/unikorn-identity-controller/Dockerfile new file mode 100644 index 0000000..65d7df9 --- /dev/null +++ b/docker/unikorn-identity-controller/Dockerfile @@ -0,0 +1,8 @@ +FROM gcr.io/distroless/static:nonroot + +# This is implcitly created by 'docker buildx build' +ARG TARGETARCH + +COPY bin/${TARGETARCH}-linux-gnu/unikorn-identity-controller / + +ENTRYPOINT ["/unikorn-identity-controller"] diff --git a/docker/unikorn-region-controller/.dockerignore b/docker/unikorn-region-controller/.dockerignore index b6a7519..c556893 100644 --- a/docker/unikorn-region-controller/.dockerignore +++ b/docker/unikorn-region-controller/.dockerignore @@ -1,3 +1,2 @@ * !bin/*-linux-gnu/unikorn-region-controller -!hack/passwd.nonroot diff --git a/docker/unikorn-region-controller/Dockerfile b/docker/unikorn-region-controller/Dockerfile index a54e581..4830e26 100644 --- a/docker/unikorn-region-controller/Dockerfile +++ b/docker/unikorn-region-controller/Dockerfile @@ -3,7 +3,6 @@ FROM gcr.io/distroless/static:nonroot # This is implcitly created by 'docker buildx build' ARG TARGETARCH -# Required as we are talking to Openstack public endpoints. COPY bin/${TARGETARCH}-linux-gnu/unikorn-region-controller / ENTRYPOINT ["/unikorn-region-controller"] diff --git a/go.mod b/go.mod index 20f195b..e203bd7 100644 --- a/go.mod +++ b/go.mod @@ -24,11 +24,14 @@ require ( require ( github.com/apapsch/go-jsonmerge/v2 v2.0.0 // indirect + github.com/beorn7/perks v1.0.1 // indirect github.com/cenkalti/backoff/v4 v4.3.0 // indirect + github.com/cespare/xxhash/v2 v2.3.0 // indirect github.com/coreos/go-oidc/v3 v3.11.0 // indirect github.com/davecgh/go-spew v1.1.1 // indirect github.com/emicklei/go-restful/v3 v3.12.1 // indirect github.com/evanphx/json-patch/v5 v5.9.0 // indirect + github.com/fsnotify/fsnotify v1.7.0 // indirect github.com/go-jose/go-jose/v3 v3.0.3 // indirect github.com/go-jose/go-jose/v4 v4.0.2 // indirect github.com/go-logr/logr v1.4.2 // indirect @@ -38,6 +41,7 @@ require ( github.com/go-openapi/jsonreference v0.21.0 // indirect github.com/go-openapi/swag v0.23.0 // indirect github.com/gogo/protobuf v1.3.2 // indirect + github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da // indirect github.com/golang/protobuf v1.5.4 // indirect github.com/google/gnostic-models v0.6.8 // indirect github.com/google/go-cmp v0.6.0 // indirect @@ -60,6 +64,10 @@ require ( github.com/perimeterx/marshmallow v1.1.5 // indirect github.com/pkg/errors v0.9.1 // indirect github.com/pmezard/go-difflib v1.0.0 // indirect + github.com/prometheus/client_golang v1.19.1 // indirect + github.com/prometheus/client_model v0.6.1 // indirect + github.com/prometheus/common v0.55.0 // indirect + github.com/prometheus/procfs v0.15.1 // indirect go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.28.0 // indirect go.opentelemetry.io/otel/metric v1.28.0 // indirect go.opentelemetry.io/proto/otlp v1.3.1 // indirect @@ -73,6 +81,7 @@ require ( golang.org/x/term v0.22.0 // indirect golang.org/x/text v0.16.0 // indirect golang.org/x/time v0.5.0 // indirect + gomodules.xyz/jsonpatch/v2 v2.4.0 // indirect google.golang.org/genproto/googleapis/api v0.0.0-20240708141625-4ad9e859172b // indirect google.golang.org/genproto/googleapis/rpc v0.0.0-20240708141625-4ad9e859172b // indirect google.golang.org/grpc v1.65.0 // indirect diff --git a/go.sum b/go.sum index 39dbfe4..255c90c 100644 --- a/go.sum +++ b/go.sum @@ -161,6 +161,8 @@ go.opentelemetry.io/proto/otlp v1.3.1 h1:TrMUixzpM0yuc/znrFTP9MMRh8trP93mkCiDVeX go.opentelemetry.io/proto/otlp v1.3.1/go.mod h1:0X1WI4de4ZsLrrJNLAQbFeLCm3T7yBkR0XqQ7niQU+8= go.uber.org/goleak v1.3.0 h1:2K3zAYmnTNqV73imy9J1T3WC+gmCePx2hEGkimedGto= go.uber.org/goleak v1.3.0/go.mod h1:CoHD4mav9JJNrW/WLlf7HGZPjdw8EucARQHekz1X6bE= +go.uber.org/mock v0.4.0 h1:VcM4ZOtdbR4f6VXfiOpwpVJDL6lCReaZ6mw31wqh7KU= +go.uber.org/mock v0.4.0/go.mod h1:a6FSlNadKUHUa9IP5Vyt1zh4fC7uAwxMutEAscFbkZc= go.uber.org/multierr v1.11.0 h1:blXXJkSxSSfBVBlC76pxqeO+LN3aDfLQo+309xJstO0= go.uber.org/multierr v1.11.0/go.mod h1:20+QtiLqy0Nd6FdQB9TLXag12DsQkrbs3htMFfDN80Y= go.uber.org/zap v1.27.0 h1:aJMhYGrd5QSmlpLMr2MftRKl7t8J8PTZPA732ud/XR8= diff --git a/pkg/apis/unikorn/v1alpha1/helpers.go b/pkg/apis/unikorn/v1alpha1/helpers.go new file mode 100644 index 0000000..041e222 --- /dev/null +++ b/pkg/apis/unikorn/v1alpha1/helpers.go @@ -0,0 +1,48 @@ +/* +Copyright 2024 the Unikorn 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 ( + unikornv1core "github.com/unikorn-cloud/core/pkg/apis/unikorn/v1alpha1" + + corev1 "k8s.io/api/core/v1" + "k8s.io/apimachinery/pkg/labels" +) + +// Paused implements the ReconcilePauser interface. +func (c *Identity) Paused() bool { + return c.Spec.Pause +} + +// StatusConditionRead scans the status conditions for an existing condition whose type +// matches. +func (c *Identity) StatusConditionRead(t unikornv1core.ConditionType) (*unikornv1core.Condition, error) { + return unikornv1core.GetCondition(c.Status.Conditions, t) +} + +// StatusConditionWrite either adds or updates a condition in the cluster manager status. +// If the condition, status and message match an existing condition the update is +// ignored. +func (c *Identity) StatusConditionWrite(t unikornv1core.ConditionType, status corev1.ConditionStatus, reason unikornv1core.ConditionReason, message string) { + unikornv1core.UpdateCondition(&c.Status.Conditions, t, status, reason, message) +} + +// ResourceLabels generates a set of labels to uniquely identify the resource +// if it were to be placed in a single global namespace. +func (c *Identity) ResourceLabels() (labels.Set, error) { + return nil, nil +} diff --git a/pkg/apis/unikorn/v1alpha1/types.go b/pkg/apis/unikorn/v1alpha1/types.go index af37331..9f8622b 100644 --- a/pkg/apis/unikorn/v1alpha1/types.go +++ b/pkg/apis/unikorn/v1alpha1/types.go @@ -291,6 +291,8 @@ type Identity struct { // IdentitySpec stores any state necessary to manage identity. type IdentitySpec struct { + // Pause, if true, will inhibit reconciliation. + Pause bool `json:"pause,omitempty"` // Tags are an abitrary list of key/value pairs that a client // may populate to store metadata for the resource. Tags TagList `json:"tags,omitempty"` @@ -316,6 +318,8 @@ type IdentitySpecOpenStack struct { } type IdentityStatus struct { + // Current service state of a cluster manager. + Conditions []unikornv1core.Condition `json:"conditions,omitempty"` } // PhysicalNetworkList s a typed list of physical networks. diff --git a/pkg/apis/unikorn/v1alpha1/zz_generated.deepcopy.go b/pkg/apis/unikorn/v1alpha1/zz_generated.deepcopy.go index 3c0d7d1..48463ee 100644 --- a/pkg/apis/unikorn/v1alpha1/zz_generated.deepcopy.go +++ b/pkg/apis/unikorn/v1alpha1/zz_generated.deepcopy.go @@ -152,7 +152,7 @@ func (in *Identity) DeepCopyInto(out *Identity) { out.TypeMeta = in.TypeMeta in.ObjectMeta.DeepCopyInto(&out.ObjectMeta) in.Spec.DeepCopyInto(&out.Spec) - out.Status = in.Status + in.Status.DeepCopyInto(&out.Status) return } @@ -262,6 +262,13 @@ func (in *IdentitySpecOpenStack) DeepCopy() *IdentitySpecOpenStack { // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *IdentityStatus) DeepCopyInto(out *IdentityStatus) { *out = *in + if in.Conditions != nil { + in, out := &in.Conditions, &out.Conditions + *out = make([]unikornv1alpha1.Condition, len(*in)) + for i := range *in { + (*in)[i].DeepCopyInto(&(*out)[i]) + } + } return } diff --git a/pkg/managers/identity/manager.go b/pkg/managers/identity/manager.go new file mode 100644 index 0000000..04db442 --- /dev/null +++ b/pkg/managers/identity/manager.go @@ -0,0 +1,74 @@ +/* +Copyright 2024 the Unikorn 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 identity + +import ( + coreclient "github.com/unikorn-cloud/core/pkg/client" + coremanager "github.com/unikorn-cloud/core/pkg/manager" + "github.com/unikorn-cloud/core/pkg/manager/options" + unikornv1 "github.com/unikorn-cloud/region/pkg/apis/unikorn/v1alpha1" + "github.com/unikorn-cloud/region/pkg/constants" + "github.com/unikorn-cloud/region/pkg/provisioners/managers/identity" + + "sigs.k8s.io/controller-runtime/pkg/client" + "sigs.k8s.io/controller-runtime/pkg/controller" + "sigs.k8s.io/controller-runtime/pkg/handler" + "sigs.k8s.io/controller-runtime/pkg/manager" + "sigs.k8s.io/controller-runtime/pkg/predicate" + "sigs.k8s.io/controller-runtime/pkg/reconcile" + "sigs.k8s.io/controller-runtime/pkg/source" +) + +// Factory provides methods that can build a type specific controller. +type Factory struct{} + +var _ coremanager.ControllerFactory = &Factory{} + +// Metadata returns the application, version and revision. +func (*Factory) Metadata() (string, string, string) { + return constants.Application, constants.Version, constants.Revision +} + +// Reconciler returns a new reconciler instance. +func (*Factory) Reconciler(options *options.Options, manager manager.Manager) reconcile.Reconciler { + return coremanager.NewReconciler(options, manager, identity.New) +} + +// RegisterWatches adds any watches that would trigger a reconcile. +func (*Factory) RegisterWatches(manager manager.Manager, controller controller.Controller) error { + // Any changes to the identity spec, trigger a reconcile. + if err := controller.Watch(source.Kind(manager.GetCache(), &unikornv1.Identity{}, &handler.TypedEnqueueRequestForObject[*unikornv1.Identity]{}, &predicate.TypedGenerationChangedPredicate[*unikornv1.Identity]{})); err != nil { + return err + } + + return nil +} + +// Upgrade can perform metadata upgrades of all versioned resources on restart/upgrade +// of the controller. This must not affect the spec in any way as it causes split brain +// and potential fail. +func (*Factory) Upgrade(_ client.Client) error { + return nil +} + +// Schemes allows controllers to add types to the client beyond +// the defaults defined in this repository. +func (*Factory) Schemes() []coreclient.SchemeAdder { + return []coreclient.SchemeAdder{ + unikornv1.AddToScheme, + } +} diff --git a/pkg/provisioners/managers/identity/provisioner.go b/pkg/provisioners/managers/identity/provisioner.go new file mode 100644 index 0000000..420d013 --- /dev/null +++ b/pkg/provisioners/managers/identity/provisioner.go @@ -0,0 +1,55 @@ +/* +Copyright 2024 the Unikorn 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 identity + +import ( + "context" + + unikornv1core "github.com/unikorn-cloud/core/pkg/apis/unikorn/v1alpha1" + "github.com/unikorn-cloud/core/pkg/provisioners" + unikornv1 "github.com/unikorn-cloud/region/pkg/apis/unikorn/v1alpha1" +) + +// Provisioner encapsulates control plane provisioning. +type Provisioner struct { + provisioners.Metadata + + // identity is the identity we're provisioning. + identity unikornv1.Identity +} + +// New returns a new initialized provisioner object. +func New() provisioners.ManagerProvisioner { + return &Provisioner{} +} + +// Ensure the ManagerProvisioner interface is implemented. +var _ provisioners.ManagerProvisioner = &Provisioner{} + +func (p *Provisioner) Object() unikornv1core.ManagableResourceInterface { + return &p.identity +} + +// Provision implements the Provision interface. +func (p *Provisioner) Provision(ctx context.Context) error { + return nil +} + +// Deprovision implements the Provision interface. +func (p *Provisioner) Deprovision(ctx context.Context) error { + return nil +}