Skip to content

Implement CAPI's v1beta2 contract #6136

@willie-yao

Description

@willie-yao

/kind cleanup

What needs cleanup:
https://cluster-api.sigs.k8s.io/developer/providers/migrations/v1.10-to-v1.11.html#how-to-implement-the-new-v1beta2-contract
v1beta1 API version is deprecated and it will be removed tentatively in August 2026

Implementation plan:

v1beta2 Contract Migration Roadmap

Create a new api/v1beta2 CAPZ provider API version with full v1beta2 CAPI contract compliance, conversion webhooks for backward compatibility, and migrate all controllers.

Why a new API version?

We initially tried adding v1beta2 contract fields to the existing api/v1beta1 types (PRs #6199, #6202). This works for initialization.provisioned and v1beta2.conditions, but fails when declaring v1beta2 contract compliance because failureDomains changed from a map to a slice in the v1beta2 contract. CAPI's backward compatibility only handles the map format when the contract label says v1beta1, so there is no way to declare v1beta2 compliance without converting failureDomains — a breaking schema change that requires a new API version. This is also consistent with how CAPZ handled previous contract transitions (v1alpha3/v1alpha4 → v1beta1).

Plan

PR 1 (Types + Conversion + CRD config) ──> PR 2 (Controllers + Tests)
  • PR 1: Create api/v1beta2 types, conversion webhooks, CRD config (~80+ files)

    • Create api/v1beta2/ and exp/api/v1beta2/ with all type definitions, applying v1beta2 contract changes:
      • status.readystatus.initialization.provisioned *bool
      • status.initializedstatus.initialization.controlPlaneInitialized *bool
      • status.conditions uses []metav1.Condition, old conditions moved to status.deprecated.v1beta1.conditions
      • status.failureDomains changed from map to slice
      • failureReason/failureMessage moved to status.deprecated.v1beta1
      • spec.providerID changed from *string to string
    • Write v1beta1 ↔ v1beta2 conversion webhooks (v1beta2 as hub/storage version)
    • Add CRD labels (cluster.x-k8s.io/v1beta2: v1beta2) and contract: v1beta2 to metadata.yaml
  • PR 2: Migrate controllers to v1beta2 types (~60+ files)

    • Switch all controllers, scopes, and services to api/v1beta2 types
    • Use permanent util/conditions + util/patch packages (not the deprecated util/deprecated/v1beta1/* packages)
    • Set initialization.provisioned instead of ready
    • Set metav1.Condition conditions, with backward compat old conditions in deprecated.v1beta1
    • Add Available condition for AzureManagedControlPlane (ControlPlane contract)

Future work

  • Add granular v1beta2 conditions (NetworkInfrastructureReady, SubnetsReady, etc.) — CAPZ-internal, not part of the CAPI contract
  • Remove api/v1beta1 and status.deprecated.v1beta1 (after transition period)
  • CRD Migrator adoption (orthogonal)

References

Metadata

Metadata

Assignees

Labels

kind/cleanupCategorizes issue or PR as related to cleaning up code, process, or technical debt.

Type

No type
No fields configured for issues without a type.

Projects

Status

Todo

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions