Files
cryptowallet/docker-compose.yml
ZOMBIIIIIII a636bd573a init2121212
2026-05-28 14:01:10 +03:00

162 lines
5.2 KiB
YAML
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# ─────────────────────────────────────────────────────────────────────
# Production docker-compose для CryptoWallet API.
#
# Что в этом stack:
# - api — наш Node.js API (multi-stage build из ./Dockerfile)
# - postgres — хранилище encrypted_mnemonic + audit_log
# - keydb — Redis-compatible для idempotency cache + asset map cache
#
# Что НЕ включено (production не использует — оператор настраивает отдельно):
# - Vault — production использует HashiCorp Vault HA cluster (VAULT_ADDR в .env)
# - JWT signer— production принимает JWT от bitok (внешний сервис, JWT_ISSUER в .env)
# - web-ui — фронтенд деплоится отдельно (Vercel / nginx CDN / etc.)
# - vault-init — production Vault уже инициализирован оператором (см. README pre-deploy)
#
# Security hardening:
# - api запускается под uid 1001, read-only fs, cap_drop ALL, no-new-privileges
# - api порт 3001 биндится на 127.0.0.1 (наружу через nginx + TLS, оператор)
# - postgres + keydb без exposed ports (только internal docker network)
# - .env с secrets — 600 permission, не в репо
#
# Usage:
# cp .env.example .env # заполнить все VAULT_*, JWT_*, REDIS_PASSWORD, CORS_ORIGINS, etc.
# chmod 600 .env
# docker compose up -d --build
# docker compose logs -f api
# ─────────────────────────────────────────────────────────────────────
services:
api:
build:
# Context = parent dir (мы внутри deployserver/, апи берёт apps/api/ из родителя)
context: ..
dockerfile: deployserver/Dockerfile
image: cryptowallet-api:latest
container_name: cw-api
restart: unless-stopped
depends_on:
postgres:
condition: service_healthy
keydb:
condition: service_healthy
env_file:
- .env
environment:
# Override DB/Redis host для docker network (если в .env стоят prod hosts —
# внутри compose их replace на internal service names)
POSTGRES_HOST: postgres
POSTGRES_PORT: "5432"
REDIS_HOST: keydb
REDIS_PORT: "6379"
ports:
# Loopback only — наружу через nginx reverse proxy + TLS
- "127.0.0.1:3001:3001"
read_only: true
tmpfs:
- /tmp
cap_drop:
- ALL
security_opt:
- no-new-privileges:true
deploy:
resources:
limits:
memory: 512M
cpus: "1.0"
pids: 200
reservations:
memory: 256M
healthcheck:
test: ["CMD", "wget", "-qO-", "http://localhost:3001/api/health"]
interval: 30s
timeout: 5s
retries: 3
start_period: 15s
logging:
driver: json-file
options:
max-size: "10m"
max-file: "5"
postgres:
image: postgres:16-alpine
container_name: cw-postgres
restart: unless-stopped
environment:
POSTGRES_USER: ${POSTGRES_USER:?POSTGRES_USER required}
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD:?POSTGRES_PASSWORD required}
POSTGRES_DB: ${POSTGRES_DB:-cryptowallet}
volumes:
- pgdata:/var/lib/postgresql/data
# Bind-mount schema.sql если оператор хочет авто-init на свежей БД.
# На existing — pg ignores 01-schema.sql (initdb запускается только если /var/lib/postgresql/data пуст).
# См. README — лучше прогонять schema руками: psql -f cryptowallet-schema.sql
# - ./cryptowallet-schema.sql:/docker-entrypoint-initdb.d/01-schema.sql:ro
# Internal only — никаких ports на host
expose:
- "5432"
healthcheck:
test: ["CMD-SHELL", "pg_isready -U ${POSTGRES_USER} -d ${POSTGRES_DB:-cryptowallet}"]
interval: 10s
timeout: 3s
retries: 5
logging:
driver: json-file
options:
max-size: "10m"
max-file: "5"
keydb:
image: eqalpha/keydb:alpine
container_name: cw-keydb
restart: unless-stopped
volumes:
- keydb_data:/data
expose:
- "6379"
command:
- keydb-server
- --requirepass
- "${REDIS_PASSWORD:?REDIS_PASSWORD required}"
- --dir
- /data
- --appendonly
- "yes"
- --appendfsync
- everysec
- --save
- "900"
- "1"
- --save
- "300"
- "10"
- --save
- "60"
- "10000"
- --maxmemory
- "256mb"
- --maxmemory-policy
- "allkeys-lru"
healthcheck:
test: ["CMD", "redis-cli", "-a", "${REDIS_PASSWORD}", "ping"]
interval: 10s
timeout: 3s
retries: 5
deploy:
resources:
limits:
memory: 320M
logging:
driver: json-file
options:
max-size: "10m"
max-file: "5"
volumes:
pgdata:
keydb_data:
networks:
default:
driver: bridge