diff --git a/cmd/flux/resume_alert.go b/cmd/flux/resume_alert.go index a33d4f5b..7bd3419e 100644 --- a/cmd/flux/resume_alert.go +++ b/cmd/flux/resume_alert.go @@ -49,6 +49,9 @@ func (obj alertAdapter) getObservedGeneration() int64 { func (obj alertAdapter) setUnsuspended() { obj.Alert.Spec.Suspend = false + if _, ok := obj.Alert.Annotations[SuspendMessageAnnotation]; ok { + delete(obj.Alert.Annotations, SuspendMessageAnnotation) + } } func (obj alertAdapter) successMessage() string { diff --git a/cmd/flux/resume_helmrelease.go b/cmd/flux/resume_helmrelease.go index 6c320b30..d9bb57b3 100644 --- a/cmd/flux/resume_helmrelease.go +++ b/cmd/flux/resume_helmrelease.go @@ -52,6 +52,9 @@ func (obj helmReleaseAdapter) getObservedGeneration() int64 { func (obj helmReleaseAdapter) setUnsuspended() { obj.HelmRelease.Spec.Suspend = false + if _, ok := obj.HelmRelease.Annotations[SuspendMessageAnnotation]; ok { + delete(obj.HelmRelease.Annotations, SuspendMessageAnnotation) + } } func (obj helmReleaseAdapter) successMessage() string { diff --git a/cmd/flux/resume_image_repository.go b/cmd/flux/resume_image_repository.go index a9ab36cd..add2a172 100644 --- a/cmd/flux/resume_image_repository.go +++ b/cmd/flux/resume_image_repository.go @@ -48,6 +48,9 @@ func (obj imageRepositoryAdapter) getObservedGeneration() int64 { func (obj imageRepositoryAdapter) setUnsuspended() { obj.ImageRepository.Spec.Suspend = false + if _, ok := obj.ImageRepository.Annotations[SuspendMessageAnnotation]; ok { + delete(obj.ImageRepository.Annotations, SuspendMessageAnnotation) + } } func (a imageRepositoryListAdapter) resumeItem(i int) resumable { diff --git a/cmd/flux/resume_image_updateauto.go b/cmd/flux/resume_image_updateauto.go index 1b29cbaf..93ab2688 100644 --- a/cmd/flux/resume_image_updateauto.go +++ b/cmd/flux/resume_image_updateauto.go @@ -44,6 +44,9 @@ func init() { func (obj imageUpdateAutomationAdapter) setUnsuspended() { obj.ImageUpdateAutomation.Spec.Suspend = false + if _, ok := obj.ImageUpdateAutomation.Annotations[SuspendMessageAnnotation]; ok { + delete(obj.ImageUpdateAutomation.Annotations, SuspendMessageAnnotation) + } } func (obj imageUpdateAutomationAdapter) getObservedGeneration() int64 { diff --git a/cmd/flux/resume_kustomization.go b/cmd/flux/resume_kustomization.go index a03aed62..23f231df 100644 --- a/cmd/flux/resume_kustomization.go +++ b/cmd/flux/resume_kustomization.go @@ -52,6 +52,9 @@ func (obj kustomizationAdapter) getObservedGeneration() int64 { func (obj kustomizationAdapter) setUnsuspended() { obj.Kustomization.Spec.Suspend = false + if _, ok := obj.Kustomization.Annotations[SuspendMessageAnnotation]; ok { + delete(obj.Kustomization.Annotations, SuspendMessageAnnotation) + } } func (obj kustomizationAdapter) successMessage() string { diff --git a/cmd/flux/resume_receiver.go b/cmd/flux/resume_receiver.go index c99bd755..c13c25f9 100644 --- a/cmd/flux/resume_receiver.go +++ b/cmd/flux/resume_receiver.go @@ -49,6 +49,9 @@ func (obj receiverAdapter) getObservedGeneration() int64 { func (obj receiverAdapter) setUnsuspended() { obj.Receiver.Spec.Suspend = false + if _, ok := obj.Receiver.Annotations[SuspendMessageAnnotation]; ok { + delete(obj.Receiver.Annotations, SuspendMessageAnnotation) + } } func (obj receiverAdapter) successMessage() string { diff --git a/cmd/flux/resume_source_bucket.go b/cmd/flux/resume_source_bucket.go index 1de754eb..6e9aa44d 100644 --- a/cmd/flux/resume_source_bucket.go +++ b/cmd/flux/resume_source_bucket.go @@ -48,6 +48,9 @@ func (obj bucketAdapter) getObservedGeneration() int64 { func (obj bucketAdapter) setUnsuspended() { obj.Bucket.Spec.Suspend = false + if _, ok := obj.Bucket.Annotations[SuspendMessageAnnotation]; ok { + delete(obj.Bucket.Annotations, SuspendMessageAnnotation) + } } func (a bucketListAdapter) resumeItem(i int) resumable { diff --git a/cmd/flux/resume_source_chart.go b/cmd/flux/resume_source_chart.go index 9e7ec759..077ff65f 100644 --- a/cmd/flux/resume_source_chart.go +++ b/cmd/flux/resume_source_chart.go @@ -50,6 +50,9 @@ func (obj helmChartAdapter) getObservedGeneration() int64 { func (obj helmChartAdapter) setUnsuspended() { obj.HelmChart.Spec.Suspend = false + if _, ok := obj.HelmChart.Annotations[SuspendMessageAnnotation]; ok { + delete(obj.HelmChart.Annotations, SuspendMessageAnnotation) + } } func (obj helmChartAdapter) successMessage() string { diff --git a/cmd/flux/resume_source_git.go b/cmd/flux/resume_source_git.go index 751714a4..120a0937 100644 --- a/cmd/flux/resume_source_git.go +++ b/cmd/flux/resume_source_git.go @@ -48,6 +48,9 @@ func (obj gitRepositoryAdapter) getObservedGeneration() int64 { func (obj gitRepositoryAdapter) setUnsuspended() { obj.GitRepository.Spec.Suspend = false + if _, ok := obj.GitRepository.Annotations[SuspendMessageAnnotation]; ok { + delete(obj.GitRepository.Annotations, SuspendMessageAnnotation) + } } func (a gitRepositoryListAdapter) resumeItem(i int) resumable { diff --git a/cmd/flux/resume_source_helm.go b/cmd/flux/resume_source_helm.go index b4cb1316..aa13757d 100644 --- a/cmd/flux/resume_source_helm.go +++ b/cmd/flux/resume_source_helm.go @@ -48,6 +48,9 @@ func (obj helmRepositoryAdapter) getObservedGeneration() int64 { func (obj helmRepositoryAdapter) setUnsuspended() { obj.HelmRepository.Spec.Suspend = false + if _, ok := obj.HelmRepository.Annotations[SuspendMessageAnnotation]; ok { + delete(obj.HelmRepository.Annotations, SuspendMessageAnnotation) + } } func (a helmRepositoryListAdapter) resumeItem(i int) resumable { diff --git a/cmd/flux/resume_source_oci.go b/cmd/flux/resume_source_oci.go index 04b20a4b..b724feb6 100644 --- a/cmd/flux/resume_source_oci.go +++ b/cmd/flux/resume_source_oci.go @@ -48,6 +48,9 @@ func (obj ociRepositoryAdapter) getObservedGeneration() int64 { func (obj ociRepositoryAdapter) setUnsuspended() { obj.OCIRepository.Spec.Suspend = false + if _, ok := obj.OCIRepository.Annotations[SuspendMessageAnnotation]; ok { + delete(obj.OCIRepository.Annotations, SuspendMessageAnnotation) + } } func (a ociRepositoryListAdapter) resumeItem(i int) resumable { diff --git a/cmd/flux/suspend.go b/cmd/flux/suspend.go index e0023c7e..ad4d745b 100644 --- a/cmd/flux/suspend.go +++ b/cmd/flux/suspend.go @@ -34,7 +34,8 @@ var suspendCmd = &cobra.Command{ } type SuspendFlags struct { - all bool + all bool + message string } var suspendArgs SuspendFlags @@ -42,6 +43,8 @@ var suspendArgs SuspendFlags func init() { suspendCmd.PersistentFlags().BoolVarP(&suspendArgs.all, "all", "", false, "suspend all resources in that namespace") + suspendCmd.PersistentFlags().StringVarP(&suspendArgs.message, "message", "m", "", + "set a message for the resource being suspended (stored in the suspend.toolkit.fluxcd.io/message annotation)") rootCmd.AddCommand(suspendCmd) } @@ -49,7 +52,7 @@ type suspendable interface { adapter copyable isSuspended() bool - setSuspended() + setSuspended(message string) } type suspendCommand struct { @@ -130,7 +133,7 @@ func (suspend suspendCommand) patch(ctx context.Context, kubeClient client.WithW obj := suspend.list.item(i) patch := client.MergeFrom(obj.deepCopyClientObject()) - obj.setSuspended() + obj.setSuspended(suspendArgs.message) if err := kubeClient.Patch(ctx, obj.asClientObject(), patch); err != nil { return err } @@ -140,3 +143,6 @@ func (suspend suspendCommand) patch(ctx context.Context, kubeClient client.WithW return nil } + +// SuspendMessageAnnotation is the metadata key used to store a message related to resource suspension +const SuspendMessageAnnotation string = "suspend.toolkit.fluxcd.io/message" diff --git a/cmd/flux/suspend_alert.go b/cmd/flux/suspend_alert.go index 67fa201a..70a851d2 100644 --- a/cmd/flux/suspend_alert.go +++ b/cmd/flux/suspend_alert.go @@ -47,8 +47,11 @@ func (obj alertAdapter) isSuspended() bool { return obj.Alert.Spec.Suspend } -func (obj alertAdapter) setSuspended() { +func (obj alertAdapter) setSuspended(message string) { obj.Alert.Spec.Suspend = true + if message != "" { + obj.Alert.Annotations[SuspendMessageAnnotation] = message + } } func (a alertListAdapter) item(i int) suspendable { diff --git a/cmd/flux/suspend_helmrelease.go b/cmd/flux/suspend_helmrelease.go index 762e70eb..4d909dcf 100644 --- a/cmd/flux/suspend_helmrelease.go +++ b/cmd/flux/suspend_helmrelease.go @@ -48,8 +48,11 @@ func (obj helmReleaseAdapter) isSuspended() bool { return obj.HelmRelease.Spec.Suspend } -func (obj helmReleaseAdapter) setSuspended() { +func (obj helmReleaseAdapter) setSuspended(message string) { obj.HelmRelease.Spec.Suspend = true + if message != "" { + obj.HelmRelease.Annotations[SuspendMessageAnnotation] = message + } } func (a helmReleaseListAdapter) item(i int) suspendable { diff --git a/cmd/flux/suspend_image_repository.go b/cmd/flux/suspend_image_repository.go index c6e562d1..56b2a775 100644 --- a/cmd/flux/suspend_image_repository.go +++ b/cmd/flux/suspend_image_repository.go @@ -47,8 +47,11 @@ func (obj imageRepositoryAdapter) isSuspended() bool { return obj.ImageRepository.Spec.Suspend } -func (obj imageRepositoryAdapter) setSuspended() { +func (obj imageRepositoryAdapter) setSuspended(message string) { obj.ImageRepository.Spec.Suspend = true + if message != "" { + obj.ImageRepository.Annotations[SuspendMessageAnnotation] = message + } } func (a imageRepositoryListAdapter) item(i int) suspendable { diff --git a/cmd/flux/suspend_image_updateauto.go b/cmd/flux/suspend_image_updateauto.go index a1035117..88d75de2 100644 --- a/cmd/flux/suspend_image_updateauto.go +++ b/cmd/flux/suspend_image_updateauto.go @@ -47,8 +47,11 @@ func (update imageUpdateAutomationAdapter) isSuspended() bool { return update.ImageUpdateAutomation.Spec.Suspend } -func (update imageUpdateAutomationAdapter) setSuspended() { +func (update imageUpdateAutomationAdapter) setSuspended(message string) { update.ImageUpdateAutomation.Spec.Suspend = true + if message != "" { + update.ImageUpdateAutomation.Annotations[SuspendMessageAnnotation] = message + } } func (a imageUpdateAutomationListAdapter) item(i int) suspendable { diff --git a/cmd/flux/suspend_kustomization.go b/cmd/flux/suspend_kustomization.go index ac6c72e1..74bd78d5 100644 --- a/cmd/flux/suspend_kustomization.go +++ b/cmd/flux/suspend_kustomization.go @@ -48,8 +48,11 @@ func (obj kustomizationAdapter) isSuspended() bool { return obj.Kustomization.Spec.Suspend } -func (obj kustomizationAdapter) setSuspended() { +func (obj kustomizationAdapter) setSuspended(message string) { obj.Kustomization.Spec.Suspend = true + if message != "" { + obj.Kustomization.Annotations[SuspendMessageAnnotation] = message + } } func (a kustomizationListAdapter) item(i int) suspendable { diff --git a/cmd/flux/suspend_receiver.go b/cmd/flux/suspend_receiver.go index 7f2e6dd7..445c5ac7 100644 --- a/cmd/flux/suspend_receiver.go +++ b/cmd/flux/suspend_receiver.go @@ -47,8 +47,11 @@ func (obj receiverAdapter) isSuspended() bool { return obj.Receiver.Spec.Suspend } -func (obj receiverAdapter) setSuspended() { +func (obj receiverAdapter) setSuspended(message string) { obj.Receiver.Spec.Suspend = true + if message != "" { + obj.Receiver.Annotations[SuspendMessageAnnotation] = message + } } func (a receiverListAdapter) item(i int) suspendable { diff --git a/cmd/flux/suspend_source_bucket.go b/cmd/flux/suspend_source_bucket.go index 168d18a0..540f0f00 100644 --- a/cmd/flux/suspend_source_bucket.go +++ b/cmd/flux/suspend_source_bucket.go @@ -47,8 +47,11 @@ func (obj bucketAdapter) isSuspended() bool { return obj.Bucket.Spec.Suspend } -func (obj bucketAdapter) setSuspended() { +func (obj bucketAdapter) setSuspended(message string) { obj.Bucket.Spec.Suspend = true + if message != "" { + obj.Bucket.Annotations[SuspendMessageAnnotation] = message + } } func (a bucketListAdapter) item(i int) suspendable { diff --git a/cmd/flux/suspend_source_chart.go b/cmd/flux/suspend_source_chart.go index 6da1d8c0..d3683802 100644 --- a/cmd/flux/suspend_source_chart.go +++ b/cmd/flux/suspend_source_chart.go @@ -47,8 +47,11 @@ func (obj helmChartAdapter) isSuspended() bool { return obj.HelmChart.Spec.Suspend } -func (obj helmChartAdapter) setSuspended() { +func (obj helmChartAdapter) setSuspended(message string) { obj.HelmChart.Spec.Suspend = true + if message != "" { + obj.HelmChart.Annotations[SuspendMessageAnnotation] = message + } } func (a helmChartListAdapter) item(i int) suspendable { diff --git a/cmd/flux/suspend_source_git.go b/cmd/flux/suspend_source_git.go index 4decf796..a60164d7 100644 --- a/cmd/flux/suspend_source_git.go +++ b/cmd/flux/suspend_source_git.go @@ -47,8 +47,11 @@ func (obj gitRepositoryAdapter) isSuspended() bool { return obj.GitRepository.Spec.Suspend } -func (obj gitRepositoryAdapter) setSuspended() { +func (obj gitRepositoryAdapter) setSuspended(message string) { obj.GitRepository.Spec.Suspend = true + if message != "" { + obj.GitRepository.Annotations[SuspendMessageAnnotation] = message + } } func (a gitRepositoryListAdapter) item(i int) suspendable { diff --git a/cmd/flux/suspend_source_helm.go b/cmd/flux/suspend_source_helm.go index a59343bd..0815343c 100644 --- a/cmd/flux/suspend_source_helm.go +++ b/cmd/flux/suspend_source_helm.go @@ -47,8 +47,11 @@ func (obj helmRepositoryAdapter) isSuspended() bool { return obj.HelmRepository.Spec.Suspend } -func (obj helmRepositoryAdapter) setSuspended() { +func (obj helmRepositoryAdapter) setSuspended(message string) { obj.HelmRepository.Spec.Suspend = true + if message != "" { + obj.HelmRepository.Annotations[SuspendMessageAnnotation] = message + } } func (a helmRepositoryListAdapter) item(i int) suspendable { diff --git a/cmd/flux/suspend_source_oci.go b/cmd/flux/suspend_source_oci.go index 3b8e36d6..acf0057b 100644 --- a/cmd/flux/suspend_source_oci.go +++ b/cmd/flux/suspend_source_oci.go @@ -47,8 +47,11 @@ func (obj ociRepositoryAdapter) isSuspended() bool { return obj.OCIRepository.Spec.Suspend } -func (obj ociRepositoryAdapter) setSuspended() { +func (obj ociRepositoryAdapter) setSuspended(message string) { obj.OCIRepository.Spec.Suspend = true + if message != "" { + obj.OCIRepository.Annotations[SuspendMessageAnnotation] = message + } } func (a ociRepositoryListAdapter) item(i int) suspendable {