Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
65 changes: 65 additions & 0 deletions api/v1alpha1/bmc_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -206,6 +206,10 @@ type BMCStatus struct {
// +optional
LastResetTime *metav1.Time `json:"lastResetTime,omitempty"`

// Tasks tracks ongoing and recent BMC operations.
// +optional
Tasks []BMCTask `json:"tasks,omitempty"`

// Conditions represents the latest available observations of the BMC's current state.
// +patchStrategy=merge
// +patchMergeKey=type
Expand All @@ -227,6 +231,67 @@ const (
BMCStatePending BMCState = "Pending"
)

// BMCTask represents a single BMC operation task.
type BMCTask struct {
// TaskURI is the URI to monitor the task on the BMC.
// +required
TaskURI string `json:"taskURI"`

// TaskType indicates the type of operation.
// +required
// +kubebuilder:validation:Enum=DiskErase;BIOSReset;BMCReset;NetworkClear;FirmwareUpdate;ConfigurationChange;AccountManagement;Other
TaskType BMCTaskType `json:"taskType"`

// TargetID identifies what the task is operating on (e.g., "BIOS", "BMC", "Drive-1").
// +optional
TargetID string `json:"targetID,omitempty"`

// State is the current state of the task.
// +optional
State string `json:"state,omitempty"`

// PercentComplete indicates completion percentage (0-100).
// +optional
PercentComplete int32 `json:"percentComplete,omitempty"`

// Message provides additional information about the task.
// +optional
Message string `json:"message,omitempty"`

// LastUpdateTime is when this task status was last updated.
// +optional
LastUpdateTime metav1.Time `json:"lastUpdateTime,omitempty"`
}

// BMCTaskType defines the type of BMC task.
type BMCTaskType string

const (
// BMCTaskTypeDiskErase indicates a disk erasing task.
BMCTaskTypeDiskErase BMCTaskType = "DiskErase"

// BMCTaskTypeBIOSReset indicates a BIOS reset task.
BMCTaskTypeBIOSReset BMCTaskType = "BIOSReset"

// BMCTaskTypeBMCReset indicates a BMC reset task.
BMCTaskTypeBMCReset BMCTaskType = "BMCReset"

// BMCTaskTypeNetworkClear indicates a network configuration clear task.
BMCTaskTypeNetworkClear BMCTaskType = "NetworkClear"

// BMCTaskTypeFirmwareUpdate indicates a firmware update task (BIOS or BMC).
BMCTaskTypeFirmwareUpdate BMCTaskType = "FirmwareUpdate"

// BMCTaskTypeConfigurationChange indicates a configuration change task.
BMCTaskTypeConfigurationChange BMCTaskType = "ConfigurationChange"

// BMCTaskTypeAccountManagement indicates an account management task.
BMCTaskTypeAccountManagement BMCTaskType = "AccountManagement"

// BMCTaskTypeOther indicates a task type not covered by the specific types.
BMCTaskTypeOther BMCTaskType = "Other"
)

// +kubebuilder:object:root=true
// +kubebuilder:subresource:status
// +kubebuilder:resource:scope=Cluster
Expand Down
23 changes: 23 additions & 0 deletions api/v1alpha1/zz_generated.deepcopy.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

3 changes: 3 additions & 0 deletions bmc/bmc.go
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,9 @@ type BMC interface {
// GetBMCUpgradeTask retrieves the task for the BMC upgrade.
GetBMCUpgradeTask(ctx context.Context, manufacturer string, taskURI string) (*schemas.Task, error)

// GetTaskStatus retrieves the status of a task by its URI.
GetTaskStatus(ctx context.Context, taskURI string) (*schemas.Task, error)

// CreateOrUpdateAccount creates or updates a BMC user account.
CreateOrUpdateAccount(ctx context.Context, userName, role, password string, enabled bool) error

Expand Down
23 changes: 23 additions & 0 deletions bmc/redfish.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import (
"io"
"maps"
"math/big"
"net/http"
"slices"
"strings"
"time"
Expand Down Expand Up @@ -873,6 +874,28 @@ func (r *RedfishBaseBMC) GetBMCUpgradeTask(_ context.Context, _ string, _ string
return nil, fmt.Errorf("firmware upgrade task not supported for manufacturer %q", r.manufacturer)
}

// GetTaskStatus retrieves the status of a task by its URI.
func (r *RedfishBaseBMC) GetTaskStatus(ctx context.Context, taskURI string) (*schemas.Task, error) {
client := r.client.GetService().GetClient()

resp, err := client.Get(taskURI)
if err != nil {
return nil, fmt.Errorf("failed to get task status: %w", err)
}
defer resp.Body.Close() // nolint: errcheck

if resp.StatusCode != http.StatusOK {
return nil, fmt.Errorf("unexpected status code %d when getting task status", resp.StatusCode)
}

var task schemas.Task
if err := json.NewDecoder(resp.Body).Decode(&task); err != nil {
return nil, fmt.Errorf("failed to decode task response: %w", err)
}

return &task, nil
}

const (
charLower = "abcdefghijklmnopqrstuvwxyz"
charUpper = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
Expand Down
6 changes: 6 additions & 0 deletions bmc/redfish_kube.go
Original file line number Diff line number Diff line change
Expand Up @@ -367,6 +367,12 @@ func (r *RedfishKubeBMC) GetBMCUpgradeTask(ctx context.Context, manufacturer, ta
return task, nil
}

// GetTaskStatus retrieves the status of a task by its URI.
func (r *RedfishKubeBMC) GetTaskStatus(ctx context.Context, taskURI string) (*schemas.Task, error) {
// Delegate to the underlying RedfishBaseBMC implementation
return r.RedfishBaseBMC.GetTaskStatus(ctx, taskURI)
}

// SetPXEBootOnce sets the boot device for the next system boot using Redfish.
func (r *RedfishKubeBMC) SetPXEBootOnce(ctx context.Context, systemURI string) error {
system, err := r.getSystemFromUri(ctx, systemURI)
Expand Down
15 changes: 15 additions & 0 deletions cmd/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,7 @@ func main() { // nolint: gocyclo
serverMaxConcurrentReconciles int
serverClaimMaxConcurrentReconciles int
dnsRecordTemplatePath string
taskPollInterval time.Duration
)

flag.IntVar(&serverMaxConcurrentReconciles, "server-max-concurrent-reconciles", 5,
Expand Down Expand Up @@ -153,6 +154,8 @@ func main() { // nolint: gocyclo
"Timeout for BIOS Settings Controller")
flag.StringVar(&dnsRecordTemplatePath, "dns-record-template-path", "",
"Path to the DNS record template file used for creating DNS records for Servers.")
flag.DurationVar(&taskPollInterval, "task-poll-interval", 30*time.Second,
"Interval for polling BMC task status.")

opts := zap.Options{
Development: true,
Expand Down Expand Up @@ -527,6 +530,18 @@ func main() { // nolint: gocyclo
setupLog.Error(err, "Failed to create controller", "controller", "BMCUser")
os.Exit(1)
}
if err = (&controller.BMCTaskReconciler{
Client: mgr.GetClient(),
Scheme: mgr.GetScheme(),
Insecure: insecure,
PollInterval: taskPollInterval,
BMCOptions: bmc.Options{
BasicAuth: true,
},
}).SetupWithManager(mgr); err != nil {
setupLog.Error(err, "Failed to create controller", "controller", "BMCTask")
os.Exit(1)
}

// nolint:goconst
if os.Getenv("ENABLE_WEBHOOKS") != "false" {
Expand Down
46 changes: 46 additions & 0 deletions config/crd/bases/metal.ironcore.dev_bmcs.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -284,6 +284,52 @@ spec:
State represents the current state of the BMC.
kubebuilder:validation:Enum=Enabled;Error;Pending
type: string
tasks:
description: Tasks tracks ongoing and recent BMC operations.
items:
description: BMCTask represents a single BMC operation task.
properties:
lastUpdateTime:
description: LastUpdateTime is when this task status was last
updated.
format: date-time
type: string
message:
description: Message provides additional information about the
task.
type: string
percentComplete:
description: PercentComplete indicates completion percentage
(0-100).
format: int32
type: integer
state:
description: State is the current state of the task.
type: string
targetID:
description: TargetID identifies what the task is operating
on (e.g., "BIOS", "BMC", "Drive-1").
type: string
taskType:
description: TaskType indicates the type of operation.
enum:
- DiskErase
- BIOSReset
- BMCReset
- NetworkClear
- FirmwareUpdate
- ConfigurationChange
- AccountManagement
- Other
type: string
taskURI:
description: TaskURI is the URI to monitor the task on the BMC.
type: string
required:
- taskType
- taskURI
type: object
type: array
type: object
type: object
served: true
Expand Down
46 changes: 46 additions & 0 deletions docs/api-reference/api.md
Original file line number Diff line number Diff line change
Expand Up @@ -670,9 +670,55 @@ _Appears in:_
| `state` _[BMCState](#bmcstate)_ | State represents the current state of the BMC.<br />kubebuilder:validation:Enum=Enabled;Error;Pending | Pending | |
| `powerState` _[BMCPowerState](#bmcpowerstate)_ | PowerState represents the current power state of the BMC. | | |
| `lastResetTime` _[Time](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.35/#time-v1-meta)_ | LastResetTime is the timestamp of the last reset operation performed on the BMC. | | |
| `tasks` _[BMCTask](#bmctask) array_ | Tasks tracks ongoing and recent BMC operations. | | |
| `conditions` _[Condition](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.35/#condition-v1-meta) array_ | Conditions represents the latest available observations of the BMC's current state. | | |


#### BMCTask



BMCTask represents a single BMC operation task.



_Appears in:_
- [BMCStatus](#bmcstatus)

| Field | Description | Default | Validation |
| --- | --- | --- | --- |
| `taskURI` _string_ | TaskURI is the URI to monitor the task on the BMC. | | |
| `taskType` _[BMCTaskType](#bmctasktype)_ | TaskType indicates the type of operation. | | Enum: [DiskErase BIOSReset BMCReset NetworkClear FirmwareUpdate ConfigurationChange AccountManagement Other] <br /> |
| `targetID` _string_ | TargetID identifies what the task is operating on (e.g., "BIOS", "BMC", "Drive-1"). | | |
| `state` _string_ | State is the current state of the task. | | |
| `percentComplete` _integer_ | PercentComplete indicates completion percentage (0-100). | | |
| `message` _string_ | Message provides additional information about the task. | | |
| `lastUpdateTime` _[Time](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.35/#time-v1-meta)_ | LastUpdateTime is when this task status was last updated. | | |


#### BMCTaskType

_Underlying type:_ _string_

BMCTaskType defines the type of BMC task.



_Appears in:_
- [BMCTask](#bmctask)

| Field | Description |
| --- | --- |
| `DiskErase` | BMCTaskTypeDiskErase indicates a disk erasing task.<br /> |
| `BIOSReset` | BMCTaskTypeBIOSReset indicates a BIOS reset task.<br /> |
| `BMCReset` | BMCTaskTypeBMCReset indicates a BMC reset task.<br /> |
| `NetworkClear` | BMCTaskTypeNetworkClear indicates a network configuration clear task.<br /> |
| `FirmwareUpdate` | BMCTaskTypeFirmwareUpdate indicates a firmware update task (BIOS or BMC).<br /> |
| `ConfigurationChange` | BMCTaskTypeConfigurationChange indicates a configuration change task.<br /> |
| `AccountManagement` | BMCTaskTypeAccountManagement indicates an account management task.<br /> |
| `Other` | BMCTaskTypeOther indicates a task type not covered by the specific types.<br /> |


#### BMCUser


Expand Down
Loading
Loading