# ============================================================ # Production / docker-compose.prod.yml # ----------------------------------------------------------- # 1. Copy: cp .env.example .env # 2. Fill every value below (never commit .env — it is gitignored). # 3. Prefer strong random secrets: # openssl rand -base64 32 # # Before deploy: ./scripts/verify-prod-env.sh # Full deploy: ./scripts/deploy-prod.sh # Stack map (FE→BE→DB→MinIO): docs/deploy-stack-overview.md # Postgres / volume quirks: docs/deploy-production-docker.md # # If .env was ever committed to git, rotate ALL secrets below. # ============================================================ # Public hostname or IP that browsers use to reach this machine. PUBLIC_HOST=your-public-hostname-or-ip.example.com FE_PORT=8081 # Optional: admin/council SPA port. Bound to 127.0.0.1 only in docker-compose.prod.yml # (reach it via SSH tunnel or an authenticated reverse-proxy vhost). Defaults to 8082. # FE_ADMIN_PORT=8082 # Optional: principal-investigator SPA port (research proposals + project cockpit). Defaults to 8083. # FE_INV_PORT=8083 # Optional: publisher SPA port (research-result publication). Defaults to 8084. # FE_PUB_PORT=8084 # Optional: extra CORS Allowed-Origins for be0 (comma-separated, no spaces). Production compose sets # CORS_ORIGINS to http://${PUBLIC_HOST}:${FE_PORT} plus these extras automatically. # CORS_ORIGINS_EXTRA=https://app.example.com,http://internal:8081 MINIO_API_PORT=19000 MINIO_CONSOLE_PORT=19001 MINIO_ROOT_USER=minio_root_change_me MINIO_ROOT_PASSWORD=replace_with_long_random_secret # --- HTTPS for MinIO presigned URLs (required if the SPA is https://…) ------------ # Mixed content blocks http://PUBLIC_HOST:19000 embedded from an HTTPS UI. Options: # A) Proxied viewer only (already in-app) — no change needed for preview. # B) HTTPS for direct MinIO links (iframe / “open presigned URL”) — put TLS in front # of the S3 API port and align these with that public URL. See docs/minio-behind-https.md . # Example subdomain (recommended): # S3_PUBLIC_ENDPOINT_URL=https://minio-api.your-domain.com # MINIO_SERVER_URL=https://minio-api.your-domain.com # Optionally point the console at HTTPS too: # MINIO_BROWSER_REDIRECT_URL=https://minio-console.your-domain.com # If omitted, Compose keeps using http://${PUBLIC_HOST}:${MINIO_API_PORT} for both. # Username + password are fixed the first time the Postgres volume is created (see comment below). # Identifier only (letters, digits, underscore) — avoids URL / healthcheck pitfalls. POSTGRES_USER=postgres_app_user POSTGRES_PASSWORD=replace_with_long_random_secret # Optional: only for scripts/sync-postgres-app-password.sh when the app role is not superuser # or you must connect as a different DB superuser (e.g. postgres) to run ALTER ROLE. # POSTGRES_SUPERUSER=postgres # Database name created on first init (normally keep "initiatives"). POSTGRES_DB=initiatives # --- Auth (required for production) ------------------------------------------------ # Generate: openssl rand -base64 48 JWT_SECRET=replace_with_openssl_rand_base64_48 # MinIO browser CORS — your public SPA origin (scheme + host, no trailing slash). MINIO_API_CORS_ALLOW_ORIGIN=https://www.example.com # Postgres + password caveat: # Changing POSTGRES_USER/POSTGRES_PASSWORD here later does NOT change an existing Docker volume — # Postgres only reads them when /var/lib/postgresql/data is empty. If login fails after editing .env: # • Use the same password as first boot (e.g. dev stack used initiative / initiative_secret), or # • With docker-compose.prod.yml stopped: docker volume rm …_initiative_pg_data then up again (drops DB), or # • Run ./scripts/sync-postgres-app-password.sh to set the DB role password from this file (no wipe), or # --------------------------------------------------------------------------- # SMTP — outbound mail from be0 (registration OTP, password reset) # --------------------------------------------------------------------------- # docker-compose / docker-compose.prod passes these into the be0 container. # Compose substitutes ${SMTP_*} from THIS file (repo-root `.env`), not from be0/.env alone. # Omit AUTH_MAIL_LOG_ONLY (or set 0/false) when using real SMTP. # # SMTP_HOST=smtp.your-mail-provider.com # SMTP_PORT=587 # SMTP_USER=your_smtp_username # SMTP_PASSWORD=your_smtp_password # AUTH_MAIL_FROM=noreply@your-institution.edu.vn # SMTP_USE_TLS=1 # # Public URL of the web app (password-reset / verify links in email). Production example: # AUTH_PUBLIC_WEB_ORIGIN=https://your-app.example.com # # Dev-only: print OTP in be0 logs instead of sending mail # AUTH_MAIL_LOG_ONLY=1 # # Microsoft 365 / Outlook (smtp.office365.com), log shows 535 Authentication unsuccessful: # • SMTP_USER = full mailbox address; SMTP_PASSWORD = correct app password if MFA is enabled # (not your normal web-login password unless basic auth is allowed — many tenants require app passwords). # • Exchange admin: enable "Authenticated SMTP" for the mailbox; security defaults may block SMTP AUTH. # • After editing .env: docker compose up -d be0 (so the container reloads env).