CYBERTEC PostgreSQL Logo

Exploration: PostgreSQL Cluster Bootstrapping with initdb(CNPG)

07.2025
Category: 

Introduction

In our previous blog, we have done an introduction to CloudNativePG (CNPG) and showed how we can create a single instance cluster. In this blog, we’ll walk through creating a PostgreSQL cluster using initdb with custom options, manage roles, and create databases—all declaratively with Kubernetes manifests. Additionally, we will explain how to connect our database outside of the Kubernetes cluster.


Bootstrap the Cluster with initdb

We’ll start by creating a PostgreSQL cluster named cluster-example-initdb using the initdb bootstrap method.

This manifest:

  • Creates a kubernetes secret (app-secret) for user cybertec with its password
  • Initializes a database named cybertec owned by user cybertec
  • The database's encoding is LATIN1 and data checksum is enabled
  • Creates roles nikola (with createdb) and tesla (as a superuser)

For the other parameters that can be used with initdb, you can check bootstrapinitdb.

Apply the manifest:


Verify Cluster and Roles

Check that the pod is running:

Enter the pod to connect to PostgreSQL:


Create More Roles and Databases (Imperative)

We can still create additional roles and databases manually via kubectl exec:


Define Roles and Databases Declaratively

We can also manage additional roles and databases using managed and Database CRs.

We will create another manifest (database.yaml) for database:

Apply both manifests:

This way, we can create different strategies for our IaC to manage our database infrastructure.

As a last example for this section, we will use the following manifest:

This manifest:

  • Creates a secret and a config map to be used after database initialization.

Depending on the goal, we can use postInitSQL, postInitApplicationSQL, or postInitTemplateSQL to customize our cluster and database(s).


Verify Role and Table

As can be seen above, the cybertec role is created and granted user on app database. Also, the demo table is created as expected.


Cluster Manifest with Custom Service

In this second part, we will showcase how to enable applications and users to connect to our database outside of the Kubernetes cluster. For this example, we will use the following manifest:

This config will:

  • Expose the writable pod with a LoadBalancer service named test-rw
  • Disable the default read-only services (-ro, -r). If we don' t disable them, CNPG creates 3 services for rw, ro, and r as default

Apply the Cluster Configuration

Wait for the pod and service to be ready:


Inspect the Custom Service

Key values to notice is

  • LoadBalancer Ingress: 10.109.19.23

Even though we didn't specify a static IP address, minikube assigned an IP address to our service. However, this IP address and TargetPort, which is 5432, cannot be used to connect to our database from outside of the cluster. That is why we will use the IP address of the minikube on our local.


Connect to PostgreSQL Externally

In order to get full information for the connection:

Sample output:

Then connect using psql:

Enter your password when prompted. If everything is configured correctly, voilà:

We can now query the cluster as usual!


Conclusion

By leveraging CloudNativePG, you bring true infrastructure as code principles to your PostgreSQL environment to gain operational consistency and automation. Whether you're running on Minikube or in a full-blown cloud environment, CNPG helps bridge the gap between DevOps and database administration.

Leave a Reply

Your email address will not be published. Required fields are marked *

CYBERTEC Logo white
Get the newest PostgreSQL Info & Tools


    This site is protected by reCAPTCHA and the Google Privacy Policy & Terms of Service apply.

    ©
    2025
    CYBERTEC PostgreSQL International GmbH
    phone-handsetmagnifiercrosscross-circle
    linkedin facebook pinterest youtube rss twitter instagram facebook-blank rss-blank linkedin-blank pinterest youtube twitter instagram