From 326abbda31cb49458cc32fa2ae3f1c563d6009c5 Mon Sep 17 00:00:00 2001 From: 13056675191 <1131648942@qq.com> Date: Fri, 2 Jul 2021 17:53:11 +0800 Subject: [PATCH] cluster: unit test for container,cluster #130 --- cluster/cluster_test.go | 575 +++++++++++++++++++++++++ cluster/container/auditlog_test.go | 71 +++ cluster/container/init_mysql_test.go | 177 ++++++++ cluster/container/init_sidecar_test.go | 278 ++++++++++++ cluster/container/metrics_test.go | 126 ++++++ cluster/container/mysql_test.go | 135 ++++++ cluster/container/slowlog_test.go | 70 +++ cluster/container/xenon_test.go | 121 ++++++ go.mod | 2 + go.sum | 2 + 10 files changed, 1557 insertions(+) create mode 100644 cluster/cluster_test.go create mode 100644 cluster/container/auditlog_test.go create mode 100644 cluster/container/init_mysql_test.go create mode 100644 cluster/container/init_sidecar_test.go create mode 100644 cluster/container/metrics_test.go create mode 100644 cluster/container/mysql_test.go create mode 100644 cluster/container/slowlog_test.go create mode 100644 cluster/container/xenon_test.go diff --git a/cluster/cluster_test.go b/cluster/cluster_test.go new file mode 100644 index 000000000..f974f65ce --- /dev/null +++ b/cluster/cluster_test.go @@ -0,0 +1,575 @@ +package cluster + +import ( + "fmt" + "reflect" + "strconv" + "testing" + + . "bou.ke/monkey" + + mysqlv1 "github.com/radondb/radondb-mysql-kubernetes/api/v1alpha1" + "github.com/radondb/radondb-mysql-kubernetes/utils" + "github.com/stretchr/testify/assert" + core "k8s.io/api/core/v1" + "k8s.io/apimachinery/pkg/api/resource" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/apimachinery/pkg/labels" + "k8s.io/apimachinery/pkg/runtime" + "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" +) + +var ( + mysqlCluster = mysqlv1.Cluster{ + ObjectMeta: metav1.ObjectMeta{ + Name: "sample", + }, + Spec: mysqlv1.ClusterSpec{ + MysqlVersion: "5.7", + }, + } + testCluster = Cluster{ + &mysqlCluster, + } +) + +func TestNew(t *testing.T) { + want := &Cluster{ + &mysqlCluster, + } + assert.Equal(t, want, New(&mysqlCluster)) +} +func TestUnwrap(t *testing.T) { + assert.Equal(t, &mysqlCluster, testCluster.Unwrap()) +} +func TestGetLabel(t *testing.T) { + //when the instance label exist + { + testMysqlCluster := mysqlCluster + testMysqlCluster.Annotations = map[string]string{ + "app.kubernetes.io/instance": "instance", + } + testCase := Cluster{ + &testMysqlCluster, + } + want := labels.Set{ + "mysql.radondb.com/cluster": "sample", + "app.kubernetes.io/name": "mysql", + "app.kubernetes.io/instance": "instance", + "app.kubernetes.io/version": "5.7.33", + "app.kubernetes.io/component": "database", + "app.kubernetes.io/managed-by": "mysql.radondb.com", + } + assert.Equal(t, want, testCase.GetLabels()) + } + //when the component label exist + { + testMysqlCluster := mysqlCluster + testMysqlCluster.Annotations = map[string]string{ + "app.kubernetes.io/component": "component", + } + testCase := Cluster{ + &testMysqlCluster, + } + want := labels.Set{ + "mysql.radondb.com/cluster": "sample", + "app.kubernetes.io/name": "mysql", + "app.kubernetes.io/instance": "sample", + "app.kubernetes.io/version": "5.7.33", + "app.kubernetes.io/component": "component", + "app.kubernetes.io/managed-by": "mysql.radondb.com", + } + assert.Equal(t, want, testCase.GetLabels()) + } + //when the part-of label exist + { + testMysqlCluster := mysqlCluster + testMysqlCluster.Annotations = map[string]string{ + "app.kubernetes.io/part-of": "part-of", + } + testCase := Cluster{ + &testMysqlCluster, + } + want := labels.Set{ + "mysql.radondb.com/cluster": "sample", + "app.kubernetes.io/name": "mysql", + "app.kubernetes.io/instance": "sample", + "app.kubernetes.io/version": "5.7.33", + "app.kubernetes.io/component": "database", + "app.kubernetes.io/managed-by": "mysql.radondb.com", + "app.kubernetes.io/part-of": "part-of", + } + assert.Equal(t, want, testCase.GetLabels()) + } +} +func TestGetSelectorLabels(t *testing.T) { + want := labels.Set{ + "mysql.radondb.com/cluster": "sample", + "app.kubernetes.io/name": "mysql", + "app.kubernetes.io/managed-by": "mysql.radondb.com", + } + assert.Equal(t, want, testCluster.GetSelectorLabels()) +} +func TestGetMySQLVersion(t *testing.T) { + //other 5.8 -> 5.7.33 + { + testMysqlCluster := mysqlCluster + testMysqlCluster.Spec.MysqlVersion = "5.8" + testCase := Cluster{ + &testMysqlCluster, + } + want := "5.7.33" + assert.Equal(t, want, testCase.GetMySQLVersion()) + } + //MySQLTagsToSemVer 5.7 -> 5.7.33 + { + testMysqlCluster := mysqlCluster + testMysqlCluster.Spec.MysqlVersion = "5.7" + testCase := Cluster{ + &testMysqlCluster, + } + want := "5.7.33" + assert.Equal(t, want, testCase.GetMySQLVersion()) + } + //MysqlImageVersions 5.7.33 -> 5.7.33 + { + testMysqlCluster := mysqlCluster + testMysqlCluster.Spec.MysqlVersion = "5.7.33" + testCase := Cluster{ + &testMysqlCluster, + } + want := "5.7.33" + assert.Equal(t, want, testCase.GetMySQLVersion()) + } +} +func TestCreatePeers(t *testing.T) { + var replicas int32 = 2 + testMysqlCluster := mysqlCluster + testMysqlCluster.ObjectMeta.Namespace = "default" + testMysqlCluster.Spec.Replicas = &replicas + testCase := Cluster{ + &testMysqlCluster, + } + want := "sample-mysql-0.sample-mysql.default:8801,sample-mysql-1.sample-mysql.default:8801" + assert.Equal(t, want, testCase.CreatePeers()) +} +func TestGetPodHostName(t *testing.T) { + testMysqlCluster := mysqlCluster + testMysqlCluster.ObjectMeta.Namespace = "default" + testCase := Cluster{ + &testMysqlCluster, + } + want0 := "sample-mysql-0.sample-mysql.default" + want1 := "sample-mysql-1.sample-mysql.default" + assert.Equal(t, want0, testCase.GetPodHostName(0)) + assert.Equal(t, want1, testCase.GetPodHostName(1)) +} +func TestEnsureVolumes(t *testing.T) { + volume := []core.Volume{ + { + Name: utils.ConfVolumeName, + VolumeSource: core.VolumeSource{ + EmptyDir: &core.EmptyDirVolumeSource{}, + }, + }, + { + Name: utils.LogsVolumeName, + VolumeSource: core.VolumeSource{ + EmptyDir: &core.EmptyDirVolumeSource{}, + }, + }, + { + Name: utils.ConfMapVolumeName, + VolumeSource: core.VolumeSource{ + ConfigMap: &core.ConfigMapVolumeSource{ + LocalObjectReference: core.LocalObjectReference{ + Name: "sample-mysql", + }, + }, + }, + }, + { + Name: utils.ScriptsVolumeName, + VolumeSource: core.VolumeSource{ + EmptyDir: &core.EmptyDirVolumeSource{}, + }, + }, + { + Name: utils.XenonVolumeName, + VolumeSource: core.VolumeSource{ + EmptyDir: &core.EmptyDirVolumeSource{}, + }, + }, + { + Name: utils.InitFileVolumeName, + VolumeSource: core.VolumeSource{ + EmptyDir: &core.EmptyDirVolumeSource{}, + }, + }, + } + //when disable Persistence + { + testMysql := mysqlCluster + testMysql.Spec.Persistence.Enabled = false + testCase := Cluster{ + &testMysql, + } + want := []core.Volume{ + { + Name: utils.DataVolumeName, + VolumeSource: core.VolumeSource{ + EmptyDir: &core.EmptyDirVolumeSource{}, + }, + }, + } + want = append(want, volume...) + assert.Equal(t, want, testCase.EnsureVolumes()) + } + //when enable tokudb + { + testMysql := mysqlCluster + testMysql.Spec.Persistence.Enabled = true + testMysql.Spec.MysqlOpts.InitTokuDB = true + testCase := Cluster{ + &testMysql, + } + want := []core.Volume{ + { + Name: utils.SysVolumeName, + VolumeSource: core.VolumeSource{ + HostPath: &core.HostPathVolumeSource{ + Path: "/sys/kernel/mm/transparent_hugepage", + }, + }, + }, + } + want = append(want, volume...) + assert.Equal(t, want, testCase.EnsureVolumes()) + } + //default(Persistence is turned on by default) + { + testMysql := mysqlCluster + testMysql.Spec.Persistence.Enabled = true + testCase := Cluster{ + &testMysql, + } + assert.Equal(t, volume, testCase.EnsureVolumes()) + } +} +func TestEnsureVolumeClaimTemplates(t *testing.T) { + var scheme runtime.Scheme + //when disable persistence + { + result, err := testCluster.EnsureVolumeClaimTemplates(&scheme) + assert.Nil(t, result) + assert.Nil(t, err) + } + + //when enable persistence + { + var cluster *Cluster + storageClass := "ssd" + testMysql := mysqlv1.Cluster{ + ObjectMeta: metav1.ObjectMeta{ + Name: "sample", + Namespace: "default", + Labels: nil, + }, + Spec: mysqlv1.ClusterSpec{ + MysqlVersion: "5.7", + Persistence: mysqlv1.Persistence{ + AccessModes: nil, + StorageClass: &storageClass, + Enabled: true, + }, + }, + } + testCase := Cluster{ + &testMysql, + } + want := []core.PersistentVolumeClaim{ + { + ObjectMeta: metav1.ObjectMeta{ + Name: "data", + Namespace: "default", + Labels: nil, + }, + Spec: core.PersistentVolumeClaimSpec{ + AccessModes: nil, + Resources: core.ResourceRequirements{ + Requests: core.ResourceList{ + core.ResourceStorage: resource.Quantity{}, + }, + }, + StorageClassName: &storageClass, + }, + }, + } + guard := PatchInstanceMethod(reflect.TypeOf(cluster), "GetLabels", func(*Cluster) labels.Set { + return nil + }) + guard1 := Patch(resource.MustParse, func(_ string) resource.Quantity { + return resource.Quantity{} + }) + guard2 := Patch(controllerutil.SetControllerReference, func(_ metav1.Object, _ metav1.Object, _ *runtime.Scheme) error { + return nil + }) + defer guard.Unpatch() + defer guard1.Unpatch() + defer guard2.Unpatch() + result, err := testCase.EnsureVolumeClaimTemplates(&scheme) + assert.Equal(t, want, result) + assert.Nil(t, err) + } + + //when the StorageClass is "-" + { + storageClass := "-" + testMysql := mysqlCluster + testMysql.Spec.Persistence.Enabled = true + testMysql.Spec.Persistence.Size = "10Gi" + testMysql.Spec.Persistence.StorageClass = &storageClass + testCase := Cluster{ + &testMysql, + } + guard := Patch(controllerutil.SetControllerReference, func(_ metav1.Object, _ metav1.Object, _ *runtime.Scheme) error { + return nil + }) + defer guard.Unpatch() + result, err := testCase.EnsureVolumeClaimTemplates(&scheme) + + assert.Equal(t, &storageClass, result[0].Spec.StorageClassName) + assert.Nil(t, err) + } + + //when SetControllerReference error + { + testMysql := mysqlCluster + testMysql.Spec.Persistence.Enabled = true + testMysql.Spec.Persistence.Size = "10Gi" + testCase := Cluster{ + &testMysql, + } + guard := Patch(controllerutil.SetControllerReference, func(_ metav1.Object, _ metav1.Object, _ *runtime.Scheme) error { + return fmt.Errorf("test") + }) + defer guard.Unpatch() + result, err := testCase.EnsureVolumeClaimTemplates(&scheme) + want := fmt.Errorf("failed setting controller reference: test") + assert.Nil(t, result) + assert.Equal(t, want, err) + } +} +func TestGetNameForResource(t *testing.T) { + //statefulset configMap headlessSvc + { + want := "sample-mysql" + assert.Equal(t, want, testCluster.GetNameForResource(utils.StatefulSet)) + assert.Equal(t, want, testCluster.GetNameForResource(utils.ConfigMap)) + assert.Equal(t, want, testCluster.GetNameForResource(utils.HeadlessSVC)) + } + //leaderSvc + { + want := "sample-leader" + assert.Equal(t, want, testCluster.GetNameForResource(utils.LeaderService)) + } + //folloerSvc + { + want := "sample-follower" + assert.Equal(t, want, testCluster.GetNameForResource(utils.FollowerService)) + } + //secret + { + want := "sample-secret" + assert.Equal(t, want, testCluster.GetNameForResource(utils.Secret)) + } + //others + { + want := "sample" + assert.Equal(t, want, testCluster.GetNameForResource("others")) + } +} +func TestEnsureMysqlConf(t *testing.T) { + var ( + gb int64 = 1 << 30 + mb int64 = 1 << 20 + wantSize, wantInstance string + ) + + requestsMemory := resource.NewQuantity(gb, resource.BinarySI) + LimitCpuCores := resource.NewQuantity(1, resource.DecimalSI) + testMysql := mysqlCluster + testMysql.Spec = mysqlv1.ClusterSpec{ + PodSpec: mysqlv1.PodSpec{ + Resources: core.ResourceRequirements{ + Limits: core.ResourceList{ + "cpu": *LimitCpuCores, + }, + }, + }, + MysqlOpts: mysqlv1.MysqlOpts{ + MysqlConf: mysqlv1.MysqlConf{}, + Resources: core.ResourceRequirements{ + Requests: core.ResourceList{ + "memory": *requestsMemory, + }, + }, + }, + } + //cpu 1 cores,memory 1 gb,innodb_buffer_pool_size not set + { + testMysqlCase := testMysql + testCase := Cluster{ + &testMysqlCase, + } + testCase.EnsureMysqlConf() + wantSize = strconv.FormatUint(uint64(0.45*float64(gb)), 10) + wantInstance = strconv.Itoa(int(1)) + assert.Equal(t, wantSize, testCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_size"]) + assert.Equal(t, wantInstance, testCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_instances"]) + } + //cpu 1 cores,memory 1 gb,innodb_buffer_pool_size 600 mb + { + guard := Patch(sizeToBytes, func(s string) (uint64, error) { + return uint64(600 * mb), nil + }) + defer guard.Unpatch() + + testMysqlCase := testMysql + testMysqlCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_size"] = strconv.FormatUint(uint64(600*mb), 10) + testCase := Cluster{ + &testMysqlCase, + } + testCase.EnsureMysqlConf() + wantSize := strconv.FormatUint(uint64(600*float64(mb)), 10) + wantInstance := strconv.Itoa(int(1)) + assert.Equal(t, wantSize, testCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_size"]) + assert.Equal(t, wantInstance, testCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_instances"]) + } + //cpu 1 cores,memory 2 gb,innodb_buffer_pool_size 1.7 gb + { + guard := Patch(sizeToBytes, func(s string) (uint64, error) { + return uint64(1700 * mb), nil + }) + defer guard.Unpatch() + + memoryCase := resource.NewQuantity(2*gb, resource.BinarySI) + testMysqlCase := testMysql + testMysqlCase.Spec.MysqlOpts.Resources.Requests["memory"] = *memoryCase + testMysqlCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_size"] = strconv.FormatUint(uint64(1.7*float64(gb)), 10) + testCase := Cluster{ + &testMysqlCase, + } + testCase.EnsureMysqlConf() + wantSize := strconv.FormatUint(uint64(1.6*float64(gb)), 10) + wantInstance := strconv.Itoa(int(1)) + assert.Equal(t, wantSize, testCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_size"]) + assert.Equal(t, wantInstance, testCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_instances"]) + } + //cpu 1 cores,memory 2 gb,innodb_buffer_pool_size 1.7 gb, sizeToBytes error + { + guard := Patch(sizeToBytes, func(s string) (uint64, error) { + return uint64(1700 * mb), fmt.Errorf("error") + }) + defer guard.Unpatch() + memoryCase := resource.NewQuantity(2*gb, resource.BinarySI) + testMysqlCase := testMysql + testMysqlCase.Spec.MysqlOpts.Resources.Requests["memory"] = *memoryCase + testMysqlCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_size"] = strconv.FormatUint(uint64(1.7*float64(gb)), 10) + testCase := Cluster{ + &testMysqlCase, + } + testCase.EnsureMysqlConf() + wantSize := strconv.FormatUint(uint64(1.2*float64(gb)), 10) + wantInstance := strconv.Itoa(int(1)) + assert.Equal(t, wantSize, testCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_size"]) + assert.Equal(t, wantInstance, testCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_instances"]) + } + //cpu 8 cores,memory 16 gb,innodb_buffer_pool_size 2 gb + { + guard := Patch(sizeToBytes, func(s string) (uint64, error) { + return uint64(2 * gb), nil + }) + defer guard.Unpatch() + + memoryCase := resource.NewQuantity(16*gb, resource.BinarySI) + limitCpuCoresCase := resource.NewQuantity(4, resource.DecimalSI) + testMysqlCase := testMysql + testMysqlCase.Spec.PodSpec.Resources.Limits["cpu"] = *limitCpuCoresCase + testMysqlCase.Spec.MysqlOpts.Resources.Requests["memory"] = *memoryCase + testCase := Cluster{ + &testMysqlCase, + } + testCase.EnsureMysqlConf() + wantSize := strconv.FormatUint(uint64(2*float64(gb)), 10) + wantInstance := strconv.Itoa(int(2)) + assert.Equal(t, wantSize, testCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_size"]) + assert.Equal(t, wantInstance, testCase.Spec.MysqlOpts.MysqlConf["innodb_buffer_pool_instances"]) + } +} +func TestSizeToBytes(t *testing.T) { + var ( + gb int64 = 1 << 30 + mb int64 = 1 << 20 + kb int64 = 1 << 10 + ) + //kb + { + testCase := "1000k" + want := uint64(1000 * kb) + result, err := sizeToBytes(testCase) + assert.Equal(t, want, result) + assert.Nil(t, err) + } + //mb + { + testCase := "1000m" + want := uint64(1000 * mb) + result, err := sizeToBytes(testCase) + assert.Equal(t, want, result) + assert.Nil(t, err) + } + //gb + { + testCase := "1000g" + want := uint64(1000 * gb) + result, err := sizeToBytes(testCase) + assert.Equal(t, want, result) + assert.Nil(t, err) + } + //others + { + testCase := "1000a" + want := uint64(0) + wantError := fmt.Errorf("'1000A' format error, must be a positive integer with a unit of measurement like K, M or G") + result, err := sizeToBytes(testCase) + assert.Equal(t, want, result) + assert.Equal(t, wantError, err) + } + //without unit + { + guard := Patch(strconv.ParseUint, func(s string, base int, bitSize int) (uint64, error) { + return uint64(666), nil + }) + defer guard.Unpatch() + + testCase := "1000" + want := uint64(666) + result, err := sizeToBytes(testCase) + assert.Equal(t, want, result) + assert.Nil(t, err) + } + //ParseUint error + { + guard := Patch(strconv.ParseUint, func(s string, base int, bitSize int) (uint64, error) { + return uint64(666), fmt.Errorf("error") + }) + defer guard.Unpatch() + + testCase := "1000k" + want := uint64(0) + result, err := sizeToBytes(testCase) + assert.Equal(t, want, result) + assert.Equal(t, err, fmt.Errorf("error")) + } +} diff --git a/cluster/container/auditlog_test.go b/cluster/container/auditlog_test.go new file mode 100644 index 000000000..edcd56951 --- /dev/null +++ b/cluster/container/auditlog_test.go @@ -0,0 +1,71 @@ +package container + +import ( + "testing" + + "github.com/stretchr/testify/assert" + + mysqlv1 "github.com/radondb/radondb-mysql-kubernetes/api/v1alpha1" + "github.com/radondb/radondb-mysql-kubernetes/cluster" + + core "k8s.io/api/core/v1" +) + +var ( + auditlogMysqlCluster = mysqlv1.Cluster{ + Spec: mysqlv1.ClusterSpec{ + PodSpec: mysqlv1.PodSpec{ + BusyboxImage: "busybox", + Resources: core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, + }, + }, + } + testAuditlogCluster = cluster.Cluster{ + Cluster: &auditlogMysqlCluster, + } + auditLogCase = EnsureContainer("auditlog", &testAuditlogCluster) + auditlogCommand = []string{"tail", "-f", "/var/log/mysql" + "/mysql-audit.log"} + auditlogVolumeMounts = []core.VolumeMount{ + { + Name: "logs", + MountPath: "/var/log/mysql", + }, + } +) + +func TestGetAuditlogName(t *testing.T) { + assert.Equal(t, "auditlog", auditLogCase.Name) +} +func TestGetAuditlogImage(t *testing.T) { + assert.Equal(t, "busybox", auditLogCase.Image) +} +func TestGetAuditlogCommand(t *testing.T) { + assert.Equal(t, auditlogCommand, auditLogCase.Command) +} +func TestGetAuditlogEnvVar(t *testing.T) { + assert.Nil(t, auditLogCase.Env) +} +func TestGetAuditlogLifecycle(t *testing.T) { + assert.Nil(t, auditLogCase.Lifecycle) +} +func TestGetAuditlogResources(t *testing.T) { + assert.Equal(t, core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, auditLogCase.Resources) +} +func TestGetAuditlogPorts(t *testing.T) { + assert.Nil(t, auditLogCase.Ports) +} +func TestGetAuditlogLivenessProbe(t *testing.T) { + assert.Nil(t, auditLogCase.LivenessProbe) +} +func TestGetAuditlogReadinessProbe(t *testing.T) { + assert.Nil(t, auditLogCase.ReadinessProbe) +} +func TestGetAuditlogVolumeMounts(t *testing.T) { + assert.Equal(t, auditlogVolumeMounts, auditLogCase.VolumeMounts) +} diff --git a/cluster/container/init_mysql_test.go b/cluster/container/init_mysql_test.go new file mode 100644 index 000000000..f69da976c --- /dev/null +++ b/cluster/container/init_mysql_test.go @@ -0,0 +1,177 @@ +package container + +import ( + "testing" + + "github.com/stretchr/testify/assert" + + mysqlv1 "github.com/radondb/radondb-mysql-kubernetes/api/v1alpha1" + "github.com/radondb/radondb-mysql-kubernetes/cluster" + "github.com/radondb/radondb-mysql-kubernetes/utils" + v1 "k8s.io/apimachinery/pkg/apis/meta/v1" + + core "k8s.io/api/core/v1" +) + +var ( + initMysqlMysqlCluster = mysqlv1.Cluster{ + ObjectMeta: v1.ObjectMeta{ + Name: "sample", + }, + Spec: mysqlv1.ClusterSpec{ + PodSpec: mysqlv1.PodSpec{ + Resources: core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, + }, + MysqlVersion: "5.7", + MysqlOpts: mysqlv1.MysqlOpts{ + InitTokuDB: false, + }, + }, + } + testInitMysqlCluster = cluster.Cluster{ + Cluster: &initMysqlMysqlCluster, + } + initMysqlVolumeMounts = []core.VolumeMount{ + { + Name: utils.ConfVolumeName, + MountPath: utils.ConfVolumeMountPath, + }, + { + Name: utils.ConfMapVolumeName, + MountPath: utils.MyCnfMountPath, + SubPath: "my.cnf", + }, + { + Name: utils.DataVolumeName, + MountPath: utils.DataVolumeMountPath, + }, + { + Name: utils.LogsVolumeName, + MountPath: utils.LogsVolumeMountPath, + }, + { + Name: utils.InitFileVolumeName, + MountPath: utils.InitFileVolumeMountPath, + }, + } + optFalse = false + optTrue = true + sctName = "sample-secret" + initMysqlEnvs = []core.EnvVar{ + { + Name: "MYSQL_ALLOW_EMPTY_PASSWORD", + Value: "yes", + }, + { + Name: "MYSQL_ROOT_HOST", + Value: "127.0.0.1", + }, + { + Name: "MYSQL_INIT_ONLY", + Value: "1", + }, + { + Name: "MYSQL_ROOT_PASSWORD", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: sctName, + }, + Key: "root-password", + Optional: &optFalse, + }, + }, + }, + { + Name: "MYSQL_DATABASE", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: sctName, + }, + Key: "mysql-database", + Optional: &optTrue, + }, + }, + }, + { + Name: "MYSQL_USER", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: sctName, + }, + Key: "mysql-user", + Optional: &optTrue, + }, + }, + }, + { + Name: "MYSQL_PASSWORD", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: sctName, + }, + Key: "mysql-password", + Optional: &optTrue, + }, + }, + }, + } + initMysqlCase = EnsureContainer("init-mysql", &testInitMysqlCluster) +) + +func TestGetInitMysqlName(t *testing.T) { + assert.Equal(t, "init-mysql", initMysqlCase.Name) +} +func TestGetInitMysqlImage(t *testing.T) { + assert.Equal(t, "percona/percona-server:5.7.33", initMysqlCase.Image) +} +func TestGetInitMysqlCommand(t *testing.T) { + assert.Nil(t, initMysqlCase.Command) +} +func TestGetInitMysqlEnvVar(t *testing.T) { + //base env + { + assert.Equal(t, initMysqlEnvs, initMysqlCase.Env) + } + //initTokuDB + { + testToKuDBMysqlCluster := initMysqlMysqlCluster + testToKuDBMysqlCluster.Spec.MysqlOpts.InitTokuDB = true + testTokuDBCluster := cluster.Cluster{ + Cluster: &testToKuDBMysqlCluster, + } + tokudbCase := EnsureContainer("init-mysql", &testTokuDBCluster) + testEnv := append(initMysqlEnvs, core.EnvVar{ + Name: "INIT_TOKUDB", + Value: "1", + }) + assert.Equal(t, testEnv, tokudbCase.Env) + } +} +func TestGetInitMysqlLifecycle(t *testing.T) { + assert.Nil(t, initMysqlCase.Lifecycle) +} +func TestGetInitMysqlResources(t *testing.T) { + assert.Equal(t, core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, initMysqlCase.Resources) +} +func TestGetInitMysqlPorts(t *testing.T) { + assert.Nil(t, initMysqlCase.Ports) +} +func TestGetInitMysqlLivenessProbe(t *testing.T) { + assert.Nil(t, initMysqlCase.LivenessProbe) +} +func TestGetInitMysqlReadinessProbe(t *testing.T) { + assert.Nil(t, initMysqlCase.ReadinessProbe) +} +func TestGetInitMysqlVolumeMounts(t *testing.T) { + assert.Equal(t, initMysqlVolumeMounts, initMysqlCase.VolumeMounts) +} diff --git a/cluster/container/init_sidecar_test.go b/cluster/container/init_sidecar_test.go new file mode 100644 index 000000000..7899bb5f2 --- /dev/null +++ b/cluster/container/init_sidecar_test.go @@ -0,0 +1,278 @@ +package container + +import ( + "strconv" + "testing" + + "github.com/stretchr/testify/assert" + + mysqlv1 "github.com/radondb/radondb-mysql-kubernetes/api/v1alpha1" + "github.com/radondb/radondb-mysql-kubernetes/cluster" + "github.com/radondb/radondb-mysql-kubernetes/utils" + v1 "k8s.io/apimachinery/pkg/apis/meta/v1" + + core "k8s.io/api/core/v1" +) + +var ( + defeatCount int32 = 1 + electionTimeout int32 = 5 + initSidecarMysqlCluster = mysqlv1.Cluster{ + ObjectMeta: v1.ObjectMeta{ + Name: "sample", + }, + Spec: mysqlv1.ClusterSpec{ + PodSpec: mysqlv1.PodSpec{ + SidecarImage: "sidecar image", + Resources: core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, + }, + XenonOpts: mysqlv1.XenonOpts{ + AdmitDefeatHearbeatCount: &defeatCount, + ElectionTimeout: &electionTimeout, + }, + MetricsOpts: mysqlv1.MetricsOpts{ + Enabled: false, + }, + MysqlOpts: mysqlv1.MysqlOpts{ + InitTokuDB: false, + }, + Persistence: mysqlv1.Persistence{ + Enabled: false, + }, + }, + } + testInitSidecarCluster = cluster.Cluster{ + Cluster: &initSidecarMysqlCluster, + } + defaultInitSidecarEnvs = []core.EnvVar{ + { + Name: "POD_HOSTNAME", + ValueFrom: &core.EnvVarSource{ + FieldRef: &core.ObjectFieldSelector{ + APIVersion: "v1", + FieldPath: "metadata.name", + }, + }, + }, + { + Name: "NAMESPACE", + Value: testInitSidecarCluster.Namespace, + }, + { + Name: "SERVICE_NAME", + Value: "sample-mysql", + }, + { + Name: "ADMIT_DEFEAT_HEARBEAT_COUNT", + Value: strconv.Itoa(int(*testInitSidecarCluster.Spec.XenonOpts.AdmitDefeatHearbeatCount)), + }, + { + Name: "ELECTION_TIMEOUT", + Value: strconv.Itoa(int(*testInitSidecarCluster.Spec.XenonOpts.ElectionTimeout)), + }, + { + Name: "MY_MYSQL_VERSION", + Value: "5.7.33", + }, + { + Name: "MYSQL_ROOT_PASSWORD", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: sctName, + }, + Key: "root-password", + Optional: &optFalse, + }, + }, + }, + { + Name: "MYSQL_REPL_USER", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: sctName, + }, + Key: "replication-user", + Optional: &optTrue, + }, + }, + }, + { + Name: "MYSQL_REPL_PASSWORD", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: sctName, + }, + Key: "replication-password", + Optional: &optTrue, + }, + }, + }, + { + Name: "METRICS_USER", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: sctName, + }, + Key: "metrics-user", + Optional: &optTrue, + }, + }, + }, + { + Name: "METRICS_PASSWORD", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: sctName, + }, + Key: "metrics-password", + Optional: &optTrue, + }, + }, + }, + { + Name: "OPERATOR_USER", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: sctName, + }, + Key: "operator-user", + Optional: &optTrue, + }, + }, + }, + { + Name: "OPERATOR_PASSWORD", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: sctName, + }, + Key: "operator-password", + Optional: &optTrue, + }, + }, + }, + } + defaultInitsidecarVolumeMounts = []core.VolumeMount{ + { + Name: utils.ConfVolumeName, + MountPath: utils.ConfVolumeMountPath, + }, + { + Name: utils.ConfMapVolumeName, + MountPath: utils.ConfMapVolumeMountPath, + }, + { + Name: utils.ScriptsVolumeName, + MountPath: utils.ScriptsVolumeMountPath, + }, + { + Name: utils.XenonVolumeName, + MountPath: utils.XenonVolumeMountPath, + }, + { + Name: utils.InitFileVolumeName, + MountPath: utils.InitFileVolumeMountPath, + }, + } + initSidecarCase = EnsureContainer("init-sidecar", &testInitSidecarCluster) +) + +func TestGetInitSidecarName(t *testing.T) { + assert.Equal(t, "init-sidecar", initSidecarCase.Name) +} +func TestGetInitSidecarImage(t *testing.T) { + assert.Equal(t, "sidecar image", initSidecarCase.Image) +} +func TestGetInitSidecarCommand(t *testing.T) { + command := []string{"sidecar", "init"} + assert.Equal(t, command, initSidecarCase.Command) +} +func TestGetInitSidecarEnvVar(t *testing.T) { + //default + { + assert.Equal(t, defaultInitSidecarEnvs, initSidecarCase.Env) + } + //initTokuDB + { + testToKuDBMysqlCluster := initSidecarMysqlCluster + testToKuDBMysqlCluster.Spec.MysqlOpts.InitTokuDB = true + testTokuDBCluster := cluster.Cluster{ + Cluster: &testToKuDBMysqlCluster, + } + tokudbCase := EnsureContainer("init-sidecar", &testTokuDBCluster) + testTokuDBEnv := make([]core.EnvVar, 13) + copy(testTokuDBEnv, defaultInitSidecarEnvs) + testTokuDBEnv = append(testTokuDBEnv, core.EnvVar{ + Name: "INIT_TOKUDB", + Value: "1", + }) + assert.Equal(t, testTokuDBEnv, tokudbCase.Env) + } +} +func TestGetInitSidecarLifecycle(t *testing.T) { + assert.Nil(t, initSidecarCase.Lifecycle) +} +func TestGetInitSidecarResources(t *testing.T) { + assert.Equal(t, core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, initSidecarCase.Resources) +} +func TestGetInitSidecarPorts(t *testing.T) { + assert.Nil(t, initSidecarCase.Ports) +} +func TestGetInitSidecarLivenessProbe(t *testing.T) { + assert.Nil(t, initSidecarCase.LivenessProbe) +} +func TestGetInitSidecarReadinessProbe(t *testing.T) { + assert.Nil(t, initSidecarCase.ReadinessProbe) +} +func TestGetInitSidecarVolumeMounts(t *testing.T) { + //default + { + assert.Equal(t, defaultInitsidecarVolumeMounts, initSidecarCase.VolumeMounts) + } + //init tokudb + { + testToKuDBMysqlCluster := initSidecarMysqlCluster + testToKuDBMysqlCluster.Spec.MysqlOpts.InitTokuDB = true + testTokuDBCluster := cluster.Cluster{ + Cluster: &testToKuDBMysqlCluster, + } + tokudbCase := EnsureContainer("init-sidecar", &testTokuDBCluster) + tokuDBVolumeMounts := make([]core.VolumeMount, 5, 6) + copy(tokuDBVolumeMounts, defaultInitsidecarVolumeMounts) + tokuDBVolumeMounts = append(tokuDBVolumeMounts, core.VolumeMount{ + Name: utils.SysVolumeName, + MountPath: utils.SysVolumeMountPath, + }) + assert.Equal(t, tokuDBVolumeMounts, tokudbCase.VolumeMounts) + } + //enable persistence + { + testPersistenceMysqlCluster := initSidecarMysqlCluster + testPersistenceMysqlCluster.Spec.Persistence.Enabled = true + testPersistenceCluster := cluster.Cluster{ + Cluster: &testPersistenceMysqlCluster, + } + persistenceCase := EnsureContainer("init-sidecar", &testPersistenceCluster) + persistenceVolumeMounts := make([]core.VolumeMount, 5, 6) + copy(persistenceVolumeMounts, defaultInitsidecarVolumeMounts) + persistenceVolumeMounts = append(persistenceVolumeMounts, core.VolumeMount{ + Name: utils.DataVolumeName, + MountPath: utils.DataVolumeMountPath, + }) + assert.Equal(t, persistenceVolumeMounts, persistenceCase.VolumeMounts) + + } +} diff --git a/cluster/container/metrics_test.go b/cluster/container/metrics_test.go new file mode 100644 index 000000000..9d3578edb --- /dev/null +++ b/cluster/container/metrics_test.go @@ -0,0 +1,126 @@ +package container + +import ( + "testing" + + mysqlv1 "github.com/radondb/radondb-mysql-kubernetes/api/v1alpha1" + "github.com/radondb/radondb-mysql-kubernetes/cluster" + "github.com/stretchr/testify/assert" + v1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/apimachinery/pkg/util/intstr" + + core "k8s.io/api/core/v1" +) + +var ( + metricsMysqlCluster = mysqlv1.Cluster{ + ObjectMeta: v1.ObjectMeta{ + Name: "sample", + }, + Spec: mysqlv1.ClusterSpec{ + PodSpec: mysqlv1.PodSpec{ + Resources: core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, + }, + MetricsOpts: mysqlv1.MetricsOpts{ + Image: "metrics-image", + }, + }, + } + testMetricsCluster = cluster.Cluster{ + Cluster: &metricsMysqlCluster, + } + metricsCase = EnsureContainer("metrics", &testMetricsCluster) +) + +func TestGetMetricsName(t *testing.T) { + assert.Equal(t, "metrics", metricsCase.Name) +} +func TestGetMetricsImage(t *testing.T) { + assert.Equal(t, "metrics-image", metricsCase.Image) +} +func TestGetMetricsCommand(t *testing.T) { + assert.Nil(t, metricsCase.Command) +} +func TestGetMetricsEnvVar(t *testing.T) { + { + optTrue := true + env := []core.EnvVar{ + { + Name: "DATA_SOURCE_NAME", + ValueFrom: &core.EnvVarSource{ + SecretKeyRef: &core.SecretKeySelector{ + LocalObjectReference: core.LocalObjectReference{ + Name: "sample-secret", + }, + Key: "data-source", + Optional: &optTrue, + }, + }, + }, + } + assert.Equal(t, env, metricsCase.Env) + } +} +func TestGetMetricsLifecycle(t *testing.T) { + assert.Nil(t, metricsCase.Lifecycle) +} +func TestGetMetricsResources(t *testing.T) { + assert.Equal(t, core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, metricsCase.Resources) +} +func TestGetMetricsPorts(t *testing.T) { + port := []core.ContainerPort{ + { + Name: "metrics", + ContainerPort: 9104, + }, + } + assert.Equal(t, port, metricsCase.Ports) +} +func TestGetMetricsLivenessProbe(t *testing.T) { + livenessProbe := &core.Probe{ + Handler: core.Handler{ + HTTPGet: &core.HTTPGetAction{ + Path: "/", + Port: intstr.IntOrString{ + Type: 0, + IntVal: int32(9104), + }, + }, + }, + InitialDelaySeconds: 15, + TimeoutSeconds: 5, + PeriodSeconds: 10, + SuccessThreshold: 1, + FailureThreshold: 3, + } + assert.Equal(t, livenessProbe, metricsCase.LivenessProbe) +} +func TestGetMetricsReadinessProbe(t *testing.T) { + readinessProbe := &core.Probe{ + Handler: core.Handler{ + HTTPGet: &core.HTTPGetAction{ + Path: "/", + Port: intstr.IntOrString{ + Type: 0, + IntVal: int32(9104), + }, + }, + }, + InitialDelaySeconds: 5, + TimeoutSeconds: 1, + PeriodSeconds: 10, + SuccessThreshold: 1, + FailureThreshold: 3, + } + assert.Equal(t, readinessProbe, metricsCase.ReadinessProbe) +} +func TestGetMetricsVolumeMounts(t *testing.T) { + + assert.Nil(t, metricsCase.VolumeMounts) +} diff --git a/cluster/container/mysql_test.go b/cluster/container/mysql_test.go new file mode 100644 index 000000000..3d2431bd9 --- /dev/null +++ b/cluster/container/mysql_test.go @@ -0,0 +1,135 @@ +package container + +import ( + "testing" + + "github.com/stretchr/testify/assert" + + mysqlv1 "github.com/radondb/radondb-mysql-kubernetes/api/v1alpha1" + "github.com/radondb/radondb-mysql-kubernetes/cluster" + + core "k8s.io/api/core/v1" +) + +var ( + mysqlMysqlCluster = mysqlv1.Cluster{ + Spec: mysqlv1.ClusterSpec{ + PodSpec: mysqlv1.PodSpec{ + Resources: core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, + }, + MysqlVersion: "5.7", + MysqlOpts: mysqlv1.MysqlOpts{ + InitTokuDB: false, + }, + }, + } + testMysqlCluster = cluster.Cluster{ + Cluster: &mysqlMysqlCluster, + } + mysqlCase = EnsureContainer("mysql", &testMysqlCluster) +) + +func TestGetMysqlName(t *testing.T) { + assert.Equal(t, "mysql", mysqlCase.Name) +} +func TestGetMysqlImage(t *testing.T) { + assert.Equal(t, "percona/percona-server:5.7.33", mysqlCase.Image) +} +func TestGetMysqlCommand(t *testing.T) { + assert.Nil(t, mysqlCase.Command) +} +func TestGetMysqlEnvVar(t *testing.T) { + //base env + { + assert.Nil(t, mysqlCase.Env) + } + //initTokuDB + { + volumeMounts := []core.EnvVar{ + { + Name: "INIT_TOKUDB", + Value: "1", + }, + } + mysqlCluster := mysqlMysqlCluster + mysqlCluster.Spec.MysqlOpts.InitTokuDB = true + testCluster := cluster.Cluster{ + Cluster: &mysqlCluster, + } + mysqlCase = EnsureContainer("mysql", &testCluster) + assert.Equal(t, volumeMounts, mysqlCase.Env) + } +} +func TestGetMysqlLifecycle(t *testing.T) { + assert.Nil(t, mysqlCase.Lifecycle) +} +func TestGetMysqlResources(t *testing.T) { + assert.Equal(t, core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, mysqlCase.Resources) +} +func TestGetMysqlPorts(t *testing.T) { + port := []core.ContainerPort{ + { + Name: "mysql", + ContainerPort: 3306, + }, + } + assert.Equal(t, port, mysqlCase.Ports) +} +func TestGetMysqlLivenessProbe(t *testing.T) { + livenessProbe := &core.Probe{ + Handler: core.Handler{ + Exec: &core.ExecAction{ + Command: []string{"sh", "-c", "mysqladmin ping -uroot -p${MYSQL_ROOT_PASSWORD}"}, + }, + }, + InitialDelaySeconds: 30, + TimeoutSeconds: 5, + PeriodSeconds: 10, + SuccessThreshold: 1, + FailureThreshold: 3, + } + assert.Equal(t, livenessProbe, mysqlCase.LivenessProbe) +} +func TestGetMysqlReadinessProbe(t *testing.T) { + readinessProbe := &core.Probe{ + Handler: core.Handler{ + Exec: &core.ExecAction{ + Command: []string{"sh", "-c", `mysql -uroot -p${MYSQL_ROOT_PASSWORD} -e "SELECT 1"`}, + }, + }, + InitialDelaySeconds: 10, + TimeoutSeconds: 1, + PeriodSeconds: 10, + SuccessThreshold: 1, + FailureThreshold: 3, + } + assert.Equal(t, readinessProbe, mysqlCase.ReadinessProbe) +} +func TestGetMysqlVolumeMounts(t *testing.T) { + volumeMounts := []core.VolumeMount{ + { + Name: "conf", + MountPath: "/etc/mysql/conf.d", + }, + { + Name: "config-map", + MountPath: "/etc/mysql/my.cnf", + SubPath: "my.cnf", + }, + { + Name: "data", + MountPath: "/var/lib/mysql", + }, + { + Name: "logs", + MountPath: "/var/log/mysql", + }, + } + assert.Equal(t, volumeMounts, mysqlCase.VolumeMounts) +} diff --git a/cluster/container/slowlog_test.go b/cluster/container/slowlog_test.go new file mode 100644 index 000000000..28d2757e6 --- /dev/null +++ b/cluster/container/slowlog_test.go @@ -0,0 +1,70 @@ +package container + +import ( + "testing" + + mysqlv1 "github.com/radondb/radondb-mysql-kubernetes/api/v1alpha1" + "github.com/radondb/radondb-mysql-kubernetes/cluster" + "github.com/stretchr/testify/assert" + + core "k8s.io/api/core/v1" +) + +var ( + slowlogMysqlCluster = mysqlv1.Cluster{ + Spec: mysqlv1.ClusterSpec{ + PodSpec: mysqlv1.PodSpec{ + SidecarImage: "sidecar image", + Resources: core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, + }, + }, + } + testSlowlogCluster = cluster.Cluster{ + Cluster: &slowlogMysqlCluster, + } + slowlogCase = EnsureContainer("slowlog", &testSlowlogCluster) +) + +func TestGetSlowlogName(t *testing.T) { + assert.Equal(t, "slowlog", slowlogCase.Name) +} +func TestGetSlowlogImage(t *testing.T) { + assert.Equal(t, "sidecar image", slowlogCase.Image) +} +func TestGetSlowlogCommand(t *testing.T) { + command := []string{"tail", "-f", "/var/log/mysql" + "/mysql-slow.log"} + assert.Equal(t, command, slowlogCase.Command) +} +func TestGetSlowlogEnvVar(t *testing.T) { + assert.Nil(t, slowlogCase.Env) +} +func TestGetSlowlogLifecycle(t *testing.T) { + assert.Nil(t, slowlogCase.Lifecycle) +} +func TestGetSlowlogResources(t *testing.T) { + assert.Equal(t, core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, slowlogCase.Resources) +} +func TestGetSlowlogPorts(t *testing.T) { + assert.Nil(t, slowlogCase.Ports) +} +func TestGetSlowlogLivenessProbe(t *testing.T) { + assert.Nil(t, slowlogCase.LivenessProbe) +} +func TestGetSlowlogReadinessProbe(t *testing.T) { + assert.Nil(t, slowlogCase.ReadinessProbe) +} +func TestGetSlowlogVolumeMounts(t *testing.T) { + volumeMounts := []core.VolumeMount{ + { + Name: "logs", + MountPath: "/var/log/mysql", + }, + } + assert.Equal(t, volumeMounts, slowlogCase.VolumeMounts) +} diff --git a/cluster/container/xenon_test.go b/cluster/container/xenon_test.go new file mode 100644 index 000000000..91a50f540 --- /dev/null +++ b/cluster/container/xenon_test.go @@ -0,0 +1,121 @@ +package container + +import ( + "testing" + + mysqlv1 "github.com/radondb/radondb-mysql-kubernetes/api/v1alpha1" + "github.com/radondb/radondb-mysql-kubernetes/cluster" + "github.com/stretchr/testify/assert" + v1 "k8s.io/apimachinery/pkg/apis/meta/v1" + + core "k8s.io/api/core/v1" +) + +var ( + xenonReplicas int32 = 1 + xenonMysqlCluster = mysqlv1.Cluster{ + ObjectMeta: v1.ObjectMeta{ + Name: "sample", + Namespace: "default", + }, + Spec: mysqlv1.ClusterSpec{ + PodSpec: mysqlv1.PodSpec{ + Resources: core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, + }, + XenonOpts: mysqlv1.XenonOpts{ + Image: "xenon image", + }, + Replicas: &xenonReplicas, + }, + } + testXenonCluster = cluster.Cluster{ + Cluster: &xenonMysqlCluster, + } + xenonCase = EnsureContainer("xenon", &testXenonCluster) +) + +func TestGetXenonName(t *testing.T) { + assert.Equal(t, "xenon", xenonCase.Name) +} +func TestGetXenonImage(t *testing.T) { + assert.Equal(t, "xenon image", xenonCase.Image) +} +func TestGetXenonCommand(t *testing.T) { + assert.Nil(t, xenonCase.Command) +} +func TestGetXenonEnvVar(t *testing.T) { + assert.Nil(t, xenonCase.Env) +} +func TestGetXenonLifecycle(t *testing.T) { + lifecycle := &core.Lifecycle{ + PostStart: &core.Handler{ + Exec: &core.ExecAction{ + Command: []string{"sh", "-c", + "until (xenoncli xenon ping && xenoncli cluster add sample-mysql-0.sample-mysql.default:8801) > /dev/null 2>&1; do sleep 2; done", + }, + }, + }, + } + assert.Equal(t, lifecycle, xenonCase.Lifecycle) +} +func TestGetXenonResources(t *testing.T) { + assert.Equal(t, core.ResourceRequirements{ + Limits: nil, + Requests: nil, + }, xenonCase.Resources) +} +func TestGetXenonPorts(t *testing.T) { + port := []core.ContainerPort{ + { + Name: "xenon", + ContainerPort: 8801, + }, + } + assert.Equal(t, port, xenonCase.Ports) +} +func TestGetXenonLivenessProbe(t *testing.T) { + livenessProbe := &core.Probe{ + Handler: core.Handler{ + Exec: &core.ExecAction{ + Command: []string{"pgrep", "xenon"}, + }, + }, + InitialDelaySeconds: 30, + TimeoutSeconds: 5, + PeriodSeconds: 10, + SuccessThreshold: 1, + FailureThreshold: 3, + } + assert.Equal(t, livenessProbe, xenonCase.LivenessProbe) +} +func TestGetXenonReadinessProbe(t *testing.T) { + readinessProbe := &core.Probe{ + Handler: core.Handler{ + Exec: &core.ExecAction{ + Command: []string{"sh", "-c", "xenoncli xenon ping"}, + }, + }, + InitialDelaySeconds: 10, + TimeoutSeconds: 1, + PeriodSeconds: 10, + SuccessThreshold: 1, + FailureThreshold: 3, + } + assert.Equal(t, readinessProbe, xenonCase.ReadinessProbe) +} +func TestGetXenonVolumeMounts(t *testing.T) { + volumeMounts := []core.VolumeMount{ + { + Name: "scripts", + MountPath: "/scripts", + }, + { + Name: "xenon", + MountPath: "/etc/xenon", + }, + } + assert.Equal(t, volumeMounts, xenonCase.VolumeMounts) +} diff --git a/go.mod b/go.mod index ba31fc67b..3700a6123 100644 --- a/go.mod +++ b/go.mod @@ -3,6 +3,7 @@ module github.com/radondb/radondb-mysql-kubernetes go 1.16 require ( + bou.ke/monkey v1.0.2 github.com/blang/semver v3.5.1+incompatible github.com/go-ini/ini v1.62.0 github.com/go-sql-driver/mysql v1.6.0 @@ -11,6 +12,7 @@ require ( github.com/onsi/gomega v1.10.5 github.com/presslabs/controller-util v0.3.0-alpha.2 github.com/spf13/cobra v1.1.1 + github.com/stretchr/testify v1.6.1 k8s.io/api v0.20.4 k8s.io/apimachinery v0.20.4 k8s.io/client-go v0.20.4 diff --git a/go.sum b/go.sum index d1d18c23e..afcaf134b 100644 --- a/go.sum +++ b/go.sum @@ -1,3 +1,5 @@ +bou.ke/monkey v1.0.2 h1:kWcnsrCNUatbxncxR/ThdYqbytgOIArtYWqcQLQzKLI= +bou.ke/monkey v1.0.2/go.mod h1:OqickVX3tNx6t33n1xvtTtu85YN5s6cKwVug+oHMaIA= cloud.google.com/go v0.26.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= cloud.google.com/go v0.34.0/go.mod h1:aQUYkXzVsufM+DwF1aE+0xfcU+56JwCaLick0ClmMTw= cloud.google.com/go v0.38.0/go.mod h1:990N+gfupTy94rShfmMCWGDn0LpTmnzTp2qbd1dvSRU=