@@ -25,6 +25,7 @@ import (
2525 "github.com/pkg/errors"
2626 corev1 "k8s.io/api/core/v1"
2727 apierrors "k8s.io/apimachinery/pkg/api/errors"
28+ metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
2829 "k8s.io/apimachinery/pkg/apis/meta/v1/unstructured"
2930 "sigs.k8s.io/controller-runtime/pkg/client"
3031
@@ -53,6 +54,10 @@ const (
5354var (
5455 //go:embed assets/cert-manager-test-resources.yaml
5556 certManagerTestManifest []byte
57+ // namespaces for all relevant objects in a cert-manager installation.
58+ // It also includes relevant resources in the kube-system namespace, which is used by cert-manager
59+ // for leader election (https://github.com/cert-manager/cert-manager/issues/6716).
60+ certManagerNamespaces = []string {certManagerNamespace , metav1 .NamespaceSystem }
5661)
5762
5863// CertManagerUpgradePlan defines the upgrade plan if cert-manager needs to be
@@ -202,9 +207,9 @@ func (cm *certManagerClient) install(ctx context.Context, version string, objs [
202207func (cm * certManagerClient ) PlanUpgrade (ctx context.Context ) (CertManagerUpgradePlan , error ) {
203208 log := logf .Log
204209
205- objs , err := cm .proxy .ListResources (ctx , map [string ]string {clusterctlv1 .ClusterctlCoreLabel : clusterctlv1 .ClusterctlCoreLabelCertManagerValue }, certManagerNamespace )
210+ objs , err := cm .proxy .ListResources (ctx , map [string ]string {clusterctlv1 .ClusterctlCoreLabel : clusterctlv1 .ClusterctlCoreLabelCertManagerValue }, certManagerNamespaces ... )
206211 if err != nil {
207- return CertManagerUpgradePlan {}, errors .Wrap (err , "failed get cert manager components" )
212+ return CertManagerUpgradePlan {}, errors .Wrap (err , "failed to get cert- manager components" )
208213 }
209214
210215 // If there are no cert manager components with the clusterctl labels, it means that cert-manager is externally managed.
@@ -240,12 +245,10 @@ func (cm *certManagerClient) PlanUpgrade(ctx context.Context) (CertManagerUpgrad
240245// older than the version currently suggested by clusterctl, upgrades it.
241246func (cm * certManagerClient ) EnsureLatestVersion (ctx context.Context ) error {
242247 log := logf .Log
243-
244- objs , err := cm .proxy .ListResources (ctx , map [string ]string {clusterctlv1 .ClusterctlCoreLabel : clusterctlv1 .ClusterctlCoreLabelCertManagerValue }, certManagerNamespace )
248+ objs , err := cm .proxy .ListResources (ctx , map [string ]string {clusterctlv1 .ClusterctlCoreLabel : clusterctlv1 .ClusterctlCoreLabelCertManagerValue }, certManagerNamespaces ... )
245249 if err != nil {
246- return errors .Wrap (err , "failed get cert manager components" )
250+ return errors .Wrap (err , "failed to get cert- manager components" )
247251 }
248-
249252 // If there are no cert manager components with the clusterctl labels, it means that cert-manager is externally managed.
250253 if len (objs ) == 0 {
251254 log .V (5 ).Info ("Skipping cert-manager upgrade because externally managed" )
@@ -338,13 +341,19 @@ func (cm *certManagerClient) shouldUpgrade(desiredVersion string, objs, installO
338341
339342 needUpgrade := false
340343 currentVersion := ""
341- for i := range objs {
342- obj := objs [i ]
343344
344- // Endpoints and EndpointSlices are generated by Kubernetes without the version annotation, so we are skipping them
345- if obj .GetKind () == "Endpoints" || obj .GetKind () == "EndpointSlice" {
346- continue
345+ // creates a new list removing resources that are generated by the kubernetes API
346+ // this is relevant if the versions are the same, because we compare
347+ // the number of objects when version of objects are equal
348+ relevantObjs := []unstructured.Unstructured {}
349+ for _ , o := range objs {
350+ if ! (o .GetKind () == "Endpoints" || o .GetKind () == "EndpointSlice" ) {
351+ relevantObjs = append (relevantObjs , o )
347352 }
353+ }
354+
355+ for i := range relevantObjs {
356+ obj := relevantObjs [i ]
348357
349358 // if there is no version annotation, this means the obj is cert-manager v0.11.0 (installed with older version of clusterctl)
350359 objVersion , ok := obj .GetAnnotations ()[clusterctlv1 .CertManagerVersionAnnotation ]
@@ -374,7 +383,7 @@ func (cm *certManagerClient) shouldUpgrade(desiredVersion string, objs, installO
374383 // The installed version is equal to the desired version. Upgrade is required only if the number
375384 // of available objects and objects to install differ. This would act as a re-install.
376385 currentVersion = objVersion
377- needUpgrade = len (objs ) != len (installObjs )
386+ needUpgrade = len (relevantObjs ) != len (installObjs )
378387 case c > 0 :
379388 // The installed version is greater than the desired version. Upgrade is not required.
380389 currentVersion = objVersion
0 commit comments