@@ -180,14 +180,14 @@ func (r *MachineSyncReconciler) SetupWithManager(mgr ctrl.Manager) error {
180180
181181// Reconcile reconciles CAPI and MAPI machines for their respective namespaces.
182182//
183- //nolint:funlen
183+ //nolint:funlen,cyclop
184184func (r * MachineSyncReconciler ) Reconcile (ctx context.Context , req reconcile.Request ) (ctrl.Result , error ) {
185185 logger := logf .FromContext (ctx , "namespace" , req .Namespace , "name" , req .Name )
186186
187187 logger .V (1 ).Info ("Reconciling machine" )
188188 defer logger .V (1 ).Info ("Finished reconciling machine" )
189189
190- var mapiMachineNotFound , capiMachineNotFound bool
190+ var mapiMachineNotFound , capiMachineNotFound , capiInfraMachineExists bool
191191
192192 // Get the MAPI Machine.
193193 mapiMachine := & mapiv1beta1.Machine {}
@@ -243,12 +243,23 @@ func (r *MachineSyncReconciler) Reconcile(ctx context.Context, req reconcile.Req
243243 return ctrl.Result {}, nil
244244 }
245245
246+ // Check for existense of the Cluster API Infrastructure Machine or if it needs to get created from MAPI first.
247+ capiInfraMachineExists , err := r .doesCAPIInfraMachineExist (ctx , capiMachine , mapiMachine )
248+ if err != nil {
249+ return ctrl.Result {}, fmt .Errorf ("failed to check for existence of Cluster API infrastructure machine: %w" , err )
250+ }
251+
246252 authoritativeAPI := mapiMachine .Status .AuthoritativeAPI
247253
248254 switch {
249255 case authoritativeAPI == mapiv1beta1 .MachineAuthorityMachineAPI :
250256 return r .reconcileMAPIMachinetoCAPIMachine (ctx , mapiMachine , capiMachine )
251257 case authoritativeAPI == mapiv1beta1 .MachineAuthorityClusterAPI && ! capiMachineNotFound :
258+ // Create Cluster API Infrastructure Machine from MAPI if it doesn't exist and the MAPI machine was created before the Cluster API machine.
259+ if ! capiInfraMachineExists && (mapiMachine .CreationTimestamp .Equal (& capiMachine .CreationTimestamp ) || mapiMachine .CreationTimestamp .Before (& capiMachine .CreationTimestamp )) {
260+ return r .reconcileMAPIMachinetoCAPIMachine (ctx , mapiMachine , capiMachine )
261+ }
262+
252263 return r .reconcileCAPIMachinetoMAPIMachine (ctx , capiMachine , mapiMachine )
253264 case authoritativeAPI == mapiv1beta1 .MachineAuthorityClusterAPI && capiMachineNotFound :
254265 return r .reconcileMAPIMachinetoCAPIMachine (ctx , mapiMachine , capiMachine )
@@ -936,20 +947,14 @@ func (r *MachineSyncReconciler) fetchCAPIInfraResources(ctx context.Context, cap
936947 return nil , nil , nil
937948 }
938949
939- var infraCluster , infraMachine client.Object
950+ var infraCluster client.Object
940951
941952 infraClusterKey := client.ObjectKey {
942953 Namespace : capiMachine .Namespace ,
943954 Name : capiMachine .Spec .ClusterName ,
944955 }
945956
946- infraMachineRef := capiMachine .Spec .InfrastructureRef
947- infraMachineKey := client.ObjectKey {
948- Namespace : infraMachineRef .Namespace ,
949- Name : infraMachineRef .Name ,
950- }
951-
952- infraMachine , infraCluster , err := controllers .InitInfraMachineAndInfraClusterFromProvider (r .Platform )
957+ _ , infraCluster , err := controllers .InitInfraMachineAndInfraClusterFromProvider (r .Platform )
953958 if err != nil {
954959 return nil , nil , fmt .Errorf ("unable to devise Cluster API infra resources: %w" , err )
955960 }
@@ -958,13 +963,52 @@ func (r *MachineSyncReconciler) fetchCAPIInfraResources(ctx context.Context, cap
958963 return nil , nil , fmt .Errorf ("failed to get Cluster API infrastructure cluster: %w" , err )
959964 }
960965
966+ infraMachineRef := capiMachine .Spec .InfrastructureRef
967+
968+ infraMachine , err := r .fetchCAPIInfraMachine (ctx , infraMachineRef .Name , infraMachineRef .Namespace )
969+ if err != nil {
970+ return nil , nil , fmt .Errorf ("failed to fetch Cluster API infrastructure machine: %w" , err )
971+ }
972+
973+ return infraCluster , infraMachine , nil
974+ }
975+
976+ func (r * MachineSyncReconciler ) fetchCAPIInfraMachine (ctx context.Context , name , namespace string ) (client.Object , error ) {
977+ infraMachine , _ , err := controllers .InitInfraMachineAndInfraClusterFromProvider (r .Platform )
978+ if err != nil {
979+ return nil , fmt .Errorf ("unable to devise Cluster API infra resources: %w" , err )
980+ }
981+
982+ infraMachineKey := client.ObjectKey {
983+ Namespace : namespace ,
984+ Name : name ,
985+ }
986+
961987 if err := r .Get (ctx , infraMachineKey , infraMachine ); err != nil && ! apierrors .IsNotFound (err ) {
962- return nil , nil , fmt .Errorf ("failed to get Cluster API infrastructure machine : %w" , err )
988+ return nil , fmt .Errorf ("failed to get: %w" , err )
963989 } else if apierrors .IsNotFound (err ) {
964990 infraMachine = nil
965991 }
966992
967- return infraCluster , infraMachine , nil
993+ return infraMachine , nil
994+ }
995+
996+ // doesCAPIInfraMachineExist checks if the Cluster API Infrastructure Machine exists. It uses the infrastructureRef of the Cluster API Machine with fallback to the name of the MAPI Machine.
997+ func (r * MachineSyncReconciler ) doesCAPIInfraMachineExist (ctx context.Context , capiMachine * clusterv1.Machine , mapiMachine * mapiv1beta1.Machine ) (bool , error ) {
998+ namespace := r .CAPINamespace
999+ name := mapiMachine .Name
1000+
1001+ if capiMachine != nil {
1002+ name = capiMachine .Spec .InfrastructureRef .Name
1003+ namespace = capiMachine .Spec .InfrastructureRef .Namespace
1004+ }
1005+
1006+ infraMachine , err := r .fetchCAPIInfraMachine (ctx , name , namespace )
1007+ if err != nil {
1008+ return false , fmt .Errorf ("checking existence: %w" , err )
1009+ }
1010+
1011+ return infraMachine != nil , nil
9681012}
9691013
9701014//nolint:funlen,gocognit,cyclop
0 commit comments