Deploy PostgreSQL to Kubernetes cluster

This article will show you how to deploy a postgresql database to kubernetes cluster

Install kubernetes cluster

Follow below article if you don’t have one

Create and deploy configmap for PostgreSQL

Create postgres configmap file: postgres-configmap.yaml

apiVersion: v1
kind: ConfigMap
metadata:
  name: postgres-secret
  labels:
    app: postgres
data:
  POSTGRES_DB: yourdb
  POSTGRES_USER: yourusername
  POSTGRES_PASSWORD: yourpassword

Deploy postgres configmap file, run below command

kubectl apply -f postgres-configmap.yaml

Verify your change

kubectl get configmap

Sample output

NAME               DATA   AGE
kube-root-ca.crt   1      3d1h
postgres-secret    3      7s

Create PersistentVolume (PV) and PersistentVolumeClaim (PVC)

Create persistent volume for postgresql: postgres-volume.yaml

apiVersion: v1
kind: PersistentVolume # Create PV 
metadata:
  name: postgres-volume # Sets PV name
  labels:
    type: local # Sets PV's type
    app: postgres
spec:
  storageClassName: manual
  capacity:
    storage: 100Gi # Sets PV's size
  accessModes:
    - ReadWriteMany
  hostPath:
    path: "/home/username/data/postgresql" # Sets PV's host path

Deploy and verify your change, run below command

kubectl apply -f postgres-volume.yaml

Verify PV

kubectl get pv

Sample output

NAME              CAPACITY   ACCESS MODES   RECLAIM POLICY   STATUS      CLAIM   STORAGECLASS   REASON   AGE
postgres-volume   100Gi      RWX            Retain           Available           manual                  5s

Create persistent volume claim for postgres: postgres-volume-claim.yaml

apiVersion: v1
kind: PersistentVolumeClaim # Create PVC
metadata:
  name: postgres-volume-claim # Sets PVC's name
  labels:
    app: postgres # Defines app to create PVC for
spec:
  storageClassName: manual
  accessModes:
    - ReadWriteMany
  resources:
    requests:
      storage: 10Gi # Sets PVC's size

Deploy your change, run below command

kubectl apply -f postgres-volume-claim.yaml

Verify

kubectl get pvc

Sample output

NAME                    STATUS   VOLUME            CAPACITY   ACCESS MODES   STORAGECLASS   AGE
postgres-volume-claim   Bound    postgres-volume   100Gi      RWX            manual         6s

Create PostgreSQL Deployment and Service

Create and deploy postgres deployment: postgres-deployment.yaml

apiVersion: apps/v1
kind: Deployment # Create a deployment
metadata:
  name: postgres # Set the name of the deployment
spec:
  replicas: 1 # Set 1 deployment replicas
  selector:
    matchLabels:
      app: postgres
  template:
    metadata:
      labels:
        app: postgres
    spec:
      containers:
        - name: postgres
          image: postgres:12.10 # Docker image
          imagePullPolicy: "IfNotPresent"
          ports:
            - containerPort: 5432 # Exposing the container port 5432 for PostgreSQL client connections.
          envFrom:
            - configMapRef:
                name: postgres-secret # Using the ConfigMap postgres-secret
          volumeMounts:
            - mountPath: /var/lib/postgresql/data
              name: postgresdata
      volumes:
        - name: postgresdata
          persistentVolumeClaim:
            claimName: postgres-volume-claim

Deploy postgres deployment, run below command

kubectl apply -f postgres-deployment.yaml

Verify your change

kubectl get pods

Sample output

NAME                                       READY   STATUS    RESTARTS   AGE
postgres-9db8ff595-tffgz                   1/1     Running   0          39s

Create and deploy postgres service: postgres-service.yaml

apiVersion: v1
kind: Service # Create service
metadata:
  name: postgres # Sets the service name
  labels:
    app: postgres # Defines app to create service for
spec:
  type: NodePort # Sets the service type
  ports:
    - port: 5432 # Sets the port to run the postgres application
      nodePort: 30432 # Node port for external access by clients
  selector:
    app: postgres

Deploy service, run below command

kubectl apply -f postgres-service.yaml

Verify your change

kubectl get services

Sample output

NAME                      TYPE        CLUSTER-IP       EXTERNAL-IP   PORT(S)          AGE
kubernetes                ClusterIP   10.96.0.1                443/TCP          3d1h
postgres                  NodePort    10.96.228.238            5432:30432/TCP   7s

Verify and test PostgreSQL via kubectl Command

# user kubectl exec to access your pod and postgres database
kubectl exec -it postgres-xxxx -- psql -h localhost -U yourusername --password -p 5432 yourdb

# Type your password and sample output
Password: 
psql (12.10 (Debian 12.10-1.pgdg110+1))
Type "help" for help.

yourdb=# 

Reference:

Scroll to Top