
Installing and Using PostgreSQL on Ubuntu 24
PostgreSQL, often called “Postgres,” stands as one of the most powerful open-source relational database management systems available today, offering advanced features like JSONB support, full-text search, and extensibility that make it a go-to choice for everything from small web applications to enterprise-grade systems. With Ubuntu 24’s release bringing improved performance and updated package repositories, setting up PostgreSQL has become even more straightforward, though there are still plenty of configuration gotchas and optimization opportunities that can make or break your database performance. This guide will walk you through the complete installation process, cover essential configuration tweaks, troubleshoot common issues, and show you how to get PostgreSQL running optimally on Ubuntu 24.
How PostgreSQL Works on Ubuntu 24
PostgreSQL operates as a client-server database system where the server process manages database files, accepts connections, and performs database actions on behalf of client applications. On Ubuntu 24, PostgreSQL integrates seamlessly with systemd for service management, uses the standard APT package manager for installation and updates, and follows Linux filesystem hierarchy standards for data and configuration file placement.
The default Ubuntu installation creates a dedicated ‘postgres’ user account that owns all database processes and files. This security model ensures database operations run with minimal privileges while maintaining proper file permissions. PostgreSQL listens on port 5432 by default and can handle multiple concurrent connections through its multi-process architecture.
Ubuntu 24 ships with PostgreSQL packages that include automatic service startup, logrotate configuration, and integration with Ubuntu’s security updates. The package system handles dependencies, creates necessary directories, and sets up basic configuration files automatically.
Step-by-Step Installation Guide
Let’s start with the straightforward installation process. Ubuntu 24’s repositories include PostgreSQL packages, but you might want to use the official PostgreSQL APT repository for the latest versions.
Installing from Ubuntu Repositories
First, update your package list and install PostgreSQL:
sudo apt update
sudo apt install postgresql postgresql-contrib
The ‘postgresql-contrib’ package includes additional utilities and extensions that you’ll likely need later. Check the installation:
sudo systemctl status postgresql
psql --version
Installing from Official PostgreSQL Repository
For the latest PostgreSQL version (recommended for production), add the official repository:
# Install required packages
sudo apt install wget ca-certificates
# Add PostgreSQL signing key
wget --quiet -O - https://www.postgresql.org/media/keys/ACCC4CF8.asc | sudo apt-key add -
# Add repository
echo "deb http://apt.postgresql.org/pub/repos/apt/ $(lsb_release -cs)-pgdg main" | sudo tee /etc/apt/sources.list.d/pgdg.list
# Update and install
sudo apt update
sudo apt install postgresql-15 postgresql-contrib-15
Replace ’15’ with your desired version number. PostgreSQL maintains several versions simultaneously, so you can be specific about which version to install.
Post-Installation Configuration
After installation, PostgreSQL creates a system user called ‘postgres’. Switch to this user to perform initial database operations:
sudo -i -u postgres
psql
You’re now in the PostgreSQL interactive terminal. Set a password for the postgres user:
ALTER USER postgres PASSWORD 'your_secure_password';
\q
Exit back to your regular user account:
exit
Essential Configuration
PostgreSQL’s main configuration files live in ‘/etc/postgresql/[version]/main/’ on Ubuntu. The two most important files are ‘postgresql.conf’ for server settings and ‘pg_hba.conf’ for authentication rules.
Basic PostgreSQL Configuration
Edit the main configuration file:
sudo nano /etc/postgresql/15/main/postgresql.conf
Key settings to modify for better performance:
# Connection settings
listen_addresses = 'localhost' # Change to '*' for remote connections
port = 5432
max_connections = 100
# Memory settings (adjust based on your system)
shared_buffers = 256MB # 25% of total RAM is a good starting point
effective_cache_size = 1GB # 75% of total RAM
work_mem = 4MB # Memory per query operation
maintenance_work_mem = 64MB # Memory for maintenance operations
# Write-ahead logging
wal_level = replica
max_wal_size = 1GB
min_wal_size = 80MB
# Logging
log_destination = 'stderr'
logging_collector = on
log_directory = '/var/log/postgresql'
log_filename = 'postgresql-%Y-%m-%d_%H%M%S.log'
log_statement = 'error' # Change to 'all' for debugging
Authentication Configuration
Configure client authentication by editing pg_hba.conf:
sudo nano /etc/postgresql/15/main/pg_hba.conf
The file controls who can connect and how they authenticate. Common configurations:
# Local connections
local all postgres peer
local all all md5
# IPv4 local connections
host all all 127.0.0.1/32 md5
# IPv6 local connections
host all all ::1/128 md5
# For remote connections (be careful with security)
host all all 192.168.1.0/24 md5
After making configuration changes, restart PostgreSQL:
sudo systemctl restart postgresql
Creating Databases and Users
Now let’s create a practical setup with a new database and user. Connect as the postgres user:
sudo -u postgres psql
Create a new database and user:
-- Create a new database
CREATE DATABASE myapp_production;
-- Create a new user with password
CREATE USER myapp_user WITH ENCRYPTED PASSWORD 'secure_password123';
-- Grant privileges
GRANT ALL PRIVILEGES ON DATABASE myapp_production TO myapp_user;
-- Grant schema privileges (PostgreSQL 15+)
\c myapp_production
GRANT ALL ON SCHEMA public TO myapp_user;
GRANT ALL PRIVILEGES ON ALL TABLES IN SCHEMA public TO myapp_user;
GRANT ALL PRIVILEGES ON ALL SEQUENCES IN SCHEMA public TO myapp_user;
-- Exit
\q
Test the new user connection:
psql -h localhost -U myapp_user -d myapp_production
Performance Optimization and Tuning
PostgreSQL performance depends heavily on proper configuration. Here’s a comparison of default vs. optimized settings for different system sizes:
Setting | Default | Small System (2GB RAM) | Medium System (8GB RAM) | Large System (32GB RAM) |
---|---|---|---|---|
shared_buffers | 128MB | 512MB | 2GB | 8GB |
effective_cache_size | 4GB | 1.5GB | 6GB | 24GB |
work_mem | 4MB | 8MB | 16MB | 32MB |
maintenance_work_mem | 64MB | 128MB | 512MB | 2GB |
max_connections | 100 | 50 | 100 | 200 |
Use the pg_tune utility for automated configuration recommendations:
sudo apt install pgtune
pgtune -i /etc/postgresql/15/main/postgresql.conf -o postgresql.conf.tuned
Monitoring and Maintenance
Set up basic monitoring with these queries:
-- Check database sizes
SELECT
datname as database_name,
pg_size_pretty(pg_database_size(datname)) as size
FROM pg_database
ORDER BY pg_database_size(datname) DESC;
-- Check active connections
SELECT
count(*) as active_connections,
state,
application_name
FROM pg_stat_activity
WHERE state IS NOT NULL
GROUP BY state, application_name;
-- Check slow queries (enable log_min_duration_statement first)
SELECT
query,
mean_time,
calls,
total_time
FROM pg_stat_statements
ORDER BY mean_time DESC
LIMIT 10;
Common Issues and Troubleshooting
Here are the most frequent problems you’ll encounter and their solutions:
Connection Issues
Problem: “psql: error: connection to server on socket failed”
# Check if PostgreSQL is running
sudo systemctl status postgresql
# Check listening ports
sudo netstat -plunt | grep 5432
# Restart service if needed
sudo systemctl restart postgresql
# Check logs
sudo tail -f /var/log/postgresql/postgresql-15-main.log
Authentication Problems
Problem: “FATAL: password authentication failed”
- Verify pg_hba.conf settings match your connection method
- Ensure you’re using the correct username and password
- Check if the database exists:
sudo -u postgres psql -l
- Reset postgres user password if necessary
Permission Errors
Problem: “ERROR: permission denied for schema public”
-- Connect as superuser and fix permissions
sudo -u postgres psql
\c your_database
GRANT ALL ON SCHEMA public TO your_user;
GRANT ALL PRIVILEGES ON ALL TABLES IN SCHEMA public TO your_user;
GRANT ALL PRIVILEGES ON ALL SEQUENCES IN SCHEMA public TO your_user;
Performance Issues
Problem: Slow query performance
# Enable query logging
sudo nano /etc/postgresql/15/main/postgresql.conf
# Add these lines:
log_min_duration_statement = 1000 # Log queries taking >1 second
log_statement = 'all' # Log all statements (for debugging only)
# Restart PostgreSQL
sudo systemctl restart postgresql
# Analyze specific queries
sudo -u postgres psql your_database
EXPLAIN ANALYZE SELECT * FROM your_table WHERE condition;
Real-World Use Cases and Examples
Let’s look at practical applications where PostgreSQL on Ubuntu 24 excels:
Web Application Backend
PostgreSQL works excellently as a backend for web applications. Here’s a typical setup for a Django application:
# Create application-specific database
sudo -u postgres createdb webapp_production
sudo -u postgres createuser webapp_user
# Set up connection pooling with pgbouncer
sudo apt install pgbouncer
# Configure pgbouncer
sudo nano /etc/pgbouncer/pgbouncer.ini
# Add database configuration
[databases]
webapp_production = host=localhost port=5432 dbname=webapp_production
[pgbouncer]
listen_port = 6432
listen_addr = 127.0.0.1
auth_type = md5
auth_file = /etc/pgbouncer/userlist.txt
pool_mode = transaction
max_client_conn = 100
default_pool_size = 25
Analytics and Reporting
PostgreSQL’s advanced features make it perfect for analytics workloads:
-- Enable additional extensions for analytics
sudo -u postgres psql
CREATE EXTENSION IF NOT EXISTS pg_stat_statements;
CREATE EXTENSION IF NOT EXISTS btree_gin;
CREATE EXTENSION IF NOT EXISTS btree_gist;
-- Example analytics query with window functions
SELECT
date_trunc('day', created_at) as day,
count(*) as daily_signups,
avg(count(*)) OVER (ORDER BY date_trunc('day', created_at)
ROWS 6 PRECEDING) as seven_day_avg
FROM users
GROUP BY date_trunc('day', created_at)
ORDER BY day;
JSON Document Storage
PostgreSQL’s JSONB support makes it competitive with NoSQL databases:
-- Create table with JSONB column
CREATE TABLE products (
id SERIAL PRIMARY KEY,
name VARCHAR(255),
metadata JSONB,
created_at TIMESTAMP DEFAULT NOW()
);
-- Insert JSON data
INSERT INTO products (name, metadata) VALUES
('Widget A', '{"color": "red", "size": "large", "tags": ["electronics", "gadget"]}'),
('Widget B', '{"color": "blue", "size": "small", "tags": ["tool", "utility"]}');
-- Query JSON data
SELECT name, metadata->'color' as color
FROM products
WHERE metadata @> '{"size": "large"}';
-- Create index on JSON field
CREATE INDEX idx_products_metadata ON products USING gin(metadata);
Comparing PostgreSQL with Alternatives
Here’s how PostgreSQL stacks up against other database options on Ubuntu:
Feature | PostgreSQL | MySQL | SQLite | MongoDB |
---|---|---|---|---|
ACID Compliance | Full | Full (InnoDB) | Full | Limited |
JSON Support | Native JSONB | Basic JSON | JSON1 extension | Native |
Full-text Search | Built-in | Basic | FTS5 extension | Text indexes |
Replication | Streaming, logical | Master-slave, group | None built-in | Replica sets |
Max DB Size | Unlimited | 256TB | 281TB | Unlimited |
Concurrent Writers | High | High | 1 | High |
Security Best Practices
Securing PostgreSQL on Ubuntu 24 requires attention to several areas:
Network Security
# Configure firewall
sudo ufw allow from 192.168.1.0/24 to any port 5432
sudo ufw enable
# Use SSL connections
sudo nano /etc/postgresql/15/main/postgresql.conf
# Enable SSL
ssl = on
ssl_cert_file = '/etc/ssl/certs/ssl-cert-snakeoil.pem'
ssl_key_file = '/etc/ssl/private/ssl-cert-snakeoil.key'
Authentication Security
# Use strong passwords and rotate regularly
ALTER USER postgres PASSWORD 'very_secure_password_123!';
# Limit connection attempts
# Add to postgresql.conf
authentication_timeout = 60s
# Use certificate authentication for high-security environments
# In pg_hba.conf:
hostssl all all 192.168.1.0/24 cert
File System Security
# Verify file permissions
ls -la /var/lib/postgresql/15/main/
# Should show postgres:postgres ownership
# Secure backup files
sudo chmod 600 /path/to/backup/files/*
sudo chown postgres:postgres /path/to/backup/files/*
Backup and Recovery
Implement a robust backup strategy from day one:
Logical Backups
# Create backup script
#!/bin/bash
BACKUP_DIR="/var/backups/postgresql"
DATE=$(date +%Y%m%d_%H%M%S)
# Create directory if it doesn't exist
mkdir -p $BACKUP_DIR
# Backup all databases
sudo -u postgres pg_dumpall > $BACKUP_DIR/all_databases_$DATE.sql
# Backup specific database
sudo -u postgres pg_dump myapp_production > $BACKUP_DIR/myapp_production_$DATE.sql
# Compress backups
gzip $BACKUP_DIR/*_$DATE.sql
# Remove backups older than 7 days
find $BACKUP_DIR -name "*.gz" -mtime +7 -delete
Physical Backups
# Set up continuous archiving
# In postgresql.conf:
wal_level = replica
archive_mode = on
archive_command = 'cp %p /var/lib/postgresql/wal_archive/%f'
# Create WAL archive directory
sudo mkdir -p /var/lib/postgresql/wal_archive
sudo chown postgres:postgres /var/lib/postgresql/wal_archive
# Restart PostgreSQL
sudo systemctl restart postgresql
Integration with Development Tools
PostgreSQL integrates well with popular development stacks on Ubuntu:
Python/Django Integration
# Install Python PostgreSQL adapter
pip install psycopg2-binary
# Django settings.py
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.postgresql',
'NAME': 'myapp_production',
'USER': 'myapp_user',
'PASSWORD': 'your_password',
'HOST': 'localhost',
'PORT': '5432',
'OPTIONS': {
'connect_timeout': 60,
}
}
}
Node.js Integration
# Install pg module
npm install pg
# Connection example
const { Pool } = require('pg');
const pool = new Pool({
user: 'myapp_user',
host: 'localhost',
database: 'myapp_production',
password: 'your_password',
port: 5432,
max: 20,
idleTimeoutMillis: 30000,
connectionTimeoutMillis: 2000,
});
// Query example
async function getUsers() {
const client = await pool.connect();
try {
const result = await client.query('SELECT * FROM users');
return result.rows;
} finally {
client.release();
}
}
PostgreSQL on Ubuntu 24 provides a rock-solid foundation for modern applications, offering enterprise-grade features with the flexibility of open-source software. The combination of Ubuntu’s stability, PostgreSQL’s advanced features, and proper configuration creates a database platform capable of handling everything from small web apps to large-scale analytics workloads. Regular maintenance, monitoring, and following security best practices will ensure your PostgreSQL installation remains performant and secure as your application grows.
For more detailed information, check the official PostgreSQL documentation and the Ubuntu PostgreSQL community guide.

This article incorporates information and material from various online sources. We acknowledge and appreciate the work of all original authors, publishers, and websites. While every effort has been made to appropriately credit the source material, any unintentional oversight or omission does not constitute a copyright infringement. All trademarks, logos, and images mentioned are the property of their respective owners. If you believe that any content used in this article infringes upon your copyright, please contact us immediately for review and prompt action.
This article is intended for informational and educational purposes only and does not infringe on the rights of the copyright owners. If any copyrighted material has been used without proper credit or in violation of copyright laws, it is unintentional and we will rectify it promptly upon notification. Please note that the republishing, redistribution, or reproduction of part or all of the contents in any form is prohibited without express written permission from the author and website owner. For permissions or further inquiries, please contact us.