Skip to content

OSAC-769: Remove legacy SubnetRef field from ComputeInstance CRD#280

Merged
openshift-merge-bot[bot] merged 1 commit into
osac-project:mainfrom
ori-amizur:OSAC-768
Jun 7, 2026
Merged

OSAC-769: Remove legacy SubnetRef field from ComputeInstance CRD#280
openshift-merge-bot[bot] merged 1 commit into
osac-project:mainfrom
ori-amizur:OSAC-768

Conversation

@ori-amizur

@ori-amizur ori-amizur commented Jun 4, 2026

Copy link
Copy Markdown
Contributor

Remove the deprecated spec.subnetRef field from ComputeInstanceSpec, completing the migration to the networkAttachments array for multi-NIC VM support. This aligns with the fulfillment-service (PR 565) which already removed its equivalent proto fields.

Changes:

  • Remove SubnetRef field and mutual-exclusion CEL validation rule
  • Relax networkAttachments size rule to allow initial population (0→N) while still preventing subsequent add/remove
  • Add startup migration (internal/migrations) that patches legacy CRs using unstructured client to read stored subnetRef from etcd
  • Migration runs as LeaderElectionRunnable — only the leader executes
  • Update PrimarySubnetRef() to return empty string instead of legacy fallback
  • Update controller comments and tests

Summary by CodeRabbit

  • New Features

    • Automatic startup migration that converts legacy single-NIC configs into the new multi-NIC networkAttachments format.
  • Behavior / Schema Changes

    • Primary subnet is now taken from the first networkAttachments entry.
    • networkAttachments may be initially set from empty to non-empty; subsequent add/remove remains disallowed.
    • Legacy single-NIC subnetRef field removed from the schema.
  • Breaking Changes

    • Legacy subnetRef removed — configure compute instances using networkAttachments.

@openshift-ci-robot

openshift-ci-robot commented Jun 4, 2026

Copy link
Copy Markdown

@ori-amizur: This pull request references OSAC-769 which is a valid jira issue.

Warning: The referenced jira issue has an invalid target version for the target branch this PR targets: expected the task to target the "5.0.0" version, but no target version was set.

Details

In response to this:

Remove the deprecated spec.subnetRef field from ComputeInstanceSpec, completing the migration to the networkAttachments array for multi-NIC VM support. This aligns with the fulfillment-service (PR 565) which already removed its equivalent proto fields.

Changes:

  • Remove SubnetRef field and mutual-exclusion CEL validation rule
  • Relax networkAttachments size rule to allow initial population (0→N) while still preventing subsequent add/remove
  • Add startup migration (internal/migrations) that patches legacy CRs using unstructured client to read stored subnetRef from etcd
  • Migration runs as LeaderElectionRunnable — only the leader executes
  • Update PrimarySubnetRef() to return empty string instead of legacy fallback
  • Update controller comments and tests

Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the openshift-eng/jira-lifecycle-plugin repository.

@openshift-ci openshift-ci Bot requested review from akshaynadkarni and danmanor June 4, 2026 09:22
@coderabbitai

coderabbitai Bot commented Jun 4, 2026

Copy link
Copy Markdown

Review Change Stack

Warning

Review limit reached

@ori-amizur, we couldn't start this review because you've reached your PR review rate limit.

More reviews will be available in 50 minutes and 6 seconds. Learn how PR review limits work.

Your organization has run out of usage credits. Purchase more in the billing tab.

⌛ How to resolve this issue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans include higher PR review limits than trial, open-source, and free plans. In all cases, reviews become available again over time. During sustained high-volume PR review activity, CodeRabbit may temporarily slow when the next review becomes available.

Please see our Fair Usage Limits Policy for further information.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository: osac-project/coderabbit/.coderabbit.yaml

Review profile: ASSERTIVE

Plan: Enterprise

Run ID: 1b241478-76de-4783-ba8b-ea283c1f1a38

📥 Commits

Reviewing files that changed from the base of the PR and between 8285a79 and 72db0fc.

📒 Files selected for processing (12)
  • api/v1alpha1/computeinstance_types.go
  • api/v1alpha1/computeinstance_types_test.go
  • charts/operator-crds/templates/osac.openshift.io_computeinstances.yaml
  • cmd/main.go
  • config/crd/bases/osac.openshift.io_computeinstances.yaml
  • internal/controller/computeinstance_controller.go
  • internal/controller/computeinstance_controller_test.go
  • internal/controller/computeinstance_validation_test.go
  • internal/migrations/migrate_subnetrefs.go
  • internal/migrations/migrate_subnetrefs_test.go
  • internal/migrations/migrations.go
  • internal/migrations/migrations_suite_test.go

Walkthrough

This PR removes the legacy single-NIC spec.subnetRef, makes networkAttachments[0].subnetRef the primary source, updates CRD docs and CEL validation (allowing initial assignment), adjusts controller/tests, and adds a leader-run startup migration that patches legacy CRs to populate spec.networkAttachments.

Risk: Moderate — the migration will modify existing CRs cluster-wide (or namespace-scoped) and must be validated to avoid unintended data changes.

Changes

Legacy subnetRef field removal and networkAttachments migration

Layer / File(s) Summary
Types and CRD schema updates
api/v1alpha1/computeinstance_types.go, config/crd/bases/osac.openshift.io_computeinstances.yaml, charts/operator-crds/templates/osac.openshift.io_computeinstances.yaml
Removed SubnetRef from spec types and CRD, updated PrimarySubnetRef() to return the first networkAttachments[].subnetRef or empty string, rewrote networkAttachments description, and changed CEL validation to permit an initial assignment while preventing later add/remove.
Controller comments, controller tests, validation tests
internal/controller/computeinstance_controller.go, internal/controller/computeinstance_controller_test.go, internal/controller/computeinstance_validation_test.go
Reworded controller comments to reference networkAttachments[0].subnetRef; tests now supply subnets via NetworkAttachments[]; PrimarySubnetRef tests updated to expect empty string when no attachments; validation tests restructured to reflect removed legacy field.
Startup migrations framework and main wiring
internal/migrations/migrations.go, internal/migrations/migrations_suite_test.go, cmd/main.go
Added ordered migration APIs, a leader-election-aware runnable, test suite entrypoint, and registered the migration runnable in main using a controller-runtime client so migrations run once on the elected leader.
SubnetRef → networkAttachments data migration and tests
internal/migrations/migrate_subnetrefs.go, internal/migrations/migrate_subnetrefs_test.go
New migrateSubnetRefs lists ComputeInstance CRs, patches legacy CRs that have spec.subnetRef and no spec.networkAttachments to populate networkAttachments[0].subnetRef, and is covered by tests for selective migration and idempotency.

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Possibly related PRs

Suggested labels

lgtm

Suggested reviewers

  • adriengentil
  • eranco74
  • akshaynadkarni
  • danmanor

Poem

🛠️ Old subnet fades, new attachments rise,
Leader runs the patch under watchful skies.
Tests stand ready, idempotent and true,
CRDs updated, primary comes from slot one too.
Migration marches—cluster tidy and new.

🚥 Pre-merge checks | ✅ 9 | ❌ 2

❌ Failed checks (2 warnings)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 37.50% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
Ai-Attribution ⚠️ Warning Commit 72db0fc uses Co-Authored-By for Claude AI instead of proper Red Hat trailers; should use Assisted-by or Generated-by for AI-assisted work. Replace Co-Authored-By trailer with Assisted-by or Generated-by trailer per Red Hat AI attribution guidelines; Co-Authored-By is reserved for human contributors.
✅ Passed checks (9 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately describes the main change: removing the legacy SubnetRef field from ComputeInstance CRD, which aligns with the primary objective across multiple files.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
No-Hardcoded-Secrets ✅ Passed No hardcoded secrets found. Code correctly uses env vars and Secret references for credentials; test files contain only example names like "legacy-subnet", not actual API keys/tokens/passwords.
No-Weak-Crypto ✅ Passed No weak cryptography patterns detected. PR contains no MD5, SHA1, DES, RC4, 3DES, Blowfish, ECB, custom crypto implementations, or non-constant-time secret comparisons.
No-Injection-Vectors ✅ Passed No injection vectors found. Migration code safely uses json.Marshal and client.RawPatch with pre-serialized bytes. Env variables validated by Kubernetes client. No SQL, shell, eval patterns.
Container-Privileges ✅ Passed PR modifies only Go source, tests, and CRD schemas. No pod/container manifests added. No privileged flags, hostPID/Network/IPC, SYS_ADMIN, or allowPrivilegeEscalation settings found.
No-Sensitive-Data-In-Logs ✅ Passed No passwords, tokens, API keys, PII, or secrets logged. Only standard Kubernetes infrastructure metadata (namespace, resource names, subnet references).

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@api/v1alpha1/computeinstance_types.go`:
- Line 161: The current kubebuilder XValidation rule only checks size, allowing
replacement of the primary subnet entry; update the validation marker (the
+kubebuilder:validation:XValidation line) to enforce that if oldSelf is
non-empty the key of the primary attachment in self must equal the key of the
primary attachment in oldSelf (i.e., find element(s) where primary==true and
require their key values to be identical), so primary subnet key cannot be
changed after initial assignment; change the marker on the network attachments
field to implement this exact equality check between oldSelf and self for the
primary==true element.

In `@internal/migrations/migrations.go`:
- Around line 44-54: The runAll function currently uses the provided ctx without
a timeout, so wrap the migration loop in a derived context with a timeout (e.g.,
context.WithTimeout(ctx, 5*time.Minute)) and ensure defer cancel() is called;
then call each migration with the timed context (use timedCtx when invoking
m.Fn) and handle context.DeadlineExceeded by returning a clear error (or logging
via ctrllog.FromContext), so migrations (the all slice and each m.Fn) will be
canceled if they hang. Ensure imports include time and that you propagate the
wrapped context instead of the original.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository: osac-project/coderabbit/.coderabbit.yaml

Review profile: ASSERTIVE

Plan: Enterprise

Run ID: 4e02485d-abe1-4cf9-a805-8163a45f5588

📥 Commits

Reviewing files that changed from the base of the PR and between b7409bf and 8bee286.

📒 Files selected for processing (11)
  • api/v1alpha1/computeinstance_types.go
  • api/v1alpha1/computeinstance_types_test.go
  • cmd/main.go
  • config/crd/bases/osac.openshift.io_computeinstances.yaml
  • internal/controller/computeinstance_controller.go
  • internal/controller/computeinstance_controller_test.go
  • internal/controller/computeinstance_validation_test.go
  • internal/migrations/migrate_subnetrefs.go
  • internal/migrations/migrate_subnetrefs_test.go
  • internal/migrations/migrations.go
  • internal/migrations/migrations_suite_test.go

Comment thread api/v1alpha1/computeinstance_types.go Outdated
Comment thread internal/migrations/migrations.go
@omer-vishlitzky

Copy link
Copy Markdown
Contributor

/retest

Remove the deprecated spec.subnetRef field from ComputeInstanceSpec,
completing the migration to the networkAttachments array for multi-NIC
VM support. This aligns with the fulfillment-service (PR 565) which
already removed its equivalent proto fields.

Changes:
- Remove SubnetRef field and mutual-exclusion CEL validation rule
- Relax networkAttachments size rule to allow initial population (0→N)
  while still preventing subsequent add/remove
- Add startup migration (internal/migrations) that patches legacy CRs
  using unstructured client to read stored subnetRef from etcd
- Migration runs as LeaderElectionRunnable — only the leader executes
- Update PrimarySubnetRef() to return empty string instead of legacy
  fallback
- Update controller comments and tests

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@charts/operator-crds/templates/osac.openshift.io_computeinstances.yaml`:
- Around line 189-191: The current CEL rule only checks sizes and allows
same-size replacements that can change subnetRef keys; update the validation
rule for the network attachment list to disallow any change to subnetRef for
existing entries by requiring either size(oldSelf) == 0 or (size(self) ==
size(oldSelf) AND each corresponding element preserves subnetRef). Replace the
existing expression (size(oldSelf) == 0 || size(self) == size(oldSelf)) with a
CEL expression that additionally asserts for all indices/keys in oldSelf that
oldSelf[i].subnetRef == self[i].subnetRef (or equivalent key-based comparison),
keep the message text, and regenerate/sync CRDs afterwards (run make helm-crds
or make check-helm-crds).

In `@internal/migrations/migrate_subnetrefs.go`:
- Around line 61-95: The current loop builds mergePatch from the list-time spec
(subnetRef) and unconditionally calls c.Patch (client.RawPatch with
types.MergePatchType), which can overwrite a concurrent update to
spec.networkAttachments; instead re-fetch the latest object before patching (use
c.Get on the same item.Name/Namespace), parse its spec and verify that
spec.networkAttachments is still empty (and spec.subnetRef still equals the
value you captured) and only then apply the mergePatch with c.Patch; if the
re-fetched object shows networkAttachments populated or subnetRef changed, skip
this item to avoid stale-write overwrite and continue the loop.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Repository: osac-project/coderabbit/.coderabbit.yaml

Review profile: ASSERTIVE

Plan: Enterprise

Run ID: e04a13b8-e2eb-4eec-90e0-369e35f24b94

📥 Commits

Reviewing files that changed from the base of the PR and between 8bee286 and 8285a79.

📒 Files selected for processing (12)
  • api/v1alpha1/computeinstance_types.go
  • api/v1alpha1/computeinstance_types_test.go
  • charts/operator-crds/templates/osac.openshift.io_computeinstances.yaml
  • cmd/main.go
  • config/crd/bases/osac.openshift.io_computeinstances.yaml
  • internal/controller/computeinstance_controller.go
  • internal/controller/computeinstance_controller_test.go
  • internal/controller/computeinstance_validation_test.go
  • internal/migrations/migrate_subnetrefs.go
  • internal/migrations/migrate_subnetrefs_test.go
  • internal/migrations/migrations.go
  • internal/migrations/migrations_suite_test.go

Comment thread charts/operator-crds/templates/osac.openshift.io_computeinstances.yaml Outdated
Comment thread internal/migrations/migrate_subnetrefs.go
@eranco74

eranco74 commented Jun 7, 2026

Copy link
Copy Markdown
Contributor

/lgtm
/approve

@openshift-ci

openshift-ci Bot commented Jun 7, 2026

Copy link
Copy Markdown

[APPROVALNOTIFIER] This PR is APPROVED

This pull-request has been approved by: eranco74, ori-amizur

The full list of commands accepted by this bot can be found here.

The pull request process is described here

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@openshift-ci openshift-ci Bot added the approved label Jun 7, 2026
@ori-amizur ori-amizur enabled auto-merge (squash) June 7, 2026 13:13
@openshift-merge-bot openshift-merge-bot Bot merged commit b192e02 into osac-project:main Jun 7, 2026
11 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants