You are viewing a plain text version of this content. The canonical link for it is here.
Posted to notifications@shardingsphere.apache.org by du...@apache.org on 2022/08/23 07:45:37 UTC
[shardingsphere-on-cloud] 03/39: Create ProxyConfig CRD Resource. (#3)
This is an automated email from the ASF dual-hosted git repository.
duanzhengqiang pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/shardingsphere-on-cloud.git
commit 8d4bedc57b55bfd7e2ba9b166e20cb30282ad404
Author: Ghoul_Lee <wi...@gmail.com>
AuthorDate: Mon Apr 18 23:43:45 2022 +0800
Create ProxyConfig CRD Resource. (#3)
* ADD: Init ProxyConfig CRD Resources
* ADD: Convert ProxyConfig spec content to yaml format && apply resources to Kubernetes
* ADD: add ProxyConfig CRD sample;
UPDATE: optimize ProxyConfig Controller logic;Update ProxyConfig status to show what cluster type now is
* FIX: export RepositoryConfig
UPDATE: change serverConfig struct location
---
PROJECT | 9 ++
api/v1alpha1/proxyconfig_types.go | 67 ++++++++++
api/v1alpha1/serverconfig.go | 65 +++++++++
api/v1alpha1/zz_generated.deepcopy.go | 89 +++++++++++++
.../shardingsphere.sphere-ex.com_proxyconfigs.yaml | 148 +++++++++++++++++++++
config/crd/kustomization.yaml | 5 +-
.../crd/patches/cainjection_in_proxyconfigs.yaml | 7 +
config/crd/patches/webhook_in_proxyconfigs.yaml | 16 +++
config/rbac/proxyconfig_editor_role.yaml | 24 ++++
config/rbac/proxyconfig_viewer_role.yaml | 20 +++
config/rbac/role.yaml | 26 ++++
config/samples/shardingsphere_v1alpha1_proxy.yaml | 1 +
.../shardingsphere_v1alpha1_proxyconfig.yaml | 27 ++++
main.go | 8 ++
pkg/controllers/proxyconfig_controller.go | 115 ++++++++++++++++
pkg/reconcile/resource.go | 31 +++++
16 files changed, 657 insertions(+), 1 deletion(-)
diff --git a/PROJECT b/PROJECT
index c933d7b..2fae1fe 100644
--- a/PROJECT
+++ b/PROJECT
@@ -13,4 +13,13 @@ resources:
kind: Proxy
path: sphere-ex.com/shardingsphere-operator/api/v1alpha1
version: v1alpha1
+- api:
+ crdVersion: v1
+ namespaced: true
+ controller: true
+ domain: sphere-ex.com
+ group: shardingsphere
+ kind: ProxyConfig
+ path: sphere-ex.com/shardingsphere-operator/api/v1alpha1
+ version: v1alpha1
version: "3"
diff --git a/api/v1alpha1/proxyconfig_types.go b/api/v1alpha1/proxyconfig_types.go
new file mode 100644
index 0000000..02108ad
--- /dev/null
+++ b/api/v1alpha1/proxyconfig_types.go
@@ -0,0 +1,67 @@
+/*
+Copyright 2022.
+
+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"
+)
+
+// EDIT THIS FILE! THIS IS SCAFFOLDING FOR YOU TO OWN!
+// NOTE: json tags are required. Any new fields you add must have json tags for the fields to be serialized.
+
+// ProxyConfigSpec defines the desired state of ProxyConfig
+type ProxyConfigSpec struct {
+ ClusterConfig ClusterConfig `json:"mode" yaml:"mode"`
+ Authority Auth `json:"authority" yaml:"authority"`
+ // +optional
+ Props Props `json:"props,omitempty" yaml:"props,omitempty"`
+}
+
+// ProxyConfigStatus defines the observed state of ProxyConfig
+type ProxyConfigStatus struct {
+ MetadataRepository string `json:"metadataRepository"`
+}
+
+//+kubebuilder:printcolumn:JSONPath=".status.metadataRepository",name=MetadataRepository,type=string
+//+kubebuilder:object:root=true
+//+kubebuilder:subresource:status
+
+// ProxyConfig is the Schema for the proxyconfigs API
+type ProxyConfig struct {
+ metav1.TypeMeta `json:",inline"`
+ metav1.ObjectMeta `json:"metadata,omitempty"`
+
+ Spec ProxyConfigSpec `json:"spec,omitempty"`
+ Status ProxyConfigStatus `json:"status,omitempty"`
+}
+
+//+kubebuilder:object:root=true
+
+// ProxyConfigList contains a list of ProxyConfig
+type ProxyConfigList struct {
+ metav1.TypeMeta `json:",inline"`
+ metav1.ListMeta `json:"metadata,omitempty"`
+ Items []ProxyConfig `json:"items"`
+}
+
+func init() {
+ SchemeBuilder.Register(&ProxyConfig{}, &ProxyConfigList{})
+}
+
+func (in *ProxyConfig) SetMetadataRepository(metadataType string) {
+ in.Status.MetadataRepository = metadataType
+}
diff --git a/api/v1alpha1/serverconfig.go b/api/v1alpha1/serverconfig.go
new file mode 100644
index 0000000..a2cb8d7
--- /dev/null
+++ b/api/v1alpha1/serverconfig.go
@@ -0,0 +1,65 @@
+package v1alpha1
+
+// User TODO: description
+type User struct {
+ // +optional
+ UserConfig string `json:"-" yaml:"user"`
+ UserName string `json:"userName" yaml:"-"`
+ PassWord string `json:"passWord" yaml:"-"`
+ // +optional
+ HostName string `json:"hostName,omitempty" yaml:"-"`
+}
+
+// Provider TODO: description
+type Provider struct {
+ Type string `json:"type" yaml:"type"`
+}
+
+// Auth TODO: description
+type Auth struct {
+ Users []User `json:"users" yaml:"users"`
+ // +optional
+ Provider Provider `json:"provider,omitempty"`
+}
+
+// Props TODO: description
+type Props struct {
+ // +optional
+ KernelExecutorSize int `json:"kernel-executor-size,omitempty" yaml:"kernel-executor-size"`
+ // +optional
+ CheckTableMetadataEnabled bool `json:"check-table-metadata-enabled,omitempty" yaml:"check-table-metadata-enabled"`
+ // +optional
+ ProxyBackendQueryFetchSize int `json:"proxy-backend-query-fetch-size,omitempty" yaml:"proxy-backend-query-fetch-size"`
+ // +optional
+ CheckDuplicateTableEnabled bool `json:"check-duplicate-table-enabled,omitempty" yaml:"check-duplicate-table-enabled"`
+ // +optional
+ ProxyFrontendExecutorSize int `json:"proxy-frontend-executor-size,omitempty" yaml:"proxy-frontend-executor-size"`
+ // +optional
+ ProxyBackendExecutorSuitable string `json:"proxy-backend-executor-suitable,omitempty" yaml:"proxy-backend-executor-suitable"`
+}
+
+type ClusterProps struct {
+ NameSpace string `json:"namespace" yaml:"namespace"`
+ ServerLists string `json:"server-lists" yaml:"server-lists"`
+ // +optional
+ RetryIntervalMilliseconds int `json:"retryIntervalMilliseconds,omitempty" yaml:"retryIntervalMilliseconds,omitempty"`
+ // +optional
+ MaxRetries int `json:"maxRetries,omitempty" yaml:"maxRetries,omitempty"`
+ // +optional
+ TimeToLiveSeconds int `json:"timeToLiveSeconds,omitempty" yaml:"timeToLiveSeconds,omitempty"`
+ // +optional
+ OperationTimeoutMilliseconds int `json:"operationTimeoutMilliseconds,omitempty" yaml:"operationTimeoutMilliseconds,omitempty"`
+ // +optional
+ Digest string `json:"digest,omitempty" yaml:"digest,omitempty"`
+}
+
+type RepositoryConfig struct {
+ Type string `json:"type" yaml:"type"`
+ Props ClusterProps `json:"props" yaml:"props"`
+}
+
+type ClusterConfig struct {
+ Type string `json:"type" yaml:"type"`
+ Repository RepositoryConfig `json:"repository" yaml:"repository"`
+ Overwrite bool `json:"overwrite" yaml:"overwrite"`
+}
diff --git a/api/v1alpha1/zz_generated.deepcopy.go b/api/v1alpha1/zz_generated.deepcopy.go
index 5a73331..77c82f2 100644
--- a/api/v1alpha1/zz_generated.deepcopy.go
+++ b/api/v1alpha1/zz_generated.deepcopy.go
@@ -105,6 +105,95 @@ func (in *Proxy) DeepCopyObject() runtime.Object {
return nil
}
+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
+func (in *ProxyConfig) DeepCopyInto(out *ProxyConfig) {
+ *out = *in
+ out.TypeMeta = in.TypeMeta
+ in.ObjectMeta.DeepCopyInto(&out.ObjectMeta)
+ out.Spec = in.Spec
+ out.Status = in.Status
+}
+
+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ProxyConfig.
+func (in *ProxyConfig) DeepCopy() *ProxyConfig {
+ if in == nil {
+ return nil
+ }
+ out := new(ProxyConfig)
+ in.DeepCopyInto(out)
+ return out
+}
+
+// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object.
+func (in *ProxyConfig) 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 *ProxyConfigList) DeepCopyInto(out *ProxyConfigList) {
+ *out = *in
+ out.TypeMeta = in.TypeMeta
+ in.ListMeta.DeepCopyInto(&out.ListMeta)
+ if in.Items != nil {
+ in, out := &in.Items, &out.Items
+ *out = make([]ProxyConfig, len(*in))
+ for i := range *in {
+ (*in)[i].DeepCopyInto(&(*out)[i])
+ }
+ }
+}
+
+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ProxyConfigList.
+func (in *ProxyConfigList) DeepCopy() *ProxyConfigList {
+ if in == nil {
+ return nil
+ }
+ out := new(ProxyConfigList)
+ in.DeepCopyInto(out)
+ return out
+}
+
+// DeepCopyObject is an autogenerated deepcopy function, copying the receiver, creating a new runtime.Object.
+func (in *ProxyConfigList) 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 *ProxyConfigSpec) DeepCopyInto(out *ProxyConfigSpec) {
+ *out = *in
+}
+
+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ProxyConfigSpec.
+func (in *ProxyConfigSpec) DeepCopy() *ProxyConfigSpec {
+ if in == nil {
+ return nil
+ }
+ out := new(ProxyConfigSpec)
+ in.DeepCopyInto(out)
+ return out
+}
+
+// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
+func (in *ProxyConfigStatus) DeepCopyInto(out *ProxyConfigStatus) {
+ *out = *in
+}
+
+// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ProxyConfigStatus.
+func (in *ProxyConfigStatus) DeepCopy() *ProxyConfigStatus {
+ if in == nil {
+ return nil
+ }
+ out := new(ProxyConfigStatus)
+ in.DeepCopyInto(out)
+ return out
+}
+
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
func (in *ProxyList) DeepCopyInto(out *ProxyList) {
*out = *in
diff --git a/config/crd/bases/shardingsphere.sphere-ex.com_proxyconfigs.yaml b/config/crd/bases/shardingsphere.sphere-ex.com_proxyconfigs.yaml
new file mode 100644
index 0000000..3536493
--- /dev/null
+++ b/config/crd/bases/shardingsphere.sphere-ex.com_proxyconfigs.yaml
@@ -0,0 +1,148 @@
+---
+apiVersion: apiextensions.k8s.io/v1
+kind: CustomResourceDefinition
+metadata:
+ annotations:
+ controller-gen.kubebuilder.io/version: v0.8.0
+ creationTimestamp: null
+ name: proxyconfigs.shardingsphere.sphere-ex.com
+spec:
+ group: shardingsphere.sphere-ex.com
+ names:
+ kind: ProxyConfig
+ listKind: ProxyConfigList
+ plural: proxyconfigs
+ singular: proxyconfig
+ scope: Namespaced
+ versions:
+ - additionalPrinterColumns:
+ - jsonPath: .status.metadataRepository
+ name: MetadataRepository
+ type: string
+ name: v1alpha1
+ schema:
+ openAPIV3Schema:
+ description: ProxyConfig is the Schema for the proxyconfigs API
+ 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: ProxyConfigSpec defines the desired state of ProxyConfig
+ properties:
+ AUTHORITY:
+ description: 'Auth TODO: description'
+ properties:
+ provider:
+ description: 'Provider TODO: description'
+ properties:
+ type:
+ type: string
+ required:
+ - type
+ type: object
+ users:
+ items:
+ description: 'User TODO: description'
+ properties:
+ hostName:
+ type: string
+ passWord:
+ type: string
+ userName:
+ type: string
+ required:
+ - passWord
+ - userName
+ type: object
+ type: array
+ required:
+ - users
+ type: object
+ mode:
+ properties:
+ overwrite:
+ type: boolean
+ repository:
+ properties:
+ props:
+ properties:
+ digest:
+ type: string
+ maxRetries:
+ type: integer
+ namespace:
+ type: string
+ operationTimeoutMilliseconds:
+ type: integer
+ retryIntervalMilliseconds:
+ type: integer
+ server-lists:
+ type: string
+ timeToLiveSeconds:
+ type: integer
+ required:
+ - namespace
+ - server-lists
+ type: object
+ type:
+ type: string
+ required:
+ - props
+ - type
+ type: object
+ type:
+ type: string
+ required:
+ - overwrite
+ - repository
+ - type
+ type: object
+ props:
+ description: 'Props TODO: description'
+ properties:
+ check-duplicate-table-enabled:
+ type: boolean
+ check-table-metadata-enabled:
+ type: boolean
+ kernel-executor-size:
+ type: integer
+ proxy-backend-executor-suitable:
+ type: string
+ proxy-backend-query-fetch-size:
+ type: integer
+ proxy-frontend-executor-size:
+ type: integer
+ type: object
+ required:
+ - AUTHORITY
+ - mode
+ type: object
+ status:
+ description: ProxyConfigStatus defines the observed state of ProxyConfig
+ properties:
+ metadataRepository:
+ type: string
+ required:
+ - metadataRepository
+ type: object
+ type: object
+ served: true
+ storage: true
+ subresources:
+ status: {}
+status:
+ acceptedNames:
+ kind: ""
+ plural: ""
+ conditions: []
+ storedVersions: []
diff --git a/config/crd/kustomization.yaml b/config/crd/kustomization.yaml
index 6738560..704404b 100644
--- a/config/crd/kustomization.yaml
+++ b/config/crd/kustomization.yaml
@@ -2,18 +2,21 @@
# since it depends on service name and namespace that are out of this kustomize package.
# It should be run by config/default
resources:
-- bases/shardingsphere.sphere-ex.com_proxies.yaml.bak
+- bases/shardingsphere.sphere-ex.com_proxies.yaml
+- bases/shardingsphere.sphere-ex.com_proxyconfigs.yaml
#+kubebuilder:scaffold:crdkustomizeresource
patchesStrategicMerge:
# [WEBHOOK] To enable webhook, uncomment all the sections with [WEBHOOK] prefix.
# patches here are for enabling the conversion webhook for each CRD
#- patches/webhook_in_proxies.yaml
+#- patches/webhook_in_proxyconfigs.yaml
#+kubebuilder:scaffold:crdkustomizewebhookpatch
# [CERTMANAGER] To enable cert-manager, uncomment all the sections with [CERTMANAGER] prefix.
# patches here are for enabling the CA injection for each CRD
#- patches/cainjection_in_proxies.yaml
+#- patches/cainjection_in_proxyconfigs.yaml
#+kubebuilder:scaffold:crdkustomizecainjectionpatch
# the following config is for teaching kustomize how to do kustomization for CRDs.
diff --git a/config/crd/patches/cainjection_in_proxyconfigs.yaml b/config/crd/patches/cainjection_in_proxyconfigs.yaml
new file mode 100644
index 0000000..3f189ca
--- /dev/null
+++ b/config/crd/patches/cainjection_in_proxyconfigs.yaml
@@ -0,0 +1,7 @@
+# The following patch adds a directive for certmanager to inject CA into the CRD
+apiVersion: apiextensions.k8s.io/v1
+kind: CustomResourceDefinition
+metadata:
+ annotations:
+ cert-manager.io/inject-ca-from: $(CERTIFICATE_NAMESPACE)/$(CERTIFICATE_NAME)
+ name: proxyconfigs.shardingsphere.sphere-ex.com
diff --git a/config/crd/patches/webhook_in_proxyconfigs.yaml b/config/crd/patches/webhook_in_proxyconfigs.yaml
new file mode 100644
index 0000000..8f80f69
--- /dev/null
+++ b/config/crd/patches/webhook_in_proxyconfigs.yaml
@@ -0,0 +1,16 @@
+# The following patch enables a conversion webhook for the CRD
+apiVersion: apiextensions.k8s.io/v1
+kind: CustomResourceDefinition
+metadata:
+ name: proxyconfigs.shardingsphere.sphere-ex.com
+spec:
+ conversion:
+ strategy: Webhook
+ webhook:
+ clientConfig:
+ service:
+ namespace: system
+ name: webhook-service
+ path: /convert
+ conversionReviewVersions:
+ - v1
diff --git a/config/rbac/proxyconfig_editor_role.yaml b/config/rbac/proxyconfig_editor_role.yaml
new file mode 100644
index 0000000..94b6bd8
--- /dev/null
+++ b/config/rbac/proxyconfig_editor_role.yaml
@@ -0,0 +1,24 @@
+# permissions for end users to edit proxyconfigs.
+apiVersion: rbac.authorization.k8s.io/v1
+kind: ClusterRole
+metadata:
+ name: proxyconfig-editor-role
+rules:
+- apiGroups:
+ - shardingsphere.sphere-ex.com
+ resources:
+ - proxyconfigs
+ verbs:
+ - create
+ - delete
+ - get
+ - list
+ - patch
+ - update
+ - watch
+- apiGroups:
+ - shardingsphere.sphere-ex.com
+ resources:
+ - proxyconfigs/status
+ verbs:
+ - get
diff --git a/config/rbac/proxyconfig_viewer_role.yaml b/config/rbac/proxyconfig_viewer_role.yaml
new file mode 100644
index 0000000..759bf01
--- /dev/null
+++ b/config/rbac/proxyconfig_viewer_role.yaml
@@ -0,0 +1,20 @@
+# permissions for end users to view proxyconfigs.
+apiVersion: rbac.authorization.k8s.io/v1
+kind: ClusterRole
+metadata:
+ name: proxyconfig-viewer-role
+rules:
+- apiGroups:
+ - shardingsphere.sphere-ex.com
+ resources:
+ - proxyconfigs
+ verbs:
+ - get
+ - list
+ - watch
+- apiGroups:
+ - shardingsphere.sphere-ex.com
+ resources:
+ - proxyconfigs/status
+ verbs:
+ - get
diff --git a/config/rbac/role.yaml b/config/rbac/role.yaml
index db72e1e..b2711b0 100644
--- a/config/rbac/role.yaml
+++ b/config/rbac/role.yaml
@@ -70,3 +70,29 @@ rules:
- get
- patch
- update
+- apiGroups:
+ - shardingsphere.sphere-ex.com
+ resources:
+ - proxyconfigs
+ verbs:
+ - create
+ - delete
+ - get
+ - list
+ - patch
+ - update
+ - watch
+- apiGroups:
+ - shardingsphere.sphere-ex.com
+ resources:
+ - proxyconfigs/finalizers
+ verbs:
+ - update
+- apiGroups:
+ - shardingsphere.sphere-ex.com
+ resources:
+ - proxyconfigs/status
+ verbs:
+ - get
+ - patch
+ - update
diff --git a/config/samples/shardingsphere_v1alpha1_proxy.yaml b/config/samples/shardingsphere_v1alpha1_proxy.yaml
index d3c7fdf..61a1776 100644
--- a/config/samples/shardingsphere_v1alpha1_proxy.yaml
+++ b/config/samples/shardingsphere_v1alpha1_proxy.yaml
@@ -8,6 +8,7 @@ spec:
type: ClusterIP
replicas: 1
proxyConfigName: "sharding-proxy"
+ port: 3307
mySQLDriver:
version: "5.1.47"
resource:
diff --git a/config/samples/shardingsphere_v1alpha1_proxyconfig.yaml b/config/samples/shardingsphere_v1alpha1_proxyconfig.yaml
new file mode 100644
index 0000000..6b18c59
--- /dev/null
+++ b/config/samples/shardingsphere_v1alpha1_proxyconfig.yaml
@@ -0,0 +1,27 @@
+apiVersion: shardingsphere.sphere-ex.com/v1alpha1
+kind: ProxyConfig
+metadata:
+ name: proxyconfig-sample
+spec:
+ AUTHORITY:
+ users:
+ - userName: root
+ passWord: root
+ hostName: "%"
+ - userName: admin
+ passWord: root
+ hostName: "%"
+ provider:
+ type: ALL_PRIVILEGES_PERMITTED
+ mode:
+ type: Cluster
+ repository:
+ type: ZooKeeper
+ props:
+ namespace: "governance_ds"
+ server-lists: "zookeeper.default:2181"
+ retryIntervalMilliseconds: 500
+ timeToLiveSeconds: 600
+ maxRetries: 3
+ operationTimeoutMilliseconds: 5000
+ overwrite: false
\ No newline at end of file
diff --git a/main.go b/main.go
index 016fb80..d2ece79 100644
--- a/main.go
+++ b/main.go
@@ -19,6 +19,7 @@ package main
import (
"flag"
"os"
+
"sphere-ex.com/shardingsphere-operator/pkg/controllers"
// Import all Kubernetes client auth plugins (e.g. Azure, GCP, OIDC, etc.)
@@ -85,6 +86,13 @@ func main() {
setupLog.Error(err, "unable to create controller", "controller", "Proxy")
os.Exit(1)
}
+ if err = (&controllers.ProxyConfigReconciler{
+ Client: mgr.GetClient(),
+ Scheme: mgr.GetScheme(),
+ }).SetupWithManager(mgr); err != nil {
+ setupLog.Error(err, "unable to create controller", "controller", "ProxyConfig")
+ os.Exit(1)
+ }
//+kubebuilder:scaffold:builder
if err := mgr.AddHealthzCheck("healthz", healthz.Ping); err != nil {
diff --git a/pkg/controllers/proxyconfig_controller.go b/pkg/controllers/proxyconfig_controller.go
new file mode 100644
index 0000000..043087a
--- /dev/null
+++ b/pkg/controllers/proxyconfig_controller.go
@@ -0,0 +1,115 @@
+/*
+Copyright 2022.
+
+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 controllers
+
+import (
+ "context"
+ v1 "k8s.io/api/core/v1"
+ "k8s.io/apimachinery/pkg/api/equality"
+ apierrors "k8s.io/apimachinery/pkg/api/errors"
+ "sphere-ex.com/shardingsphere-operator/pkg/reconcile"
+
+ "k8s.io/apimachinery/pkg/runtime"
+ ctrl "sigs.k8s.io/controller-runtime"
+ "sigs.k8s.io/controller-runtime/pkg/client"
+ logger "sigs.k8s.io/controller-runtime/pkg/log"
+
+ shardingspherev1alpha1 "sphere-ex.com/shardingsphere-operator/api/v1alpha1"
+)
+
+// ProxyConfigReconciler reconciles a ProxyConfig object
+type ProxyConfigReconciler struct {
+ client.Client
+ Scheme *runtime.Scheme
+}
+
+//+kubebuilder:rbac:groups=shardingsphere.sphere-ex.com,resources=proxyconfigs,verbs=get;list;watch;create;update;patch;delete
+//+kubebuilder:rbac:groups=shardingsphere.sphere-ex.com,resources=proxyconfigs/status,verbs=get;update;patch
+//+kubebuilder:rbac:groups=shardingsphere.sphere-ex.com,resources=proxyconfigs/finalizers,verbs=update
+
+// Reconcile is part of the main kubernetes reconciliation loop which aims to
+// move the current state of the cluster closer to the desired state.
+// TODO(user): Modify the Reconcile function to compare the state specified by
+// the ProxyConfig object against the actual cluster state, and then
+// perform operations to make the cluster state reflect the state specified by
+// the user.
+//
+// For more details, check Reconcile and its Result here:
+// - https://pkg.go.dev/sigs.k8s.io/controller-runtime@v0.11.0/pkg/reconcile
+func (r *ProxyConfigReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl.Result, error) {
+ log := logger.FromContext(ctx)
+
+ run := &shardingspherev1alpha1.ProxyConfig{}
+ err := r.Get(ctx, req.NamespacedName, run)
+ if apierrors.IsNotFound(err) {
+ log.Error(err, "ProxyConfig in work queue no longer exists!")
+ return ctrl.Result{}, nil
+ } else if err != nil {
+ log.Error(err, "Get CRD Resource Error")
+ return ctrl.Result{RequeueAfter: SyncBuildStatusInterval}, err
+ }
+
+ cm := &v1.ConfigMap{}
+ configmap := reconcile.ConstructCascadingConfigmap(run)
+ err = r.Get(ctx, req.NamespacedName, cm)
+ if err != nil {
+ if apierrors.IsNotFound(err) {
+ log.Info("Create the configmap")
+ err = r.Create(ctx, configmap)
+ if err != nil {
+ log.Error(err, "Create Configmap Resource Error")
+ return ctrl.Result{RequeueAfter: SyncBuildStatusInterval}, err
+ }
+ run.SetMetadataRepository(run.Spec.ClusterConfig.Repository.Type)
+ err = r.Status().Update(ctx, run)
+ if err != nil {
+ log.Error(err, "Update CRD Resource Status Error")
+ return ctrl.Result{RequeueAfter: SyncBuildStatusInterval}, err
+ }
+ return ctrl.Result{}, nil
+ } else {
+ log.Error(err, "Get Configmap Resource Error")
+ return ctrl.Result{RequeueAfter: SyncBuildStatusInterval}, err
+ }
+ }
+ if !equality.Semantic.DeepEqual(configmap.Data, cm.Data) {
+ cm = configmap
+ log.Info("Update or correct the configmap")
+ err = r.Update(ctx, configmap)
+ if err != nil {
+ log.Error(err, "Update Configmap Resource Error")
+ return ctrl.Result{RequeueAfter: SyncBuildStatusInterval}, err
+ }
+ }
+ if run.Status.MetadataRepository != run.Spec.ClusterConfig.Repository.Type || run.Status.MetadataRepository == "" {
+ run.SetMetadataRepository(run.Spec.ClusterConfig.Repository.Type)
+ err = r.Status().Update(ctx, run)
+ if err != nil {
+ log.Error(err, "Update CRD Resource Status Error")
+ return ctrl.Result{RequeueAfter: SyncBuildStatusInterval}, err
+ }
+ }
+ return ctrl.Result{}, nil
+}
+
+// SetupWithManager sets up the controller with the Manager.
+func (r *ProxyConfigReconciler) SetupWithManager(mgr ctrl.Manager) error {
+ return ctrl.NewControllerManagedBy(mgr).
+ For(&shardingspherev1alpha1.ProxyConfig{}).
+ Owns(&v1.ConfigMap{}).
+ Complete(r)
+}
diff --git a/pkg/reconcile/resource.go b/pkg/reconcile/resource.go
index 9d46f76..5f4cc04 100644
--- a/pkg/reconcile/resource.go
+++ b/pkg/reconcile/resource.go
@@ -2,6 +2,7 @@ package reconcile
import (
"fmt"
+ "gopkg.in/yaml.v2"
"html/template"
appsv1 "k8s.io/api/apps/v1"
v1 "k8s.io/api/core/v1"
@@ -211,3 +212,33 @@ func processOptionalParameter(proxy *shardingspherev1alpha1.Proxy, dp *appsv1.De
}
return dp
}
+
+// ConstructCascadingConfigmap Construct spec resources to Configmap
+func ConstructCascadingConfigmap(proxyConfig *shardingspherev1alpha1.ProxyConfig) *v1.ConfigMap {
+ y := toYaml(proxyConfig)
+ return &v1.ConfigMap{
+ ObjectMeta: metav1.ObjectMeta{
+ Name: proxyConfig.Name,
+ Namespace: proxyConfig.Namespace,
+ OwnerReferences: []metav1.OwnerReference{
+ *metav1.NewControllerRef(proxyConfig.GetObjectMeta(), proxyConfig.GroupVersionKind()),
+ },
+ },
+ Data: map[string]string{
+ "server.yaml": y,
+ },
+ }
+
+}
+
+// ToYaml Convert ProxyConfig spec content to yaml format
+func toYaml(proxyConfig *shardingspherev1alpha1.ProxyConfig) string {
+
+ for i := 0; i < len(proxyConfig.Spec.AUTHORITY.Users); i++ {
+ proxyConfig.Spec.AUTHORITY.Users[i].UserConfig = proxyConfig.Spec.AUTHORITY.Users[i].UserName +
+ "@" + proxyConfig.Spec.AUTHORITY.Users[i].HostName +
+ ":" + proxyConfig.Spec.AUTHORITY.Users[i].PassWord
+ }
+ y, _ := yaml.Marshal(proxyConfig.Spec)
+ return string(y)
+}