services: # ========== Milvus 向量库及其依赖(与 MySQL 一样在 Docker 中运行) ========== etcd: image: quay.io/coreos/etcd:v3.5.5 container_name: milvus-etcd environment: - ETCD_AUTO_COMPACTION_MODE=revision - ETCD_AUTO_COMPACTION_RETENTION=1000 - ETCD_QUOTA_BACKEND_BYTES=4294967296 - ETCD_SNAPSHOT_COUNT=50000 volumes: - etcd_data:/etcd command: etcd -advertise-client-urls=http://127.0.0.1:2379 -listen-client-urls http://0.0.0.0:2379 --data-dir /etcd healthcheck: test: ["CMD", "etcdctl", "endpoint", "health"] interval: 30s timeout: 20s retries: 3 networks: - ai-cs-network restart: unless-stopped minio: image: minio/minio:RELEASE.2023-03-20T20-16-18Z container_name: milvus-minio environment: MINIO_ACCESS_KEY: minioadmin MINIO_SECRET_KEY: minioadmin volumes: - minio_data:/minio_data command: minio server /minio_data --console-address ":9001" healthcheck: test: ["CMD", "curl", "-f", "http://localhost:9000/minio/health/live"] interval: 30s timeout: 20s retries: 3 networks: - ai-cs-network restart: unless-stopped milvus-standalone: image: milvusdb/milvus:v2.3.3 container_name: milvus-standalone command: ["milvus", "run", "standalone"] environment: ETCD_ENDPOINTS: etcd:2379 MINIO_ADDRESS: minio:9000 volumes: - milvus_data:/var/lib/milvus ports: - "${MILVUS_PORT:-19530}:19530" depends_on: etcd: condition: service_healthy minio: condition: service_healthy healthcheck: test: ["CMD", "curl", "-f", "http://localhost:9091/healthz"] interval: 30s start_period: 90s timeout: 20s retries: 5 networks: - ai-cs-network restart: unless-stopped # MySQL 数据库 mysql: image: mysql:8.0 container_name: ai-cs-mysql environment: MYSQL_ROOT_PASSWORD: ${MYSQL_ROOT_PASSWORD:-rootpassword} MYSQL_DATABASE: ${MYSQL_DATABASE:-ai_cs} MYSQL_USER: ${MYSQL_USER:-ai_cs_user} MYSQL_PASSWORD: ${MYSQL_PASSWORD:-ai_cs_password} ports: - "${MYSQL_PORT:-3306}:3306" volumes: - mysql_data:/var/lib/mysql command: --character-set-server=utf8mb4 --collation-server=utf8mb4_unicode_ci healthcheck: test: ["CMD", "mysqladmin", "ping", "-h", "localhost", "-u", "root", "-p${MYSQL_ROOT_PASSWORD:-rootpassword}"] interval: 10s timeout: 5s retries: 5 start_period: 30s networks: - ai-cs-network restart: unless-stopped security_opt: - no-new-privileges:true cap_drop: - ALL cap_add: - CHOWN - DAC_OVERRIDE - FOWNER # 后端服务(使用预构建镜像) backend: image: ${BACKEND_IMAGE:-537yaha/ai-cs-backend:latest} container_name: ai-cs-backend environment: DB_HOST: mysql DB_PORT: 3306 DB_USER: ${MYSQL_USER:-ai_cs_user} DB_PASSWORD: ${MYSQL_PASSWORD:-ai_cs_password} DB_NAME: ${MYSQL_DATABASE:-ai_cs} ADMIN_USERNAME: ${ADMIN_USERNAME:-admin} ADMIN_PASSWORD: ${ADMIN_PASSWORD:-admin123} SERVER_HOST: 0.0.0.0 SERVER_PORT: 8080 GIN_MODE: ${GIN_MODE:-release} ENCRYPTION_KEY: ${ENCRYPTION_KEY:-default-key} MILVUS_HOST: milvus-standalone MILVUS_PORT: 19530 ports: - "${BACKEND_PORT:-18080}:8080" volumes: - ./backend/uploads:/app/uploads depends_on: mysql: condition: service_healthy milvus-standalone: condition: service_healthy networks: - ai-cs-network restart: unless-stopped security_opt: - no-new-privileges:true cap_drop: - ALL cap_add: - NET_BIND_SERVICE read_only: true tmpfs: - /tmp - /var/tmp # 前端服务(使用预构建镜像) frontend: image: ${FRONTEND_IMAGE:-537yaha/ai-cs-frontend:latest} container_name: ai-cs-frontend environment: NEXT_PUBLIC_API_BASE_URL: ${NEXT_PUBLIC_API_BASE_URL:-http://localhost:8080} ports: - "${FRONTEND_PORT:-3000}:3000" depends_on: - backend networks: - ai-cs-network restart: unless-stopped security_opt: - no-new-privileges:true cap_drop: - ALL cap_add: - NET_BIND_SERVICE read_only: true # 只读文件系统(防止写入恶意文件) tmpfs: - /tmp - /var/tmp - /app/.next/cache # Next.js 需要缓存目录 volumes: mysql_data: driver: local etcd_data: driver: local minio_data: driver: local milvus_data: driver: local networks: ai-cs-network: driver: bridge