Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
52 changes: 25 additions & 27 deletions controllers/redis_manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -420,13 +420,6 @@ func (r *RedkeyClusterReconciler) doSlowUpgradeUpgrading(ctx context.Context, re
return err
}

// Reset node
err = redkeyRobin.ClusterResetNode(currentPartition)
if err != nil {
r.logError(redkeyCluster.NamespacedName(), err, "Error from Robin forgeting the node", "node index", currentPartition)
return err
}

err = r.updateClusterSubStatus(ctx, redkeyCluster, redkeyv1.SubstatusRollingConfig, strconv.Itoa(currentPartition))
if err != nil {
r.logError(redkeyCluster.NamespacedName(), err, "Error updating substatus")
Expand Down Expand Up @@ -460,6 +453,20 @@ func (r *RedkeyClusterReconciler) doSlowUpgradeRollingUpdate(ctx context.Context
return err
}

// Get the current partition
currentPartition, err := strconv.Atoi(redkeyCluster.Status.Substatus.UpgradingPartition)
if err != nil {
r.logError(redkeyCluster.NamespacedName(), err, "Error getting Upgrading Partition from RedkeyCluster object")
return err
}

// Reset node
err = redkeyRobin.ClusterResetNode(currentPartition)
if err != nil {
r.logError(redkeyCluster.NamespacedName(), err, "Error from Robin forgeting the node", "node index", currentPartition)
return err
}

// Check all cluster nodes are ready from Robin.
clusterNodes, err := redkeyRobin.GetClusterNodes()
if err != nil {
Expand All @@ -482,23 +489,6 @@ func (r *RedkeyClusterReconciler) doSlowUpgradeRollingUpdate(ctx context.Context
return nil // Cluster not ready --> keep waiting
}

// Get the current partition and update Upgrading Partition in RedkeyCluster Status if starting iterating over partitions.
var currentPartition int
if redkeyCluster.Status.Substatus.UpgradingPartition == "" {
currentPartition = int(*(existingStatefulSet.Spec.Replicas)) - 1
err := r.updateClusterSubStatus(ctx, redkeyCluster, redkeyv1.SubstatusSlowUpgrading, strconv.Itoa(currentPartition))
if err != nil {
r.logError(redkeyCluster.NamespacedName(), err, "Error updating substatus")
return err
}
} else {
currentPartition, err = strconv.Atoi(redkeyCluster.Status.Substatus.UpgradingPartition)
if err != nil {
r.logError(redkeyCluster.NamespacedName(), err, "Error getting Upgrading Partition from RedkeyCluster object")
return err
}
}

// If first partition reached, we can move to the next step.
// Else step over to the next partition.
if currentPartition == 0 {
Expand Down Expand Up @@ -820,10 +810,18 @@ func (r *RedkeyClusterReconciler) doFastScaling(ctx context.Context, redkeyClust
return true, err
}

err = robin.SetAndPersistRobinStatus(ctx, r.Client, redkeyCluster, redkeyv1.RobinStatusScalingUp)
if err != nil {
r.logError(redkeyCluster.NamespacedName(), err, "Error updating/persisting Robin status", "status", redkeyv1.RobinStatusScalingUp)
return true, err
}

return true, nil
case redkeyv1.SubstatusEndingFastScaling:
// Rebuilding the cluster after recreating all node pods. Check if the cluster is ready to end the Fast scaling.
logger := r.getHelperLogger(redkeyCluster.NamespacedName())

r.logInfo(redkeyCluster.NamespacedName(), "Finishing fast scaling")
robin, err := robin.NewRobin(ctx, r.Client, redkeyCluster, logger)
if err != nil {
r.logError(redkeyCluster.NamespacedName(), err, "Error getting Robin to check its readiness")
Expand Down Expand Up @@ -999,10 +997,10 @@ func (r *RedkeyClusterReconciler) scaleDownCluster(ctx context.Context, redkeyCl
existingPrimaryNodes := len(clusterNodes.GetPrimaryNodes())
existingReplicaNodes := len(clusterNodes.GetReplicaNodes())
expectedPrimaryNodes := int(redkeyCluster.Spec.Primaries)
expectedRelicaNodes := int(redkeyCluster.Spec.Primaries * redkeyCluster.Spec.ReplicasPerPrimary)
if existingPrimaryNodes != expectedPrimaryNodes || existingReplicaNodes != expectedRelicaNodes {
expectedReplicaNodes := int(redkeyCluster.Spec.Primaries * redkeyCluster.Spec.ReplicasPerPrimary)
if existingPrimaryNodes != expectedPrimaryNodes || existingReplicaNodes != expectedReplicaNodes {
r.logInfo(redkeyCluster.NamespacedName(), "Waiting for Robin to scale the cluster", "expected primary nodes", expectedPrimaryNodes,
"existing primary nodes", existingPrimaryNodes, "expected replica nodes", expectedRelicaNodes,
"existing primary nodes", existingPrimaryNodes, "expected replica nodes", expectedReplicaNodes,
"existing replica nodes", existingReplicaNodes)
return true, nil // Requeue
}
Expand Down
1 change: 1 addition & 0 deletions controllers/redkeycluster_manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,7 @@ func (r *RedkeyClusterReconciler) ReconcileClusterObject(ctx context.Context, re
err = r.clusterScaledToZeroPrimaries(ctx, redkeyCluster)
if err != nil {
r.logError(redkeyCluster.NamespacedName(), err, "Error managing cluster scaled to 0 primaries")
return ctrl.Result{RequeueAfter: time.Second * ErrorRequeueTimeout}, err
}

// Requeue to recheck, reconciliation ends here!
Expand Down
9 changes: 8 additions & 1 deletion controllers/robin.go
Original file line number Diff line number Diff line change
Expand Up @@ -83,7 +83,8 @@ func (r *RedkeyClusterReconciler) handleRobinConfig(ctx context.Context, req ctr
return nil // No changes detected, no more to do here
}

// Robin configmap changed: update configmap
// Robin config changed: update configmap
r.logInfo(req.NamespacedName, "Robin's configuration has changed, updating ConfigMap")

// Serialize robin configuration to YAML
configYAML, err := yaml.Marshal(declaredConfig)
Expand Down Expand Up @@ -139,6 +140,12 @@ func (r *RedkeyClusterReconciler) handleRobinDeployment(ctx context.Context, req
replicas := int32(1)
deployment.Spec.Replicas = &replicas
changed = true

// Update replicas in robin configuration
err = robin.PersistRobinReplicas(ctx, r.Client, redkeyCluster, int(redkeyCluster.Spec.Primaries), int(redkeyCluster.Spec.ReplicasPerPrimary))
if err != nil {
r.logError(redkeyCluster.NamespacedName(), err, "Error persisting Robin primaries/replicasPerPrimary")
}
}

if !changed {
Expand Down
2 changes: 1 addition & 1 deletion controllers/status.go
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ func (r *RedkeyClusterReconciler) updateClusterStatus(ctx context.Context, redke
// Update Robin status
// Do not update if we are switching to Initializing status because Robin needs some
// time to be ready to accept API requests.
if redkeyCluster.Status.Status != redkeyv1.StatusInitializing {
if redkeyCluster.Status.Status != redkeyv1.StatusInitializing && redkeyCluster.Spec.Primaries > 0 {
logger := r.getHelperLogger(redkeyCluster.NamespacedName())
robin, err := robin.NewRobin(ctx, r.Client, redkeyCluster, logger)
if err != nil {
Expand Down
17 changes: 15 additions & 2 deletions internal/robin/robin.go
Original file line number Diff line number Diff line change
Expand Up @@ -386,7 +386,11 @@ func (r *Robin) GetClusterStatus() (string, error) {
}

func doSimpleGet(url string) ([]byte, error) {
resp, err := http.Get(url)
client := &http.Client{
Timeout: time.Second * 10,
}

resp, err := client.Get(url)
if err != nil {
return nil, err
}
Expand All @@ -400,7 +404,9 @@ func doSimpleGet(url string) ([]byte, error) {
}

func doPut(url string, payload []byte) ([]byte, error) {
client := &http.Client{}
client := &http.Client{
Timeout: time.Second * 20,
}

req, err := http.NewRequest(http.MethodPut, url, bytes.NewBuffer(payload))
req.Header.Set("Content-Type", "application/json")
Expand All @@ -425,8 +431,15 @@ func doPut(url string, payload []byte) ([]byte, error) {
func CompareConfigurations(a, b *Configuration) bool {
a2 := new(Configuration)
*a2 = *a

// Normalize nil vs empty slice for RedisInfoKeys. This is needed because comparing a nil slice with an empty slice returns false.
if len(b.Redis.Metrics.RedisInfoKeys) == 0 {
a2.Redis.Metrics.RedisInfoKeys = []string{}
}

a2.Redis.Cluster.Status = b.Redis.Cluster.Status
a2.Redis.Cluster.Primaries = b.Redis.Cluster.Primaries
a2.Redis.Cluster.ReplicasPerPrimary = b.Redis.Cluster.ReplicasPerPrimary
return reflect.DeepEqual(a2, b)
}

Expand Down
2 changes: 1 addition & 1 deletion test/cmd/k6scripts/test-300k.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
// SPDX-License-Identifier: Apache-2.0

/*
Test that imitates a redis-cluster that was causing rebalancing errors:
Test that imitates a redkey-cluster that was causing rebalancing errors:
- Value Size: 1Byte - 300KBytes
- Timeout: 30s
- Some deletes
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
apiVersion: v1
kind: ServiceAccount
metadata:
name: redis-operator-sa
name: redkey-operator-sa
---
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
Expand Down Expand Up @@ -37,7 +37,7 @@ rules:
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:
name: redis-operator-role
name: redkey-operator-role
rules:
- apiGroups:
- ""
Expand Down Expand Up @@ -140,7 +140,7 @@ kind: ClusterRole
metadata:
labels:
rbac.authorization.k8s.io/aggregate-to-admin: "true"
name: redis-operator-role
name: redkey-operator-role
rules:
- apiGroups:
- ""
Expand Down Expand Up @@ -263,19 +263,19 @@ roleRef:
name: leader-election-role
subjects:
- kind: ServiceAccount
name: redis-operator-sa
name: redkey-operator-sa
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:
name: redis-operator-rolebinding
name: redkey-operator-rolebinding
roleRef:
apiGroup: rbac.authorization.k8s.io
kind: Role
name: redis-operator-role
name: redkey-operator-role
subjects:
- kind: ServiceAccount
name: redis-operator-sa
name: redkey-operator-sa
---
apiVersion: v1
data:
Expand All @@ -291,19 +291,19 @@ data:
resourceName: db95d8a6.inditex.com
kind: ConfigMap
metadata:
name: redis-operator-config
name: redkey-operator-config
---
apiVersion: apps/v1
kind: Deployment
metadata:
labels:
control-plane: redis-operator
name: redis-operator
control-plane: redkey-operator
name: redkey-operator
spec:
primaries: 1
selector:
matchLabels:
control-plane: redis-operator
control-plane: redkey-operator
template:
metadata:
annotations:
Expand All @@ -312,7 +312,7 @@ spec:
prometheus.io/scheme: http
prometheus.io/scrape: "true"
labels:
control-plane: redis-operator
control-plane: redkey-operator
domain: DOMAIN
environment: ENVIRONMENT
layer: middleware-redkeyoperator
Expand All @@ -333,9 +333,9 @@ spec:
valueFrom:
fieldRef:
fieldPath: metadata.namespace
image: redis-operator:0.1.0-test
image: redkey-operator:0.1.0-test
imagePullPolicy: IfNotPresent
name: redis-operator
name: redkey-operator
resources:
limits:
cpu: 300m
Expand All @@ -347,5 +347,5 @@ spec:
allowPrivilegeEscalation: false
securityContext:
runAsNonRoot: true
serviceAccountName: redis-operator-sa
serviceAccountName: redkey-operator-sa
terminationGracePeriodSeconds: 10
10 changes: 5 additions & 5 deletions test/cmd/manifests/rdcl-test-local.yml
Original file line number Diff line number Diff line change
Expand Up @@ -8,16 +8,16 @@ metadata:
annotations:
amiga-admin: ""
paas-details: |
{"workloads":[{"kind":"StatefulSet", "name":"redis-cluster-test"}]}
{"workloads":[{"kind":"StatefulSet", "name":"redkey-cluster-test"}]}
technology: redis_7.4.0
labels:
app: redis-cluster-test
app: redkey-cluster-test
slot: test
technology: redis_7.4.0
version: 7.4.0
redkey-cluster-name: redis-cluster-test
redkey-cluster-name: redkey-cluster-test
redis.redkeycluster.operator/component: redis
name: redis-cluster-test
name: redkey-cluster-test
spec:
config: |
save ""
Expand All @@ -28,7 +28,7 @@ spec:
image: redis/redis-stack-server:7.4.0-v3
labels:
application: greta
deployment: redis-cluster-test
deployment: redkey-cluster-test
domain: comdistrib
environment: pre
slot: test
Expand Down
10 changes: 5 additions & 5 deletions test/cmd/manifests/rdcl-test-loki-local.yml
Original file line number Diff line number Diff line change
Expand Up @@ -8,20 +8,20 @@ metadata:
annotations:
amiga-admin: ""
paas-details: |
{"workloads":[{"kind":"StatefulSet", "name":"redis-cluster-test"}]}
{"workloads":[{"kind":"StatefulSet", "name":"redkey-cluster-test"}]}
technology: redis_7.4.0
nodes-extra-annotations: |
{"log-format": "lineformat"}
nodes-extra-labels: |
{"log-scrape": "true"}
labels:
app: redis-cluster-test
app: redkey-cluster-test
slot: test
technology: redis_7.4.0
version: 7.4.0
redkey-cluster-name: redis-cluster-test
redkey-cluster-name: redkey-cluster-test
redis.redkeycluster.operator/component: redis
name: redis-cluster-test
name: redkey-cluster-test
spec:
config: |
save ""
Expand All @@ -32,7 +32,7 @@ spec:
image: redis/redis-stack-server:7.4.0-v3
labels:
application: redis-app
deployment: redis-cluster-test
deployment: redkey-cluster-test
slot: test
technology: redis_7.4.0
version: 7.4.0
Expand Down
10 changes: 5 additions & 5 deletions test/cmd/manifests/rdcl-test-size-local.yml
Original file line number Diff line number Diff line change
Expand Up @@ -8,17 +8,17 @@ metadata:
annotations:
amiga-admin: ""
paas-details: |
{"workloads":[{"kind":"StatefulSet", "name":"redis-cluster-test"}]}
{"workloads":[{"kind":"StatefulSet", "name":"redkey-cluster-test"}]}
technology: redis_7.4.0
labels:
app: redis-cluster-test
app: redkey-cluster-test
application: redis-app
slot: test
technology: redis_7.4.0
version: 7.4.0
redkey-cluster-name: redis-cluster-test
redkey-cluster-name: redkey-cluster-test
redis.redkeycluster.operator/component: redis
name: redis-cluster-test
name: redkey-cluster-test
spec:
config: |
save ""
Expand All @@ -30,7 +30,7 @@ spec:
image: redis/redis-stack-server:7.4.0-v3
labels:
application: redis-app
deployment: redis-cluster-test
deployment: redkey-cluster-test
slot: test
technology: redis_7.4.0
version: 7.4.0
Expand Down
File renamed without changes.
Loading