RAM Docker Setup
Containerized deployment guide for RAM PostgreSQL clustering with Docker Compose.
Single Node Setup
Basic Docker Compose
version: '3.8'
services:
postgres:
image: postgres:16
environment:
POSTGRES_DB: postgres
POSTGRES_USER: postgres
POSTGRES_PASSWORD: password
ports:
- "5432:5432"
volumes:
- postgres_data:/var/lib/postgresql/data
- ./postgresql.conf:/etc/postgresql/postgresql.conf
- ./init.sql:/docker-entrypoint-initdb.d/init.sql
ramd:
image: pgelephant/ramd:latest
ports:
- "8080:8080"
- "9090:9090"
environment:
RAM_CLUSTER_NAME: "single-cluster"
RAM_NODE_ID: "node1"
RAM_POSTGRES_HOST: "postgres"
RAM_POSTGRES_PORT: "5432"
depends_on:
- postgres
volumes:
postgres_data:
PostgreSQL Configuration
# postgresql.conf
shared_preload_libraries = 'pgraft'
max_connections = 200
listen_addresses = '*'
wal_level = replica
max_wal_senders = 10
hot_standby = on
Initialization Script
-- init.sql
CREATE EXTENSION IF NOT EXISTS pgraft;
SELECT pgraft_init_cluster('single-cluster');
SELECT pgraft_add_member('single-cluster', 'node1', 'host=postgres port=5432');
Multi-Node Cluster
3-Node Cluster Setup
version: '3.8'
services:
postgres1:
image: postgres:16
environment:
POSTGRES_DB: postgres
POSTGRES_USER: postgres
POSTGRES_PASSWORD: password
ports:
- "5432:5432"
volumes:
- postgres1_data:/var/lib/postgresql/data
command: ["postgres", "-c", "shared_preload_libraries=pgraft"]
postgres2:
image: postgres:16
environment:
POSTGRES_DB: postgres
POSTGRES_USER: postgres
POSTGRES_PASSWORD: password
ports:
- "5433:5432"
volumes:
- postgres2_data:/var/lib/postgresql/data
command: ["postgres", "-c", "shared_preload_libraries=pgraft"]
postgres3:
image: postgres:16
environment:
POSTGRES_DB: postgres
POSTGRES_USER: postgres
POSTGRES_PASSWORD: password
ports:
- "5434:5432"
volumes:
- postgres3_data:/var/lib/postgresql/data
command: ["postgres", "-c", "shared_preload_libraries=pgraft"]
volumes:
postgres1_data:
postgres2_data:
postgres3_data:
RAM Daemon Configuration
# ramd.conf for node1
[cluster]
name = "production-cluster"
node_id = "node1"
[postgresql]
host = "postgres1"
port = 5432
user = "postgres"
password = "password"
[raft]
listen_addr = "0.0.0.0:8080"
peers = ["node1:8080", "node2:8080", "node3:8080"]
Production Setup
Production Docker Compose
version: '3.8'
services:
postgres:
image: postgres:16
restart: unless-stopped
environment:
POSTGRES_DB: ${POSTGRES_DB}
POSTGRES_USER: ${POSTGRES_USER}
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}
ports:
- "${POSTGRES_PORT}:5432"
volumes:
- postgres_data:/var/lib/postgresql/data
- ./config/postgresql.conf:/etc/postgresql/postgresql.conf
- ./ssl:/etc/ssl/postgresql
healthcheck:
test: ["CMD-SHELL", "pg_isready -U ${POSTGRES_USER}"]
interval: 30s
timeout: 10s
retries: 3
ramd:
image: pgelephant/ramd:latest
restart: unless-stopped
ports:
- "${RAM_PORT}:8080"
- "${METRICS_PORT}:9090"
environment:
RAM_CLUSTER_NAME: ${CLUSTER_NAME}
RAM_NODE_ID: ${NODE_ID}
RAM_POSTGRES_HOST: postgres
RAM_POSTGRES_PORT: 5432
RAM_LOG_LEVEL: info
depends_on:
postgres:
condition: service_healthy
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:8080/api/v1/health"]
interval: 30s
timeout: 10s
retries: 3
Environment Variables
# .env file
POSTGRES_DB=production
POSTGRES_USER=postgres
POSTGRES_PASSWORD=secure_password
POSTGRES_PORT=5432
CLUSTER_NAME=production-cluster
NODE_ID=node1
RAM_PORT=8080
METRICS_PORT=9090
Monitoring with Docker
Prometheus & Grafana
prometheus:
image: prom/prometheus:latest
ports:
- "9090:9090"
volumes:
- ./config/prometheus.yml:/etc/prometheus/prometheus.yml
grafana:
image: grafana/grafana:latest
ports:
- "3000:3000"
environment:
GF_SECURITY_ADMIN_PASSWORD: admin
volumes:
- grafana_data:/var/lib/grafana
- ./config/grafana/dashboards:/etc/grafana/provisioning/dashboards
- ./config/grafana/datasources:/etc/grafana/provisioning/datasources
Prometheus Configuration
# prometheus.yml
global:
scrape_interval: 15s
scrape_configs:
- job_name: 'ram-cluster'
static_configs:
- targets: ['ramd:9090']
scrape_interval: 5s
- job_name: 'postgresql'
static_configs:
- targets: ['postgres:9187']
Deployment Commands
Basic Deployment
# Start the cluster
docker-compose up -d
# Check status
docker-compose ps
# View logs
docker-compose logs -f ramd
# Stop the cluster
docker-compose down
# Stop and remove volumes
docker-compose down -v
Cluster Management
# Check cluster status
docker exec -it ramd_ramd_1 ramctrl status --cluster production-cluster
# Add node to cluster
docker exec -it ramd_ramd_1 ramctrl nodes add --cluster production-cluster --node node2:8080
# Trigger failover
docker exec -it ramd_ramd_1 ramctrl failover --cluster production-cluster
# View metrics
curl http://localhost:9090/metrics
Health Checks
# Check PostgreSQL health
docker exec -it ramd_postgres_1 pg_isready -U postgres
# Check RAM health
curl http://localhost:8080/api/v1/health
# Check cluster health
docker exec -it ramd_ramd_1 ramctrl health --cluster production-cluster