From 1d82a29eebbc9e0e8b4814c69d3c7ef601ec1d87 Mon Sep 17 00:00:00 2001
From: Tom Pantelis <tompantelis@gmail.com>
Date: Thu, 6 Jun 2024 15:20:02 -0400
Subject: [PATCH] Migrate the broker secret on upgrade to 0.18

The broker secret has been renamed to submariner-broker-secret
so copy the old secret with the new name and delete the old one.
Also update the BrokerK8sSecret field in the Submariner object.

Fixes https://github.com/submariner-io/subctl/issues/1148

Signed-off-by: Tom Pantelis <tompantelis@gmail.com>
---
 cmd/subctl/upgrade.go | 66 +++++++++++++++++++++++++++++++++++++++++--
 pkg/broker/rbac.go    |  1 +
 pkg/join/join.go      |  2 +-
 3 files changed, 66 insertions(+), 3 deletions(-)

diff --git a/cmd/subctl/upgrade.go b/cmd/subctl/upgrade.go
index b33c9e650..14dfabd29 100644
--- a/cmd/subctl/upgrade.go
+++ b/cmd/subctl/upgrade.go
@@ -36,13 +36,16 @@ import (
 	"github.com/submariner-io/subctl/internal/constants"
 	"github.com/submariner-io/subctl/internal/exit"
 	"github.com/submariner-io/subctl/internal/restconfig"
+	"github.com/submariner-io/subctl/pkg/broker"
 	"github.com/submariner-io/subctl/pkg/cluster"
 	"github.com/submariner-io/subctl/pkg/deploy"
 	"github.com/submariner-io/subctl/pkg/image"
 	"github.com/submariner-io/subctl/pkg/operator"
+	"github.com/submariner-io/subctl/pkg/secret"
 	"github.com/submariner-io/subctl/pkg/version"
 	"k8s.io/apimachinery/pkg/api/errors"
 	metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
+	"k8s.io/client-go/kubernetes"
 )
 
 var (
@@ -251,6 +254,49 @@ func upgradeBroker(ctx context.Context, clusterInfo *cluster.Info, status report
 	return err == nil, status.Error(err, "Error upgrading the Broker")
 }
 
+func migrateBrokerSecret(ctx context.Context, kubeClient kubernetes.Interface, fromSecretName string, status reporter.Interface,
+) (string, error) {
+	if !strings.HasPrefix(fromSecretName, "broker-secret-") {
+		return fromSecretName, nil
+	}
+
+	ns := constants.OperatorNamespace
+
+	_, err := kubeClient.CoreV1().Secrets(ns).Get(ctx, broker.LocalClientBrokerSecretName, metav1.GetOptions{})
+	if err == nil {
+		// Already migrated
+		return broker.LocalClientBrokerSecretName, nil
+	}
+
+	if err != nil && !errors.IsNotFound(err) {
+		return "", status.Error(err, "Error retrieving Broker secret %q", broker.LocalClientBrokerSecretName)
+	}
+
+	oldSecret, err := kubeClient.CoreV1().Secrets(ns).Get(ctx, fromSecretName, metav1.GetOptions{})
+	if err != nil {
+		return "", status.Error(err, "Error retrieving old Broker secret %q", fromSecretName)
+	}
+
+	newSecret := *oldSecret
+	newSecret.ObjectMeta = metav1.ObjectMeta{
+		Name: broker.LocalClientBrokerSecretName,
+	}
+
+	_, err = secret.Ensure(ctx, kubeClient, ns, &newSecret)
+	if err != nil {
+		return "", status.Error(err, "Error creating Broker secret %q", newSecret.Name)
+	}
+
+	err = kubeClient.CoreV1().Secrets(ns).Delete(ctx, oldSecret.Name, metav1.DeleteOptions{})
+	if err != nil {
+		status.Warning("Error deleting the old broker secret %q: %v", oldSecret.Name, err)
+	}
+
+	status.Success("Successfully migrated the Broker secret from %q to %q", fromSecretName, broker.LocalClientBrokerSecretName)
+
+	return newSecret.Name, nil
+}
+
 func upgradeOperator(ctx context.Context, clusterInfo *cluster.Info, repository string, debug bool, imageOverride map[string]string,
 	status reporter.Interface,
 ) error {
@@ -284,7 +330,15 @@ func upgradeConnectivity(ctx context.Context, clusterInfo *cluster.Info, logVers
 
 		clusterInfo.Submariner.Spec.Version = upgradeSubmarinerVersion
 
-		err := deploy.SubmarinerFromSpec(ctx, clusterInfo.ClientProducer.ForGeneral(), &clusterInfo.Submariner.Spec)
+		var err error
+
+		clusterInfo.Submariner.Spec.BrokerK8sSecret, err = migrateBrokerSecret(ctx, clusterInfo.ClientProducer.ForKubernetes(),
+			clusterInfo.Submariner.Spec.BrokerK8sSecret, status)
+		if err != nil {
+			return err
+		}
+
+		err = deploy.SubmarinerFromSpec(ctx, clusterInfo.ClientProducer.ForGeneral(), &clusterInfo.Submariner.Spec)
 
 		return status.Error(err, "Error upgrading the Connectivity component")
 	}
@@ -299,7 +353,15 @@ func upgradeServiceDiscovery(ctx context.Context, clusterInfo *cluster.Info, log
 
 		clusterInfo.ServiceDiscovery.Spec.Version = upgradeSubmarinerVersion
 
-		err := deploy.ServiceDiscoveryFromSpec(ctx, clusterInfo.ClientProducer.ForGeneral(), &clusterInfo.ServiceDiscovery.Spec)
+		var err error
+
+		clusterInfo.ServiceDiscovery.Spec.BrokerK8sSecret, err = migrateBrokerSecret(ctx, clusterInfo.ClientProducer.ForKubernetes(),
+			clusterInfo.ServiceDiscovery.Spec.BrokerK8sSecret, status)
+		if err != nil {
+			return err
+		}
+
+		err = deploy.ServiceDiscoveryFromSpec(ctx, clusterInfo.ClientProducer.ForGeneral(), &clusterInfo.ServiceDiscovery.Spec)
 
 		return status.Error(err, "Error upgrading Service Discovery")
 	}
diff --git a/pkg/broker/rbac.go b/pkg/broker/rbac.go
index ac5706162..a0c53f373 100644
--- a/pkg/broker/rbac.go
+++ b/pkg/broker/rbac.go
@@ -27,6 +27,7 @@ import (
 )
 
 const (
+	LocalClientBrokerSecretName = "submariner-broker-secret"
 	submarinerBrokerClusterRole = "submariner-k8s-broker-cluster"
 )
 
diff --git a/pkg/join/join.go b/pkg/join/join.go
index d62781635..0d10f5d2b 100644
--- a/pkg/join/join.go
+++ b/pkg/join/join.go
@@ -198,7 +198,7 @@ func populateBrokerSecret(brokerInfo *broker.Info) *v1.Secret {
 	// We need to copy the broker token secret as an opaque secret to store it in the connecting cluster
 	return &v1.Secret{
 		ObjectMeta: metav1.ObjectMeta{
-			Name: "submariner-broker-secret",
+			Name: broker.LocalClientBrokerSecretName,
 		},
 		Type: v1.SecretTypeOpaque,
 		Data: brokerInfo.ClientToken.Data,