#!/usr/bin/env bash
#
# tools/up-dev.sh — ciclo de vida do ambiente de desenvolvimento.
#
# Premissa (mesma do deploy): **backup → build limpo → down/up → otimizar**.
#   - backup: `tools/db-backup.sh` (pulado se o banco ainda não existe);
#   - build limpo: `docker compose build --no-cache` só quando `NO_CACHE=1` (dev);
#   - down/up: `down` mantém volumes, `up` recria os containers com a imagem nova;
#   - otimizar: `optimize:clear` → `core:cache-modules` → `optimize`, abortando na 1ª falha.
#
# Validação **não** é responsabilidade do `up` (são alvos distintos): rode `make check`
# (ou `make check E2E=1`) separadamente, quando fizer sentido.
#
# Uso: tools/up-dev.sh [--dry-run]
set -Eeuo pipefail

ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
cd "$ROOT"

DRY_RUN=0
for arg in "$@"; do
    case "$arg" in
        --dry-run) DRY_RUN=1 ;;
        -h | --help) sed -n '2,14p' "$0" | sed 's/^# \{0,1\}//'; exit 0 ;;
        *) echo "up-dev: flag desconhecida: $arg" >&2; exit 2 ;;
    esac
done

PROJECT="$(bash "$ROOT/tools/project-name.sh")"
# shellcheck source=tools/runtime.sh
. "$ROOT/tools/runtime.sh"
command -v "${ENGINE[0]}" >/dev/null 2>&1 || { echo "up-dev: ${ENGINE[0]} indisponível." >&2; exit 1; }
COMPOSE=("${ENGINE[@]}" compose -p "$PROJECT" --env-file .env "${COMPOSE_FILES[@]}")

step() { printf '\n== %s ==\n' "$*"; }

run() {
    printf '+'
    printf ' %q' "$@"
    printf '\n'
    [ "$DRY_RUN" = 1 ] && return 0
    "$@"
}

# 0) Ambiente determinístico: `.env` presente, porta da cópia e `APP_URL` coerentes (e, se
#    `--instance` foi usado, a stack já é a isolada).
step "0/5 ambiente (.env, porta, APP_URL)"
run bash "$ROOT/tools/dev-env.sh"

# 1) Stack atual precisa estar de pé para o backup.
step "1/5 subir o stack atual"
run "${COMPOSE[@]}" up -d --remove-orphans

# 2) Backup antes de qualquer mudança (primeiro run é pulado pelo próprio script).
step "2/5 backup do banco"
run bash "$ROOT/tools/db-backup.sh"

# 3) Build limpo só sob demanda em dev (prod sempre usa --no-cache).
step "3/5 build da imagem"
if [ "${NO_CACHE:-0}" = "1" ]; then
    run "${COMPOSE[@]}" build --no-cache php-fpm queue
else
    run "${COMPOSE[@]}" build php-fpm queue
fi

# 4) Troca dos containers com a imagem recém-construída.
step "4/5 down/up"
run "${COMPOSE[@]}" down --remove-orphans
run "${COMPOSE[@]}" up -d --remove-orphans

# 5) Otimização completa e sequencial (fail-fast).
step "5/5 otimizar"
run "${COMPOSE[@]}" exec -T php-fpm sh -c \
    'php artisan optimize:clear && php artisan core:cache-modules && php artisan optimize'

printf '\nup-dev: OK (%s)\n' "$([ "$DRY_RUN" = 1 ] && echo 'dry-run' || echo 'ambiente atualizado')"
