Infrastructure at your Service

Daniel Westermann

Getting started with the Zalando Operator for PostgreSQL

In the previous posts (Rancher, up and running, on EC2 – 1 – One node, Rancher, up and running, on EC2 – 2 – Three nodes, Rancher, up and running, on EC2 – 3 – Rancher setup, Rancher on SLES 15 as a demo environment, and Deploying a Kubernetes cluster on EC2 with Rancher) it was all about deploying a Kubernetes cluster and getting Rancher up and running. In this post we’ll use one of those systems to deploy a PostgreSQL cluster. I’ll be using my one node Rancher demo environment for this, but you can of course also use a cluster as described in the posts above. Zalando does not only provide Patroni but also provides a PostgreSQL operator for Kubernetes, and we’ll be using this one for this demo.

Before we start with the PostgreSQL operator we need to prepare the system. PostgreSQL needs to safely store it’s data somewhere, and for being able to do that we need persistent storage. We could do all the following steps using the command line, but we’ll use the Rancher UI for this. The easiest way to do this is by using the “Cluster Explorer”

On the left side you’ll find the Persistent Volumes:


As there is no storage system attached to the demo environment, we’ll be using the “Host Path” plugin for my persistent volumes, and I’ll be creating two of them:



We can also use the command line for checking the persistent volumes we’ve just created:

[email protected]:~$ kubectl get pv
NAME              CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS      CLAIM   STORAGECLASS   REASON   AGE
pv-postgresql-1   10Gi       RWO            Retain           Available                                   8m50s
pv-postgresql-2   10Gi       RWO            Retain           Available                                   7m32s

That’s it for the preparation and we are ready to clone the PostgreSQL operator repository:

[email protected]:~$ git clone https://github.com/zalando/postgres-operator.git
Cloning into 'postgres-operator'...
remote: Enumerating objects: 273, done.
remote: Counting objects: 100% (273/273), done.
remote: Compressing objects: 100% (178/178), done.
remote: Total 20089 (delta 176), reused 173 (delta 93), pack-reused 19816
Receiving objects: 100% (20089/20089), 7.75 MiB | 13.29 MiB/s, done.
Resolving deltas: 100% (14256/14256), done.
[email protected]:~$ cd postgres-operator/

The first step is to create the config map (have a look at it to get an idea of all the parameters and values):

[email protected]:~/postgres-operator$ kubectl create -f manifests/configmap.yaml 
configmap/postgres-operator created

This was the way to do it on the command line, the same is possible with the Rancher UI as well:

Next is the RBAC (role based access control) stuff (I’ve done that already before and did not do a proper cleanup, that’s why the postgres-operator service account already exists):

[email protected]:~/postgres-operator$ kubectl create -f manifests/operator-service-account-rbac.yaml
clusterrole.rbac.authorization.k8s.io/postgres-operator created
clusterrolebinding.rbac.authorization.k8s.io/postgres-operator created
clusterrole.rbac.authorization.k8s.io/postgres-pod created
Error from server (AlreadyExists): error when creating "manifests/operator-service-account-rbac.yaml": serviceaccounts "postgres-operator" already exists

The PostgreSQL operator itself:

[email protected]:~/postgres-operator$ kubectl create -f manifests/postgres-operator.yaml
deployment.apps/postgres-operator created

… and finally the service:

[email protected]:~/postgres-operator$ kubectl create -f manifests/api-service.yaml
service/postgres-operator created

A few seconds later the operator pod should be running:

[email protected]:~/postgres-operator$ cd ..
[email protected]:~$ kubectl get pod -l name=postgres-operator
NAME                                 READY   STATUS    RESTARTS   AGE
postgres-operator-6775b6dcf9-cpp86   1/1     Running   0          2m42s

For getting the graphical user interface for the PostgreSQL operator install the UI components:

[email protected]:~$ kubectl apply -f postgres-operator/ui/manifests/
deployment.apps/postgres-operator-ui created
ingress.networking.k8s.io/postgres-operator-ui created
service/postgres-operator-ui created
serviceaccount/postgres-operator-ui unchanged
clusterrole.rbac.authorization.k8s.io/postgres-operator-ui created
clusterrolebinding.rbac.authorization.k8s.io/postgres-operator-ui created
error: unable to recognize "postgres-operator/ui/manifests/kustomization.yaml": no matches for kind "Kustomization" in version "kustomize.config.k8s.io/v1beta1"

Same procedure as before, check if the pod is running:

[email protected]:~$ kubectl get pod -l name=postgres-operator-ui
NAME                                    READY   STATUS    RESTARTS   AGE
postgres-operator-ui-5478dcfd7b-r2rzr   1/1     Running   0          74s

Check the Rancher UI for the service that got created (or use the command line to get that information):

… and access the Operator user interface with your browser:

Using this interface, a two node PostgreSQL cluster can easily be created:


The new cluster is ready:

[email protected]:~$ kubectl get pods 
NAME                                    READY   STATUS    RESTARTS   AGE
acid-my-demo-cluster-0                  1/1     Running   0          4m58s
acid-my-demo-cluster-1                  1/1     Running   0          4m54s
postgres-operator-6775b6dcf9-cpp86      1/1     Running   0          24m
postgres-operator-ui-5478dcfd7b-r2rzr   1/1     Running   0          19m

Quite easy to get that up and running in a demo environment.

Leave a Reply

This site uses Akismet to reduce spam. Learn how your comment data is processed.

Daniel Westermann
Daniel Westermann

Principal Consultant & Technology Leader Open Infrastructure