pg_dump ile uğraşmayı bıraktığım gün, sistem yazılım mühendisi olarak ciddiyetimin arttığını düşünüyorum. pg_dump bir araştırma aracı — production yedek aracı değil.

Üretim yedeği üç şeyi sağlamalı:

  1. Point-in-time recovery (PITR). “Dün gece 02:13’te silindi” diyebilmek.
  2. Bütünlük doğrulaması. Yedek dosyasının açıldığında çalıştığını test etmek.
  3. Saklamayı politikayla yönetmek. Saatlik/günlük/haftalık/aylık rotasyon.

pg_dump üç maddeyi de karşılamıyor.

pgBackRest temel kurulum

pgbackrest.conf:

[global]
repo1-path=/var/lib/pgbackrest
repo1-retention-full=4
repo1-retention-diff=14
repo1-cipher-pass=...
repo1-cipher-type=aes-256-cbc
compress-type=zst
compress-level=6
process-max=4
start-fast=y

[main]
pg1-path=/var/lib/postgresql/16/main
pg1-port=5432

postgresql.conf tarafında ise WAL archiving’i pgBackRest’e yönlendiriyoruz:

archive_mode = on
archive_command = 'pgbackrest --stanza=main archive-push %p'
archive_timeout = 60
wal_level = replica

archive_timeout = 60 — son 60 saniyenin işlemleri kaybedilebilir; çoğu uygulama için yeterli, finansal işlemler için değil.

Backup planı

Cron tarafından:

0 2 * * 0  pgbackrest --stanza=main --type=full backup
0 2 * * 1-6  pgbackrest --stanza=main --type=diff backup
0 */6 * * *  pgbackrest --stanza=main --type=incr backup

Haftalık full, günlük diff, 6 saatlik incremental. Storage tüketimi şaşırtıcı derecede düşük — pgBackRest delta block tekniği ile değişen sayfaları tespit ediyor.

Bütünlük: yedek varsa restore edilebilir mi?

Yedeği almak yeterli değil. Haftada bir restore tatbikatı:

pgbackrest --stanza=main --delta restore --pg1-path=/tmp/pg_restore_test

Sonra o instance’ı geçici bir port üzerinde başlatıp birkaç sanity query çalıştırıyorum. Bu adım atlanırsa yedek sahte güven olur.

PITR provası

Belirli bir zamana geri dönmek:

pgbackrest --stanza=main \
  --type=time \
  --target='2026-05-07 02:13:00+03' \
  restore

Bu komutun gerçek bir incidentte ilk kez çalıştırılması felakettir. Provayı önceden yapın — adımlar runbook’a yazılsın.

Saklama

Repository’deki kullanılmayan yedeklerin temizliği expire komutuyla:

pgbackrest --stanza=main expire

repo1-retention-full=4 ile son 4 full yedek tutuluyor; daha eskileri (ve onlara bağlı diff/incr’ler) otomatik temizleniyor.

Off-site copy

Repository tek bir diskte duruyorsa bir VPS yangını her şeyi siler. pgBackRest S3 veya S3-uyumlu (R2, MinIO) kovaya yazabiliyor:

repo1-type=s3
repo1-s3-bucket=...
repo1-s3-endpoint=...
repo1-s3-region=auto
repo1-s3-key=...
repo1-s3-key-secret=...

Tercih: kovayı versiyon-kilitli ve delete’i yasaklayan bir policy ile koruyun. Ransomware senaryosunda kritik.

Sonuç

pg_dump ile schema kopyalamak veya küçük bir tabloyu taşımak hâlâ doğru araç. Ama PITR isteyen herhangi bir sistemde yedek yazılımı pgBackRest (veya barman, ya da veritabanı sağlayıcının yerli aracı) olmalı. Backup’ın test edilmediği anda “backup’ım var” demek yalan söylemenin sofistike bir yoludur.