From 13d2f4fa0a8a3f8d2528081e5473daf476a1669f Mon Sep 17 00:00:00 2001 From: Hardik Dodiya Date: Thu, 6 Jun 2024 18:58:38 +0000 Subject: [PATCH 1/4] Support HTTPBoot conversion for ServerBootConfiguration --- api/v1alpha1/httpbootconfig_types.go | 9 +- cmd/main.go | 26 ++- config/rbac/role.yaml | 17 ++ ...serverbootconfiguration_http_controller.go | 148 ++++++++++++++++++ ...serverbootconfiguration_pxe_controller.go} | 0 ...rbootconfiguration_pxe_controller_test.go} | 0 6 files changed, 189 insertions(+), 11 deletions(-) create mode 100644 internal/controller/serverbootconfiguration_http_controller.go rename internal/controller/{serverbootconfiguration_controller.go => serverbootconfiguration_pxe_controller.go} (100%) rename internal/controller/{serverbootconfiguration_controller_test.go => serverbootconfiguration_pxe_controller_test.go} (100%) diff --git a/api/v1alpha1/httpbootconfig_types.go b/api/v1alpha1/httpbootconfig_types.go index 0bdd7b36..f839aa67 100644 --- a/api/v1alpha1/httpbootconfig_types.go +++ b/api/v1alpha1/httpbootconfig_types.go @@ -29,10 +29,11 @@ const ( HTTPBootConfigStateError HTTPBootConfigState = "Error" ) -//+kubebuilder:object:root=true -//+kubebuilder:subresource:status -//+kubebuilder:printcolumn:name="State",type=string,JSONPath=`.status.state` -//+kubebuilder:printcolumn:name="Age",type=date,JSONPath=`.metadata.creationTimestamp` +// +kubebuilder:object:root=true +// +kubebuilder:subresource:status +// +kubebuilder:printcolumn:name="State",type=string,JSONPath=`.status.state` +// +kubebuilder:printcolumn:name="Age",type=date,JSONPath=`.metadata.creationTimestamp` +// +genclient // HTTPBootConfig is the Schema for the httpbootconfigs API type HTTPBootConfig struct { diff --git a/cmd/main.go b/cmd/main.go index 7bb912d8..bef134f7 100644 --- a/cmd/main.go +++ b/cmd/main.go @@ -41,9 +41,10 @@ var ( const ( // core controllers - ipxeBootConfigController = "ipxebootconfig" - serverBootConfigController = "serverbootconfig" - httpBootConfigController = "httpbootconfig" + ipxeBootConfigController = "ipxebootconfig" + serverBootConfigControllerPxe = "serverbootconfigpxe" + httpBootConfigController = "httpbootconfig" + serverBootConfigControllerHttp = "serverbootconfighttp" ) func init() { @@ -88,7 +89,8 @@ func main() { controllers := switches.New( // core controllers ipxeBootConfigController, - serverBootConfigController, + serverBootConfigControllerPxe, + serverBootConfigControllerHttp, httpBootConfigController, ) @@ -176,13 +178,23 @@ func main() { } } - if controllers.Enabled(serverBootConfigController) { - if err = (&controller.ServerBootConfigurationReconciler{ + if controllers.Enabled(serverBootConfigControllerPxe) { + if err = (&controller.ServerBootConfigurationReconciler{ // TODO: Fix this, add pxe hint. Client: mgr.GetClient(), Scheme: mgr.GetScheme(), IPXEServiceURL: ipxeServiceURL, }).SetupWithManager(mgr); err != nil { - setupLog.Error(err, "unable to create controller", "controller", "ServerBootConfig") + setupLog.Error(err, "unable to create controller", "controller", "ServerBootConfigPxe") + os.Exit(1) + } + } + + if controllers.Enabled(serverBootConfigControllerHttp) { + if err = (&controller.ServerBootConfigurationHTTPReconciler{ + Client: mgr.GetClient(), + Scheme: mgr.GetScheme(), + }).SetupWithManager(mgr); err != nil { + setupLog.Error(err, "unable to create controller", "controller", "ServerBootConfigHttp") os.Exit(1) } } diff --git a/config/rbac/role.yaml b/config/rbac/role.yaml index cd557415..781af475 100644 --- a/config/rbac/role.yaml +++ b/config/rbac/role.yaml @@ -12,6 +12,23 @@ rules: - get - list - watch +- apiGroups: + - boot.ironcore.dev + resources: + - httpbootconfig + verbs: + - create + - delete + - get + - list + - patch + - watch +- apiGroups: + - boot.ironcore.dev + resources: + - httpbootconfig/status + verbs: + - get - apiGroups: - boot.ironcore.dev resources: diff --git a/internal/controller/serverbootconfiguration_http_controller.go b/internal/controller/serverbootconfiguration_http_controller.go new file mode 100644 index 00000000..4b7d77b7 --- /dev/null +++ b/internal/controller/serverbootconfiguration_http_controller.go @@ -0,0 +1,148 @@ +package controller + +import ( + "context" + "fmt" + "strings" + + "github.com/go-logr/logr" + "github.com/ironcore-dev/ipxe-operator/api/v1alpha1" + bootv1alpha1 "github.com/ironcore-dev/ipxe-operator/api/v1alpha1" + corev1 "k8s.io/api/core/v1" + metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" + "k8s.io/apimachinery/pkg/runtime" + ctrl "sigs.k8s.io/controller-runtime" + "sigs.k8s.io/controller-runtime/pkg/client" + "sigs.k8s.io/controller-runtime/pkg/controller/controllerutil" + + metalv1alpha1 "github.com/afritzler/metal-operator/api/v1alpha1" +) + +type ServerBootConfigurationHTTPReconciler struct { + client.Client + Scheme *runtime.Scheme + ImageServerURL string +} + +//+kubebuilder:rbac:groups=metal.ironcore.dev,resources=serverbootconfigurations,verbs=get;list;watch +//+kubebuilder:rbac:groups=metal.ironcore.dev,resources=serverbootconfigurations/status,verbs=get;update;patch +//+kubebuilder:rbac:groups=metal.ironcore.dev,resources=serverbootconfigurations/finalizers,verbs=update +//+kubebuilder:rbac:groups=boot.ironcore.dev,resources=httpbootconfig,verbs=get;list;watch;create;delete;patch +//+kubebuilder:rbac:groups=boot.ironcore.dev,resources=httpbootconfig/status,verbs=get +//+kubebuilder:rbac:groups=metal.ironcore.dev,resources=servers,verbs=get;list;watch + +func (r *ServerBootConfigurationHTTPReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl.Result, error) { + log := ctrl.LoggerFrom(ctx) + bootConfig := &metalv1alpha1.ServerBootConfiguration{} + if err := r.Get(ctx, req.NamespacedName, bootConfig); err != nil { + return ctrl.Result{}, client.IgnoreNotFound(err) + } + + return r.reconcileExists(ctx, log, bootConfig) +} + +func (r *ServerBootConfigurationHTTPReconciler) reconcileExists(ctx context.Context, log logr.Logger, config *metalv1alpha1.ServerBootConfiguration) (ctrl.Result, error) { + if !config.DeletionTimestamp.IsZero() { + return r.delete(ctx, log, config) + } + return r.reconcile(ctx, log, config) +} + +func (r *ServerBootConfigurationHTTPReconciler) delete(ctx context.Context, log logr.Logger, config *metalv1alpha1.ServerBootConfiguration) (ctrl.Result, error) { + // TODO + return ctrl.Result{}, nil +} + +func (r *ServerBootConfigurationHTTPReconciler) reconcile(ctx context.Context, log logr.Logger, config *metalv1alpha1.ServerBootConfiguration) (ctrl.Result, error) { + log.V(1).Info("Reconciling ServerBootConfiguration for HTTPBoot") + + systemUUID, err := r.getSystemUUIDFromServer(ctx, config) + if err != nil { + return ctrl.Result{}, fmt.Errorf("failed to get system UUID from Server: %w", err) + } + log.V(1).Info("Got system UUID from Server", "systemUUID", systemUUID) + + systemIPs, err := r.getSystemIPFromServer(ctx, config) + if err != nil { + return ctrl.Result{}, fmt.Errorf("failed to get system IPs from Server: %w", err) + } + log.V(1).Info("Got system IPs from Server", "systemIPs", systemIPs) + + ukiURL, err := r.constructUKIURL(config.Spec.Image) + if err != nil { + return ctrl.Result{}, fmt.Errorf("failed to get UKI URL from Config: %w", err) + } + log.V(1).Info("Extracted UKI URL for boot") + + httpBootConfig := &bootv1alpha1.HTTPBootConfig{ + TypeMeta: metav1.TypeMeta{ + APIVersion: "boot.ironcore.dev/v1alpha1", + Kind: "HTTPBootConfig", + }, + ObjectMeta: metav1.ObjectMeta{ + Namespace: config.Namespace, + Name: config.Name, + }, + Spec: bootv1alpha1.HTTPBootConfigSpec{ + SystemUUID: systemUUID, + SystemIPs: systemIPs, + UKIURL: ukiURL, + IgnitionSecretRef: &corev1.LocalObjectReference{Name: config.Spec.IgnitionSecretRef.Name}, + }, + } + + if err := controllerutil.SetControllerReference(config, httpBootConfig, r.Scheme); err != nil { + return ctrl.Result{}, fmt.Errorf("failed to set controller reference: %w", err) + } + log.V(1).Info("Set controller reference") + + if err := r.Patch(ctx, httpBootConfig, client.Apply, client.FieldOwner("server-boot-controller"), client.ForceOwnership); err != nil { + return ctrl.Result{}, fmt.Errorf("failed to apply HTTPBoot config: %w", err) + } + log.V(1).Info("Applied HTTPBoot config for server boot configuration") + + return ctrl.Result{}, nil +} + +// getSystemUUIDFromServer fetches the UUID from the referenced Server object. +func (r *ServerBootConfigurationHTTPReconciler) getSystemUUIDFromServer(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration) (string, error) { + server := &metalv1alpha1.Server{} + if err := r.Get(ctx, client.ObjectKey{Name: config.Spec.ServerRef.Name}, server); err != nil { + return "", fmt.Errorf("failed to get Server: %w", err) + } + return server.Spec.UUID, nil +} + +// getSystemIPFromServer fetches the IPs from the network interfaces of the referenced Server object. +func (r *ServerBootConfigurationHTTPReconciler) getSystemIPFromServer(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration) ([]string, error) { + server := &metalv1alpha1.Server{} + if err := r.Get(ctx, client.ObjectKey{Name: config.Spec.ServerRef.Name}, server); err != nil { + return nil, fmt.Errorf("failed to get Server: %w", err) + } + + systemIPs := make([]string, len(server.Status.NetworkInterfaces)) + for i, nic := range server.Status.NetworkInterfaces { + systemIPs[i] = nic.IP.String() // Ensure the IP address format is handled correctly + } + return systemIPs, nil +} + +func (r *ServerBootConfigurationHTTPReconciler) constructUKIURL(image string) (string, error) { + sanitizedImage := strings.Replace(image, "/", "-", -1) + sanitizedImage = strings.Replace(sanitizedImage, ":", "-", -1) + sanitizedImage = strings.Replace(sanitizedImage, "https://", "", -1) + sanitizedImage = strings.Replace(sanitizedImage, "http://", "", -1) + + filename := fmt.Sprintf("%s-uki.efi", sanitizedImage) + + ukiURL := fmt.Sprintf("%s/%s", r.ImageServerURL, filename) + return ukiURL, nil +} + +// SetupWithManager sets up the controller with the Manager. +func (r *ServerBootConfigurationHTTPReconciler) SetupWithManager(mgr ctrl.Manager) error { + return ctrl.NewControllerManagedBy(mgr). + For(&metalv1alpha1.ServerBootConfiguration{}). + Owns(&v1alpha1.HTTPBootConfig{}). + Complete(r) +} diff --git a/internal/controller/serverbootconfiguration_controller.go b/internal/controller/serverbootconfiguration_pxe_controller.go similarity index 100% rename from internal/controller/serverbootconfiguration_controller.go rename to internal/controller/serverbootconfiguration_pxe_controller.go diff --git a/internal/controller/serverbootconfiguration_controller_test.go b/internal/controller/serverbootconfiguration_pxe_controller_test.go similarity index 100% rename from internal/controller/serverbootconfiguration_controller_test.go rename to internal/controller/serverbootconfiguration_pxe_controller_test.go From dde467f9451c808a21553d6aef03c04a31b2c6a2 Mon Sep 17 00:00:00 2001 From: Hardik Dodiya Date: Thu, 6 Jun 2024 19:04:34 +0000 Subject: [PATCH 2/4] Adapt hint of PXE in ServerBootConfigReconciler --- cmd/main.go | 9 +++++--- .../serverbootconfiguration_pxe_controller.go | 22 +++++++++---------- internal/controller/suite_test.go | 2 +- 3 files changed, 18 insertions(+), 15 deletions(-) diff --git a/cmd/main.go b/cmd/main.go index bef134f7..58e6714e 100644 --- a/cmd/main.go +++ b/cmd/main.go @@ -70,10 +70,12 @@ func main() { var ipxeServiceURL string var ipxeServiceProtocol string var ipxeServicePort int + var imageServerURL string flag.IntVar(&ipxeServicePort, "ipxe-service-port", 5000, "IPXE Service port to listen on.") flag.StringVar(&ipxeServiceProtocol, "ipxe-service-protocol", "http", "IPXE Service Protocol.") flag.StringVar(&ipxeServiceURL, "ipxe-service-url", "", "IPXE Service URL.") + flag.StringVar(&imageServerURL, "image-server-url", "", "OS Image Server URL.") flag.StringVar(&metricsAddr, "metrics-bind-address", ":8080", "The address the metric endpoint binds to.") flag.StringVar(&probeAddr, "health-probe-bind-address", ":8081", "The address the probe endpoint binds to.") flag.StringVar(&ipxeServerAddr, "ipxe-server-address", ":8082", "The address the ipxe-server binds to.") @@ -179,7 +181,7 @@ func main() { } if controllers.Enabled(serverBootConfigControllerPxe) { - if err = (&controller.ServerBootConfigurationReconciler{ // TODO: Fix this, add pxe hint. + if err = (&controller.ServerBootConfigurationPXEReconciler{ Client: mgr.GetClient(), Scheme: mgr.GetScheme(), IPXEServiceURL: ipxeServiceURL, @@ -191,8 +193,9 @@ func main() { if controllers.Enabled(serverBootConfigControllerHttp) { if err = (&controller.ServerBootConfigurationHTTPReconciler{ - Client: mgr.GetClient(), - Scheme: mgr.GetScheme(), + Client: mgr.GetClient(), + Scheme: mgr.GetScheme(), + ImageServerURL: imageServerURL, }).SetupWithManager(mgr); err != nil { setupLog.Error(err, "unable to create controller", "controller", "ServerBootConfigHttp") os.Exit(1) diff --git a/internal/controller/serverbootconfiguration_pxe_controller.go b/internal/controller/serverbootconfiguration_pxe_controller.go index bff6ab3e..da3ba8ce 100644 --- a/internal/controller/serverbootconfiguration_pxe_controller.go +++ b/internal/controller/serverbootconfiguration_pxe_controller.go @@ -34,7 +34,7 @@ import ( "sigs.k8s.io/controller-runtime/pkg/client" ) -type ServerBootConfigurationReconciler struct { +type ServerBootConfigurationPXEReconciler struct { client.Client Scheme *runtime.Scheme IPXEServiceURL string @@ -49,7 +49,7 @@ type ServerBootConfigurationReconciler struct { // Reconcile is part of the main kubernetes reconciliation loop which aims to // move the current state of the cluster closer to the desired state. -func (r *ServerBootConfigurationReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl.Result, error) { +func (r *ServerBootConfigurationPXEReconciler) Reconcile(ctx context.Context, req ctrl.Request) (ctrl.Result, error) { log := ctrl.LoggerFrom(ctx) bootConfig := &metalv1alpha1.ServerBootConfiguration{} if err := r.Get(ctx, req.NamespacedName, bootConfig); err != nil { @@ -59,18 +59,18 @@ func (r *ServerBootConfigurationReconciler) Reconcile(ctx context.Context, req c return r.reconcileExists(ctx, log, bootConfig) } -func (r *ServerBootConfigurationReconciler) reconcileExists(ctx context.Context, log logr.Logger, config *metalv1alpha1.ServerBootConfiguration) (ctrl.Result, error) { +func (r *ServerBootConfigurationPXEReconciler) reconcileExists(ctx context.Context, log logr.Logger, config *metalv1alpha1.ServerBootConfiguration) (ctrl.Result, error) { if !config.DeletionTimestamp.IsZero() { return r.delete(ctx, log, config) } return r.reconcile(ctx, log, config) } -func (r *ServerBootConfigurationReconciler) delete(ctx context.Context, log logr.Logger, config *metalv1alpha1.ServerBootConfiguration) (ctrl.Result, error) { +func (r *ServerBootConfigurationPXEReconciler) delete(ctx context.Context, log logr.Logger, config *metalv1alpha1.ServerBootConfiguration) (ctrl.Result, error) { return ctrl.Result{}, nil } -func (r *ServerBootConfigurationReconciler) reconcile(ctx context.Context, log logr.Logger, config *metalv1alpha1.ServerBootConfiguration) (ctrl.Result, error) { +func (r *ServerBootConfigurationPXEReconciler) reconcile(ctx context.Context, log logr.Logger, config *metalv1alpha1.ServerBootConfiguration) (ctrl.Result, error) { log.V(1).Info("Reconciling ServerBootConfiguration") systemUUID, err := r.getSystemUUIDFromBootConfig(ctx, config) @@ -133,7 +133,7 @@ func (r *ServerBootConfigurationReconciler) reconcile(ctx context.Context, log l return ctrl.Result{}, nil } -func (r *ServerBootConfigurationReconciler) patchConfigStateFromIPXEState(ctx context.Context, ipxeConfig *v1alpha1.IPXEBootConfig, config *metalv1alpha1.ServerBootConfiguration) error { +func (r *ServerBootConfigurationPXEReconciler) patchConfigStateFromIPXEState(ctx context.Context, ipxeConfig *v1alpha1.IPXEBootConfig, config *metalv1alpha1.ServerBootConfiguration) error { if ipxeConfig.Status.State == v1alpha1.IPXEBootConfigStateReady { return r.patchState(ctx, config, metalv1alpha1.ServerBootConfigurationStateReady) } @@ -144,7 +144,7 @@ func (r *ServerBootConfigurationReconciler) patchConfigStateFromIPXEState(ctx co return nil } -func (r *ServerBootConfigurationReconciler) patchState(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration, state metalv1alpha1.ServerBootConfigurationState) error { +func (r *ServerBootConfigurationPXEReconciler) patchState(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration, state metalv1alpha1.ServerBootConfigurationState) error { configBase := config.DeepCopy() config.Status.State = state if err := r.Status().Patch(ctx, config, client.MergeFrom(configBase)); err != nil { @@ -153,7 +153,7 @@ func (r *ServerBootConfigurationReconciler) patchState(ctx context.Context, conf return nil } -func (r *ServerBootConfigurationReconciler) getSystemUUIDFromBootConfig(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration) (string, error) { +func (r *ServerBootConfigurationPXEReconciler) getSystemUUIDFromBootConfig(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration) (string, error) { server := &metalv1alpha1.Server{} if err := r.Get(ctx, client.ObjectKey{Name: config.Spec.ServerRef.Name}, server); err != nil { return "", fmt.Errorf("failed to get Server: %w", err) @@ -162,7 +162,7 @@ func (r *ServerBootConfigurationReconciler) getSystemUUIDFromBootConfig(ctx cont return server.Spec.UUID, nil } -func (r *ServerBootConfigurationReconciler) getSystemIPFromBootConfig(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration) ([]string, error) { +func (r *ServerBootConfigurationPXEReconciler) getSystemIPFromBootConfig(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration) ([]string, error) { server := &metalv1alpha1.Server{} if err := r.Get(ctx, client.ObjectKey{Name: config.Spec.ServerRef.Name}, server); err != nil { return nil, fmt.Errorf("failed to get Server: %w", err) @@ -177,7 +177,7 @@ func (r *ServerBootConfigurationReconciler) getSystemIPFromBootConfig(ctx contex return nil, nil } -func (r *ServerBootConfigurationReconciler) getImageDetailsFromConfig(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration) (string, string, string, error) { +func (r *ServerBootConfigurationPXEReconciler) getImageDetailsFromConfig(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration) (string, string, string, error) { imageDetails := strings.Split(config.Spec.Image, ":") if len(imageDetails) != 2 { return "", "", "", fmt.Errorf("invalid image format") @@ -192,7 +192,7 @@ func (r *ServerBootConfigurationReconciler) getImageDetailsFromConfig(ctx contex } // SetupWithManager sets up the controller with the Manager. -func (r *ServerBootConfigurationReconciler) SetupWithManager(mgr ctrl.Manager) error { +func (r *ServerBootConfigurationPXEReconciler) SetupWithManager(mgr ctrl.Manager) error { return ctrl.NewControllerManagedBy(mgr). For(&metalv1alpha1.ServerBootConfiguration{}). Owns(&v1alpha1.IPXEBootConfig{}). diff --git a/internal/controller/suite_test.go b/internal/controller/suite_test.go index 025f2f24..2891d686 100644 --- a/internal/controller/suite_test.go +++ b/internal/controller/suite_test.go @@ -121,7 +121,7 @@ func SetupTest() *corev1.Namespace { }) Expect(err).ToNot(HaveOccurred()) - Expect((&ServerBootConfigurationReconciler{ + Expect((&ServerBootConfigurationPXEReconciler{ Client: k8sManager.GetClient(), Scheme: k8sManager.GetScheme(), IPXEServiceURL: "http://localhost:5000", From cfd7f7cf8e8d7d650d89c0c0dff4391a8d62ca5d Mon Sep 17 00:00:00 2001 From: Hardik Dodiya Date: Thu, 6 Jun 2024 19:14:02 +0000 Subject: [PATCH 3/4] Update state of the ServerBootConfig --- ...serverbootconfiguration_http_controller.go | 31 +++++++++++++++++++ 1 file changed, 31 insertions(+) diff --git a/internal/controller/serverbootconfiguration_http_controller.go b/internal/controller/serverbootconfiguration_http_controller.go index 4b7d77b7..4f1c2fce 100644 --- a/internal/controller/serverbootconfiguration_http_controller.go +++ b/internal/controller/serverbootconfiguration_http_controller.go @@ -101,9 +101,40 @@ func (r *ServerBootConfigurationHTTPReconciler) reconcile(ctx context.Context, l } log.V(1).Info("Applied HTTPBoot config for server boot configuration") + if err := r.Get(ctx, client.ObjectKey{Namespace: config.Namespace, Name: config.Name}, httpBootConfig); err != nil { + return ctrl.Result{}, fmt.Errorf("failed to get HTTPBoot config: %w", err) + } + + if err := r.patchConfigStateFromHTTPState(ctx, httpBootConfig, config); err != nil { + return ctrl.Result{}, fmt.Errorf("failed to patch server boot config state to %s: %w", httpBootConfig.Status.State, err) + } + log.V(1).Info("Patched server boot config state") + + log.V(1).Info("Reconciled ServerBootConfiguration") + return ctrl.Result{}, nil } +func (r *ServerBootConfigurationHTTPReconciler) patchConfigStateFromHTTPState(ctx context.Context, httpBootConfig *v1alpha1.HTTPBootConfig, config *metalv1alpha1.ServerBootConfiguration) error { + if httpBootConfig.Status.State == bootv1alpha1.HTTPBootConfigStateReady { + return r.patchState(ctx, config, metalv1alpha1.ServerBootConfigurationStateReady) + } + + if httpBootConfig.Status.State == bootv1alpha1.HTTPBootConfigStateError { + return r.patchState(ctx, config, metalv1alpha1.ServerBootConfigurationStateError) + } + return nil +} + +func (r *ServerBootConfigurationHTTPReconciler) patchState(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration, state metalv1alpha1.ServerBootConfigurationState) error { + configBase := config.DeepCopy() + config.Status.State = state + if err := r.Status().Patch(ctx, config, client.MergeFrom(configBase)); err != nil { + return err + } + return nil +} + // getSystemUUIDFromServer fetches the UUID from the referenced Server object. func (r *ServerBootConfigurationHTTPReconciler) getSystemUUIDFromServer(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration) (string, error) { server := &metalv1alpha1.Server{} From 3278710c0ef0eaf68c5b2cf10f430bea2436fb4f Mon Sep 17 00:00:00 2001 From: Hardik Dodiya Date: Thu, 6 Jun 2024 21:56:53 +0000 Subject: [PATCH 4/4] Add MACAddresses as well to bootconfig identifiers --- .../controller/serverbootconfiguration_http_controller.go | 7 ++++--- .../controller/serverbootconfiguration_pxe_controller.go | 3 +-- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/internal/controller/serverbootconfiguration_http_controller.go b/internal/controller/serverbootconfiguration_http_controller.go index 4f1c2fce..7c4b729b 100644 --- a/internal/controller/serverbootconfiguration_http_controller.go +++ b/internal/controller/serverbootconfiguration_http_controller.go @@ -151,9 +151,10 @@ func (r *ServerBootConfigurationHTTPReconciler) getSystemIPFromServer(ctx contex return nil, fmt.Errorf("failed to get Server: %w", err) } - systemIPs := make([]string, len(server.Status.NetworkInterfaces)) - for i, nic := range server.Status.NetworkInterfaces { - systemIPs[i] = nic.IP.String() // Ensure the IP address format is handled correctly + var systemIPs []string + for _, nic := range server.Status.NetworkInterfaces { + systemIPs = append(systemIPs, nic.IP.String()) + systemIPs = append(systemIPs, nic.MACAddress) } return systemIPs, nil } diff --git a/internal/controller/serverbootconfiguration_pxe_controller.go b/internal/controller/serverbootconfiguration_pxe_controller.go index da3ba8ce..dba3fd9a 100644 --- a/internal/controller/serverbootconfiguration_pxe_controller.go +++ b/internal/controller/serverbootconfiguration_pxe_controller.go @@ -171,10 +171,9 @@ func (r *ServerBootConfigurationPXEReconciler) getSystemIPFromBootConfig(ctx con systemIPs := []string{} for _, nic := range server.Status.NetworkInterfaces { systemIPs = append(systemIPs, nic.IP.String()) - return systemIPs, nil } - return nil, nil + return systemIPs, nil } func (r *ServerBootConfigurationPXEReconciler) getImageDetailsFromConfig(ctx context.Context, config *metalv1alpha1.ServerBootConfiguration) (string, string, string, error) {