PostgreSQL pe un VPS: cum dimensionați memoria și discul

O bază PostgreSQL rapidă este o bază ale cărei date consultate des încap în memorie. Întreaga dimensionare pornește de aici: volumul bazei, partea care lucrează cu adevărat, numărul de conexiuni, apoi discul și marja lui. Acest ghid prezintă metoda, setările de pornire pentru 4, 8 și 16 GB de memorie și interogările care măsoară o bază existentă.

Publicat la 29 octombrie 2026 Autor: Timp de citire: 10 minute

Toate ghidurile

Esențialul

  1. Măsurați volumul bazei și al indecșilor ei, apoi partea consultată des: ea trebuie să încapă în memorie.
  2. Punct de plecare: shared_buffers la 25% din memorie, effective_cache_size la 75%, random_page_cost = 1.1 pe SSD NVMe.
  3. Fiecare conexiune este un proces: peste câteva zeci de conexiuni active, puneți PgBouncer în fața bazei de date.
  4. Disc: datele și indecșii la un an, plus o marjă de cel puțin 30%. Un disc plin oprește PostgreSQL.
  5. Rata de citire din cache trebuie să rămână peste 99%: sub acest prag, bazei îi lipsește memoria.
  6. Faceți backup zilnic cu pg_dump, în afara serverului, și restaurați regulat pentru a-l verifica.

Porniți de la volumul util

Memoria unui server de baze de date servește în primul rând drept cache: o pagină citită din memorie este servită mult mai repede decât una citită de pe disc, chiar și NVMe. Întrebarea nu este deci doar „cât cântărește baza?”, ci „ce parte din ea este citită des?”. O bază de 50 GB din care sunt consultate doar ultimele douăsprezece luni lucrează poate pe 8 GB.

Pe o bază existentă, două interogări dau volumul total și cele mai mari tabele, inclusiv indecșii:

SQL (psql)
SELECT pg_size_pretty(pg_database_size(current_database()));

SELECT relname AS nume,
       pg_size_pretty(pg_total_relation_size(relid)) AS dimensiune_cu_indecsi
FROM pg_catalog.pg_statio_user_tables
ORDER BY pg_total_relation_size(relid) DESC
LIMIT 10;

Pentru o bază care urmează să fie creată, estimați tabel cu tabel: numărul de rânduri așteptate la un an × dimensiunea medie a unui rând, apoi adăugați indecșii, care cântăresc frecvent între 30 și 100% din date. Exemplu: 2 milioane de rânduri pe lună, de 500 de octeți fiecare, fac 12 GB de date la un an și între 18 și 24 GB cu indecșii.

Memoria: setările de pornire

PostgreSQL păstrează paginile citite pe două niveluri: propriul cache (shared_buffers) și cache-ul de fișiere al sistemului. Documentația sa recomandă să porniți de la 25% din memorie pentru shared_buffers pe un server dedicat și observă că peste 40% câștigul devine rar: restul rămâne în folosul cache-ului sistemului și al sortărilor.

Parametru4 GB8 GB16 GBRol
shared_buffers1 GB2 GB4 GBCache-ul propriu al PostgreSQL
effective_cache_size3 GB6 GB12 GBCache-ul total estimat, care orientează alegerea planurilor de interogare
work_mem8 MB16 MB32 MBMemoria fiecărei sortări sau operații de hash, per conexiune: de înmulțit cu numărul de interogări simultane
maintenance_work_mem256 MB512 MB1 GBCrearea indecșilor și VACUUM
random_page_cost1.11.11.1Costul estimat al unei citiri aleatorii: 4 implicit, mult peste costul real pe SSD NVMe

Aceste valori presupun o bază singură pe server. Dacă aplicația rulează alături, scădeți mai întâi memoria ei (procese, cache, compilare) și aplicați procentele la rest: un server de 8 GB care rulează o aplicație de 3 GB se reglează ca o bază de 5 GB.

postgresql.conf, pentru un server de 8 GB dedicat bazei de date
shared_buffers = 2GB
effective_cache_size = 6GB
work_mem = 16MB
maintenance_work_mem = 512MB
random_page_cost = 1.1

shared_buffers intră în vigoare doar la repornirea PostgreSQL; ceilalți parametri se reîncarcă fără întrerupere, cu SELECT pg_reload_conf();.

Pentru a ști dacă memoria ajunge, citiți rata de citire din cache. Pe o aplicație de gestiune sau pe un site, ea depășește 99%:

SQL (psql)
SELECT round(100.0 * blks_hit / nullif(blks_hit + blks_read, 0), 2) AS rata_cache
FROM pg_stat_database
WHERE datname = current_database();

Conexiunile: câte un proces fiecare

PostgreSQL deschide un proces pentru fiecare conexiune și acceptă implicit 100 (max_connections). Fiecare proces ocupă câțiva megaocteți în repaus, mai mult când sortează sau aplică hash pe date (work_mem, uneori de mai multe ori în aceeași interogare). A ridica max_connections la 500 pentru a ține pasul cu o aplicație care deschide multe conexiuni înseamnă a expune serverul lipsei de memorie la primul vârf.

Răspunsul potrivit este un pooler de conexiuni: PgBouncer, în modul transaction, face ca sute de conexiuni ale aplicației să împartă câteva zeci de conexiuni reale. Framework-urile au și ele propriul pool (SQLAlchemy, Prisma, HikariCP): reglați-i dimensiunea după numărul de vCPU al serverului de baze de date, nu după numărul de utilizatori.

Discul: volum, marjă și jurnal

Discul unui server PostgreSQL conține mai mult decât tabelele:

Regula: volumul la un an, plus o marjă de cel puțin 30%. Nu este un lux: când discul care găzduiește jurnalul de tranzacții se umple, PostgreSQL se oprește pentru a-și proteja datele. Urmăriți gradul de ocupare și măriți discul înainte de 80%.

Din punctul de vedere al performanței, fiecare validare de tranzacție așteaptă scrierea jurnalului pe disc: latența stocării stabilește debitul de scriere. Aici face diferența un SSD NVMe, mult mai mult decât la citiri, pe care memoria le servește deja.

Procesorul: o interogare, un nucleu

O interogare PostgreSQL rulează pe un singur nucleu, cu excepția citirilor mari pe care motorul le paralelizează. Numărul de vCPU stabilește deci câte interogări grele sunt procesate în același timp: 2 vCPU ajung unei aplicații de gestiune la lansare, între 4 și 8 se potrivesc bazelor foarte solicitate și rapoartelor grele.

Înainte de a adăuga vCPU, căutați interogările care le consumă. Extensia pg_stat_statements le ordonează după timpul total:

postgresql.conf, apoi repornire
shared_preload_libraries = 'pg_stat_statements'
SQL (psql)
CREATE EXTENSION IF NOT EXISTS pg_stat_statements;

SELECT calls, round(total_exec_time) AS ms_total,
       round(mean_exec_time::numeric, 1) AS ms_mediu, query
FROM pg_stat_statements
ORDER BY total_exec_time DESC
LIMIT 10;

Același server cu aplicația sau un server separat?

La lansare, baza de date pe același server cu aplicația este alegerea potrivită: nicio latență de rețea între cele două, o conexiune prin socket Unix, un singur server de salvat și de monitorizat. Le separați când își dispută resursele: o compilare sau un vârf de trafic care golește cache-ul bazei, o bază care are nevoie de toată memoria pentru datele ei sau cerințe de backup diferite.

Securitate și backupuri

Terminal: export comprimat, apoi restaurare într-o bază de test
pg_dump -Fc -d baza_mea -f baza_mea-$(date +%F).dump
createdb baza_mea_test
pg_restore -d baza_mea_test baza_mea-2026-10-29.dump

O bază PostgreSQL rapidă, pe serverul potrivit

VPS Pro rulează pe procesoare Intel Xeon, memorie ECC care corectează erorile din mers și SSD NVMe în oglindă, cu fiecare bloc de date verificat prin sumă de control și un backup criptat în fiecare noapte, în afara mașinii. Asistența integrală este inclusă: când baza dumneavoastră de date încetinește, analizăm interogările lente și indecșii, apoi vă indicăm setările care îi redau aplicației dumneavoastră viteza.

Descoperiți gama VPS Pro

Întrebări frecvente

Câtă memorie RAM pentru PostgreSQL?

Suficientă pentru ca datele consultate des să încapă în memorie. Pentru o aplicație de gestiune la lansare ajung 4 GB, bază de date și aplicație incluse. Apoi măsurați rata de citire din cache: cât timp rămâne peste 99%, memoria este suficientă.

Ce valoare pentru shared_buffers?

25% din memorie pe un server dedicat bazei de date, așa cum recomandă documentația PostgreSQL: 1 GB din 4 GB, 2 GB din 8 GB, 4 GB din 16 GB. Peste 40%, câștigul devine rar, cache-ul sistemului făcând restul.

Câte conexiuni PostgreSQL poate accepta un VPS?

PostgreSQL acceptă implicit 100, iar fiecare conexiune este un proces care consumă memorie. În loc să ridicați acest plafon, puneți un pooler precum PgBouncer în fața bazei de date: câteva zeci de conexiuni reale servesc atunci sute de conexiuni ale aplicației.

Trebuie separate baza de date și aplicația?

Nu la lansare: pe același server, baza de date răspunde fără latență de rețea, iar întregul ansamblu se salvează dintr-o dată. Le separați atunci când una o stânjenește pe cealaltă, de exemplu când o compilare sau un vârf de trafic golește cache-ul bazei.

Contactați-ne