diff --git a/api/v1alpha1/repo_types.go b/api/v1alpha1/repo_types.go index 6c3b622..b124b32 100644 --- a/api/v1alpha1/repo_types.go +++ b/api/v1alpha1/repo_types.go @@ -30,8 +30,6 @@ const ( AWS_SECRET_ACCESS_KEY = "AWS_SECRET_ACCESS_KEY" ) -// EDIT THIS FILE! THIS IS SCAFFOLDING FOR YOU TO OWN! -// NOTE: json tags are required. Any new fields you add must have json tags for the fields to be serialized. type S3 struct { Server string `json:"server"` Bucket string `json:"bucket"` @@ -39,11 +37,15 @@ type S3 struct { Prefix string `json:"prefix,omitempty"` } +type Local struct { + Path string `json:"path"` +} + type Backend struct { // +optional S3 *S3 `json:"s3,omitempty"` // +optional - Nfs *string `json:"nfs,omitempty"` + Local *Local `json:"local,omitempty"` } // RepoSpec defines the desired state of Repo @@ -96,7 +98,6 @@ func (repo *Repo) GetResticEnv(backupConf BackupConfiguration) []corev1.EnvVar { for _, key := range []string{ AWS_ACCESS_KEY_ID, AWS_SECRET_ACCESS_KEY, - RESTIC_PASSWORD, } { env = append(env, corev1.EnvVar{ Name: key, @@ -111,6 +112,23 @@ func (repo *Repo) GetResticEnv(backupConf BackupConfiguration) []corev1.EnvVar { }) } } + if repo.Spec.Backend.Local != nil { + env = append(env, corev1.EnvVar{ + Name: RESTIC_REPOSITORY, + Value: repo.Spec.Backend.Local.Path, + }) + } + env = append(env, corev1.EnvVar{ + Name: RESTIC_PASSWORD, + ValueFrom: &corev1.EnvVarSource{ + SecretKeyRef: &corev1.SecretKeySelector{ + LocalObjectReference: corev1.LocalObjectReference{ + Name: repo.Spec.RepositorySecrets, + }, + Key: RESTIC_PASSWORD, + }, + }, + }) return env } diff --git a/api/v1alpha1/zz_generated.deepcopy.go b/api/v1alpha1/zz_generated.deepcopy.go index 3cd2fac..e8cf666 100644 --- a/api/v1alpha1/zz_generated.deepcopy.go +++ b/api/v1alpha1/zz_generated.deepcopy.go @@ -34,9 +34,9 @@ func (in *Backend) DeepCopyInto(out *Backend) { *out = new(S3) **out = **in } - if in.Nfs != nil { - in, out := &in.Nfs, &out.Nfs - *out = new(string) + if in.Local != nil { + in, out := &in.Local, &out.Local + *out = new(Local) **out = **in } } @@ -347,6 +347,21 @@ func (in *Keep) DeepCopy() *Keep { return out } +// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. +func (in *Local) DeepCopyInto(out *Local) { + *out = *in +} + +// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new Local. +func (in *Local) DeepCopy() *Local { + if in == nil { + return nil + } + out := new(Local) + in.DeepCopyInto(out) + return out +} + // DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil. func (in *Repo) DeepCopyInto(out *Repo) { *out = *in diff --git a/controllers/backupconfiguration_controller_helpers.go b/controllers/backupconfiguration_controller_helpers.go index 7de1a43..6770056 100644 --- a/controllers/backupconfiguration_controller_helpers.go +++ b/controllers/backupconfiguration_controller_helpers.go @@ -150,30 +150,54 @@ func (r *BackupConfigurationReconciler) DeleteSidecar(backupConf formolv1alpha1. } } } + repo := formolv1alpha1.Repo{} + if err := r.Get(r.Context, client.ObjectKey{ + Namespace: backupConf.Namespace, + Name: backupConf.Spec.Repository, + }, &repo); err != nil { + r.Log.Error(err, "unable to get Repo") + return err + } + r.Log.V(1).Info("Got Repository", "repo", repo) for _, target := range backupConf.Spec.Targets { + var targetObject client.Object + var targetPodSpec *corev1.PodSpec switch target.TargetKind { case formolv1alpha1.Deployment: - deployment := &appsv1.Deployment{} + deployment := appsv1.Deployment{} if err := r.Get(r.Context, client.ObjectKey{ Namespace: backupConf.Namespace, Name: target.TargetName, - }, deployment); err != nil { + }, &deployment); err != nil { r.Log.Error(err, "cannot get deployment", "Deployment", target.TargetName) return err } - restoreContainers := []corev1.Container{} - for _, container := range deployment.Spec.Template.Spec.Containers { - if container.Name == formolv1alpha1.SIDECARCONTAINER_NAME { + targetObject = &deployment + targetPodSpec = &deployment.Spec.Template.Spec + + } + restoreContainers := []corev1.Container{} + for _, container := range targetPodSpec.Containers { + if container.Name == formolv1alpha1.SIDECARCONTAINER_NAME { + continue + } + restoreContainers = append(restoreContainers, container) + } + targetPodSpec.Containers = restoreContainers + if repo.Spec.Backend.Local != nil { + restoreVolumes := []corev1.Volume{} + for _, volume := range targetPodSpec.Volumes { + if volume.Name == "restic-local-repo" { continue } - restoreContainers = append(restoreContainers, container) - } - deployment.Spec.Template.Spec.Containers = restoreContainers - removeTags(&deployment.Spec.Template.Spec, target) - if err := r.Update(r.Context, deployment); err != nil { - r.Log.Error(err, "unable to update deployment", "deployment", deployment) - return err + restoreVolumes = append(restoreVolumes, volume) } + targetPodSpec.Volumes = restoreVolumes + } + removeTags(targetPodSpec, target) + if err := r.Update(r.Context, targetObject); err != nil { + r.Log.Error(err, "unable to remove sidecar", "targetObject", targetObject) + return err } } @@ -280,14 +304,28 @@ func (r *BackupConfigurationReconciler) addOnlineSidecar(backupConf formolv1alph return } sidecarPaths, vms := addTags(targetPodSpec, target) - sidecar.VolumeMounts = vms sidecar.Env = append(sidecar.Env, corev1.EnvVar{ Name: formolv1alpha1.BACKUP_PATHS, Value: strings.Join(sidecarPaths, string(os.PathListSeparator)), }) + if repo.Spec.Backend.Local != nil { + sidecar.VolumeMounts = append(vms, corev1.VolumeMount{ + Name: "restic-local-repo", + MountPath: "/repo", + }) + targetPodSpec.Volumes = append(targetPodSpec.Volumes, corev1.Volume{ + Name: "restic-local-repo", + VolumeSource: corev1.VolumeSource{ + EmptyDir: &corev1.EmptyDirVolumeSource{}, + }, + }) + } else { + sidecar.VolumeMounts = vms + } // The sidecar definition is complete. Add it to the targetObject targetPodSpec.Containers = append(targetPodSpec.Containers, sidecar) + targetPodSpec.ShareProcessNamespace = func() *bool { b := true; return &b }() r.Log.V(1).Info("Adding sidecar", "targetObject", targetObject, "sidecar", sidecar) if err = r.Update(r.Context, targetObject); err != nil { r.Log.Error(err, "unable to add sidecar", "targetObject", targetObject) @@ -333,7 +371,7 @@ func (r *BackupConfigurationReconciler) createRBACSidecar(sa corev1.ServiceAccou rbacv1.PolicyRule{ Verbs: []string{"get", "list", "watch"}, APIGroups: []string{"formol.desmojim.fr"}, - Resources: []string{"backupsessions", "backupconfigurations"}, + Resources: []string{"backupsessions", "backupconfigurations", "functions", "repos"}, }, rbacv1.PolicyRule{ Verbs: []string{"get", "list", "watch", "create", "update", "patch", "delete"},