1 of 18

From CONF to YAML: Redefining Database

Management

Using CloudNativePG

Mohammad Zulfikar

DevOps Engineer

Muhammad Fikri A

DevOps Engineer

1

2 of 18

The constraint

2

2

KUBERNETES COMMUNITY DAYS INDONESIA 2026

3 of 18

Operator Pattern

3

3

https://cloudnative-pg.io/docs/1.30/operator_capability_levels

KUBERNETES COMMUNITY DAYS INDONESIA 2026

4 of 18

Before: the CONF era

Hand-edited: postgresql.conf and pg_hba.conf on every VM

Cron: backups and failover lived in shell scripts

Drift: every server a little different from the others

4

4

$ ssh db-vm-02

$ sudo vim /etc/postgresql/18/main/postgresql.conf

$ sudo vim /etc/postgresql/18/main/pg_hba.conf

$ sudo systemctl restart postgresql

$ crontab -l

0 1 * * * /opt/scripts/pg_backup.sh

* * * * * /opt/scripts/failover_check.sh

Same parameter, three servers:

db-vm-01

max_connections

200

db-vm-02

max_connections

400

db-vm-03

max_connections

1000

KUBERNETES COMMUNITY DAYS INDONESIA 2026

5 of 18

CloudNativePG changes Everything

5

5

KUBERNETES COMMUNITY DAYS INDONESIA 2026

6 of 18

7 of 18

How we “Ship” the Database

7

7

  • Argo CD syncs every database from Git
  • One Argo CD application per database
  • The DBA team changes a database by pull request

KUBERNETES COMMUNITY DAYS INDONESIA 2026

8 of 18

High availability

CNPG can easily scale to multiple pods using instances on spec

primaryUpdateMethod: switchover

kubectl cnpg promote picks the new primary

Apps use the -rw service, which follows the primary: the connection string never changes

Exposing database via LB possible by creating, spec.managed.services.additional on Cluster CRD

8

8

KUBERNETES COMMUNITY DAYS INDONESIA 2026

9 of 18

Backup and PITR

CNPG Uses several CRDs for defining backups

  • ObjectStore (Connectors)
  • ScheduledBackup (Cron)
  • Backup (On-Demand)

Best Practice:

  • Set the retention
  • Compression for WAL
  • Test restores regularly

9

9

KUBERNETES COMMUNITY DAYS INDONESIA 2026

10 of 18

11 of 18

Monitoring

PodMonitor: Prometheus scrapes every Postgres pod

  • The metrics exporter runs inside each pod, on port 9187
  • Keep the exporter in mind: it comes back on patch day

11

11

KUBERNETES COMMUNITY DAYS INDONESIA 2026

12 of 18

13 of 18

The day it hurt

13

13

14 of 18

The setup

The damage

The fix

1 instance,�Ceph storage min_size 1

Application Exception,�Zeroed pages, carried into the restores

Rebuilt with 2 instances

14

14

KUBERNETES COMMUNITY DAYS INDONESIA 2026

15 of 18

CNPG != Silver Bullet

15

15

KUBERNETES COMMUNITY DAYS INDONESIA 2026

16 of 18

Day-2 operations

Plugin commands run as: kubectl cnpg <command> <cluster>

16

16

1 · INSPECT

status

Health, replication and backups

logs cluster

Logs from every instance

psql

A shell on the primary

→

2 · PROTECT

backup

On demand, before a migration or any risky change

→

3 · CHANGE

restart

Rolling restart, replicas first

hibernate on|off

Stop the pods, keep the data

imageName

Major upgrade: the operator runs pg_upgrade

→

4 · REPAIR

destroy

Remove a broken instance; the operator rebuilds it from the others

KUBERNETES COMMUNITY DAYS INDONESIA 2026

17 of 18

Takeaways and Q&A

One Cluster spec in Git replaced conf files and cron scripts

The -rw service hides failover from apps

One instance != HA: run at least three

Test restores: a backup of corrupted DB can carry the damage

Maintenance: patch the operator like any tools you have

17

17

KUBERNETES COMMUNITY DAYS INDONESIA 2026

18 of 18

18

18

THANK YOU