Files
EchoChat/deploy/docker-compose.dev.yml
2026-05-19 18:25:28 +08:00

175 lines
7.1 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.

services:
# ============================================================
# 中间件层Postgres / Redis / MinIO
# ============================================================
postgres:
image: postgres:17
container_name: echochat-postgres
environment:
POSTGRES_DB: ${POSTGRES_DB:-echochat}
POSTGRES_USER: ${POSTGRES_USER:-echochat}
POSTGRES_PASSWORD: ${POSTGRES_PASSWORD:-echochat_dev_2026}
ports:
- "7432:5432"
volumes:
- pgdata:/var/lib/postgresql/data
- ./docker/postgres/init.sql:/docker-entrypoint-initdb.d/init.sql
healthcheck:
test: ["CMD-SHELL", "pg_isready -U ${POSTGRES_USER:-echochat}"]
interval: 5s
timeout: 5s
retries: 5
redis:
image: redis:7
container_name: echochat-redis
ports:
- "7379:6379"
volumes:
- redisdata:/data
- ./docker/redis/redis.conf:/usr/local/etc/redis/redis.conf
command: redis-server /usr/local/etc/redis/redis.conf
healthcheck:
test: ["CMD", "redis-cli", "ping"]
interval: 5s
timeout: 5s
retries: 5
minio:
image: minio/minio:latest
container_name: echochat-minio
command: server /data --console-address ":9201"
ports:
- "9200:9000"
- "9201:9001"
environment:
MINIO_ROOT_USER: ${MINIO_ROOT_USER:-echochat}
MINIO_ROOT_PASSWORD: ${MINIO_ROOT_PASSWORD:-echochat123456}
volumes:
- minio_data:/data
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:9000/minio/health/live"]
interval: 10s
timeout: 5s
retries: 5
restart: unless-stopped
# ============================================================
# 应用层Go backend
# ============================================================
go-service:
build:
context: ../backend/go-service
dockerfile: Dockerfile
container_name: echochat-go-service
environment:
CONFIG_NAME: config.docker
# 透传关键环境变量config.docker.yaml 内部引用(可选覆盖)
ECHOCHAT_JWT_SECRET: ${JWT_SECRET:-1b6d0271700f2db39b2ac7c44811235c55e4e0e61cc47d963f7212b29a39c98f}
ECHOCHAT_MINIO_ACCESS_KEY: ${MINIO_ROOT_USER:-echochat}
ECHOCHAT_MINIO_SECRET_KEY: ${MINIO_ROOT_PASSWORD:-echochat123456}
ECHOCHAT_MEDIA_SERVER_INTERNAL_TOKEN: ${MEDIA_INTERNAL_TOKEN:-internal-token-22xqs}
ECHOCHAT_MINIO_PUBLIC_BASE_URL: ${MINIO_PUBLIC_BASE_URL:-https://yl.z64.cn/echochat}
# media-server 失败回调共享密钥:与 media-server 服务的 INTERNAL_WEBHOOK_SECRET 保持一致
# 未配置时 go-service 会拒绝所有 webhookForbidden录制失败状态将无法及时落 failed
ECHOCHAT_MEETING_INTERNAL_WEBHOOK_SECRET: ${INTERNAL_WEBHOOK_SECRET:-internal-webhook-12xqs}
ECHOCHAT_MEETING_RECORDING_TRANSCODE_ENABLED: ${RECORDING_TRANSCODE_ENABLED:-true}
ECHOCHAT_MEETING_RECORDING_TRANSCODE_FFMPEG_PATH: ${RECORDING_TRANSCODE_FFMPEG_PATH:-ffmpeg}
ECHOCHAT_MEETING_RECORDING_TRANSCODE_TIMEOUT_SECONDS: ${RECORDING_TRANSCODE_TIMEOUT_SECONDS:-600}
ports:
- "${GO_SERVICE_PORT:-8085}:8085"
depends_on:
postgres:
condition: service_healthy
redis:
condition: service_healthy
minio:
condition: service_healthy
media-server:
condition: service_healthy
volumes:
# 与 media-server 使用同一个 host 目录,确保容器部署 go-service 时也能读取录制产物并转码/上传
- ${RECORDING_OUTPUT_DIR:-/home/ykf/jenkins/yuyin/data}:${RECORDING_OUTPUT_DIR:-/home/ykf/jenkins/yuyin/data}
restart: unless-stopped
# ============================================================
# 媒体层mediasoup Node SFU
# ============================================================
media-server:
build:
context: ../media-server
dockerfile: Dockerfile
network_mode: host
container_name: echochat-media-server
environment:
HTTP_HOST: 0.0.0.0
HTTP_PORT: 3300
LOG_LEVEL: info
LOG_PRETTY: "false"
MEDIA_INTERNAL_TOKEN: ${MEDIA_INTERNAL_TOKEN:-internal-token-22xqs}
MEDIASOUP_LISTEN_IP: ${MEDIASOUP_LISTEN_IP:-0.0.0.0}
# 关键:公网部署时必须填服务器公网 IP本机留空
MEDIASOUP_ANNOUNCED_IP: ${MEDIASOUP_ANNOUNCED_IP:-123.6.102.114}
MEDIASOUP_RTC_MIN_PORT: ${MEDIASOUP_RTC_MIN_PORT:-30000}
MEDIASOUP_RTC_MAX_PORT: ${MEDIASOUP_RTC_MAX_PORT:-30199}
MEDIASOUP_WORKER_LOG_LEVEL: warn
MEDIASOUP_MAX_ROUTERS: "200"
# 录制输出目录:与 host 路径保持一致,使 go-servicehost 进程)可直接读取 ffmpeg 写出的 mp4
# 容器内路径 = host 路径ffmpeg 写出的 outputPath 字符串可在两侧通用
RECORDING_OUTPUT_DIR: ${RECORDING_OUTPUT_DIR:-/home/ykf/jenkins/yuyin/data}
# ffmpeg 异常退出回调地址media-server 容器使用 network_mode=host可直连 host 上 go-service 的 8085 端口
# 路径与 backend/go-service/app/meeting/router.go 注册的 /internal/meeting/recordings/failure 一致
RECORDING_FAILURE_WEBHOOK_URL: ${RECORDING_FAILURE_WEBHOOK_URL:-http://127.0.0.1:8085/internal/meeting/recordings/failure}
# webhook 共享密钥:必须与 go-service 端 INTERNAL_WEBHOOK_SECRET 一致,否则 go-service 直接 403
INTERNAL_WEBHOOK_SECRET: ${INTERNAL_WEBHOOK_SECRET:-internal-webhook-12xqs}
volumes:
# 录制文件 host 共享卷media-server 容器内 ffmpeg 写入此目录go-service host 进程直接读
# 没有这条挂载时 go-service 会报 "stat ...: no such file or directory"
- ${RECORDING_OUTPUT_DIR:-/home/ykf/jenkins/yuyin/data}:${RECORDING_OUTPUT_DIR:-/home/ykf/jenkins/yuyin/data}
#ports:
# - "3300:3300"
# mediasoup RTC 流量端口范围UDP + TCP 双栈ICE-TCP fallback 用)
# - "30000-30199:40000-40199/udp"
# - "30000-30199:40000-40199/tcp"
healthcheck:
test: ["CMD", "curl", "-fsS", "http://127.0.0.1:3300/healthz"]
interval: 10s
timeout: 3s
start_period: 15s
retries: 3
restart: unless-stopped
# ============================================================
# TURN 层coturn仅公网部署profiles=public 才启动)
# ------------------------------------------------------------
# 本机 Demo 默认不拉起coturn 在 profiles 里)
# 公网部署docker compose --profile public up -d
# 或使用 scripts/deploy-public.sh 一键启动
# ============================================================
coturn:
image: coturn/coturn:latest
container_name: echochat-coturn
profiles: ["public"]
network_mode: host
command: >
-n
--log-file=stdout
--external-ip=123.6.102.114
--listening-ip=0.0.0.0
--listening-port=${TURN_LISTEN_PORT:-3478}
--tls-listening-port=${TURN_TLS_PORT:-5349}
--min-port=${TURN_MIN_PORT:-49160}
--max-port=${TURN_MAX_PORT:-49200}
--realm=${TURN_REALM:-echochat}
--user=${TURN_USERNAME:-echochat}:${TURN_PASSWORD:-echochat_2026-1s32dswW@#}
--fingerprint
--lt-cred-mech
--no-multicast-peers
--cli=false
restart: unless-stopped
volumes:
pgdata:
redisdata:
minio_data: