Skip to content

On-Premise Deployment

Docker Compose Deployment on Rocky Linux / RHEL

Document Version: 1.0.0
Last Updated: 2026-02-10
License Tier: All


1. Architecture Overview

graph LR
    FW["🛡️ Firewall"] --> Nginx["🌐 Nginx<br/>(TLS Termination)<br/>:443"]
    Nginx --> BE["⚙️ API Server<br/>:8080"]
    Nginx --> OCSP["📜 OCSP Responder<br/>:8081"]
    Nginx --> FE["🖥️ Web Interface<br/>:5173"]
    BE --> PG["🗄️ PostgreSQL<br/>:5432"]
    BE --> Redis["⚡ Redis<br/>:6379"]

    classDef network fill:#F5F5F5,stroke:#9E9E9E,stroke-width:2px,color:#424242
    classDef app fill:#EBF5FB,stroke:#2196F3,stroke-width:2px,color:#1565C0
    classDef data fill:#E8F5E9,stroke:#4CAF50,stroke-width:2px,color:#2E7D32

    class FW,Nginx network
    class BE,OCSP,FE app
    class PG,Redis data

2. System Requirements

Component Minimum Recommended
OS Rocky Linux 9.x / RHEL 9.x Rocky Linux 9.4+
CPU 2 cores 4+ cores
RAM 4 GB 8+ GB
Storage 50 GB SSD 100+ GB SSD
Docker Engine 24+ Latest stable
Docker Compose 2.20+ Latest stable

3. Installation

Step 1: Install Docker

# Rocky Linux 9 / RHEL 9
sudo dnf config-manager --add-repo \
  https://download.docker.com/linux/rhel/docker-ce.repo

sudo dnf install -y docker-ce docker-ce-cli containerd.io docker-compose-plugin

sudo systemctl enable --now docker
sudo usermod -aG docker $USER

Step 2: Prepare Directory Structure

sudo mkdir -p /opt/mazevault/{data,config,certs,backups}
cd /opt/mazevault

Step 3: Load Container Images

For air-gapped environments, load the pre-built images from the offline package:

# Extract offline package
tar xzf mazevault-1.8.0-offline.tar.gz

# Load Docker images
docker load < images/mazevault-backend.tar
docker load < images/mazevault-frontend.tar
docker load < images/mazevault-ocsp.tar
docker load < images/postgres-15-alpine.tar
docker load < images/redis-7-alpine.tar
docker load < images/nginx-alpine.tar

For connected environments, images are pulled automatically from the container registry.

Step 4: Configure Environment

Create the environment file /opt/mazevault/.env:

# Database
POSTGRES_HOST=client-postgres
POSTGRES_PORT=5432
POSTGRES_USER=mazevault
POSTGRES_PASSWORD=<strong-password>
POSTGRES_DB=mazevault

# Redis
REDIS_HOST=client-redis
REDIS_PORT=6379
REDIS_PASSWORD=<strong-password>

# Application
APP_DOMAIN=vault.example.com
APP_PORT=8080
APP_ENV=production
TLS_ENABLED=true

# License
LICENSE_KEY=<your-license-key>

# Encryption (generate with: openssl rand -hex 32)
MASTER_KEY=<64-char-hex-string>

Master Key

The MASTER_KEY is the root encryption key for all secrets. Back it up securely — loss of this key means loss of access to all encrypted data. Store a copy in a physically separate, secure location.

Step 5: Configure TLS Certificates

Place your TLS certificates in /opt/mazevault/certs/:

# Required files:
/opt/mazevault/certs/server.crt    # Server certificate (PEM)
/opt/mazevault/certs/server.key    # Private key (PEM)
/opt/mazevault/certs/ca.crt        # CA chain (PEM)

See TLS Configuration for detailed certificate setup.

Step 6: Deploy

cd /opt/mazevault
docker compose up -d

Step 7: Verify Deployment

# Check all containers are running
docker compose ps

# Check API health
curl -sk https://localhost/api/v1/health | jq .

# Check logs
docker compose logs backend --tail=50

4. Nginx Configuration

The default Nginx configuration provides TLS termination and reverse proxy:

server {
    listen 443 ssl http2;
    server_name vault.example.com;

    ssl_certificate     /etc/nginx/certs/server.crt;
    ssl_certificate_key /etc/nginx/certs/server.key;
    ssl_protocols       TLSv1.2 TLSv1.3;
    ssl_ciphers         ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384;
    ssl_prefer_server_ciphers off;

    # Security headers
    add_header Strict-Transport-Security "max-age=31536000; includeSubDomains" always;
    add_header X-Content-Type-Options "nosniff" always;
    add_header X-Frame-Options "SAMEORIGIN" always;

    # API Server
    location /api/ {
        proxy_pass http://backend:8080;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
    }

    # OCSP Responder
    location /ocsp {
        proxy_pass http://ocsp-responder:8081;
    }

    # Web Interface
    location / {
        proxy_pass http://frontend:5173;
    }
}

server {
    listen 80;
    server_name vault.example.com;
    return 301 https://$server_name$request_uri;
}

5. Firewall Configuration

# Rocky Linux / RHEL with firewalld
sudo firewall-cmd --permanent --add-service=https
sudo firewall-cmd --permanent --add-service=http
sudo firewall-cmd --reload

# Verify
sudo firewall-cmd --list-all

Warning

Do not expose ports 5432 (PostgreSQL), 6379 (Redis), or 8080 (API internal) to the network. These must only be accessible within the Docker network.

sudo systemctl enable mazevault

Automatic systemd integration (since vX.X)

The install script (sudo ./install-mazevault.sh or sudo ./install-mazevault-offline.sh) now automatically creates and enables the systemd service for MazeVault. You do not need to perform the manual steps below unless you are customizing the service or using a non-standard deployment.

Note: The install script must be run as root (sudo).

To manually create or customize the systemd service:

sudo cat > /etc/systemd/system/mazevault.service << 'EOF'
[Unit]
Description=MazeVault Enterprise Secrets Manager
Requires=docker.service
After=docker.service

[Service]
Type=oneshot
RemainAfterExit=yes
WorkingDirectory=/opt/mazevault
ExecStart=/usr/bin/docker compose up -d
ExecStop=/usr/bin/docker compose down
TimeoutStartSec=120

[Install]
WantedBy=multi-user.target
EOF

sudo systemctl enable mazevault

7. Offline Deployment Package

For air-gapped environments, the offline deployment package includes:

Component Format Size (approx.)
Backend image .tar ~150 MB
Frontend image .tar ~50 MB
OCSP image .tar ~30 MB
PostgreSQL image .tar ~80 MB
Redis image .tar ~30 MB
Nginx image .tar ~20 MB
Docker Compose config .yml <1 KB
Documentation .tar (static HTML) ~10 MB
Total ~370 MB

Contact your MazeVault account manager to obtain the offline deployment package.