diff --git a/internal/controller/reconcilers/configmap_reconciler.go b/internal/controller/reconcilers/configmap_reconciler.go new file mode 100644 index 0000000..7b96fb1 --- /dev/null +++ b/internal/controller/reconcilers/configmap_reconciler.go @@ -0,0 +1,99 @@ +package reconcilers + +import ( + _ "embed" + + "context" + cachev1alpha1 "github.com/tomp21/yazio-challenge/api/v1alpha1" + "github.com/tomp21/yazio-challenge/internal/util" + corev1 "k8s.io/api/core/v1" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/apimachinery/pkg/runtime" + "sigs.k8s.io/controller-runtime/pkg/client" + "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" +) + +//go:embed configmaps/scripts/start-master.sh +var masterStartScript string + +//go:embed configmaps/scripts/start-replica.sh +var replicaStartScript string + +//go:embed configmaps/conf/redis.conf +var redisAllConf string + +//go:embed configmaps/conf/master.conf +var redisMasterConf string + +//go:embed configmaps/conf/replica.conf +var redisReplicaConf string + +type ConfigMapReconciler struct { + client *client.Client + scheme *runtime.Scheme +} + +func NewConfigMapReconciler(client *client.Client, scheme *runtime.Scheme) *ConfigMapReconciler { + return &ConfigMapReconciler{ + client: client, + scheme: scheme, + } +} + +func (r *ConfigMapReconciler) Reconcile(ctx context.Context, redis *cachev1alpha1.Redis) error { + err := r.ReconcileStartScripts(ctx, redis) + if err != nil { + return err + } + err = r.ReconcileConfigs(ctx, redis) + if err != nil { + return err + } + return nil +} + +func (r *ConfigMapReconciler) ReconcileStartScripts(ctx context.Context, redis *cachev1alpha1.Redis) error { + cmStartScripts := &corev1.ConfigMap{ + ObjectMeta: metav1.ObjectMeta{ + Name: "start-scripts", + Namespace: redis.Namespace, + Labels: util.GetLabels(redis, nil), + }, + Data: map[string]string{ + "start-master.sh": masterStartScript, + "start-replica.sh": replicaStartScript, + }, + } + _, err := controllerutil.CreateOrUpdate(ctx, *r.client, cmStartScripts, func() error { + return controllerutil.SetControllerReference(redis, cmStartScripts, r.scheme) + }) + if err != nil { + return err + } + return nil +} + +func (r *ConfigMapReconciler) ReconcileConfigs(ctx context.Context, redis *cachev1alpha1.Redis) error { + cmConfig := &corev1.ConfigMap{ + ObjectMeta: metav1.ObjectMeta{ + Name: "redis-conf", + Namespace: redis.Namespace, + Labels: util.GetLabels(redis, nil), + }, + Data: map[string]string{ + "redis.conf": redisAllConf, + "master.conf": redisMasterConf, + "replica.conf": redisReplicaConf, + }, + } + + _, err := controllerutil.CreateOrUpdate(ctx, *r.client, cmConfig, func() error { + return controllerutil.SetControllerReference(redis, cmConfig, r.scheme) + }) + + if err != nil { + return err + } + + return nil +} diff --git a/internal/controller/reconcilers/configmaps/conf/master.conf b/internal/controller/reconcilers/configmaps/conf/master.conf new file mode 100644 index 0000000..ea7639e --- /dev/null +++ b/internal/controller/reconcilers/configmaps/conf/master.conf @@ -0,0 +1,5 @@ +dir /data +# User-supplied master configuration: +rename-command FLUSHDB "" +rename-command FLUSHALL "" +# End of master configuration diff --git a/internal/controller/reconcilers/configmaps/conf/redis.conf b/internal/controller/reconcilers/configmaps/conf/redis.conf new file mode 100644 index 0000000..62f1ed6 --- /dev/null +++ b/internal/controller/reconcilers/configmaps/conf/redis.conf @@ -0,0 +1,6 @@ +# User-supplied common configuration: +# Enable AOF https://redis.io/topics/persistence#append-only-file +appendonly yes +# Disable RDB persistence, AOF persistence already enabled. +save "" +# End of common configuration diff --git a/internal/controller/reconcilers/configmaps/conf/replica.conf b/internal/controller/reconcilers/configmaps/conf/replica.conf new file mode 100644 index 0000000..e69de29 diff --git a/internal/controller/reconcilers/configmaps/scripts/start-master.sh b/internal/controller/reconcilers/configmaps/scripts/start-master.sh new file mode 100644 index 0000000..4284839 --- /dev/null +++ b/internal/controller/reconcilers/configmaps/scripts/start-master.sh @@ -0,0 +1,15 @@ +#!/bin/bash + +[[ -f $REDIS_PASSWORD_FILE ]] && export REDIS_PASSWORD="$(< "${REDIS_PASSWORD_FILE}")" +if [[ -f /opt/bitnami/redis/mounted-etc/master.conf ]];then + cp /opt/bitnami/redis/mounted-etc/master.conf /opt/bitnami/redis/etc/master.conf +fi +if [[ -f /opt/bitnami/redis/mounted-etc/redis.conf ]];then + cp /opt/bitnami/redis/mounted-etc/redis.conf /opt/bitnami/redis/etc/redis.conf +fi +ARGS=("--port" "${REDIS_PORT}") +ARGS+=("--requirepass" "${REDIS_PASSWORD}") +ARGS+=("--masterauth" "${REDIS_PASSWORD}") +ARGS+=("--include" "/opt/bitnami/redis/etc/redis.conf") +ARGS+=("--include" "/opt/bitnami/redis/etc/master.conf") +exec redis-server "${ARGS[@]}" diff --git a/internal/controller/reconcilers/configmaps/scripts/start-replica.sh b/internal/controller/reconcilers/configmaps/scripts/start-replica.sh new file mode 100644 index 0000000..4ba65e4 --- /dev/null +++ b/internal/controller/reconcilers/configmaps/scripts/start-replica.sh @@ -0,0 +1,50 @@ +#!/bin/bash + +get_port() { + hostname="$1" + type="$2" + + port_var=$(echo "${hostname^^}_SERVICE_PORT_$type" | sed "s/-/_/g") + port=${!port_var} + + if [ -z "$port" ]; then + case $type in + "SENTINEL") + echo 26379 + ;; + "REDIS") + echo 6379 + ;; + esac + else + echo $port + fi +} + +get_full_hostname() { + hostname="$1" + full_hostname="${hostname}.${HEADLESS_SERVICE}" + echo "${full_hostname}" +} + +REDISPORT=$(get_port "$HOSTNAME" "REDIS") + +[[ -f $REDIS_PASSWORD_FILE ]] && export REDIS_PASSWORD="$(< "${REDIS_PASSWORD_FILE}")" +[[ -f $REDIS_MASTER_PASSWORD_FILE ]] && export REDIS_MASTER_PASSWORD="$(< "${REDIS_MASTER_PASSWORD_FILE}")" +if [[ -f /opt/bitnami/redis/mounted-etc/replica.conf ]];then + cp /opt/bitnami/redis/mounted-etc/replica.conf /opt/bitnami/redis/etc/replica.conf +fi +if [[ -f /opt/bitnami/redis/mounted-etc/redis.conf ]];then + cp /opt/bitnami/redis/mounted-etc/redis.conf /opt/bitnami/redis/etc/redis.conf +fi + +echo "" >> /opt/bitnami/redis/etc/replica.conf +echo "replica-announce-port $REDISPORT" >> /opt/bitnami/redis/etc/replica.conf +echo "replica-announce-ip $(get_full_hostname "$HOSTNAME")" >> /opt/bitnami/redis/etc/replica.conf +ARGS=("--port" "${REDIS_PORT}") +ARGS+=("--replicaof" "${REDIS_MASTER_HOST}" "${REDIS_MASTER_PORT_NUMBER}") +ARGS+=("--requirepass" "${REDIS_PASSWORD}") +ARGS+=("--masterauth" "${REDIS_MASTER_PASSWORD}") +ARGS+=("--include" "/opt/bitnami/redis/etc/redis.conf") +ARGS+=("--include" "/opt/bitnami/redis/etc/replica.conf") +exec redis-server "${ARGS[@]}"