diff --git a/internal/controller/phases.go b/internal/controller/phases.go index 28db644b..d3590222 100644 --- a/internal/controller/phases.go +++ b/internal/controller/phases.go @@ -147,11 +147,13 @@ func (p *phaseReconciler) initializePhaseReconciler(ctx context.Context) (reconc return reconcile.Result{}, err } - customProviders, err := p.getCustomProviders(ctx) + // Get all providers using fetchConfig that aren't the current provider. + customProviders, err := util.GetCustomProviders(ctx, p.ctrlClient, p.provider) if err != nil { return reconcile.Result{}, err } + // Load all custom providers into MemoryReader. reader, err = loadCustomProviders(customProviders, reader) if err != nil { return reconcile.Result{}, err @@ -572,44 +574,7 @@ func getProvider(provider operatorv1.GenericProvider, defaultVersion string) clu return *clusterctlProvider } -func (p *phaseReconciler) getCustomProviders(ctx context.Context) ([]operatorv1.GenericProvider, error) { - customProviders := []operatorv1.GenericProvider{} - currProviderName := p.provider.GetName() - currProviderType := p.provider.GetType() - - providerLists := []client.ObjectList{ - &operatorv1.CoreProviderList{}, - &operatorv1.BootstrapProviderList{}, - &operatorv1.ControlPlaneProviderList{}, - &operatorv1.InfrastructureProviderList{}, - &operatorv1.AddonProviderList{}, - &operatorv1.IPAMProviderList{}, - &operatorv1.RuntimeExtensionProviderList{}, - } - - for _, providerList := range providerLists { - if err := p.ctrlClient.List(ctx, providerList); err != nil { - return nil, fmt.Errorf("cannot get a list of providers from the server: %w", err) - } - - genericProviderList, ok := providerList.(operatorv1.GenericProviderList) - if !ok { - return nil, fmt.Errorf("cannot cast providers list to GenericProviderList") - } - - genericProviderListItems := genericProviderList.GetItems() - for i, provider := range genericProviderListItems { - if provider.GetName() == currProviderName && provider.GetType() == currProviderType || provider.GetSpec().FetchConfig == nil { - continue - } - - customProviders = append(customProviders, genericProviderListItems[i]) - } - } - - return customProviders, nil -} - +// loadCustomProviders loads the passed providers list into the clusterctl configuration via the MemoryReader. func loadCustomProviders(providers []operatorv1.GenericProvider, reader configclient.Reader) (configclient.Reader, error) { mr, ok := reader.(*configclient.MemoryReader) if !ok { diff --git a/test/e2e/air_gapped_test.go b/test/e2e/air_gapped_test.go index 21cf6c95..0500c73c 100644 --- a/test/e2e/air_gapped_test.go +++ b/test/e2e/air_gapped_test.go @@ -35,7 +35,7 @@ import ( ) var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapped environment", func() { - It("should successfully create config maps with Core and Bootstrap Provider manifests", func() { + It("should successfully create config maps with Controlplane, Core, and Bootstrap Provider manifests", func() { // Ensure that there are no Cluster API installed deleteClusterAPICRDs(bootstrapClusterProxy) @@ -62,7 +62,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp } By("Creating provider namespaces") - for _, namespaceName := range []string{capkbSystemNamespace, capkcpSystemNamespace, capiSystemNamespace} { + for _, namespaceName := range []string{cabpkSystemNamespace, cacpkSystemNamespace, capiSystemNamespace} { namespace := &corev1.Namespace{ ObjectMeta: metav1.ObjectMeta{ Name: namespaceName, @@ -82,7 +82,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp bootstrapProvider := &operatorv1.BootstrapProvider{ ObjectMeta: metav1.ObjectMeta{ Name: customProviderName, - Namespace: capkbSystemNamespace, + Namespace: cabpkSystemNamespace, }, Spec: operatorv1.BootstrapProviderSpec{ ProviderSpec: operatorv1.ProviderSpec{ @@ -105,7 +105,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp By("Waiting for the bootstrap provider deployment to be ready") framework.WaitForDeploymentsAvailable(ctx, framework.WaitForDeploymentsAvailableInput{ Getter: bootstrapClusterProxy.GetClient(), - Deployment: &appsv1.Deployment{ObjectMeta: metav1.ObjectMeta{Name: bootstrapProviderDeploymentName, Namespace: capkbSystemNamespace}}, + Deployment: &appsv1.Deployment{ObjectMeta: metav1.ObjectMeta{Name: bootstrapProviderDeploymentName, Namespace: cabpkSystemNamespace}}, }, e2eConfig.GetIntervals(bootstrapClusterProxy.GetName(), "wait-controllers")...) By("Waiting for bootstrap provider to be ready") @@ -166,7 +166,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp controlPlaneProvider := &operatorv1.ControlPlaneProvider{ ObjectMeta: metav1.ObjectMeta{ Name: customProviderName, - Namespace: capkcpSystemNamespace, + Namespace: cacpkSystemNamespace, }, Spec: operatorv1.ControlPlaneProviderSpec{ ProviderSpec: operatorv1.ProviderSpec{ @@ -189,7 +189,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp By("Waiting for the controlplane provider deployment to be ready") framework.WaitForDeploymentsAvailable(ctx, framework.WaitForDeploymentsAvailableInput{ Getter: bootstrapClusterProxy.GetClient(), - Deployment: &appsv1.Deployment{ObjectMeta: metav1.ObjectMeta{Name: cpProviderDeploymentName, Namespace: capkcpSystemNamespace}}, + Deployment: &appsv1.Deployment{ObjectMeta: metav1.ObjectMeta{Name: cpProviderDeploymentName, Namespace: cacpkSystemNamespace}}, }, e2eConfig.GetIntervals(bootstrapClusterProxy.GetName(), "wait-controllers")...) By("Waiting for controlplane provider to be ready") @@ -210,13 +210,13 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp coreProvider := &operatorv1.CoreProvider{} controlPlaneProvider := &operatorv1.ControlPlaneProvider{} - bootstrapKey := client.ObjectKey{Namespace: capkbSystemNamespace, Name: customProviderName} + bootstrapKey := client.ObjectKey{Namespace: cabpkSystemNamespace, Name: customProviderName} Expect(bootstrapCluster.Get(ctx, bootstrapKey, bootstrapProvider)).To(Succeed()) coreKey := client.ObjectKey{Namespace: capiSystemNamespace, Name: coreProviderName} Expect(bootstrapCluster.Get(ctx, coreKey, coreProvider)).To(Succeed()) - cpKey := client.ObjectKey{Namespace: capkcpSystemNamespace, Name: customProviderName} + cpKey := client.ObjectKey{Namespace: cacpkSystemNamespace, Name: customProviderName} Expect(bootstrapCluster.Get(ctx, cpKey, controlPlaneProvider)).To(Succeed()) bootstrapProvider.Spec.Version = nextCAPIVersion @@ -233,7 +233,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp By("Waiting for the bootstrap provider deployment to be ready") framework.WaitForDeploymentsAvailable(ctx, framework.WaitForDeploymentsAvailableInput{ Getter: bootstrapClusterProxy.GetClient(), - Deployment: &appsv1.Deployment{ObjectMeta: metav1.ObjectMeta{Name: bootstrapProviderDeploymentName, Namespace: capkbSystemNamespace}}, + Deployment: &appsv1.Deployment{ObjectMeta: metav1.ObjectMeta{Name: bootstrapProviderDeploymentName, Namespace: cabpkSystemNamespace}}, }, e2eConfig.GetIntervals(bootstrapClusterProxy.GetName(), "wait-controllers")...) By("Waiting for bootstrap provider to be ready") @@ -265,7 +265,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp By("Waiting for the controlplane provider deployment to be ready") framework.WaitForDeploymentsAvailable(ctx, framework.WaitForDeploymentsAvailableInput{ Getter: bootstrapClusterProxy.GetClient(), - Deployment: &appsv1.Deployment{ObjectMeta: metav1.ObjectMeta{Name: cpProviderDeploymentName, Namespace: capkcpSystemNamespace}}, + Deployment: &appsv1.Deployment{ObjectMeta: metav1.ObjectMeta{Name: cpProviderDeploymentName, Namespace: cacpkSystemNamespace}}, }, e2eConfig.GetIntervals(bootstrapClusterProxy.GetName(), "wait-controllers")...) By("Waiting for controlplane provider to be ready") @@ -283,7 +283,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp bootstrapCluster := bootstrapClusterProxy.GetClient() bootstrapProvider := &operatorv1.BootstrapProvider{ObjectMeta: metav1.ObjectMeta{ Name: customProviderName, - Namespace: capkbSystemNamespace, + Namespace: cabpkSystemNamespace, }} Expect(bootstrapCluster.Delete(ctx, bootstrapProvider)).To(Succeed()) @@ -291,7 +291,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp By("Waiting for the bootstrap provider deployment to be deleted") WaitForDelete(ctx, For(&appsv1.Deployment{ObjectMeta: metav1.ObjectMeta{ Name: bootstrapProviderDeploymentName, - Namespace: capkbSystemNamespace, + Namespace: cabpkSystemNamespace, }}).In(bootstrapCluster), e2eConfig.GetIntervals(bootstrapClusterProxy.GetName(), "wait-controllers")...) By("Waiting for the bootstrap provider object to be deleted") @@ -323,7 +323,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp By("Deleting capkb-system namespace") namespace := &corev1.Namespace{ ObjectMeta: metav1.ObjectMeta{ - Name: capkbSystemNamespace, + Name: cabpkSystemNamespace, }, } Expect(bootstrapCluster.Delete(ctx, namespace)).To(Succeed()) @@ -383,7 +383,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp bootstrapCluster := bootstrapClusterProxy.GetClient() ControlPlaneProvider := &operatorv1.ControlPlaneProvider{ObjectMeta: metav1.ObjectMeta{ Name: customProviderName, - Namespace: capkcpSystemNamespace, + Namespace: cacpkSystemNamespace, }} Expect(bootstrapCluster.Delete(ctx, ControlPlaneProvider)).To(Succeed()) @@ -391,7 +391,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp By("Waiting for the controlplane provider deployment to be deleted") WaitForDelete(ctx, For(&appsv1.Deployment{ObjectMeta: metav1.ObjectMeta{ Name: cpProviderDeploymentName, - Namespace: capkcpSystemNamespace, + Namespace: cacpkSystemNamespace, }}).In(bootstrapCluster), e2eConfig.GetIntervals(bootstrapClusterProxy.GetName(), "wait-controllers")...) By("Waiting for the controlplane provider object to be deleted") @@ -423,7 +423,7 @@ var _ = Describe("Install Controlplane, Core, Bootstrap Providers in an air-gapp By("Deleting capkcp-system namespace") namespace := &corev1.Namespace{ ObjectMeta: metav1.ObjectMeta{ - Name: capkcpSystemNamespace, + Name: cacpkSystemNamespace, }, } Expect(bootstrapCluster.Delete(ctx, namespace)).To(Succeed()) diff --git a/test/e2e/helpers_test.go b/test/e2e/helpers_test.go index 61639291..93cb38ef 100644 --- a/test/e2e/helpers_test.go +++ b/test/e2e/helpers_test.go @@ -27,11 +27,11 @@ import ( var ctx = context.Background() const ( - operatorNamespace = "capi-operator-system" - capkbSystemNamespace = "capi-kubeadm-bootstrap-system" - capkcpSystemNamespace = "capi-kubeadm-control-plane-system" - capiSystemNamespace = "capi-system" - capiOperatorRelease = "capi-operator" + operatorNamespace = "capi-operator-system" + cabpkSystemNamespace = "capi-kubeadm-bootstrap-system" + cacpkSystemNamespace = "capi-kubeadm-control-plane-system" + capiSystemNamespace = "capi-system" + capiOperatorRelease = "capi-operator" previousCAPIVersion = "v1.7.7" nextCAPIVersion = "v1.8.0" diff --git a/util/util.go b/util/util.go index bb204379..7901a2ac 100644 --- a/util/util.go +++ b/util/util.go @@ -70,6 +70,40 @@ func ClusterctlProviderType(genericProvider operatorv1.GenericProvider) clusterc return clusterctlv1.ProviderTypeUnknown } +// GetCustomProviders retrieves all custom providers using `FetchConfig` that aren't the current provider name / type. +func GetCustomProviders(ctx context.Context, cl ctrlclient.Client, currProvider genericprovider.GenericProvider) ([]operatorv1.GenericProvider, error) { + customProviders := []operatorv1.GenericProvider{} + currProviderName := currProvider.GetName() + currProviderType := currProvider.GetType() + + for _, providerList := range operatorv1.ProviderLists { + providerList, ok := providerList.(ctrlclient.ObjectList) + if !ok { + return nil, fmt.Errorf("cannot cast providers list to ObjectList") + } + + if err := cl.List(ctx, providerList); err != nil { + return nil, fmt.Errorf("cannot get a list of providers from the server: %w", err) + } + + genericProviderList, ok := providerList.(operatorv1.GenericProviderList) + if !ok { + return nil, fmt.Errorf("cannot cast providers list to GenericProviderList") + } + + genericProviderListItems := genericProviderList.GetItems() + for i, provider := range genericProviderListItems { + if provider.GetName() == currProviderName && provider.GetType() == currProviderType || provider.GetSpec().FetchConfig == nil { + continue + } + + customProviders = append(customProviders, genericProviderListItems[i]) + } + } + + return customProviders, nil +} + // GetGenericProvider returns the first of generic providers matching the type and the name from the configclient.Provider. func GetGenericProvider(ctx context.Context, cl ctrlclient.Client, provider configclient.Provider) (operatorv1.GenericProvider, error) { var list genericProviderList