From d06a2936cc9fbc62ddbc46576c1a2d7a2a587bd9 Mon Sep 17 00:00:00 2001
From: Somtochi Onyekwere <somtochionyekwere@gmail.com>
Date: Wed, 29 Sep 2021 17:17:07 +0100
Subject: [PATCH] Better checks for reconciliation in reconcile run command

Signed-off-by: Somtochi Onyekwere <somtochionyekwere@gmail.com>
---
 cmd/flux/reconcile.go                              | 14 +++++++++-----
 cmd/flux/reconcile_with_source.go                  | 13 +++++++++----
 .../reconcile_helmrelease_from_git.golden          |  2 --
 .../reconcile_kustomization_from_git.golden        |  2 --
 4 files changed, 18 insertions(+), 13 deletions(-)

diff --git a/cmd/flux/reconcile.go b/cmd/flux/reconcile.go
index eece61be..cf6bdee2 100644
--- a/cmd/flux/reconcile.go
+++ b/cmd/flux/reconcile.go
@@ -116,11 +116,13 @@ func (reconcile reconcileCommand) run(cmd *cobra.Command, args []string) error {
 		reconciliationHandled(ctx, kubeClient, namespacedName, reconcile.object, lastHandledReconcileAt)); err != nil {
 		return err
 	}
+	readyCond := apimeta.FindStatusCondition(*reconcile.object.GetStatusConditions(), meta.ReadyCondition)
+	if readyCond == nil {
+		return fmt.Errorf("status can't be determined")
+	}
 
-	logger.Successf("%s reconciliation completed", reconcile.kind)
-
-	if apimeta.IsStatusConditionFalse(*reconcile.object.GetStatusConditions(), meta.ReadyCondition) {
-		return fmt.Errorf("%s reconciliation failed", reconcile.kind)
+	if readyCond.Status != metav1.ConditionTrue {
+		return fmt.Errorf("%s reconciliation failed: ''%s", reconcile.kind, readyCond.Message)
 	}
 	logger.Successf(reconcile.object.successMessage())
 	return nil
@@ -133,7 +135,9 @@ func reconciliationHandled(ctx context.Context, kubeClient client.Client,
 		if err != nil {
 			return false, err
 		}
-		return obj.lastHandledReconcileRequest() != lastHandledReconcileAt, nil
+		isProgressing := apimeta.IsStatusConditionPresentAndEqual(*obj.GetStatusConditions(),
+			meta.ReadyCondition, metav1.ConditionUnknown)
+		return obj.lastHandledReconcileRequest() != lastHandledReconcileAt && !isProgressing, nil
 	}
 }
 
diff --git a/cmd/flux/reconcile_with_source.go b/cmd/flux/reconcile_with_source.go
index dc293788..7052b879 100644
--- a/cmd/flux/reconcile_with_source.go
+++ b/cmd/flux/reconcile_with_source.go
@@ -6,6 +6,7 @@ import (
 
 	"github.com/spf13/cobra"
 	apimeta "k8s.io/apimachinery/pkg/api/meta"
+	metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
 	"k8s.io/apimachinery/pkg/types"
 	"k8s.io/apimachinery/pkg/util/wait"
 
@@ -68,22 +69,26 @@ func (reconcile reconcileWithSourceCommand) run(cmd *cobra.Command, args []strin
 		rootArgs.namespace = nsCopy
 	}
 
+	lastHandledReconcileAt := reconcile.object.lastHandledReconcileRequest()
 	logger.Actionf("annotating %s %s in %s namespace", reconcile.kind, name, rootArgs.namespace)
 	if err := requestReconciliation(ctx, kubeClient, namespacedName, reconcile.object); err != nil {
 		return err
 	}
 	logger.Successf("%s annotated", reconcile.kind)
 
-	lastHandledReconcileAt := reconcile.object.lastHandledReconcileRequest()
 	logger.Waitingf("waiting for %s reconciliation", reconcile.kind)
 	if err := wait.PollImmediate(rootArgs.pollInterval, rootArgs.timeout,
 		reconciliationHandled(ctx, kubeClient, namespacedName, reconcile.object, lastHandledReconcileAt)); err != nil {
 		return err
 	}
-	logger.Successf("%s reconciliation completed", reconcile.kind)
 
-	if apimeta.IsStatusConditionFalse(*reconcile.object.GetStatusConditions(), meta.ReadyCondition) {
-		return fmt.Errorf("%s reconciliation failed", reconcile.kind)
+	readyCond := apimeta.FindStatusCondition(*reconcile.object.GetStatusConditions(), meta.ReadyCondition)
+	if readyCond == nil {
+		return fmt.Errorf("status can't be determined")
+	}
+
+	if readyCond.Status != metav1.ConditionTrue {
+		return fmt.Errorf("%s reconciliation failed: %s", reconcile.kind, readyCond.Message)
 	}
 	logger.Successf(reconcile.object.successMessage())
 	return nil
diff --git a/cmd/flux/testdata/helmrelease/reconcile_helmrelease_from_git.golden b/cmd/flux/testdata/helmrelease/reconcile_helmrelease_from_git.golden
index b785dc65..a1cf24b4 100644
--- a/cmd/flux/testdata/helmrelease/reconcile_helmrelease_from_git.golden
+++ b/cmd/flux/testdata/helmrelease/reconcile_helmrelease_from_git.golden
@@ -1,10 +1,8 @@
 â–º annotating GitRepository thrfg in {{ .ns }} namespace
 ✔ GitRepository annotated
 â—Ž waiting for GitRepository reconciliation
-✔ GitRepository reconciliation completed
 ✔ fetched revision 6.0.0/627d5c4bb67b77185f37e31d734b085019ff2951
 â–º annotating HelmRelease thrfg in {{ .ns }} namespace
 ✔ HelmRelease annotated
 â—Ž waiting for HelmRelease reconciliation
-✔ HelmRelease reconciliation completed
 ✔ applied revision 6.0.0
diff --git a/cmd/flux/testdata/kustomization/reconcile_kustomization_from_git.golden b/cmd/flux/testdata/kustomization/reconcile_kustomization_from_git.golden
index bdcea5ca..e87dc391 100644
--- a/cmd/flux/testdata/kustomization/reconcile_kustomization_from_git.golden
+++ b/cmd/flux/testdata/kustomization/reconcile_kustomization_from_git.golden
@@ -1,10 +1,8 @@
 â–º annotating GitRepository tkfg in {{ .ns }} namespace
 ✔ GitRepository annotated
 â—Ž waiting for GitRepository reconciliation
-✔ GitRepository reconciliation completed
 ✔ fetched revision 6.0.0/627d5c4bb67b77185f37e31d734b085019ff2951
 â–º annotating Kustomization tkfg in {{ .ns }} namespace
 ✔ Kustomization annotated
 â—Ž waiting for Kustomization reconciliation
-✔ Kustomization reconciliation completed
 ✔ applied revision 6.0.0/627d5c4bb67b77185f37e31d734b085019ff2951
-- 
GitLab