Chuẩn bị môi trường cụm
[root@mast ~]# kubectl label nodes node1 postgres-env=dev # Gắn nhãn nút
node/node1 labeled
[root@mast ~]# kubectl label nodes node1 disk-type=ssd # Tùy chọn: nhãn mở rộng cho lập lịch nâng cao
node/node1 labeled
[root@mast ~]# kubectl create namespace postgres-dev # Cách ly môi trường phát triển
namespace/postgres-dev created
Tạo thể tích lưu trữ
Thể tích lưu trữ (Persistent Volume - PV) là tài nguyên lưu trữ cấp cụm do quản trị viên tạo. Đây là trừu tượng hóa hệ thống lưu trữ nền tảng (NFS, iSCSI, Ceph...) cung cấp lưu trữ bền vững cho Pod, độc lập với nút và hỗ trợ nhiều chế độ truy cập như ReadWriteOnce, ReadOnlyMany, ReadWriteMany.
Khai báo thể tích (Persistent Volume Claim - PVC) là yêu cầu sử dụng lưu trữ từ người dùng. Tương tự Pod yêu cầu tài nguyên CPU/Memory, PVC yêu cầu PV với dung lượng và chế độ truy cập cụ thể. Kubernetes sẽ tự động kết nối PVC với PV phù hợp hoặc tạo PV mới qua dynamic provisioning.
[root@mast ~]# kubectl apply -f pv-pvc.yaml -n postgres-dev
persistentvolume/postgres-pv-dev created
persistentvolumeclaim/postgres-pvc-dev created
[root@mast ~]# cat pv-pvc.yaml
#PV
apiVersion: v1
kind: PersistentVolume
metadata:
name: postgres-pv-dev
namespace: postgres-dev
labels:
app: postgres-dev # Nhãn cho lập lịch liên kết
spec:
capacity:
storage: 5Gi # Dung lượng (khuyến nghị 5Gi cho môi trường phát triển)
storageClassName: manual
accessModes:
- ReadWriteOnce
hostPath:
path: /data/postgres-dev # Đường dẫn cục bộ trên nút (phải tạo trước)
nodeAffinity: # Liên kết PV với nút cụ thể
required:
nodeSelectorTerms:
- matchExpressions:
- key: kubernetes.io/hostname
operator: In
values: [node1] # Gắn chặt với node1
---
#PVC
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: postgres-pvc-dev
namespace: postgres-dev
spec:
storageClassName: manual
accessModes: [ReadWriteOnce]
resources:
requests:
storage: 5Gi # Phù hợp với PV
selector: # Chọn PV có nhãn cụ thể
matchLabels:
app: postgres-dev
Tạo Secret và ConfigMap
ConfigMap lưu trữ dữ liệu cấu hình phi nhạy cảm dạng key-value, cho phép tách biệt cấu hình khỏi hình ảnh container. Có thể dùng để thiết lập biến môi trường, tham số dòng lệnh hoặc gắn file cấu hình.
Secret lưu trữ thông tin nhạy cảm như mật khẩu, token, SSH key. Dữ liệu được mã hóa trong quá trình lưu trữ và truyền tải, thường dùng cho xác thực và khóa mật mã.
[root@mast ~]# vim secret.yaml
[root@mast ~]# kubectl apply -f secret.yaml -n postgres-dev
secret/postgres-secret-dev created
[root@mast ~]# cat secret.yaml
apiVersion: v1
kind: Secret
metadata:
name: postgres-secret-dev
namespace: postgres-dev
type: Opaque
stringData: # Xử lý đơn giản cho môi trường phát triển
DB_USER: "dev_admin"
DB_PASSWORD: "d3v!P@ss"
data: # Trường có thể mã hóa thủ công
# echo -n "backup" | base64 → YmFja3Vw
# BACKUP_USER: YmFja3Vw
Tạo tệp triển khai PostgreSQL
Pod là đơn vị nhỏ nhất chạy container, chứa nhiều thông tin quan trọng. Trong YAML, có thể giới hạn nhiều yếu tố cho Pod:
[root@mast ~]# kubectl apply -f deployment.yaml -n postgres-dev
deployment.apps/postgres-deployment-dev created
[root@mast ~]# cat deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: postgres-deployment-dev
namespace: postgres-dev
spec:
replicas: 1
selector:
matchLabels:
app: postgres-dev
template:
metadata:
labels:
app: postgres-dev # Nhận diện bởi service
env: dev
spec:
affinity: # Cấu hình lập lịch liên kết
nodeAffinity:
requiredDuringSchedulingIgnoredDuringExecution:
nodeSelectorTerms:
- matchExpressions:
- key: postgres-env # Phù hợp với nhãn nút
operator: In
values: [dev]
- key: disk-type # Đa nhãn
operator: Exists
containers:
- name: pgsql-container # Tên container
image: postgres:15-alpine
imagePullPolicy: IfNotPresent # Chỉ tải khi cần
ports:
- containerPort: 5432
envFrom: # Tải biến môi trường
- secretRef: # Từ Secret
name: postgres-secret-dev
env:
- name: DB_NAME
value: "dev_core" # Tên cơ sở dữ liệu
volumeMounts: # Gắn thể tích
- name: pgsql-data
mountPath: /var/lib/postgresql/data
resources:
limits:
cpu: "1" # Giới hạn cứng
memory: "1Gi"
requests:
cpu: "0.7" # Yêu cầu linh hoạt
memory: "768Mi"
volumes:
- name: pgsql-data
persistentVolumeClaim:
claimName: postgres-pvc-dev
Tạo Service
Service cung cấp cổng mạng ổn định cho Pod, trừu tượng hóa nhiều Pod thành dịch vụ duy nhất để các ứng dụng khác truy cập:
[root@mast ~]# kubectl apply -f service.yaml -n postgres-dev
service/postgres-service-dev created
[root@mast ~]# cat service.yaml
apiVersion: v1
kind: Service
metadata:
name: postgres-service-dev
namespace: postgres-dev
spec:
type: ClusterIP
selector:
app: postgres-dev
ports:
- name: postgres
port: 5432
targetPort: 5432
Kiểm tra Pod
[root@mast ~]# kubectl get pods -n postgres-dev -o wide | grep -E "NAME|postgres"
NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES
pgsql-deployment-dev-69475b468c-9w5sl 1/1 Running 0 41s 10.244.1.23 node1 <none> <none>
Kết quả kiểm tra Pod và kết nối cơ sở dữ liệu sẽ tương tự như trong tài liệu gốc.
Triển khai đơn máy và cấu hình cụm
Khi cần triển khai cụm PostgreSQL, cần thêm ConfigMap chứa cấu hình:
# postgres-configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:
name: postgres-config
namespace: postgres-dev
data:
# Cấu hình master
postgresql-master.conf: |
wal_level = replica
max_wal_senders = 3
hot_standby = on
# Cấu hình slave
postgresql-replica.conf: |
hot_standby = on
primary_conninfo = 'host=pgsql-master user=repluser password=${REPL_PASSWORD}'
# Tạo user sao chép
init-replication.sql: |
CREATE ROLE repluser WITH REPLICATION LOGIN PASSWORD '${REPL_PASSWORD}';
Phân biệt Pod PostgreSQL và Nginx
Pod PostgreSQL là dịch vụ có trạng thái, cần lưu trữ dữ liệu bền vững qua thể tích. Trong khi đó, Nginx thường chỉ cần sao lưu cấu hình và giao tiếp bên ngoài qua HTTPS.