Files
Aether/docker-compose.yml
T
elky 579f2c7cc1 feat(security): harden gateway boundaries and usage policies
Consolidate subscription usage policy enforcement, privacy-safe persistence, and gateway security hardening into one reviewable change.

Includes bounded HTTP and execution envelopes, header and protocol guards, DNS and relay validation, authentication and secret projection hardening, secure backup/install paths, and regression coverage.
2026-09-04 03:45:52 +08:00

124 lines
4.1 KiB
YAML

# Aether 部署配置 - 使用预构建镜像
# 使用方法: docker compose up -d
services:
postgres:
# OCI index digest for the official multi-architecture postgres:15.19 image.
image: postgres:15.19@sha256:5f72c7b5bd616308ccfd2e74d6be16fb06364e5eecbb815fe9dc6ab9761d2111
container_name: aether-postgres
shm_size: ${POSTGRES_SHM_SIZE:-512mb}
environment:
POSTGRES_DB: aether
POSTGRES_USER: postgres
POSTGRES_PASSWORD: ${DB_PASSWORD:?set DB_PASSWORD in .env}
TZ: Asia/Shanghai
volumes:
- postgres_data:/var/lib/postgresql/data
ports:
- "127.0.0.1:${DB_PORT:-5432}:5432"
command: >
postgres
-c idle_in_transaction_session_timeout=30000
-c tcp_keepalives_idle=30
-c tcp_keepalives_interval=10
-c shared_preload_libraries=pg_stat_statements
-c pg_stat_statements.track=all
-c pg_stat_statements.max=10000
-c shared_buffers=${POSTGRES_SHARED_BUFFERS:-1GB}
-c effective_cache_size=${POSTGRES_EFFECTIVE_CACHE_SIZE:-3GB}
-c work_mem=${POSTGRES_WORK_MEM:-16MB}
-c maintenance_work_mem=${POSTGRES_MAINTENANCE_WORK_MEM:-256MB}
healthcheck:
test: [ "CMD-SHELL", "pg_isready -U postgres" ]
interval: 5s
timeout: 5s
retries: 5
logging:
driver: local
options:
max-size: "100m"
max-file: "3"
compress: "true"
restart: unless-stopped
redis:
# OCI index digest for the official multi-architecture redis:7.4.11-alpine image.
image: redis:7.4.11-alpine@sha256:ff02b58f971e7d7d156a1267e283fcbbeee91773b6aa36c49dac28ecfe28eadf
container_name: aether-redis
command: redis-server --dir /tmp --appendonly no --save "" --requirepass ${REDIS_PASSWORD:?set REDIS_PASSWORD in .env} --maxclients ${REDIS_MAXCLIENTS:-10000}
ports:
- "127.0.0.1:${REDIS_PORT:-6379}:6379"
healthcheck:
test: [ "CMD-SHELL", "redis-cli -a \"${REDIS_PASSWORD:?set REDIS_PASSWORD in .env}\" ping | grep -q PONG" ]
interval: 5s
timeout: 3s
retries: 5
restart: unless-stopped
mysql:
# OCI index digest for the official multi-architecture mysql:8.0.46 image.
image: mysql:8.0.46@sha256:7dcddc01f13bab2f15cde676d44d01f61fc9f99fe7785e86196dfc07d358ae2b
container_name: aether-mysql
profiles:
- mysql
environment:
MYSQL_DATABASE: ${MYSQL_DATABASE:-aether}
MYSQL_USER: ${MYSQL_USER:-aether}
MYSQL_PASSWORD: ${MYSQL_PASSWORD:?set MYSQL_PASSWORD in .env}
MYSQL_ROOT_PASSWORD: ${MYSQL_ROOT_PASSWORD:?set MYSQL_ROOT_PASSWORD in .env}
TZ: Asia/Shanghai
volumes:
- mysql_data:/var/lib/mysql
healthcheck:
test:
[
"CMD-SHELL",
"mysqladmin ping -h 127.0.0.1 -u$${MYSQL_USER} -p$${MYSQL_PASSWORD} --silent"
]
interval: 5s
timeout: 5s
retries: 10
restart: unless-stopped
app:
image: ${APP_IMAGE:-ghcr.io/fawney19/aether:latest}
container_name: aether-app
user: "${AETHER_CONTAINER_UID:-65532}:${AETHER_CONTAINER_GID:-65532}"
read_only: true
cap_drop:
- ALL
security_opt:
- no-new-privileges:true
tmpfs:
- /tmp:rw,nosuid,nodev,noexec,mode=1777
env_file:
- .env
environment:
DATABASE_URL: postgresql://postgres:${DB_PASSWORD:?set DB_PASSWORD in .env}@postgres:5432/aether
REDIS_URL: redis://:${REDIS_PASSWORD:?set REDIS_PASSWORD in .env}@redis:6379/0
TZ: Asia/Shanghai
AETHER_BASE_DIR: /opt/aether
AETHER_UPDATE_STRATEGY: docker
AETHER_DOCKER_UPDATE_COMMAND: ${AETHER_DOCKER_UPDATE_COMMAND:-./update.sh}
AETHER_LOG_DESTINATION: stdout
AETHER_LOG_FORMAT: ${AETHER_LOG_FORMAT:-pretty}
APP_PORT: ${APP_PORT:-8084}
AETHER_GATEWAY_AUTO_PREPARE_DATABASE: ${AETHER_GATEWAY_AUTO_PREPARE_DATABASE:-true}
depends_on:
postgres:
condition: service_healthy
redis:
condition: service_healthy
ports:
- "${APP_PORT:-8084}:${APP_PORT:-8084}"
logging:
driver: json-file
options:
max-size: "100m"
max-file: "10"
restart: unless-stopped
volumes:
postgres_data:
mysql_data: