KRaft Migration Prerequisites

Before you migrate from ZooKeeper to KRaft with Confluent for Kubernetes, verify that your deployment meets the prerequisites.

Confluent Platform version

You need Confluent Platform 7.6 or later.

Check your version:

# Check the Confluent Platform version
kubectl get kafka <kafka-cr-name> -n <namespace> -o jsonpath='{.status.currentClusterVersion}'

Expected:

7.9

CFK version

You need one of the following CFK versions:

  • 2.9.2 or later in the 2.9.x branch

  • 2.10.x or later

Check your installed version:

# Check the CFK version
helm list -n <operator-namespace>

Expected:

NAME                NAMESPACE             REVISION  UPDATED      STATUS    CHART                                     APP VERSION
confluent-operator  <operator-namespace>  1         <timestamp>  deployed  confluent-for-kubernetes-<chart-version>  3.2.2

In the output, the CHART column shows the Helm chart name and version, and the APP VERSION column shows the CFK release. Ensure the APP VERSION matches one of the supported CFK versions listed earlier in this section.

Confluent plugin

The Confluent plugin provides kubectl confluent commands that simplify the migration and is available in CFK 3.2.2 or later. To use these commands, verify the plugin is installed. If it is not installed, see Install Confluent plugin using Krew.

kubectl confluent cluster kraft-migration --help

Important

Keep the Confluent plugin and Confluent operator at the same version.

The plugin uses the following syntax. The alias is kmj:

kubectl confluent cluster kraft-migration <subcommand> [flags]

Confluent CRDs match the operator version

CFK does not upgrade CRDs automatically when you upgrade the operator. Stale CRDs can cause migration to fail in confusing ways, for example, missing fields on the KRaftController or KRaftMigrationJob CR, or admission policies that do not exist in your cluster. Before starting the migration, reinstall the CRDs from the same CFK version you upgraded to. For details, see Install Confluent CRDs.

CR lock enforcement

During migration, CFK locks the Kafka, ZooKeeper, and KRaftController CRs with the platform.confluent.io/kraft-migration-cr-lock=true annotation to prevent accidental modifications or deletions. Only the CFK operator service account can modify locked CRs. CFK denies UPDATE and DELETE on these CRs for all other users.

How CFK enforces the lock depends on your versions and configuration, which CFK auto-detects at Helm install or upgrade. Confirm which case applies to your setup:

  • Confluent for Kubernetes 3.2.2 or later on Kubernetes 1.30 or later (default)

    ValidatingAdmissionPolicy (VAP) is active when Kubernetes is 1.30 or later and vapPolicies.enabled: true. Verify with:

    kubectl get validatingadmissionpolicies | grep kraft-migration
    

    Expected:

    cfk-kraft-migration-cr-lock-confluent   1   <unset>   5h14m
    

    The policy name follows the pattern cfk-kraft-migration-cr-lock-<operator-namespace>. The preceding example shows the confluent namespace.

    To disable VAP, set vapPolicies.enabled: false during Helm install or upgrade.

  • Older Confluent for Kubernetes versions or when VAP is disabled

    The validating webhook is the automatic fallback when the VAP API is unavailable or VAP is disabled. Verify with:

    kubectl get validatingwebhookconfigurations | grep confluent
    

    Expected:

    confluent-operator-validating-webhook-configuration
    
  • Deployments without webhooks or VAP

    If your deployment has neither enabled, ensure no other actor updates or deletes ZooKeeper, Kafka, and KRaft resources during migration. Other actors include continuous integration and continuous delivery (CI/CD) tools such as GitOps or FluxCD.

To make an emergency change to a locked CR during migration, see Bypass CR locks for emergency changes on the troubleshooting page.

Pre-migration backup

Take a backup of your Kafka, ZooKeeper, and any related CRs before you start. Export the CR YAML files so you can restore the configuration if you need to roll back.

kubectl get zookeeper <zookeeper-name> -n <namespace> -o yaml > zookeeper-backup.yaml
kubectl get kafka <kafka-name> -n <namespace> -o yaml > kafka-backup.yaml

Also back up ZooKeeper persistent data through your standard process, for example, a PVC snapshot. After finalization, you cannot recover the ZooKeeper state.

Multi-region cluster considerations

A multi-region cluster (MRC) is a Kafka deployment that spans more than one Kubernetes cluster or region, with one KRaftController quorum per region. In an MRC migration, CFK cannot always derive the correct ZooKeeper endpoint from the cross-region Kafka CRs, so you must set zookeeper.connect manually on the KRaftController CR in each region.

In CFK 3.2.1 and later, zookeeper.connect is on the CFK pre-flight blocklist (a list of fields CFK validates on the KRaftController CR before starting migration), so an MRC migration must explicitly bypass the pre-flight check. Do not use the bypass for single-cluster deployments. Let CFK manage zookeeper.connect automatically.

For the bypass annotation and warning, see Step 3.1 in the migration procedure.

Migration command conventions

KRaft migration is driven entirely by annotations on the Kafka, KRaftController, Zookeeper, and KRaftMigrationJob CRs. The rollback and release-lock annotations are re-applied during the procedure, so those commands include --overwrite.

The commands use two distinct namespace placeholders. Substitute the correct value for each:

<namespace>

The namespace where your Kafka, ZooKeeper, and KRaftController CRs run.

<operator-namespace>

The namespace where CFK is installed (confluent by default). This might be the same as <namespace> or different, depending on how you installed CFK. Use <operator-namespace> only when the command targets the operator itself, such as helm list or kubectl logs deployment/confluent-operator.

Next steps

After you complete the prerequisites, start the migration by following the migration procedure.