Kodeloka
  1. Kodeloka
  2. Kelas PostgreSQL
  3. Materi

8 · Praktik · Modul 12 dari 12

Pemantauan & Daftar Periksa Produksi

Metrik yang benar-benar perlu diawasi, konfigurasi yang harus diperiksa sebelum melayani pengguna, dan cara mengatur connection pooler.

Metrik yang Perlu Dipantau

-- Cache hit ratio: idealnya di atas 99%
SELECT
    sum(heap_blks_hit) * 100.0 / nullif(sum(heap_blks_hit + heap_blks_read), 0)
        AS persen_cache_hit
FROM pg_statio_user_tables;

-- Pemakaian koneksi
SELECT count(*) AS terpakai,
       current_setting('max_connections')::int AS maksimum,
       count(*) FILTER (WHERE state = 'idle in transaction') AS menganggur_dlm_transaksi
FROM pg_stat_activity;

-- Transaksi terlama
SELECT max(now() - xact_start) FROM pg_stat_activity WHERE xact_start IS NOT NULL;

-- Umur transaction ID — untuk alert wraparound
SELECT max(age(datfrozenxid)) FROM pg_database;

-- Deadlock, konflik, berkas temporer
SELECT datname, deadlocks, conflicts, temp_files,
       pg_size_pretty(temp_bytes) AS ukuran_temp
FROM pg_stat_database WHERE datname = current_database();
📌 Ambang alert yang masuk akal
MetrikPeringatanKritis
Cache hit ratio< 98%< 95%
Koneksi terpakai> 70%> 85%
Transaksi terlama> 5 menit> 30 menit
Lag replikasi> 50 MB> 500 MB
Umur XID> 1 miliar> 1,5 miliar
Disk terpakai> 75%> 85%

PgBouncer

# pgbouncer.ini
[databases]
toko = host=127.0.0.1 port=5432 dbname=toko

[pgbouncer]
listen_port = 6432
auth_type = scram-sha-256

pool_mode = transaction        # paling efisien
max_client_conn = 2000         # dari aplikasi
default_pool_size = 25         # ke PostgreSQL
reserve_pool_size = 5
server_idle_timeout = 600
pool_modeKoneksi dikembalikan setelahEfisiensiBatasan
sessionKlien memutusRendahTidak ada
transactionSetiap COMMITTinggiTanpa prepared statement bernama, tanpa SET lintas transaksi, tanpa LISTEN/NOTIFY
statementSetiap pernyataanTertinggiTidak mendukung transaksi multi-pernyataan
🚫 Mode transaction memutus beberapa asumsi umum

Karena koneksi fisik berpindah-pindah antar klien setiap selesai transaksi, hal-hal yang bergantung pada sesi menjadi berbahaya: SET biasa bocor ke permintaan berikutnya, LISTEN/NOTIFY tidak berfungsi, dan prepared statement bernama menjadi tidak valid.

Driver modern menyediakan penyesuaian untuk ini — misalnya pgx dengan QueryExecModeSimpleProtocol, atau JDBC dengan prepareThreshold=0. Pastikan driver Anda dikonfigurasi sesuai, kalau tidak Anda akan menemui error yang sangat membingungkan di bawah beban.

Daftar Periksa Produksi

Konfigurasi

shared_buffers ≈ 25% RAMCache halaman yang memadai
effective_cache_size ≈ 50–75% RAMPerencana membuat keputusan yang lebih baik
work_mem konservatif secara globalMencegah OOM saat banyak kueri paralel
max_connections wajar + PgBouncerModel proses PostgreSQL mahal per koneksi
statement_timeout disetelKueri liar tidak berjalan selamanya
idle_in_transaction_session_timeoutMencegah bloat akibat transaksi menggantung
random_page_cost = 1.1 pada SSDBawaan 4.0 mengasumsikan cakram berputar

Keandalan & Keamanan

fsync = onJangan pernah dimatikan pada data sungguhan
Backup otomatis + arsip WALMemungkinkan pemulihan titik waktu
Uji pemulihan berkalaBackup yang belum diuji bukan backup
Alert umur XIDWraparound menghentikan seluruh penulisan
Autovacuum disetel per tabel besarNilai bawaan tidak cocok untuk tabel besar
scram-sha-256, bukan md5md5 sudah lemah
TLS diwajibkan, peran aplikasi bukan superuserHak akses terkecil
pg_hba.conf membatasi sumberBasis data tidak boleh terbuka ke internet
🚫 Dua kesalahan yang paling sering ditemui

1. Tidak ada statement_timeout. Satu kueri analitik yang lupa dibatasi bisa berjalan berjam-jam, menahan kunci, menghambat vacuum, dan membuat replika tertinggal jauh. Setel nilai global yang wajar dan naikkan hanya untuk pekerjaan yang memang butuh.

2. random_page_cost dibiarkan 4.0 pada SSD. Nilai bawaan berasal dari era cakram berputar ketika akses acak jauh lebih mahal daripada berurutan. Pada SSD, selisihnya kecil. Membiarkan nilai lama membuat perencana terlalu enggan memakai indeks dan lebih memilih pemindaian penuh yang sebenarnya lebih lambat.