From 37d804bdafb976c4685f09341b1c3f7103570def Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Wed, 30 Nov 2022 17:51:38 +0530 Subject: [PATCH 01/15] add Generated Secrets - api+manifest+deepcopy --- api/v1beta1/common_types.go | 26 +++++++--- api/v1beta1/zz_generated.deepcopy.go | 51 +++++++++++++++++-- .../redis.redis.opstreelabs.in_redis.yaml | 36 +++++++++---- ...is.redis.opstreelabs.in_redisclusters.yaml | 36 +++++++++---- 4 files changed, 121 insertions(+), 28 deletions(-) diff --git a/api/v1beta1/common_types.go b/api/v1beta1/common_types.go index fdee1aea9..b3dc435c4 100644 --- a/api/v1beta1/common_types.go +++ b/api/v1beta1/common_types.go @@ -23,13 +23,19 @@ import ( // KubernetesConfig will be the JSON struct for Basic Redis Config type KubernetesConfig struct { - Image string `json:"image"` - ImagePullPolicy corev1.PullPolicy `json:"imagePullPolicy,omitempty"` - Resources *corev1.ResourceRequirements `json:"resources,omitempty"` - ExistingPasswordSecret *ExistingPasswordSecret `json:"redisSecret,omitempty"` - ImagePullSecrets *[]corev1.LocalObjectReference `json:"imagePullSecrets,omitempty"` - UpdateStrategy appsv1.StatefulSetUpdateStrategy `json:"updateStrategy,omitempty"` - Service *ServiceConfig `json:"service,omitempty"` + Image string `json:"image"` + ImagePullPolicy corev1.PullPolicy `json:"imagePullPolicy,omitempty"` + Resources *corev1.ResourceRequirements `json:"resources,omitempty"` + ExistOrGenerateSecret *ExistOrGenerateSecrets `json:"existOrGenerateSecrets,omitempty"` + ImagePullSecrets *[]corev1.LocalObjectReference `json:"imagePullSecrets,omitempty"` + UpdateStrategy appsv1.StatefulSetUpdateStrategy `json:"updateStrategy,omitempty"` + Service *ServiceConfig `json:"service,omitempty"` +} + +// +kubebuilder:validation:MaxProperties=1 +type ExistOrGenerateSecrets struct { + ExistingPasswordSecret *ExistingPasswordSecret `json:"redisSecret,omitempty"` + GeneratePasswordSecret *GeneratePassword `json:"generatePasswordSecret,omitempty"` } // ServiceConfig define the type of service to be created and its annotations @@ -50,6 +56,12 @@ type ExistingPasswordSecret struct { Key *string `json:"key,omitempty"` } +type GeneratePassword struct { + Name string `json:"name"` + Key string `json:"key"` + NameSpace []string `json:"namespace,omitempty"` +} + // Storage is the inteface to add pvc and pv support in redis type Storage struct { VolumeClaimTemplate corev1.PersistentVolumeClaim `json:"volumeClaimTemplate,omitempty"` diff --git a/api/v1beta1/zz_generated.deepcopy.go b/api/v1beta1/zz_generated.deepcopy.go index d263faab4..719c8c9bc 100644 --- a/api/v1beta1/zz_generated.deepcopy.go +++ b/api/v1beta1/zz_generated.deepcopy.go @@ -26,6 +26,31 @@ import ( runtime "k8s.io/apimachinery/pkg/runtime" ) +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *ExistOrGenerateSecrets) DeepCopyInto(out *ExistOrGenerateSecrets) { + *out = *in + if in.ExistingPasswordSecret != nil { + in, out := &in.ExistingPasswordSecret, &out.ExistingPasswordSecret + *out = new(ExistingPasswordSecret) + (*in).DeepCopyInto(*out) + } + if in.GeneratePasswordSecret != nil { + in, out := &in.GeneratePasswordSecret, &out.GeneratePasswordSecret + *out = new(GeneratePassword) + (*in).DeepCopyInto(*out) + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ExistOrGenerateSecrets. +func (in *ExistOrGenerateSecrets) DeepCopy() *ExistOrGenerateSecrets { + if in == nil { + return nil + } + out := new(ExistOrGenerateSecrets) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *ExistingPasswordSecret) DeepCopyInto(out *ExistingPasswordSecret) { *out = *in @@ -51,6 +76,26 @@ func (in *ExistingPasswordSecret) DeepCopy() *ExistingPasswordSecret { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *GeneratePassword) DeepCopyInto(out *GeneratePassword) { + *out = *in + if in.NameSpace != nil { + in, out := &in.NameSpace, &out.NameSpace + *out = make([]string, len(*in)) + copy(*out, *in) + } +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new GeneratePassword. +func (in *GeneratePassword) DeepCopy() *GeneratePassword { + if in == nil { + return nil + } + out := new(GeneratePassword) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *KubernetesConfig) DeepCopyInto(out *KubernetesConfig) { *out = *in @@ -59,9 +104,9 @@ func (in *KubernetesConfig) DeepCopyInto(out *KubernetesConfig) { *out = new(v1.ResourceRequirements) (*in).DeepCopyInto(*out) } - if in.ExistingPasswordSecret != nil { - in, out := &in.ExistingPasswordSecret, &out.ExistingPasswordSecret - *out = new(ExistingPasswordSecret) + if in.ExistOrGenerateSecret != nil { + in, out := &in.ExistOrGenerateSecret, &out.ExistOrGenerateSecret + *out = new(ExistOrGenerateSecrets) (*in).DeepCopyInto(*out) } if in.ImagePullSecrets != nil { diff --git a/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml b/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml index 4fcdb8b16..86f45a417 100644 --- a/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml +++ b/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml @@ -939,6 +939,33 @@ spec: description: KubernetesConfig will be the JSON struct for Basic Redis Config properties: + existOrGenerateSecrets: + maxProperties: 1 + properties: + generatePasswordSecret: + properties: + key: + type: string + name: + type: string + namespace: + items: + type: string + type: array + required: + - key + - name + type: object + redisSecret: + description: ExistingPasswordSecret is the struct to access + the existing secret + properties: + key: + type: string + name: + type: string + type: object + type: object image: type: string imagePullPolicy: @@ -956,15 +983,6 @@ spec: type: string type: object type: array - redisSecret: - description: ExistingPasswordSecret is the struct to access the - existing secret - properties: - key: - type: string - name: - type: string - type: object resources: description: ResourceRequirements describes the compute resource requirements. diff --git a/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml b/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml index 5210cc3d2..8aaaf5a4c 100644 --- a/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml +++ b/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml @@ -137,6 +137,33 @@ spec: description: KubernetesConfig will be the JSON struct for Basic Redis Config properties: + existOrGenerateSecrets: + maxProperties: 1 + properties: + generatePasswordSecret: + properties: + key: + type: string + name: + type: string + namespace: + items: + type: string + type: array + required: + - key + - name + type: object + redisSecret: + description: ExistingPasswordSecret is the struct to access + the existing secret + properties: + key: + type: string + name: + type: string + type: object + type: object image: type: string imagePullPolicy: @@ -154,15 +181,6 @@ spec: type: string type: object type: array - redisSecret: - description: ExistingPasswordSecret is the struct to access the - existing secret - properties: - key: - type: string - name: - type: string - type: object resources: description: ResourceRequirements describes the compute resource requirements. From d59c594fc9cb78d9343641ac56f83e0bd477257e Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Wed, 30 Nov 2022 19:12:07 +0530 Subject: [PATCH 02/15] add Generated Secrets - generateSecrets() --- controllers/redis_controller.go | 8 ++++ controllers/rediscluster_controller.go | 8 ++++ go.mod | 2 +- go.sum | 2 + k8sutils/redis-cluster.go | 15 ++++-- k8sutils/redis-standalone.go | 15 ++++-- k8sutils/redis.go | 12 ++--- k8sutils/secrets.go | 63 ++++++++++++++++++++++++++ 8 files changed, 110 insertions(+), 15 deletions(-) diff --git a/controllers/redis_controller.go b/controllers/redis_controller.go index 6b993bcd5..23c25f81f 100644 --- a/controllers/redis_controller.go +++ b/controllers/redis_controller.go @@ -63,6 +63,14 @@ func (r *RedisReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl return ctrl.Result{}, err } + if instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { + err = k8sutils.GenerateSecrets(instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) + if err != nil { + reqLogger.Error(err, "Failed to create the Secrets") + return ctrl.Result{}, err + } + } + err = k8sutils.CreateStandaloneRedis(instance) if err != nil { return ctrl.Result{}, err diff --git a/controllers/rediscluster_controller.go b/controllers/rediscluster_controller.go index c14306abf..d51a9500a 100644 --- a/controllers/rediscluster_controller.go +++ b/controllers/rediscluster_controller.go @@ -70,6 +70,14 @@ func (r *RedisClusterReconciler) Reconcile(ctx context.Context, req ctrl.Request return ctrl.Result{RequeueAfter: time.Second * 60}, err } + if instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { + err = k8sutils.GenerateSecrets(instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) + if err != nil { + reqLogger.Error(err, "Failed to create the Secrets") + return ctrl.Result{}, err + } + } + err = k8sutils.CreateRedisLeader(instance) if err != nil { return ctrl.Result{RequeueAfter: time.Second * 60}, err diff --git a/go.mod b/go.mod index 2931eb770..d2f7274d2 100644 --- a/go.mod +++ b/go.mod @@ -35,7 +35,7 @@ require ( github.com/golang/protobuf v1.5.2 // indirect github.com/google/go-cmp v0.5.5 // indirect github.com/google/gofuzz v1.1.0 // indirect - github.com/google/uuid v1.1.2 // indirect + github.com/google/uuid v1.3.0 // indirect github.com/googleapis/gnostic v0.5.5 // indirect github.com/imdario/mergo v0.3.12 // indirect github.com/json-iterator/go v1.1.12 // indirect diff --git a/go.sum b/go.sum index 62a6ce859..5afb2985b 100644 --- a/go.sum +++ b/go.sum @@ -262,6 +262,8 @@ github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm4 github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.1.2 h1:EVhdT+1Kseyi1/pUmXKaFxYsDNy9RQYkMWRH68J/W7Y= github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= +github.com/google/uuid v1.3.0 h1:t6JiXgmwXMjEs8VusXIJk2BXHsn+wx8BZdTaoZ5fu7I= +github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/googleapis/gax-go/v2 v2.0.4/go.mod h1:0Wqv26UfaUD9n4G6kQubkQ+KchISgw+vpHVxEJEs9eg= github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5mhpdKc/us6bOk= github.com/googleapis/gnostic v0.4.1/go.mod h1:LRhVm6pbyptWbWbuZ38d1eyptfvIytN3ir6b65WBswg= diff --git a/k8sutils/redis-cluster.go b/k8sutils/redis-cluster.go index 1b68fca3f..91336e40a 100644 --- a/k8sutils/redis-cluster.go +++ b/k8sutils/redis-cluster.go @@ -60,11 +60,18 @@ func generateRedisClusterContainerParams(cr *redisv1beta1.RedisCluster, readines AdditionalVolume: cr.Spec.Storage.VolumeMount.Volume, AdditionalMountPath: cr.Spec.Storage.VolumeMount.MountPath, } - if cr.Spec.KubernetesConfig.ExistingPasswordSecret != nil { + switch true { + case cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret != nil: containerProp.EnabledPassword = &trueProperty - containerProp.SecretName = cr.Spec.KubernetesConfig.ExistingPasswordSecret.Name - containerProp.SecretKey = cr.Spec.KubernetesConfig.ExistingPasswordSecret.Key - } else { + containerProp.SecretName = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret.Name + containerProp.SecretKey = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret.Key + + case cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil: + containerProp.EnabledPassword = &trueProperty + containerProp.SecretName = &cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name + containerProp.SecretKey = &cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key + + default: containerProp.EnabledPassword = &falseProperty } if cr.Spec.RedisExporter != nil { diff --git a/k8sutils/redis-standalone.go b/k8sutils/redis-standalone.go index 3ca2d81bd..f19ea37e4 100644 --- a/k8sutils/redis-standalone.go +++ b/k8sutils/redis-standalone.go @@ -108,11 +108,18 @@ func generateRedisStandaloneContainerParams(cr *redisv1beta1.Redis) containerPar AdditionalVolume: cr.Spec.Storage.VolumeMount.Volume, AdditionalMountPath: cr.Spec.Storage.VolumeMount.MountPath, } - if cr.Spec.KubernetesConfig.ExistingPasswordSecret != nil { + switch true { + case cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret != nil: containerProp.EnabledPassword = &trueProperty - containerProp.SecretName = cr.Spec.KubernetesConfig.ExistingPasswordSecret.Name - containerProp.SecretKey = cr.Spec.KubernetesConfig.ExistingPasswordSecret.Key - } else { + containerProp.SecretName = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret.Name + containerProp.SecretKey = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret.Key + + case cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil: + containerProp.EnabledPassword = &trueProperty + containerProp.SecretName = &cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name + containerProp.SecretKey = &cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key + + default: containerProp.EnabledPassword = &falseProperty } if cr.Spec.RedisExporter != nil { diff --git a/k8sutils/redis.go b/k8sutils/redis.go index 8235b6bc8..8719727cf 100644 --- a/k8sutils/redis.go +++ b/k8sutils/redis.go @@ -103,8 +103,8 @@ func ExecuteRedisClusterCommand(cr *redisv1beta1.RedisCluster) { cmd = CreateMultipleLeaderRedisCommand(cr) } - if cr.Spec.KubernetesConfig.ExistingPasswordSecret != nil { - pass, err := getRedisPassword(cr.Namespace, *cr.Spec.KubernetesConfig.ExistingPasswordSecret.Name, *cr.Spec.KubernetesConfig.ExistingPasswordSecret.Key) + if cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret != nil { + pass, err := getRedisPassword(cr.Namespace, *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret.Name, *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret.Key) if err != nil { logger.Error(err, "Error in getting redis password") } @@ -141,8 +141,8 @@ func createRedisReplicationCommand(cr *redisv1beta1.RedisCluster, leaderPod Redi } cmd = append(cmd, "--cluster-slave") - if cr.Spec.KubernetesConfig.ExistingPasswordSecret != nil { - pass, err := getRedisPassword(cr.Namespace, *cr.Spec.KubernetesConfig.ExistingPasswordSecret.Name, *cr.Spec.KubernetesConfig.ExistingPasswordSecret.Key) + if cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret != nil { + pass, err := getRedisPassword(cr.Namespace, *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret.Name, *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret.Key) if err != nil { logger.Error(err, "Error in getting redis password") } @@ -313,8 +313,8 @@ func configureRedisClient(cr *redisv1beta1.RedisCluster, podName string) *redis. } var client *redis.Client - if cr.Spec.KubernetesConfig.ExistingPasswordSecret != nil { - pass, err := getRedisPassword(cr.Namespace, *cr.Spec.KubernetesConfig.ExistingPasswordSecret.Name, *cr.Spec.KubernetesConfig.ExistingPasswordSecret.Key) + if cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret != nil { + pass, err := getRedisPassword(cr.Namespace, *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret.Name, *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.ExistingPasswordSecret.Key) if err != nil { logger.Error(err, "Error in getting redis password") } diff --git a/k8sutils/secrets.go b/k8sutils/secrets.go index 840d157a2..43cac635a 100644 --- a/k8sutils/secrets.go +++ b/k8sutils/secrets.go @@ -8,6 +8,9 @@ import ( "strings" "github.com/go-logr/logr" + "github.com/google/uuid" + corev1 "k8s.io/api/core/v1" + kerror "k8s.io/apimachinery/pkg/api/errors" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" logf "sigs.k8s.io/controller-runtime/pkg/log" ) @@ -82,3 +85,63 @@ func getRedisTLSConfig(cr *redisv1beta1.RedisCluster, redisInfo RedisDetails) *t } return nil } +func GenerateSecrets(name string, namespacelist []string, key string) error { + genLogger := log.WithValues() + + rndID, err := uuid.NewRandom() + if err != nil { + genLogger.Error(err, "Unable to generate the UUID") + } + // If no namespacelist is defined default would be added. + if namespacelist == nil { + namespacelist = append(namespacelist, "default") + } + + // Key and Value for the secret + value := rndID.NodeID() + + for _, namespace := range namespacelist { + + generatedSecretTemplate := generateSecretTemplate() + generatedSecretTemplate.Name = name + generatedSecretTemplate.Namespace = namespace + generatedSecretTemplate.Data = map[string][]byte{ + key: value, + } + + // Check whether the secret exist or not If not then create it + _, err := generateK8sClient().CoreV1().Secrets(namespace).Get(context.Background(), name, metav1.GetOptions{}) + if kerror.IsNotFound(err) { + _, err := generateK8sClient().CoreV1().Secrets(namespace).Create(context.Background(), generatedSecretTemplate, metav1.CreateOptions{}) + if err != nil { + genLogger.Error(err, "Failed to create the Secrets by the operator") + return err + } + } else { + return err + } + + } + + return nil + +} + +func generateSecretTemplate() *corev1.Secret { + + return &corev1.Secret{ + TypeMeta: metav1.TypeMeta{ + Kind: "Secret", + APIVersion: "v1", + }, + ObjectMeta: metav1.ObjectMeta{ + Name: "", + Namespace: "", + }, + + Data: map[string][]byte{}, + + Type: "Opaque", + } + +} From 6d134bb27f332cdc0874a687da0716324724c8d4 Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Wed, 30 Nov 2022 19:12:41 +0530 Subject: [PATCH 03/15] go Mod tidy --- go.mod | 2 +- go.sum | 1 - 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/go.mod b/go.mod index d2f7274d2..ce65b3552 100644 --- a/go.mod +++ b/go.mod @@ -6,6 +6,7 @@ require ( github.com/banzaicloud/k8s-objectmatcher v1.7.0 github.com/go-logr/logr v1.2.2 github.com/go-redis/redis v6.15.9+incompatible + github.com/google/uuid v1.3.0 github.com/onsi/ginkgo v1.16.5 github.com/onsi/gomega v1.17.0 k8s.io/api v0.23.0 @@ -35,7 +36,6 @@ require ( github.com/golang/protobuf v1.5.2 // indirect github.com/google/go-cmp v0.5.5 // indirect github.com/google/gofuzz v1.1.0 // indirect - github.com/google/uuid v1.3.0 // indirect github.com/googleapis/gnostic v0.5.5 // indirect github.com/imdario/mergo v0.3.12 // indirect github.com/json-iterator/go v1.1.12 // indirect diff --git a/go.sum b/go.sum index 5afb2985b..5275d4f0c 100644 --- a/go.sum +++ b/go.sum @@ -260,7 +260,6 @@ github.com/google/pprof v0.0.0-20210122040257-d980be63207e/go.mod h1:kpwsk12EmLe github.com/google/pprof v0.0.0-20210226084205-cbba55b83ad5/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE= github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI= github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= -github.com/google/uuid v1.1.2 h1:EVhdT+1Kseyi1/pUmXKaFxYsDNy9RQYkMWRH68J/W7Y= github.com/google/uuid v1.1.2/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/google/uuid v1.3.0 h1:t6JiXgmwXMjEs8VusXIJk2BXHsn+wx8BZdTaoZ5fu7I= github.com/google/uuid v1.3.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= From 3e1a383537732fc4f07f9a5d5dd478837744fc3a Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Sat, 3 Dec 2022 02:05:48 +0530 Subject: [PATCH 04/15] add Requeue time --- controllers/redis_controller.go | 2 +- controllers/rediscluster_controller.go | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/controllers/redis_controller.go b/controllers/redis_controller.go index 23c25f81f..f3ce6683f 100644 --- a/controllers/redis_controller.go +++ b/controllers/redis_controller.go @@ -67,7 +67,7 @@ func (r *RedisReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl err = k8sutils.GenerateSecrets(instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) if err != nil { reqLogger.Error(err, "Failed to create the Secrets") - return ctrl.Result{}, err + return ctrl.Result{RequeueAfter: time.Second * 10}, err } } diff --git a/controllers/rediscluster_controller.go b/controllers/rediscluster_controller.go index d51a9500a..e0bce6c38 100644 --- a/controllers/rediscluster_controller.go +++ b/controllers/rediscluster_controller.go @@ -74,7 +74,7 @@ func (r *RedisClusterReconciler) Reconcile(ctx context.Context, req ctrl.Request err = k8sutils.GenerateSecrets(instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) if err != nil { reqLogger.Error(err, "Failed to create the Secrets") - return ctrl.Result{}, err + return ctrl.Result{RequeueAfter: time.Second * 10}, err } } From 1aea3c0fd5e7819299ce4b0b275b5fd1b76d789e Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Thu, 8 Dec 2022 19:31:07 +0530 Subject: [PATCH 05/15] update generated secrets --- api/v1beta1/common_types.go | 8 +-- api/v1beta1/zz_generated.deepcopy.go | 10 ++++ .../redis.redis.opstreelabs.in_redis.yaml | 53 +++++++++---------- ...is.redis.opstreelabs.in_redisclusters.yaml | 53 +++++++++---------- controllers/redis_controller.go | 2 +- controllers/rediscluster_controller.go | 2 +- example/generated_secrets/redis-cluster.yaml | 44 +++++++++++++++ k8sutils/redis-cluster.go | 4 +- k8sutils/redis-standalone.go | 4 +- k8sutils/secrets.go | 9 +++- 10 files changed, 123 insertions(+), 66 deletions(-) create mode 100644 example/generated_secrets/redis-cluster.yaml diff --git a/api/v1beta1/common_types.go b/api/v1beta1/common_types.go index 7a464ddce..0823bc505 100644 --- a/api/v1beta1/common_types.go +++ b/api/v1beta1/common_types.go @@ -26,7 +26,7 @@ type KubernetesConfig struct { Image string `json:"image"` ImagePullPolicy corev1.PullPolicy `json:"imagePullPolicy,omitempty"` Resources *corev1.ResourceRequirements `json:"resources,omitempty"` - ExistOrGenerateSecret *ExistOrGenerateSecrets `json:"existOrGenerateSecrets,omitempty"` + ExistOrGenerateSecret *ExistOrGenerateSecrets `json:"redisSecret,omitempty"` ImagePullSecrets *[]corev1.LocalObjectReference `json:"imagePullSecrets,omitempty"` UpdateStrategy appsv1.StatefulSetUpdateStrategy `json:"updateStrategy,omitempty"` Service *ServiceConfig `json:"service,omitempty"` @@ -34,7 +34,7 @@ type KubernetesConfig struct { // +kubebuilder:validation:MaxProperties=1 type ExistOrGenerateSecrets struct { - ExistingPasswordSecret *ExistingPasswordSecret `json:"redisSecret,omitempty"` + ExistingPasswordSecret *ExistingPasswordSecret `json:"existRedisSecret,omitempty"` GeneratePasswordSecret *GeneratePassword `json:"generatePasswordSecret,omitempty"` } @@ -57,8 +57,8 @@ type ExistingPasswordSecret struct { } type GeneratePassword struct { - Name string `json:"name"` - Key string `json:"key"` + Name *string `json:"name"` + Key *string `json:"key,omitempty"` NameSpace []string `json:"namespace,omitempty"` } diff --git a/api/v1beta1/zz_generated.deepcopy.go b/api/v1beta1/zz_generated.deepcopy.go index ab9465703..b1b462e62 100644 --- a/api/v1beta1/zz_generated.deepcopy.go +++ b/api/v1beta1/zz_generated.deepcopy.go @@ -108,6 +108,16 @@ func (in *ExistingPasswordSecret) DeepCopy() *ExistingPasswordSecret { // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *GeneratePassword) DeepCopyInto(out *GeneratePassword) { *out = *in + if in.Name != nil { + in, out := &in.Name, &out.Name + *out = new(string) + **out = **in + } + if in.Key != nil { + in, out := &in.Key, &out.Key + *out = new(string) + **out = **in + } if in.NameSpace != nil { in, out := &in.NameSpace, &out.NameSpace *out = make([]string, len(*in)) diff --git a/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml b/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml index 0e3126ad3..e304bb77e 100644 --- a/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml +++ b/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml @@ -939,33 +939,6 @@ spec: description: KubernetesConfig will be the JSON struct for Basic Redis Config properties: - existOrGenerateSecrets: - maxProperties: 1 - properties: - generatePasswordSecret: - properties: - key: - type: string - name: - type: string - namespace: - items: - type: string - type: array - required: - - key - - name - type: object - redisSecret: - description: ExistingPasswordSecret is the struct to access - the existing secret - properties: - key: - type: string - name: - type: string - type: object - type: object image: type: string imagePullPolicy: @@ -983,6 +956,32 @@ spec: type: string type: object type: array + redisSecret: + maxProperties: 1 + properties: + existRedisSecret: + description: ExistingPasswordSecret is the struct to access + the existing secret + properties: + key: + type: string + name: + type: string + type: object + generatePasswordSecret: + properties: + key: + type: string + name: + type: string + namespace: + items: + type: string + type: array + required: + - name + type: object + type: object resources: description: ResourceRequirements describes the compute resource requirements. diff --git a/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml b/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml index c87a9a986..d1ec324fc 100644 --- a/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml +++ b/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml @@ -137,33 +137,6 @@ spec: description: KubernetesConfig will be the JSON struct for Basic Redis Config properties: - existOrGenerateSecrets: - maxProperties: 1 - properties: - generatePasswordSecret: - properties: - key: - type: string - name: - type: string - namespace: - items: - type: string - type: array - required: - - key - - name - type: object - redisSecret: - description: ExistingPasswordSecret is the struct to access - the existing secret - properties: - key: - type: string - name: - type: string - type: object - type: object image: type: string imagePullPolicy: @@ -181,6 +154,32 @@ spec: type: string type: object type: array + redisSecret: + maxProperties: 1 + properties: + existRedisSecret: + description: ExistingPasswordSecret is the struct to access + the existing secret + properties: + key: + type: string + name: + type: string + type: object + generatePasswordSecret: + properties: + key: + type: string + name: + type: string + namespace: + items: + type: string + type: array + required: + - name + type: object + type: object resources: description: ResourceRequirements describes the compute resource requirements. diff --git a/controllers/redis_controller.go b/controllers/redis_controller.go index f3ce6683f..ba213b080 100644 --- a/controllers/redis_controller.go +++ b/controllers/redis_controller.go @@ -64,7 +64,7 @@ func (r *RedisReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl } if instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { - err = k8sutils.GenerateSecrets(instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) + err = k8sutils.GenerateSecrets(*instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) if err != nil { reqLogger.Error(err, "Failed to create the Secrets") return ctrl.Result{RequeueAfter: time.Second * 10}, err diff --git a/controllers/rediscluster_controller.go b/controllers/rediscluster_controller.go index e0bce6c38..d3898501d 100644 --- a/controllers/rediscluster_controller.go +++ b/controllers/rediscluster_controller.go @@ -71,7 +71,7 @@ func (r *RedisClusterReconciler) Reconcile(ctx context.Context, req ctrl.Request } if instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { - err = k8sutils.GenerateSecrets(instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) + err = k8sutils.GenerateSecrets(*instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) if err != nil { reqLogger.Error(err, "Failed to create the Secrets") return ctrl.Result{RequeueAfter: time.Second * 10}, err diff --git a/example/generated_secrets/redis-cluster.yaml b/example/generated_secrets/redis-cluster.yaml new file mode 100644 index 000000000..f099cf457 --- /dev/null +++ b/example/generated_secrets/redis-cluster.yaml @@ -0,0 +1,44 @@ +--- +apiVersion: redis.redis.opstreelabs.in/v1beta1 +kind: RedisCluster +metadata: + name: shubham +spec: + clusterSize: 3 + clusterVersion: v7 + persistenceEnabled: true + securityContext: + runAsUser: 1000 + fsGroup: 1000 + kubernetesConfig: + image: quay.io/opstree/redis:v7.0.5 + imagePullPolicy: IfNotPresent + resources: + requests: + cpu: 101m + memory: 128Mi + limits: + cpu: 101m + memory: 128Mi + # redisSecret: + # name: shubham + # key: random + redisExporter: + enabled: false + image: quay.io/opstree/redis-exporter:v1.44.0 + imagePullPolicy: Always + resources: + requests: + cpu: 100m + memory: 128Mi + limits: + cpu: 100m + memory: 128Mi + storage: + volumeClaimTemplate: + spec: + # storageClassName: standard + accessModes: ["ReadWriteOnce"] + resources: + requests: + storage: 1Gi diff --git a/k8sutils/redis-cluster.go b/k8sutils/redis-cluster.go index 91336e40a..d0344dd3f 100644 --- a/k8sutils/redis-cluster.go +++ b/k8sutils/redis-cluster.go @@ -68,8 +68,8 @@ func generateRedisClusterContainerParams(cr *redisv1beta1.RedisCluster, readines case cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil: containerProp.EnabledPassword = &trueProperty - containerProp.SecretName = &cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name - containerProp.SecretKey = &cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key + containerProp.SecretName = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name + containerProp.SecretKey = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key default: containerProp.EnabledPassword = &falseProperty diff --git a/k8sutils/redis-standalone.go b/k8sutils/redis-standalone.go index f19ea37e4..7d4dd82d6 100644 --- a/k8sutils/redis-standalone.go +++ b/k8sutils/redis-standalone.go @@ -116,8 +116,8 @@ func generateRedisStandaloneContainerParams(cr *redisv1beta1.Redis) containerPar case cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil: containerProp.EnabledPassword = &trueProperty - containerProp.SecretName = &cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name - containerProp.SecretKey = &cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key + containerProp.SecretName = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name + containerProp.SecretKey = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key default: containerProp.EnabledPassword = &falseProperty diff --git a/k8sutils/secrets.go b/k8sutils/secrets.go index 43cac635a..6ded2c98f 100644 --- a/k8sutils/secrets.go +++ b/k8sutils/secrets.go @@ -85,13 +85,18 @@ func getRedisTLSConfig(cr *redisv1beta1.RedisCluster, redisInfo RedisDetails) *t } return nil } -func GenerateSecrets(name string, namespacelist []string, key string) error { +func GenerateSecrets(name string, namespacelist []string, key *string) error { genLogger := log.WithValues() rndID, err := uuid.NewRandom() if err != nil { genLogger.Error(err, "Unable to generate the UUID") } + // If key is empty add the default value + if key == nil { + *key = "key" + } + // If no namespacelist is defined default would be added. if namespacelist == nil { namespacelist = append(namespacelist, "default") @@ -106,7 +111,7 @@ func GenerateSecrets(name string, namespacelist []string, key string) error { generatedSecretTemplate.Name = name generatedSecretTemplate.Namespace = namespace generatedSecretTemplate.Data = map[string][]byte{ - key: value, + *key: value, } // Check whether the secret exist or not If not then create it From 12181cb461b7b57d4758e89c243fe18dbfdd7522 Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Tue, 17 Jan 2023 13:34:58 +0530 Subject: [PATCH 06/15] add owner Reference --- controllers/rediscluster_controller.go | 2 +- k8sutils/secrets.go | 10 +++++++++- 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/controllers/rediscluster_controller.go b/controllers/rediscluster_controller.go index d3898501d..713392999 100644 --- a/controllers/rediscluster_controller.go +++ b/controllers/rediscluster_controller.go @@ -71,7 +71,7 @@ func (r *RedisClusterReconciler) Reconcile(ctx context.Context, req ctrl.Request } if instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { - err = k8sutils.GenerateSecrets(*instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) + err = k8sutils.GenerateSecrets(instance) if err != nil { reqLogger.Error(err, "Failed to create the Secrets") return ctrl.Result{RequeueAfter: time.Second * 10}, err diff --git a/k8sutils/secrets.go b/k8sutils/secrets.go index 6ded2c98f..d1b174609 100644 --- a/k8sutils/secrets.go +++ b/k8sutils/secrets.go @@ -85,7 +85,13 @@ func getRedisTLSConfig(cr *redisv1beta1.RedisCluster, redisInfo RedisDetails) *t } return nil } -func GenerateSecrets(name string, namespacelist []string, key *string) error { + +//func GenerateSecrets(name string, namespacelist []string, key *string, ownerRef metav1.OwnerReference) error { +func GenerateSecrets(instance *redisv1beta1.RedisCluster) error { + var name = *instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name + var namespacelist = instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace + var key = instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key + genLogger := log.WithValues() rndID, err := uuid.NewRandom() @@ -114,6 +120,8 @@ func GenerateSecrets(name string, namespacelist []string, key *string) error { *key: value, } + AddOwnerRefToObject(generatedSecretTemplate, redisClusterAsOwner(instance)) + // Check whether the secret exist or not If not then create it _, err := generateK8sClient().CoreV1().Secrets(namespace).Get(context.Background(), name, metav1.GetOptions{}) if kerror.IsNotFound(err) { From 3498d1914edea27fdf1922c80a18a844f7f64ee5 Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Tue, 17 Jan 2023 16:42:09 +0530 Subject: [PATCH 07/15] temp commit --- controllers/redis_controller.go | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/controllers/redis_controller.go b/controllers/redis_controller.go index ba213b080..e273abd50 100644 --- a/controllers/redis_controller.go +++ b/controllers/redis_controller.go @@ -63,13 +63,13 @@ func (r *RedisReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl return ctrl.Result{}, err } - if instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { - err = k8sutils.GenerateSecrets(*instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) - if err != nil { - reqLogger.Error(err, "Failed to create the Secrets") - return ctrl.Result{RequeueAfter: time.Second * 10}, err - } - } + // if instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { + // err = k8sutils.GenerateSecrets(*instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) + // if err != nil { + // reqLogger.Error(err, "Failed to create the Secrets") + // return ctrl.Result{RequeueAfter: time.Second * 10}, err + // } + // } err = k8sutils.CreateStandaloneRedis(instance) if err != nil { From ac36a0ae687220f17d03b336ab92d680a7e4eadf Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Tue, 17 Jan 2023 21:00:08 +0530 Subject: [PATCH 08/15] make code modular --- controllers/redis_controller.go | 14 +++---- controllers/rediscluster_controller.go | 2 +- k8sutils/redis-cluster.go | 26 ++++++++++++ k8sutils/redis-standalone.go | 26 ++++++++++++ k8sutils/secrets.go | 58 +++++++++++++------------- 5 files changed, 90 insertions(+), 36 deletions(-) diff --git a/controllers/redis_controller.go b/controllers/redis_controller.go index e273abd50..36b5483cb 100644 --- a/controllers/redis_controller.go +++ b/controllers/redis_controller.go @@ -63,13 +63,13 @@ func (r *RedisReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl return ctrl.Result{}, err } - // if instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { - // err = k8sutils.GenerateSecrets(*instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace, instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) - // if err != nil { - // reqLogger.Error(err, "Failed to create the Secrets") - // return ctrl.Result{RequeueAfter: time.Second * 10}, err - // } - // } + if instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { + err = k8sutils.CreateRedisSecrets(instance) + if err != nil { + reqLogger.Error(err, "Failed to create the Secrets") + return ctrl.Result{RequeueAfter: time.Second * 10}, err + } + } err = k8sutils.CreateStandaloneRedis(instance) if err != nil { diff --git a/controllers/rediscluster_controller.go b/controllers/rediscluster_controller.go index 713392999..3ef2274dc 100644 --- a/controllers/rediscluster_controller.go +++ b/controllers/rediscluster_controller.go @@ -71,7 +71,7 @@ func (r *RedisClusterReconciler) Reconcile(ctx context.Context, req ctrl.Request } if instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { - err = k8sutils.GenerateSecrets(instance) + err = k8sutils.CreateRedisClusterSecrets(instance) if err != nil { reqLogger.Error(err, "Failed to create the Secrets") return ctrl.Result{RequeueAfter: time.Second * 10}, err diff --git a/k8sutils/redis-cluster.go b/k8sutils/redis-cluster.go index 07a9aa8cc..9bccf6def 100644 --- a/k8sutils/redis-cluster.go +++ b/k8sutils/redis-cluster.go @@ -214,3 +214,29 @@ func (service RedisClusterService) CreateRedisClusterService(cr *redisv1beta1.Re } return nil } + +func CreateRedisClusterSecrets(cr *redisv1beta1.RedisCluster) error { + + var name = *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name + var namespacelist = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace + var key = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key + + genLogger := log.WithValues() + + // If key is empty add the default value + if key == nil { + *key = "key" + } + genLogger.Info("The key is set to ", *key) + + // If no namespacelist is defined default would be added automatically + if namespacelist == nil { + namespacelist = append(namespacelist, "default") + } + genLogger.Info("Secrets would be generated in namespace", namespacelist) + + ownerRef := redisClusterAsOwner(cr) + + return GenerateSecrets(name, namespacelist, key, ownerRef) + +} diff --git a/k8sutils/redis-standalone.go b/k8sutils/redis-standalone.go index 7faed344c..bf1d31ff0 100644 --- a/k8sutils/redis-standalone.go +++ b/k8sutils/redis-standalone.go @@ -152,3 +152,29 @@ func generateRedisStandaloneContainerParams(cr *redisv1beta1.Redis) containerPar } return containerProp } + +func CreateRedisSecrets(cr *redisv1beta1.Redis) error { + + var name = *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name + var namespacelist = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace + var key = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key + + genLogger := log.WithValues() + + // If key is empty add the default value + if key == nil { + *key = "key" + } + genLogger.Info("The key is set to ", *key) + + // If no namespacelist is defined default would be added automatically + if namespacelist == nil { + namespacelist = append(namespacelist, "default") + } + genLogger.Info("Secrets would be generated in namespace", namespacelist) + + ownerRef := redisAsOwner(cr) + + return GenerateSecrets(name, namespacelist, key, ownerRef) + +} diff --git a/k8sutils/secrets.go b/k8sutils/secrets.go index d1b174609..0cf161902 100644 --- a/k8sutils/secrets.go +++ b/k8sutils/secrets.go @@ -86,11 +86,11 @@ func getRedisTLSConfig(cr *redisv1beta1.RedisCluster, redisInfo RedisDetails) *t return nil } -//func GenerateSecrets(name string, namespacelist []string, key *string, ownerRef metav1.OwnerReference) error { -func GenerateSecrets(instance *redisv1beta1.RedisCluster) error { - var name = *instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name - var namespacelist = instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace - var key = instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key +func GenerateSecrets(name string, namespacelist []string, key *string, ownerRef metav1.OwnerReference) error { + + // var name = *instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name + // var namespacelist = instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace + // var key = instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key genLogger := log.WithValues() @@ -98,39 +98,25 @@ func GenerateSecrets(instance *redisv1beta1.RedisCluster) error { if err != nil { genLogger.Error(err, "Unable to generate the UUID") } - // If key is empty add the default value - if key == nil { - *key = "key" - } - - // If no namespacelist is defined default would be added. - if namespacelist == nil { - namespacelist = append(namespacelist, "default") - } - // Key and Value for the secret value := rndID.NodeID() for _, namespace := range namespacelist { - generatedSecretTemplate := generateSecretTemplate() - generatedSecretTemplate.Name = name - generatedSecretTemplate.Namespace = namespace + generatedSecretTemplate := generateSecretTemplate(name, namespace) generatedSecretTemplate.Data = map[string][]byte{ *key: value, } - AddOwnerRefToObject(generatedSecretTemplate, redisClusterAsOwner(instance)) + AddOwnerRefToObject(generatedSecretTemplate, ownerRef) // Check whether the secret exist or not If not then create it - _, err := generateK8sClient().CoreV1().Secrets(namespace).Get(context.Background(), name, metav1.GetOptions{}) - if kerror.IsNotFound(err) { - _, err := generateK8sClient().CoreV1().Secrets(namespace).Create(context.Background(), generatedSecretTemplate, metav1.CreateOptions{}) - if err != nil { + _, err := getSecrets(namespace, name) + if err != nil { + if kerror.IsNotFound(err) { + _, err := generateK8sClient().CoreV1().Secrets(namespace).Create(context.TODO(), generatedSecretTemplate, metav1.CreateOptions{}) genLogger.Error(err, "Failed to create the Secrets by the operator") - return err } - } else { return err } @@ -140,7 +126,7 @@ func GenerateSecrets(instance *redisv1beta1.RedisCluster) error { } -func generateSecretTemplate() *corev1.Secret { +func generateSecretTemplate(name string, namespace string) *corev1.Secret { return &corev1.Secret{ TypeMeta: metav1.TypeMeta{ @@ -148,8 +134,8 @@ func generateSecretTemplate() *corev1.Secret { APIVersion: "v1", }, ObjectMeta: metav1.ObjectMeta{ - Name: "", - Namespace: "", + Name: name, + Namespace: namespace, }, Data: map[string][]byte{}, @@ -158,3 +144,19 @@ func generateSecretTemplate() *corev1.Secret { } } + +// GetStateFulSet is a method to get statefulset in Kubernetes +func getSecrets(namespace string, secret string) (*corev1.Secret, error) { + logger := secretLogger(namespace, secret) + getOpts := metav1.GetOptions{ + TypeMeta: generateMetaInformation("Secrets", "v1"), + } + secretInfo, err := generateK8sClient().CoreV1().Secrets(namespace).Get(context.TODO(), secret, getOpts) + + if err != nil { + logger.Info("Redis secret get action failed") + return nil, err + } + logger.Info("Redis secret get action was successful") + return secretInfo, nil +} From c1476d287682d019ac80b291c0b6eccbc12bbc94 Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Wed, 18 Jan 2023 01:17:56 +0530 Subject: [PATCH 09/15] add Examples --- example/generated_secrets/redis-cluster.yaml | 64 +++++++++++++---- .../generated_secrets/redis-standalone.yaml | 69 +++++++++++++++++++ k8sutils/redis-cluster.go | 23 +++++-- k8sutils/redis-standalone.go | 23 +++++-- k8sutils/secrets.go | 54 +++++---------- 5 files changed, 175 insertions(+), 58 deletions(-) create mode 100644 example/generated_secrets/redis-standalone.yaml diff --git a/example/generated_secrets/redis-cluster.yaml b/example/generated_secrets/redis-cluster.yaml index f099cf457..0a2fd1d38 100644 --- a/example/generated_secrets/redis-cluster.yaml +++ b/example/generated_secrets/redis-cluster.yaml @@ -2,7 +2,8 @@ apiVersion: redis.redis.opstreelabs.in/v1beta1 kind: RedisCluster metadata: - name: shubham + name: redis-cluster-random + namespace: redis-operator spec: clusterSize: 3 clusterVersion: v7 @@ -20,20 +21,48 @@ spec: limits: cpu: 101m memory: 128Mi - # redisSecret: - # name: shubham - # key: random - redisExporter: - enabled: false - image: quay.io/opstree/redis-exporter:v1.44.0 - imagePullPolicy: Always - resources: - requests: - cpu: 100m - memory: 128Mi - limits: - cpu: 100m - memory: 128Mi + redisSecret: + generatePasswordSecret: + name: redis-secret-cluster + namespace : + - redis-operator + key : operator-key # Default is set to 'key' + # existRedisSecret: + # name: redis-secret + # key: password + # imagePullSecrets: + # - name: regcred + # redisExporter: + # enabled: false + # image: quay.io/opstree/redis-exporter:v1.44.0 + # imagePullPolicy: Always + # resources: + # requests: + # cpu: 100m + # memory: 128Mi + # limits: + # cpu: 100m + # memory: 128Mi +# Environment Variables for Redis Exporter + # env: + # - name: REDIS_EXPORTER_INCL_SYSTEM_METRICS + # value: "true" + # - name: UI_PROPERTIES_FILE_NAME + # valueFrom: + # configMapKeyRef: + # name: game-demo + # key: ui_properties_file_name + # - name: SECRET_USERNAME + # valueFrom: + # secretKeyRef: + # name: mysecret + # key: username +# redisLeader: +# redisConfig: +# additionalRedisConfig: redis-external-config +# redisFollower: +# redisConfig: +# additionalRedisConfig: redis-external-config storage: volumeClaimTemplate: spec: @@ -42,3 +71,8 @@ spec: resources: requests: storage: 1Gi + # nodeSelector: + # kubernetes.io/hostname: minikube + # priorityClassName: + # Affinity: + # Tolerations: [] diff --git a/example/generated_secrets/redis-standalone.yaml b/example/generated_secrets/redis-standalone.yaml new file mode 100644 index 000000000..089c1c12f --- /dev/null +++ b/example/generated_secrets/redis-standalone.yaml @@ -0,0 +1,69 @@ +--- +apiVersion: redis.redis.opstreelabs.in/v1beta1 +kind: Redis +metadata: + name: redis-standalone + namespace: redis-operator +spec: + # redisConfig: + # additionalRedisConfig: redis-external-config + kubernetesConfig: + image: quay.io/opstree/redis:v7.0.5 + imagePullPolicy: IfNotPresent + resources: + requests: + cpu: 101m + memory: 128Mi + limits: + cpu: 101m + memory: 128Mi + redisSecret: + generatePasswordSecret: + name: redis-secret-standalone + namespace : + - redis-operator + key : operator-key # Default is set to 'key' + # existRedisSecret: + # name: redis-secret + # key: password + # imagePullSecrets: + # - name: regcred + # redisExporter: + # enabled: false + # image: quay.io/opstree/redis-exporter:v1.44.0 + # imagePullPolicy: Always + # resources: + # requests: + # cpu: 100m + # memory: 128Mi + # limits: + # cpu: 100m + # memory: 128Mi +# Environment Variables for Redis Exporter + # env: + # - name: REDIS_EXPORTER_INCL_SYSTEM_METRICS + # value: "true" + # - name: UI_PROPERTIES_FILE_NAME + # valueFrom: + # configMapKeyRef: + # name: game-demo + # key: ui_properties_file_name + # - name: SECRET_USERNAME + # valueFrom: + # secretKeyRef: + # name: mysecret + # key: username + storage: + volumeClaimTemplate: + spec: + # storageClassName: standard + accessModes: ["ReadWriteOnce"] + resources: + requests: + storage: 1Gi + # nodeSelector: + # kubernetes.io/hostname: minikube + # securityContext: {} + # priorityClassName: + # affinity: + # Tolerations: [] diff --git a/k8sutils/redis-cluster.go b/k8sutils/redis-cluster.go index 9bccf6def..fa3183e2a 100644 --- a/k8sutils/redis-cluster.go +++ b/k8sutils/redis-cluster.go @@ -3,6 +3,7 @@ package k8sutils import ( redisv1beta1 "redis-operator/api/v1beta1" + "github.com/google/uuid" corev1 "k8s.io/api/core/v1" ) @@ -220,6 +221,7 @@ func CreateRedisClusterSecrets(cr *redisv1beta1.RedisCluster) error { var name = *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name var namespacelist = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace var key = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key + ownerRef := redisClusterAsOwner(cr) genLogger := log.WithValues() @@ -227,16 +229,29 @@ func CreateRedisClusterSecrets(cr *redisv1beta1.RedisCluster) error { if key == nil { *key = "key" } - genLogger.Info("The key is set to ", *key) + genLogger.Info("The key is set to ", "key", *key) // If no namespacelist is defined default would be added automatically if namespacelist == nil { namespacelist = append(namespacelist, "default") } - genLogger.Info("Secrets would be generated in namespace", namespacelist) + genLogger.Info("Namespaces passed to generate secrets are", "namespaces", namespacelist) - ownerRef := redisClusterAsOwner(cr) + rndID, err := uuid.NewRandom() + if err != nil { + genLogger.Error(err, "Unable to generate the UUID") + } + value := rndID.NodeID() + genLogger.Info("Secrets would be generated in ", "namespace", namespacelist) + + for _, namespace := range namespacelist { + err := createSecretIfNotExist(name, namespace, key, value, ownerRef) + if err != nil { - return GenerateSecrets(name, namespacelist, key, ownerRef) + return err + } + } + + return nil } diff --git a/k8sutils/redis-standalone.go b/k8sutils/redis-standalone.go index bf1d31ff0..a880e8173 100644 --- a/k8sutils/redis-standalone.go +++ b/k8sutils/redis-standalone.go @@ -2,6 +2,8 @@ package k8sutils import ( redisv1beta1 "redis-operator/api/v1beta1" + + "github.com/google/uuid" ) var ( @@ -158,6 +160,7 @@ func CreateRedisSecrets(cr *redisv1beta1.Redis) error { var name = *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name var namespacelist = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace var key = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key + ownerRef := redisAsOwner(cr) genLogger := log.WithValues() @@ -165,16 +168,28 @@ func CreateRedisSecrets(cr *redisv1beta1.Redis) error { if key == nil { *key = "key" } - genLogger.Info("The key is set to ", *key) + genLogger.Info("The key is set to ", "key", *key) // If no namespacelist is defined default would be added automatically if namespacelist == nil { namespacelist = append(namespacelist, "default") } - genLogger.Info("Secrets would be generated in namespace", namespacelist) + genLogger.Info("Namespaces passed to generate secrets are", "namespaces", namespacelist) - ownerRef := redisAsOwner(cr) + rndID, err := uuid.NewRandom() + if err != nil { + genLogger.Error(err, "Unable to generate the UUID") + } + value := rndID.NodeID() + genLogger.Info("Secrets would be generated in ", "namespace", namespacelist) - return GenerateSecrets(name, namespacelist, key, ownerRef) + for _, namespace := range namespacelist { + err := createSecretIfNotExist(name, namespace, key, value, ownerRef) + if err != nil { + return err + } + } + + return nil } diff --git a/k8sutils/secrets.go b/k8sutils/secrets.go index 0cf161902..7f9983842 100644 --- a/k8sutils/secrets.go +++ b/k8sutils/secrets.go @@ -8,7 +8,6 @@ import ( "strings" "github.com/go-logr/logr" - "github.com/google/uuid" corev1 "k8s.io/api/core/v1" kerror "k8s.io/apimachinery/pkg/api/errors" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" @@ -86,44 +85,29 @@ func getRedisTLSConfig(cr *redisv1beta1.RedisCluster, redisInfo RedisDetails) *t return nil } -func GenerateSecrets(name string, namespacelist []string, key *string, ownerRef metav1.OwnerReference) error { - - // var name = *instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name - // var namespacelist = instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace - // var key = instance.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key - +func createSecretIfNotExist(name, namespace string, key *string, value []byte, ownerRef metav1.OwnerReference) error { + secret := generateSecretTemplate(name, namespace) + secret.Data = map[string][]byte{ + *key: value, + } genLogger := log.WithValues() + AddOwnerRefToObject(secret, ownerRef) - rndID, err := uuid.NewRandom() + _, err := getSecrets(namespace, name) if err != nil { - genLogger.Error(err, "Unable to generate the UUID") - } - // Key and Value for the secret - value := rndID.NodeID() - - for _, namespace := range namespacelist { - - generatedSecretTemplate := generateSecretTemplate(name, namespace) - generatedSecretTemplate.Data = map[string][]byte{ - *key: value, - } - - AddOwnerRefToObject(generatedSecretTemplate, ownerRef) - - // Check whether the secret exist or not If not then create it - _, err := getSecrets(namespace, name) - if err != nil { - if kerror.IsNotFound(err) { - _, err := generateK8sClient().CoreV1().Secrets(namespace).Create(context.TODO(), generatedSecretTemplate, metav1.CreateOptions{}) - genLogger.Error(err, "Failed to create the Secrets by the operator") + if kerror.IsNotFound(err) { + _, err := generateK8sClient().CoreV1().Secrets(namespace).Create(context.TODO(), secret, metav1.CreateOptions{}) + if err != nil { + genLogger.Error(err, "Failed to create the Secrets by the operator in ", "namespaces", namespace) + return err } + genLogger.Info("Secret Created Successfully in ", "namespaces", namespace) + + } else { return err } - } - return nil - } func generateSecretTemplate(name string, namespace string) *corev1.Secret { @@ -146,12 +130,12 @@ func generateSecretTemplate(name string, namespace string) *corev1.Secret { } // GetStateFulSet is a method to get statefulset in Kubernetes -func getSecrets(namespace string, secret string) (*corev1.Secret, error) { - logger := secretLogger(namespace, secret) +func getSecrets(namespace string, name string) (*corev1.Secret, error) { + logger := secretLogger(namespace, name) getOpts := metav1.GetOptions{ - TypeMeta: generateMetaInformation("Secrets", "v1"), + TypeMeta: generateMetaInformation("Secret", "v1"), } - secretInfo, err := generateK8sClient().CoreV1().Secrets(namespace).Get(context.TODO(), secret, getOpts) + secretInfo, err := generateK8sClient().CoreV1().Secrets(namespace).Get(context.TODO(), name, getOpts) if err != nil { logger.Info("Redis secret get action failed") From 05e6fdfc97c6a1fd4a40fc0ab74cb9a4ecbcf0fd Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Wed, 18 Jan 2023 02:48:01 +0530 Subject: [PATCH 10/15] secrets --- example/generated_secrets/redis-cluster.yaml | 2 +- k8sutils/redis-cluster.go | 5 ++++- k8sutils/redis.go | 18 ++++++++++++++++++ 3 files changed, 23 insertions(+), 2 deletions(-) diff --git a/example/generated_secrets/redis-cluster.yaml b/example/generated_secrets/redis-cluster.yaml index 0a2fd1d38..7627fbf7e 100644 --- a/example/generated_secrets/redis-cluster.yaml +++ b/example/generated_secrets/redis-cluster.yaml @@ -2,7 +2,7 @@ apiVersion: redis.redis.opstreelabs.in/v1beta1 kind: RedisCluster metadata: - name: redis-cluster-random + name: redis-cluster namespace: redis-operator spec: clusterSize: 3 diff --git a/k8sutils/redis-cluster.go b/k8sutils/redis-cluster.go index fa3183e2a..276dddd59 100644 --- a/k8sutils/redis-cluster.go +++ b/k8sutils/redis-cluster.go @@ -241,7 +241,10 @@ func CreateRedisClusterSecrets(cr *redisv1beta1.RedisCluster) error { if err != nil { genLogger.Error(err, "Unable to generate the UUID") } - value := rndID.NodeID() + value, err := rndID.MarshalBinary() + if err != nil { + genLogger.Error(err, "Failed to create password") + } genLogger.Info("Secrets would be generated in ", "namespace", namespacelist) for _, namespace := range namespacelist { diff --git a/k8sutils/redis.go b/k8sutils/redis.go index 8719727cf..72a42a783 100644 --- a/k8sutils/redis.go +++ b/k8sutils/redis.go @@ -111,6 +111,15 @@ func ExecuteRedisClusterCommand(cr *redisv1beta1.RedisCluster) { cmd = append(cmd, "-a") cmd = append(cmd, pass) } + + if cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { + pass, err := getRedisPassword(cr.Namespace, *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) + if err != nil { + logger.Error(err, "Error in getting redis password") + } + cmd = append(cmd, "-a") + cmd = append(cmd, pass) + } cmd = append(cmd, getRedisTLSArgs(cr.Spec.TLS, cr.ObjectMeta.Name+"-leader-0")...) logger.Info("Redis cluster creation command is", "Command", cmd) executeCommand(cr, cmd, cr.ObjectMeta.Name+"-leader-0") @@ -149,6 +158,15 @@ func createRedisReplicationCommand(cr *redisv1beta1.RedisCluster, leaderPod Redi cmd = append(cmd, "-a") cmd = append(cmd, pass) } + + if cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret != nil { + pass, err := getRedisPassword(cr.Namespace, *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key) + if err != nil { + logger.Error(err, "Error in getting redis password") + } + cmd = append(cmd, "-a") + cmd = append(cmd, pass) + } cmd = append(cmd, getRedisTLSArgs(cr.Spec.TLS, leaderPod.PodName)...) logger.V(2).Info("Redis replication creation command is", "Command", cmd) return cmd From f55f2a83a896e7c63c6aabebe5db3ccc2ff56b19 Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Wed, 18 Jan 2023 02:51:09 +0530 Subject: [PATCH 11/15] update --- k8sutils/redis-standalone.go | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/k8sutils/redis-standalone.go b/k8sutils/redis-standalone.go index a880e8173..c1d13d309 100644 --- a/k8sutils/redis-standalone.go +++ b/k8sutils/redis-standalone.go @@ -180,7 +180,10 @@ func CreateRedisSecrets(cr *redisv1beta1.Redis) error { if err != nil { genLogger.Error(err, "Unable to generate the UUID") } - value := rndID.NodeID() + value, err := rndID.MarshalBinary() + if err != nil { + genLogger.Error(err, "Failed to create password") + } genLogger.Info("Secrets would be generated in ", "namespace", namespacelist) for _, namespace := range namespacelist { From d5458ec7e681f0493acab5a9fda239463d5d30ac Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Wed, 18 Jan 2023 03:04:27 +0530 Subject: [PATCH 12/15] change encoding --- k8sutils/redis-cluster.go | 5 +---- k8sutils/redis-standalone.go | 5 +---- 2 files changed, 2 insertions(+), 8 deletions(-) diff --git a/k8sutils/redis-cluster.go b/k8sutils/redis-cluster.go index 276dddd59..a306f6e98 100644 --- a/k8sutils/redis-cluster.go +++ b/k8sutils/redis-cluster.go @@ -241,10 +241,7 @@ func CreateRedisClusterSecrets(cr *redisv1beta1.RedisCluster) error { if err != nil { genLogger.Error(err, "Unable to generate the UUID") } - value, err := rndID.MarshalBinary() - if err != nil { - genLogger.Error(err, "Failed to create password") - } + value := []byte(rndID.String()) genLogger.Info("Secrets would be generated in ", "namespace", namespacelist) for _, namespace := range namespacelist { diff --git a/k8sutils/redis-standalone.go b/k8sutils/redis-standalone.go index c1d13d309..670a654c3 100644 --- a/k8sutils/redis-standalone.go +++ b/k8sutils/redis-standalone.go @@ -180,10 +180,7 @@ func CreateRedisSecrets(cr *redisv1beta1.Redis) error { if err != nil { genLogger.Error(err, "Unable to generate the UUID") } - value, err := rndID.MarshalBinary() - if err != nil { - genLogger.Error(err, "Failed to create password") - } + value := []byte(rndID.String()) genLogger.Info("Secrets would be generated in ", "namespace", namespacelist) for _, namespace := range namespacelist { From 84dff5ab0e08ca0702188a0e69fce0a77974b257 Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Wed, 18 Jan 2023 04:27:57 +0530 Subject: [PATCH 13/15] update example --- example/generated_secrets/redis-standalone.yaml | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/example/generated_secrets/redis-standalone.yaml b/example/generated_secrets/redis-standalone.yaml index 089c1c12f..3268d5c38 100644 --- a/example/generated_secrets/redis-standalone.yaml +++ b/example/generated_secrets/redis-standalone.yaml @@ -6,7 +6,10 @@ metadata: namespace: redis-operator spec: # redisConfig: - # additionalRedisConfig: redis-external-config + # additionalRedisConfig: redis-external-config\ + securityContext: + runAsUser: 1000 + fsGroup: 1000 kubernetesConfig: image: quay.io/opstree/redis:v7.0.5 imagePullPolicy: IfNotPresent From 75c3e4c35254f4c7d9ee30ed1b9e4d3df81e4cac Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Wed, 18 Jan 2023 19:10:32 +0530 Subject: [PATCH 14/15] refactor code --- k8sutils/labels.go | 9 ++++++ k8sutils/redis-cluster.go | 28 +++++++++++------- k8sutils/redis-standalone.go | 28 +++++++++++------- k8sutils/secrets.go | 55 +++++++++++++++++++++++++----------- 4 files changed, 83 insertions(+), 37 deletions(-) diff --git a/k8sutils/labels.go b/k8sutils/labels.go index 2edf8f7fa..e23e91a97 100644 --- a/k8sutils/labels.go +++ b/k8sutils/labels.go @@ -107,3 +107,12 @@ func getRedisLabels(name, setupType, role string, labels map[string]string) map[ } return lbls } + +func getSecretLabels(name, setupType string) map[string]string { + lbls := map[string]string{ + "app": name, + "redis_setup_type": setupType, + } + + return lbls +} diff --git a/k8sutils/redis-cluster.go b/k8sutils/redis-cluster.go index a306f6e98..5c4f89c03 100644 --- a/k8sutils/redis-cluster.go +++ b/k8sutils/redis-cluster.go @@ -218,12 +218,11 @@ func (service RedisClusterService) CreateRedisClusterService(cr *redisv1beta1.Re func CreateRedisClusterSecrets(cr *redisv1beta1.RedisCluster) error { - var name = *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name + // Create Logger + genLogger := log.WithValues() + var namespacelist = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace var key = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key - ownerRef := redisClusterAsOwner(cr) - - genLogger := log.WithValues() // If key is empty add the default value if key == nil { @@ -233,21 +232,30 @@ func CreateRedisClusterSecrets(cr *redisv1beta1.RedisCluster) error { // If no namespacelist is defined default would be added automatically if namespacelist == nil { - namespacelist = append(namespacelist, "default") + namespacelist = append(namespacelist, cr.Namespace) } genLogger.Info("Namespaces passed to generate secrets are", "namespaces", namespacelist) - + // Create a random UUID which is used as redis password rndID, err := uuid.NewRandom() if err != nil { genLogger.Error(err, "Unable to generate the UUID") } - value := []byte(rndID.String()) - genLogger.Info("Secrets would be generated in ", "namespace", namespacelist) + + genLogger.Info("Secrets would be generated in ", "namespaces", namespacelist) + + secretParams := RedisSecretParams{ + name: *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, + key: *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key, + ownerRef: redisClusterAsOwner(cr), + ownerNS: cr.Namespace, + value: []byte(rndID.String()), + labels: getSecretLabels(cr.Name, "Redis-Cluster"), + } for _, namespace := range namespacelist { - err := createSecretIfNotExist(name, namespace, key, value, ownerRef) + secretParams.namespace = namespace + err := createSecretIfNotExist(secretParams) if err != nil { - return err } } diff --git a/k8sutils/redis-standalone.go b/k8sutils/redis-standalone.go index 670a654c3..6066a8c94 100644 --- a/k8sutils/redis-standalone.go +++ b/k8sutils/redis-standalone.go @@ -157,12 +157,11 @@ func generateRedisStandaloneContainerParams(cr *redisv1beta1.Redis) containerPar func CreateRedisSecrets(cr *redisv1beta1.Redis) error { - var name = *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name + // Create logger + genLogger := log.WithValues() + var namespacelist = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.NameSpace var key = cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key - ownerRef := redisAsOwner(cr) - - genLogger := log.WithValues() // If key is empty add the default value if key == nil { @@ -172,21 +171,30 @@ func CreateRedisSecrets(cr *redisv1beta1.Redis) error { // If no namespacelist is defined default would be added automatically if namespacelist == nil { - namespacelist = append(namespacelist, "default") + namespacelist = append(namespacelist, cr.Namespace) } genLogger.Info("Namespaces passed to generate secrets are", "namespaces", namespacelist) - + // Create a random UUID which is used as redis password rndID, err := uuid.NewRandom() if err != nil { genLogger.Error(err, "Unable to generate the UUID") } - value := []byte(rndID.String()) - genLogger.Info("Secrets would be generated in ", "namespace", namespacelist) + + genLogger.Info("Secrets would be generated in ", "namespaces", namespacelist) + + secretParams := RedisSecretParams{ + name: *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Name, + key: *cr.Spec.KubernetesConfig.ExistOrGenerateSecret.GeneratePasswordSecret.Key, + ownerRef: redisAsOwner(cr), + ownerNS: cr.Namespace, + value: []byte(rndID.String()), + labels: getSecretLabels(cr.Name, "Redis-Standalone"), + } for _, namespace := range namespacelist { - err := createSecretIfNotExist(name, namespace, key, value, ownerRef) + secretParams.namespace = namespace + err := createSecretIfNotExist(secretParams) if err != nil { - return err } } diff --git a/k8sutils/secrets.go b/k8sutils/secrets.go index 7f9983842..45fa4fd0a 100644 --- a/k8sutils/secrets.go +++ b/k8sutils/secrets.go @@ -14,6 +14,17 @@ import ( logf "sigs.k8s.io/controller-runtime/pkg/log" ) +type RedisSecretParams struct { + name string + namespace string + key string + value []byte + ownerRef metav1.OwnerReference + ownerNS string + labels map[string]string + annotation map[string]string +} + var log = logf.Log.WithName("controller_redis") // getRedisPassword method will return the redis password @@ -85,52 +96,62 @@ func getRedisTLSConfig(cr *redisv1beta1.RedisCluster, redisInfo RedisDetails) *t return nil } -func createSecretIfNotExist(name, namespace string, key *string, value []byte, ownerRef metav1.OwnerReference) error { - secret := generateSecretTemplate(name, namespace) - secret.Data = map[string][]byte{ - *key: value, - } - genLogger := log.WithValues() - AddOwnerRefToObject(secret, ownerRef) +func createSecretIfNotExist(secretParams RedisSecretParams) error { + //Create a secret template and adding name, namespace, key and value + secret := generateSecretTemplate(secretParams) + + genLogger := secretLogger(secretParams.namespace, secretParams.name) - _, err := getSecrets(namespace, name) + _, err := getSecret(secretParams.namespace, secretParams.name) if err != nil { if kerror.IsNotFound(err) { - _, err := generateK8sClient().CoreV1().Secrets(namespace).Create(context.TODO(), secret, metav1.CreateOptions{}) + _, err := generateK8sClient().CoreV1().Secrets(secretParams.namespace).Create(context.TODO(), secret, metav1.CreateOptions{}) if err != nil { - genLogger.Error(err, "Failed to create the Secrets by the operator in ", "namespaces", namespace) + genLogger.Error(err, "Failed to create the Secrets by the operator in ", "namespaces", secretParams.namespace) return err + } else { + genLogger.Info("Secret Created Successfully in ", "namespace", secretParams.namespace) } - genLogger.Info("Secret Created Successfully in ", "namespaces", namespace) } else { + genLogger.Error(err, "Miscellaneous error found in while getting the secret") return err } } return nil } -func generateSecretTemplate(name string, namespace string) *corev1.Secret { +func generateSecretTemplate(secretParams RedisSecretParams) *corev1.Secret { - return &corev1.Secret{ + secret := &corev1.Secret{ TypeMeta: metav1.TypeMeta{ Kind: "Secret", APIVersion: "v1", }, ObjectMeta: metav1.ObjectMeta{ - Name: name, - Namespace: namespace, + Name: secretParams.name, + Namespace: secretParams.namespace, + Labels: secretParams.labels, + Annotations: secretParams.annotation, }, - Data: map[string][]byte{}, + Data: map[string][]byte{ + secretParams.key: secretParams.value, + }, Type: "Opaque", } + // Add owner reference to secret if exist in same namespace + if secretParams.namespace == secretParams.ownerNS { + AddOwnerRefToObject(secret, secretParams.ownerRef) + } + + return secret } // GetStateFulSet is a method to get statefulset in Kubernetes -func getSecrets(namespace string, name string) (*corev1.Secret, error) { +func getSecret(namespace string, name string) (*corev1.Secret, error) { logger := secretLogger(namespace, name) getOpts := metav1.GetOptions{ TypeMeta: generateMetaInformation("Secret", "v1"), From 1707146a2a93443e364a24c897f8c84ee6d467fd Mon Sep 17 00:00:00 2001 From: Shubham Gupta Date: Wed, 18 Jan 2023 19:58:22 +0530 Subject: [PATCH 15/15] add default key --- api/v1beta1/common_types.go | 3 ++- config/crd/bases/redis.redis.opstreelabs.in_redis.yaml | 1 + config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml | 1 + 3 files changed, 4 insertions(+), 1 deletion(-) diff --git a/api/v1beta1/common_types.go b/api/v1beta1/common_types.go index 1a078f7c5..416f38935 100644 --- a/api/v1beta1/common_types.go +++ b/api/v1beta1/common_types.go @@ -57,7 +57,8 @@ type ExistingPasswordSecret struct { } type GeneratePassword struct { - Name *string `json:"name"` + Name *string `json:"name"` + // +kubebuilder:default=key Key *string `json:"key,omitempty"` NameSpace []string `json:"namespace,omitempty"` } diff --git a/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml b/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml index acbce3b35..1a224d77b 100644 --- a/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml +++ b/config/crd/bases/redis.redis.opstreelabs.in_redis.yaml @@ -971,6 +971,7 @@ spec: generatePasswordSecret: properties: key: + default: key type: string name: type: string diff --git a/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml b/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml index c00718db0..5a541dbc3 100644 --- a/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml +++ b/config/crd/bases/redis.redis.opstreelabs.in_redisclusters.yaml @@ -169,6 +169,7 @@ spec: generatePasswordSecret: properties: key: + default: key type: string name: type: string