#!/bin/bash set -euo pipefail cd "$(dirname "$0")" command -v docker >/dev/null 2>&1 || { echo "[ERROR] Docker not installed"; exit 1; } docker compose version >/dev/null 2>&1 || { echo "[ERROR] docker compose plugin missing"; exit 1; } # .env handling if [ ! -f .env ]; then if [ -f .env.example ]; then cp .env.example .env chmod 600 .env echo "[INFO] .env создан из примера (mode 600) — заполни Vault креды и запусти снова" exit 1 else echo "[ERROR] нет ни .env, ни .env.example" exit 1 fi fi # Защита: .env должен быть 600 (только владелец) — содержит Vault role/secret IDs. ENV_MODE=$(stat -c %a .env 2>/dev/null || stat -f %A .env 2>/dev/null) if [ "$ENV_MODE" != "600" ]; then echo "[WARN] .env mode is $ENV_MODE, enforcing 600" chmod 600 .env fi # Logs dir для audit-log mount — container's app user is uid 1001 mkdir -p logs chmod 750 logs # Если есть права — попытаться выставить нужный owner (требует sudo на host) if [ "$(stat -c %u logs 2>/dev/null)" != "1001" ]; then chown 1001:1001 logs 2>/dev/null || echo "[INFO] chown logs 1001:1001 пропущен (нет прав; audit может не писаться)" fi echo "[INFO] Building and starting containers..." docker compose up -d --build echo "[INFO] Waiting for API to become healthy..." for i in $(seq 1 30); do if curl -sf http://127.0.0.1:3001/api/health >/dev/null 2>&1; then echo "[OK] API is healthy" break fi if [ "$i" = "30" ]; then echo "[ERROR] API not healthy after 60s. Запусти 'docker compose logs --tail=50 api' для диагностики." exit 1 fi sleep 2 done echo "" echo "API: http://127.0.0.1:3001" echo " Порт 3001 слушает на всех интерфейсах — для prod ограничьте фаерволом до IP reverse proxy." echo "Health: http://127.0.0.1:3001/api/health" echo "Docs: http://127.0.0.1:3001/api/docs" echo "Logs: docker compose logs -f api" echo "Audit: tail -f logs/audit.log"