Choosing PostgreSQL capacity for an OLTP application is not simply a matter of estimating the number of users.
Online Transaction Processing workloads usually involve many small, concurrent operations such as inserts, updates, deletes, and short queries. The database therefore needs enough CPU, memory, storage performance, and connection capacity to handle peak activity reliably.
The right starting point is workload measurement rather than a fixed server size.
What Does OLTP Mean?
OLTP systems process frequent transactions with relatively small amounts of data.
Typical examples include:
Order processing
Banking transactions
Inventory systems
Customer management
Payment processing
Business applications
A simplified request looks like this:
Application
|
v
PostgreSQL
|
+-- Read
+-- Insert
+-- Update
+-- Commit
The database may execute thousands of these operations while serving many users simultaneously.
Capacity Is More Than Disk Space
When developers ask how much PostgreSQL capacity they need, they may be referring to different resources.
Resource | What it affects |
|---|---|
CPU | Query execution and concurrency |
RAM | Caching and working data |
Storage capacity | Database size, indexes, WAL, backups |
Storage performance | Query and transaction latency |
Connections | Concurrent client activity |
Network | Application-database communication |
A database can have plenty of free disk space and still be overloaded because CPU, memory, or storage performance is insufficient.
Start With Workload Numbers
Before choosing infrastructure, estimate:
Transactions per second
Peak transactions per second
Concurrent connections
Database size
Daily data growth
Read/write ratio
Largest tables
Index size
Backup requirements
Peak workload is particularly important.
For example, an application might normally process:
500 transactions/second
but reach:
1,500 transactions/second
during a peak period.
Sizing only for the average workload can leave insufficient capacity during traffic spikes.
CPU Capacity
PostgreSQL uses CPU for activities such as:
Query execution
Sorting
Aggregation
Index processing
Background database work
Connection handling
CPU requirements depend heavily on the queries being executed.
A simple indexed lookup:
SELECT id, status
FROM orders
WHERE customer_id = $1;
can have very different CPU requirements from a complex analytical query.
For OLTP systems, keep queries focused and make sure frequently used predicates have appropriate indexes.
Memory Capacity
PostgreSQL uses memory for several purposes, including shared buffers and per-operation working memory.
A database server with insufficient memory may depend heavily on storage access.
A simplified flow is:
Query
|
v
Memory cache?
/ \
Yes No
| |
Fast Storage
access access
Memory is therefore important for keeping frequently accessed data and indexes readily available.
However, allocating as much memory as possible to PostgreSQL is not automatically correct. The operating system and other processes also need memory.
Storage Capacity
Estimate storage using more than the current database size.
A basic model is:
Required capacity =
Current data
+ Indexes
+ WAL
+ Growth
+ Temporary space
+ Backup requirements
+ Operational headroom
For example, if the database currently uses 300 GB, provisioning exactly 300 GB leaves no room for normal growth or operational requirements.
Account for Indexes
Indexes improve query performance but consume storage.
For example:
CREATE INDEX idx_orders_customer_id
ON orders(customer_id);
The index becomes another structure that PostgreSQL must maintain.
Every insert or update affecting the indexed column can require index maintenance.
Therefore, when estimating capacity, include indexes rather than considering only table data.
WAL Also Matters
PostgreSQL uses Write-Ahead Logging (WAL) for durability and recovery.
A simplified transaction flow is:
Transaction
|
v
WAL record
|
v
Commit
|
v
Data pages
WAL storage requirements depend on workload and configuration.
High-write systems should monitor WAL generation rather than estimating it solely from database size.
Connections Need Planning
Applications often create more database connections than necessary.
For example:
100 application instances
×
20 database connections
=
2,000 connections
That can create unnecessary pressure on PostgreSQL.
Connection pooling can reduce the number of direct database connections.
A typical architecture is:
Users
|
v
Application instances
|
v
Connection Pool
|
v
PostgreSQL
The correct pool size depends on the workload and database capacity.
More connections do not automatically mean more throughput.
Read and Write Ratio
Two applications with the same number of requests can require very different resources.
Example:
Application A
80% reads
20% writes
Application B
20% reads
80% writes
The second workload may generate substantially more write activity and WAL traffic.
Measure the actual read/write pattern when sizing the database.
Query Design Matters
Infrastructure cannot compensate for inefficient queries indefinitely.
For example:
SELECT *
FROM orders
WHERE customer_id = $1;
may retrieve significantly more data than required.
Prefer:
SELECT id, status, total
FROM orders
WHERE customer_id = $1;
Selecting only required columns can reduce data transfer and processing.
Use EXPLAIN to understand query behavior:
EXPLAIN (ANALYZE, BUFFERS)
SELECT id, status
FROM orders
WHERE customer_id = 1001;
This can help identify sequential scans, expensive operations, and buffer activity.
Capacity Planning Example
Suppose an application has:
Peak transactions: 1,000 TPS
Database size: 500 GB
Growth: 50 GB/month
High write volume
Multiple app instances
Do not immediately translate those numbers into a specific CPU and RAM configuration.
Instead, build a representative test environment and measure:
CPU utilization
Memory utilization
Transaction latency
Storage latency
IOPS
WAL generation
Connections
Cache behavior
The measurements tell you whether the selected infrastructure can handle the workload.
Headroom Is Important
Do not size a production database so that normal peak traffic consumes 100% of available resources.
Leave room for:
Traffic growth
Maintenance
Temporary workload increases
Background operations
Deployment events
Unexpected traffic
The exact amount of headroom depends on the application's requirements and scaling strategy.
Common Mistakes
Sizing Only by Database Size
A 500 GB database can have very different performance requirements depending on workload.
Using Average Traffic
Peak traffic is more useful for capacity planning than average traffic alone.
Adding More Connections
More connections can increase contention and memory usage.
Ignoring WAL
Write-heavy workloads can generate significant WAL activity.
Ignoring Index Size
Indexes can consume substantial storage and require maintenance.
Optimizing Hardware Before Queries
An inefficient query can remain expensive even on a larger server.
What to Monitor in Production
A useful PostgreSQL capacity dashboard should include:
CPU utilization
Memory utilization
Disk usage
Storage latency
IOPS
Database connections
Transaction rate
Query latency
WAL generation
Cache behavior
Replication lag
Monitor both averages and peak values.
Averages can hide short periods of severe resource pressure.
Capacity Planning Checklist
Before selecting PostgreSQL infrastructure, answer:
How many transactions occur per second?
What is the expected peak TPS?
How many concurrent connections are required?
How large is the database today?
How quickly is the data growing?
How much storage do indexes require?
How write-heavy is the workload?
How much WAL is generated?
What are the most expensive queries?
How much operational headroom is required?
Best Practices
Size PostgreSQL from measured workload data.
Use peak traffic rather than averages alone.
Monitor CPU, memory, storage, and connections together.
Account for indexes and WAL when estimating storage.
Use connection pooling for applications with many clients.
Optimize expensive queries before simply increasing hardware.
Test with production-like data volumes.
Leave capacity for growth and operational activity.
Revisit capacity estimates as the workload changes.
Summary
There is no single PostgreSQL server size that fits every OLTP application.
Capacity depends on transaction rate, concurrency, query complexity, read/write ratio, database size, indexes, WAL activity, storage performance, and growth.
The most reliable approach is to measure the workload, test it under realistic peak conditions, and monitor the resources that actually limit performance.
Start with the workload rather than the hardware. Once you know the application's TPS, concurrency, storage growth, query behavior, and performance requirements, PostgreSQL capacity planning becomes much more predictable.

Join the conversation! Your thoughts help the community grow.