You are looking at the documentation of a prior release. To read the documentation of the latest release, please
visit here.
New to KubeDB? Please start here.
Reconfigure ZooKeeper Ensemble
This guide will show you how to use KubeDB
Ops-manager operator to reconfigure a ZooKeeper ensemble.
Before You Begin
At first, you need to have a Kubernetes cluster, and the
kubectl
command-line tool must be configured to communicate with your cluster.Install
KubeDB
Provisioner and Ops-manager operator in your cluster following the steps here.You should be familiar with the following
KubeDB
concepts:
To keep everything isolated, we are going to use a separate namespace called demo
throughout this tutorial.
$ kubectl create ns demo
namespace/demo created
Note: YAML files used in this tutorial are stored in examples directory of kubedb/docs repository.
Now, we are going to deploy a ZooKeeper
cluster using a supported version by KubeDB
operator. Then we are going to apply ZooKeeperOpsRequest
to reconfigure its configuration.
Prepare ZooKeeper Ensemble
Now, we are going to deploy a ZooKeeper
cluster with version 3.8.3
.
Deploy ZooKeeper Ensemble
At first, we will create secret
named zk-configuration containing required configuration settings.
apiVersion: v1
stringData:
zoo.cfg: |
maxClientCnxns=70
kind: Secret
metadata:
name: zk-configuration
namespace: demo
Here, maxClientCnxns
is set to 70
, whereas the default value is 60
.
Now, we will apply the secret with custom configuration.
$ kubectl create -f https://github.com/kubedb/docs/raw/v2025.4.30/docs/examples/zookeeper/reconfiguration/secret.yaml
secret/zk-configuration created
In this section, we are going to create a ZooKeeper object specifying spec.configSecret
field to apply this custom configuration. Below is the YAML of the ZooKeeper
CR that we are going to create,
apiVersion: kubedb.com/v1alpha2
kind: ZooKeeper
metadata:
name: zk-quickstart
namespace: demo
spec:
version: "3.8.3"
adminServerPort: 8080
replicas: 3
configSecret:
name: zk-configuration
storage:
resources:
requests:
storage: "1Gi"
accessModes:
- ReadWriteOnce
deletionPolicy: "WipeOut"
Let’s create the ZooKeeper
CR we have shown above,
$ kubectl create -f https://github.com/kubedb/docs/raw/v2025.4.30/docs/examples/zookeeper/reconfiguration/sample-zk-configuration.yaml
zookeeper.kubedb.com/zk-quickstart created
Now, wait until zk-quickstart
has status Ready
. i.e,
$ kubectl get zk -n demo
NAME VERSION STATUS AGE
zk-quickstart 3.8.3 Ready 23s
Now, we will check if the database has started with the custom configuration we have provided.
Now, you can exec into the zookeeper pod and find if the custom configuration is there,
$ Defaulted container "zookeeper" out of: zookeeper, zookeeper-init (init)
zookeeper@zk-quickstart-0:/apache-zookeeper-3.8.3-bin$ echo conf | nc localhost 2181
clientPort=2181
secureClientPort=-1
dataDir=/data/version-2
dataDirSize=134218330
dataLogDir=/data/version-2
dataLogSize=134218330
tickTime=2000
maxClientCnxns=70
minSessionTimeout=4000
maxSessionTimeout=40000
clientPortListenBacklog=-1
serverId=1
initLimit=10
syncLimit=2
electionAlg=3
electionPort=3888
quorumPort=2888
peerType=0
membership:
server.1=zk-quickstart-0.zk-quickstart-pods.demo.svc.cluster.local:2888:3888:participant;0.0.0.0:2181
server.2=zk-quickstart-1.zk-quickstart-pods.demo.svc.cluster.local:2888:3888:participant;0.0.0.0:2181
server.3=zk-quickstart-2.zk-quickstart-pods.demo.svc.cluster.local:2888:3888:participant;0.0.0.0:2181
version=100000011zookeeper@zk-quickstart-0:/apache-zookeeper-3.8.3-bin$ exit
exit
As we can see from the configuration of running zookeeper, the value of maxClientCnxns
has been set to 70
.
Reconfigure using new secret
Now we will reconfigure this database to set maxClientCnxns
to 100
.
At first, we will create secret
named new-configuration containing required configuration settings.
apiVersion: v1
stringData:
zoo.cfg: |
maxClientCnxns=100
kind: Secret
metadata:
name: zk-new-configuration
namespace: demo
Here, maxClientCnxns
is set to 100
.
Now, we will apply the secret with custom configuration.
$ kubectl create -f https://github.com/kubedb/docs/raw/v2025.4.30/docs/examples/zookeeper/reconfiguration/new-secret.yaml
secret/zk-new-configuration created
Create ZooKeeperOpsRequest
Now, we will use this secret to replace the previous secret using a ZooKeeperOpsRequest
CR. The ZooKeeperOpsRequest
yaml is given below,
apiVersion: ops.kubedb.com/v1alpha1
kind: ZooKeeperOpsRequest
metadata:
name: zk-reconfig
namespace: demo
spec:
type: Reconfigure
databaseRef:
name: zk-quickstart
configuration:
configSecret:
name: zk-new-configuration
Here,
spec.databaseRef.name
specifies that we are reconfiguringzk-quickstart
database.spec.type
specifies that we are performingReconfigure
on our database.spec.configuration.configSecret.name
specifies the name of the new secret.
Let’s create the ZooKeeperOpsRequest
CR we have shown above,
$ kubectl apply -f https://github.com/kubedb/docs/raw/v2025.4.30/docs/examples/zookeeper/reconfiguration/zkops-reconfiguration.yaml
zookeeperopsrequest.ops.kubedb.com/zk-reconfig created
Verify the new configuration is working
If everything goes well, KubeDB
Ops-manager operator will update the configSecret
of ZooKeeper
object.
Let’s wait for ZooKeeperOpsRequest
to be Successful
. Run the following command to watch ZooKeeperOpsRequest
CR,
$ watch kubectl get zookeeperopsrequest -n demo
Every 2.0s: kubectl get zookeeperopsrequest -n demo
NAME TYPE STATUS AGE
zk-reconfig Reconfigure Successful 1m
We can see from the above output that the ZooKeeperOpsRequest
has succeeded. If we describe the ZooKeeperOpsRequest
we will get an overview of the steps that were followed to reconfigure the database.
$ kubectl describe zookeeperopsrequest -n demo zk-reconfig
Name: zk-reconfig
Namespace: demo
Labels: <none>
Annotations: <none>
API Version: ops.kubedb.com/v1alpha1
Kind: ZooKeeperOpsRequest
Metadata:
Creation Timestamp: 2024-10-30T08:27:00Z
Generation: 1
Resource Version: 1548116
UID: 4f3daa11-c41b-4079-a8d8-1040931284ef
Spec:
Apply: IfReady
Configuration:
Config Secret:
Name: zk-new-configuration
Database Ref:
Name: zk-quickstart
Type: Reconfigure
Status:
Conditions:
Last Transition Time: 2024-10-30T08:27:00Z
Message: ZooKeeper ops-request has started to reconfigure ZooKeeper nodes
Observed Generation: 1
Reason: Reconfigure
Status: True
Type: Reconfigure
Last Transition Time: 2024-10-30T08:27:08Z
Message: successfully reconciled the ZooKeeper with new configure
Observed Generation: 1
Reason: UpdatePetSets
Status: True
Type: UpdatePetSets
Last Transition Time: 2024-10-30T08:29:18Z
Message: Successfully restarted all nodes
Observed Generation: 1
Reason: RestartNodes
Status: True
Type: RestartNodes
Last Transition Time: 2024-10-30T08:27:13Z
Message: get pod; ConditionStatus:True; PodName:zk-quickstart-0
Observed Generation: 1
Status: True
Type: GetPod--zk-quickstart-0
Last Transition Time: 2024-10-30T08:27:13Z
Message: evict pod; ConditionStatus:True; PodName:zk-quickstart-0
Observed Generation: 1
Status: True
Type: EvictPod--zk-quickstart-0
Last Transition Time: 2024-10-30T08:27:18Z
Message: running pod; ConditionStatus:False
Observed Generation: 1
Status: False
Type: RunningPod
Last Transition Time: 2024-10-30T08:27:58Z
Message: get pod; ConditionStatus:True; PodName:zk-quickstart-1
Observed Generation: 1
Status: True
Type: GetPod--zk-quickstart-1
Last Transition Time: 2024-10-30T08:27:58Z
Message: evict pod; ConditionStatus:True; PodName:zk-quickstart-1
Observed Generation: 1
Status: True
Type: EvictPod--zk-quickstart-1
Last Transition Time: 2024-10-30T08:28:38Z
Message: get pod; ConditionStatus:True; PodName:zk-quickstart-2
Observed Generation: 1
Status: True
Type: GetPod--zk-quickstart-2
Last Transition Time: 2024-10-30T08:28:38Z
Message: evict pod; ConditionStatus:True; PodName:zk-quickstart-2
Observed Generation: 1
Status: True
Type: EvictPod--zk-quickstart-2
Last Transition Time: 2024-10-30T08:29:18Z
Message: Successfully completed reconfigure ZooKeeper
Observed Generation: 1
Reason: Successful
Status: True
Type: Successful
Observed Generation: 1
Phase: Successful
Events: <none>
Now need to check the new configuration we have provided.
Now, wait until zk-quickstart
has status Ready
. i.e,
$ kubectl get zk -n demo
NAME VERSION STATUS AGE
zk-quickstart 3.8.3 Ready 20s
Now let’s exec into the zookeeper pod and check the new configuration we have provided.
$ Defaulted container "zookeeper" out of: zookeeper, zookeeper-init (init)
zookeeper@zk-quickstart-0:/apache-zookeeper-3.8.3-bin$ echo conf | nc localhost 2181
clientPort=2181
secureClientPort=-1
dataDir=/data/version-2
dataDirSize=134218330
dataLogDir=/data/version-2
dataLogSize=134218330
tickTime=2000
maxClientCnxns=100
minSessionTimeout=4000
maxSessionTimeout=40000
clientPortListenBacklog=-1
serverId=1
initLimit=10
syncLimit=2
electionAlg=3
electionPort=3888
quorumPort=2888
peerType=0
membership:
server.1=zk-quickstart-0.zk-quickstart-pods.demo.svc.cluster.local:2888:3888:participant;0.0.0.0:2181
server.2=zk-quickstart-1.zk-quickstart-pods.demo.svc.cluster.local:2888:3888:participant;0.0.0.0:2181
server.3=zk-quickstart-2.zk-quickstart-pods.demo.svc.cluster.local:2888:3888:participant;0.0.0.0:2181
version=100000011zookeeper@zk-quickstart-0:/apache-zookeeper-3.8.3-bin$ exit
exit
As we can see from the configuration of running zookeeper, the value of maxClientCnxns
has been changed from 70
to 100
. So the reconfiguration of the zookeeper is successful.
Reconfigure using apply config
Now we will reconfigure this database again to set maxClientCnxns
to 90
. This time we won’t use a new secret. We will use the applyConfig
field of the ZooKeeperOpsRequest
. This will merge the new config in the existing secret.
Create ZooKeeperOpsRequest
Now, we will use the new configuration in the data
field in the ZooKeeperOpsRequest
CR. The ZooKeeperOpsRequest
yaml is given below,
apiVersion: ops.kubedb.com/v1alpha1
kind: ZooKeeperOpsRequest
metadata:
name: zk-reconfig-apply
namespace: demo
spec:
type: Reconfigure
databaseRef:
name: zk-quickstart
configuration:
applyConfig:
zoo.cfg: |
maxClientCnxns=90
Here,
spec.databaseRef.name
specifies that we are reconfiguringzk-quickstart
database.spec.type
specifies that we are performingReconfigure
on our database.spec.configuration.applyConfig
specifies the new configuration that will be merged in the existing secret.
Let’s create the ZooKeeperOpsRequest
CR we have shown above,
$ kubectl apply -f https://github.com/kubedb/docs/raw/v2025.4.30/docs/examples/zookeeper/reconfiguration/zkops-apply-reconfiguration.yaml
zookeeperopsrequest.ops.kubedb.com/zk-reconfig-apply created
Verify the new configuration is working
If everything goes well, KubeDB
Ops-manager operator will merge this new config with the existing configuration.
Let’s wait for ZooKeeperOpsRequest
to be Successful
. Run the following command to watch ZooKeeperOpsRequest
CR,
$ watch kubectl get zookeeperopsrequest -n demo
NAME TYPE STATUS AGE
zk-reconfig-apply Reconfigure Successful 38s
We can see from the above output that the ZooKeeperOpsRequest
has succeeded. If we describe the ZooKeeperOpsRequest
we will get an overview of the steps that were followed to reconfigure the database.
$ kubectl describe zookeeperopsrequest -n demo zk-reconfig-apply
Name: zk-reconfig-apply
Namespace: demo
Labels: <none>
Annotations: <none>
API Version: ops.kubedb.com/v1alpha1
Kind: ZooKeeperOpsRequest
Metadata:
Creation Timestamp: 2024-10-30T08:27:00Z
Generation: 1
Resource Version: 1548116
UID: 4f3daa11-c41b-4079-a8d8-1040931284ef
Spec:
Apply: IfReady
Configuration:
Config Secret:
Name: zk-new-configuration
Database Ref:
Name: zk-quickstart
Type: Reconfigure
Status:
Conditions:
Last Transition Time: 2024-10-30T08:27:00Z
Message: ZooKeeper ops-request has started to reconfigure ZooKeeper nodes
Observed Generation: 1
Reason: Reconfigure
Status: True
Type: Reconfigure
Last Transition Time: 2024-10-30T08:27:08Z
Message: successfully reconciled the ZooKeeper with new configure
Observed Generation: 1
Reason: UpdatePetSets
Status: True
Type: UpdatePetSets
Last Transition Time: 2024-10-30T08:29:18Z
Message: Successfully restarted all nodes
Observed Generation: 1
Reason: RestartNodes
Status: True
Type: RestartNodes
Last Transition Time: 2024-10-30T08:27:13Z
Message: get pod; ConditionStatus:True; PodName:zk-quickstart-0
Observed Generation: 1
Status: True
Type: GetPod--zk-quickstart-0
Last Transition Time: 2024-10-30T08:27:13Z
Message: evict pod; ConditionStatus:True; PodName:zk-quickstart-0
Observed Generation: 1
Status: True
Type: EvictPod--zk-quickstart-0
Last Transition Time: 2024-10-30T08:27:18Z
Message: running pod; ConditionStatus:False
Observed Generation: 1
Status: False
Type: RunningPod
Last Transition Time: 2024-10-30T08:27:58Z
Message: get pod; ConditionStatus:True; PodName:zk-quickstart-1
Observed Generation: 1
Status: True
Type: GetPod--zk-quickstart-1
Last Transition Time: 2024-10-30T08:27:58Z
Message: evict pod; ConditionStatus:True; PodName:zk-quickstart-1
Observed Generation: 1
Status: True
Type: EvictPod--zk-quickstart-1
Last Transition Time: 2024-10-30T08:28:38Z
Message: get pod; ConditionStatus:True; PodName:zk-quickstart-2
Observed Generation: 1
Status: True
Type: GetPod--zk-quickstart-2
Last Transition Time: 2024-10-30T08:28:38Z
Message: evict pod; ConditionStatus:True; PodName:zk-quickstart-2
Observed Generation: 1
Status: True
Type: EvictPod--zk-quickstart-2
Last Transition Time: 2024-10-30T08:29:18Z
Message: Successfully completed reconfigure ZooKeeper
Observed Generation: 1
Reason: Successful
Status: True
Type: Successful
Observed Generation: 1
Phase: Successful
Events: <none>
Now need to check the new configuration we have provided.
Now, wait until zk-quickstart
has status Ready
. i.e,
$ kubectl get zk -n demo
NAME VERSION STATUS AGE
zk-quickstart 3.8.3 Ready 20s
Now let’s exec into the zookeeper pod and check the new configuration we have provided.
$ Defaulted container "zookeeper" out of: zookeeper, zookeeper-init (init)
zookeeper@zk-quickstart-0:/apache-zookeeper-3.8.3-bin$ echo conf | nc localhost 2181
clientPort=2181
secureClientPort=-1
dataDir=/data/version-2
dataDirSize=134218330
dataLogDir=/data/version-2
dataLogSize=134218330
tickTime=2000
maxClientCnxns=90
minSessionTimeout=4000
maxSessionTimeout=40000
clientPortListenBacklog=-1
serverId=1
initLimit=10
syncLimit=2
electionAlg=3
electionPort=3888
quorumPort=2888
peerType=0
membership:
server.1=zk-quickstart-0.zk-quickstart-pods.demo.svc.cluster.local:2888:3888:participant;0.0.0.0:2181
server.2=zk-quickstart-1.zk-quickstart-pods.demo.svc.cluster.local:2888:3888:participant;0.0.0.0:2181
server.3=zk-quickstart-2.zk-quickstart-pods.demo.svc.cluster.local:2888:3888:participant;0.0.0.0:2181
version=100000011zookeeper@zk-quickstart-0:/apache-zookeeper-3.8.3-bin$ exit
exit
As we can see from the configuration of running zookeeper, the value of maxClientCnxns
has been changed from 100
to 90
. So, the reconfiguration of the database using the applyConfig
field is successful.
Cleaning Up
To clean up the Kubernetes resources created by this tutorial, run:
kubectl delete zk -n demo zk-quickstart
kubectl delete zookeeperopsrequest -n demo zk-reconfig zk-reconfig-apply