#!/usr/bin/env bash
# RecreaHUB — Teste externo da API
# Uso: bash test-api.sh [BASE_URL]
# Ex:  bash test-api.sh https://api.recreahub.com.br
#      bash test-api.sh https://api.recreahub.com.br
set -euo pipefail

# ─────────────────────────────────────────────
#  Variáveis
# ─────────────────────────────────────────────
BASE_URL="${1:-https://api.recreahub.com.br}"
EMAIL="admin@recreahub.com"
SENHA="123456"
TOKEN=""
EVENT_ID=""
PART_ID=""
PASS=0
FAIL=0
SKIP=0

BODY_TMP="/tmp/rh_body"

# ─────────────────────────────────────────────
#  Cores
# ─────────────────────────────────────────────
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[0;33m'
CYAN='\033[0;36m'
BOLD='\033[1m'
RESET='\033[0m'

# ─────────────────────────────────────────────
#  jq opcional (fallback para saída raw)
# ─────────────────────────────────────────────
if command -v jq &>/dev/null; then
    HAS_JQ=1
else
    HAS_JQ=0
fi

json_get() {
    local json="$1"
    local key="$2"
    if [ "$HAS_JQ" -eq 1 ]; then
        echo "$json" | jq -r "$key" 2>/dev/null || echo ""
    else
        # Fallback simples: grep/sed sem jq
        echo "$json" | grep -o "\"${key#.}\":\"[^\"]*\"" | head -1 | sed 's/.*":"\(.*\)"/\1/'
    fi
}

json_is_array() {
    local json="$1"
    if [ "$HAS_JQ" -eq 1 ]; then
        echo "$json" | jq -e 'if type == "array" then true else false end' &>/dev/null
    else
        [[ "$json" == \[* ]]
    fi
}

json_contains() {
    local json="$1"
    local pattern="$2"
    echo "$json" | grep -q "$pattern"
}

# ─────────────────────────────────────────────
#  Helpers de output
# ─────────────────────────────────────────────
ok() {
    echo -e "  ${GREEN}✅  $1${RESET}"
    PASS=$((PASS + 1))
}

fail() {
    echo -e "  ${RED}❌  $1${RESET}"
    FAIL=$((FAIL + 1))
}

skip() {
    echo -e "  ${YELLOW}⏭  $1${RESET}"
    SKIP=$((SKIP + 1))
}

section() {
    echo ""
    echo -e "${CYAN}${BOLD}══ $1 ══${RESET}"
}

check() {
    local name="$1"
    local expected="$2"
    local actual="$3"
    local body="$4"

    if [ "$actual" -eq "$expected" ] 2>/dev/null; then
        ok "$name → HTTP $actual"
    else
        fail "$name → esperado HTTP $expected, obtido HTTP $actual"
        if [ -n "$body" ]; then
            echo -e "       ${RED}Body: $(echo "$body" | head -c 300)${RESET}"
        fi
    fi
}

# ─────────────────────────────────────────────
#  Função de requisição
#  Retorna: STATUS_CODE
#  Body disponível em: $BODY_TMP
# ─────────────────────────────────────────────
do_request() {
    # Uso: do_request METHOD URL [extra_curl_args...]
    local method="$1"
    local url="$2"
    shift 2

    local response
    response=$(curl -s -w "\n%{http_code}" \
        -X "$method" \
        "$url" \
        "$@" \
        -o "$BODY_TMP" 2>/dev/null || true)

    # O status code é a última linha do output de curl -w
    local http_code
    http_code=$(curl -s -o "$BODY_TMP" -w "%{http_code}" \
        -X "$method" \
        "$url" \
        "$@" 2>/dev/null || echo "000")

    echo "$http_code"
}

read_body() {
    cat "$BODY_TMP" 2>/dev/null || echo ""
}

# ─────────────────────────────────────────────
#  Início
# ─────────────────────────────────────────────
echo ""
echo -e "${BOLD}${CYAN}╔══════════════════════════════════════════╗${RESET}"
echo -e "${BOLD}${CYAN}║     RecreaHUB — Teste Externo da API     ║${RESET}"
echo -e "${BOLD}${CYAN}╚══════════════════════════════════════════╝${RESET}"
echo -e "  ${BOLD}Alvo:${RESET} $BASE_URL"
if [ "$HAS_JQ" -eq 1 ]; then
    echo -e "  ${GREEN}jq detectado — saída formatada disponível${RESET}"
else
    echo -e "  ${YELLOW}jq não encontrado — usando parsing simples${RESET}"
fi

# ─────────────────────────────────────────────
#  1. HEALTH CHECK
# ─────────────────────────────────────────────
section "1. Health Check"

STATUS=$(do_request GET "$BASE_URL/health")
BODY=$(read_body)

check "GET /health" 200 "$STATUS" "$BODY"

if json_contains "$BODY" '"status"'; then
    ok "Body contém campo 'status'"
else
    fail "Body não contém campo 'status' — resposta: $(echo "$BODY" | head -c 200)"
fi

# ─────────────────────────────────────────────
#  2. AUTH — LOGIN VÁLIDO
# ─────────────────────────────────────────────
section "2. Autenticação"

STATUS=$(do_request POST "$BASE_URL/api/auth/login" \
    -H "Content-Type: application/json" \
    -d "{\"email\":\"$EMAIL\",\"senha\":\"$SENHA\"}")
BODY=$(read_body)

check "POST /api/auth/login (credenciais válidas)" 200 "$STATUS" "$BODY"

if [ "$STATUS" -eq 200 ] 2>/dev/null; then
    TOKEN=$(json_get "$BODY" ".token")
    if [ -n "$TOKEN" ] && [ "$TOKEN" != "null" ]; then
        ok "Token extraído com sucesso (${#TOKEN} chars)"
    else
        fail "Token não encontrado na resposta — body: $(echo "$BODY" | head -c 300)"
        TOKEN=""
    fi
fi

# ─────────────────────────────────────────────
#  3. AUTH — LOGIN INVÁLIDO
# ─────────────────────────────────────────────
STATUS=$(do_request POST "$BASE_URL/api/auth/login" \
    -H "Content-Type: application/json" \
    -d '{"email":"admin@recreahub.com","senha":"senha_errada_xyz"}')
BODY=$(read_body)

check "POST /api/auth/login (senha incorreta → 401)" 401 "$STATUS" "$BODY"

# ─────────────────────────────────────────────
#  4. ACESSO SEM TOKEN
# ─────────────────────────────────────────────
section "3. Proteção de rotas"

STATUS=$(do_request GET "$BASE_URL/api/eventos")
BODY=$(read_body)

check "GET /api/eventos sem token → 401" 401 "$STATUS" "$BODY"

# ─────────────────────────────────────────────
#  A partir daqui precisamos do token
# ─────────────────────────────────────────────
if [ -z "$TOKEN" ]; then
    echo ""
    echo -e "  ${YELLOW}Token não disponível — pulando testes autenticados${RESET}"
    SKIP=$((SKIP + 12))
else

# ─────────────────────────────────────────────
#  5. LISTAR EVENTOS
# ─────────────────────────────────────────────
section "4. Eventos"

STATUS=$(do_request GET "$BASE_URL/api/eventos" \
    -H "Authorization: Bearer $TOKEN")
BODY=$(read_body)

check "GET /api/eventos (autenticado)" 200 "$STATUS" "$BODY"

if [ "$STATUS" -eq 200 ] 2>/dev/null; then
    if json_is_array "$BODY"; then
        ok "Resposta é um array JSON"
    else
        # Pode vir paginado: { data: [...], total: N }
        if json_contains "$BODY" '"data"'; then
            ok "Resposta contém campo 'data' (lista paginada)"
        else
            fail "Resposta não é array nem objeto paginado — body: $(echo "$BODY" | head -c 200)"
        fi
    fi
fi

# ─────────────────────────────────────────────
#  6. CRIAR EVENTO
# ─────────────────────────────────────────────
EVENTO_PAYLOAD='{
  "titulo": "Evento de Teste Automatizado",
  "descricao": "Criado pelo script test-api.sh",
  "inicio": "2025-12-01T09:00:00.000Z",
  "fim": "2025-12-01T18:00:00.000Z",
  "max_vagas": 50
}'

STATUS=$(do_request POST "$BASE_URL/api/eventos" \
    -H "Authorization: Bearer $TOKEN" \
    -H "Content-Type: application/json" \
    -d "$EVENTO_PAYLOAD")
BODY=$(read_body)

check "POST /api/eventos (criar evento)" 201 "$STATUS" "$BODY"

if [ "$STATUS" -eq 201 ] 2>/dev/null; then
    EVENT_ID=$(json_get "$BODY" ".id")
    if [ -z "$EVENT_ID" ] || [ "$EVENT_ID" = "null" ]; then
        EVENT_ID=$(json_get "$BODY" ".data.id")
    fi
    if [ -n "$EVENT_ID" ] && [ "$EVENT_ID" != "null" ]; then
        ok "Evento criado com ID: $EVENT_ID"
    else
        fail "ID do evento não encontrado na resposta — body: $(echo "$BODY" | head -c 300)"
        EVENT_ID=""
    fi
fi

# ─────────────────────────────────────────────
#  7. OBTER EVENTO POR ID
# ─────────────────────────────────────────────
if [ -n "$EVENT_ID" ]; then
    STATUS=$(do_request GET "$BASE_URL/api/eventos/$EVENT_ID" \
        -H "Authorization: Bearer $TOKEN")
    BODY=$(read_body)
    check "GET /api/eventos/$EVENT_ID" 200 "$STATUS" "$BODY"
else
    skip "GET /api/eventos/:id — EVENT_ID não disponível"
fi

# ─────────────────────────────────────────────
#  8. PUBLICAR EVENTO
# ─────────────────────────────────────────────
if [ -n "$EVENT_ID" ]; then
    STATUS=$(do_request PATCH "$BASE_URL/api/eventos/$EVENT_ID/publicar" \
        -H "Authorization: Bearer $TOKEN" \
        -H "Content-Type: application/json")
    BODY=$(read_body)
    check "PATCH /api/eventos/$EVENT_ID/publicar" 200 "$STATUS" "$BODY"
else
    skip "PATCH /publicar — EVENT_ID não disponível"
fi

# ─────────────────────────────────────────────
#  9. LISTAR PARTICIPANTES
# ─────────────────────────────────────────────
section "5. Participantes"

STATUS=$(do_request GET "$BASE_URL/api/participantes" \
    -H "Authorization: Bearer $TOKEN")
BODY=$(read_body)
check "GET /api/participantes" 200 "$STATUS" "$BODY"

# ─────────────────────────────────────────────
#  10. CRIAR PARTICIPANTE
# ─────────────────────────────────────────────
PART_PAYLOAD='{
  "nome": "Participante Teste Script",
  "email": "teste.script@recreahub.com",
  "telefone": "11999990000"
}'

STATUS=$(do_request POST "$BASE_URL/api/participantes" \
    -H "Authorization: Bearer $TOKEN" \
    -H "Content-Type: application/json" \
    -d "$PART_PAYLOAD")
BODY=$(read_body)
check "POST /api/participantes (criar)" 201 "$STATUS" "$BODY"

if [ "$STATUS" -eq 201 ] 2>/dev/null; then
    PART_ID=$(json_get "$BODY" ".id")
    if [ -z "$PART_ID" ] || [ "$PART_ID" = "null" ]; then
        PART_ID=$(json_get "$BODY" ".data.id")
    fi
    if [ -n "$PART_ID" ] && [ "$PART_ID" != "null" ]; then
        ok "Participante criado com ID: $PART_ID"
    else
        fail "ID do participante não encontrado — body: $(echo "$BODY" | head -c 300)"
        PART_ID=""
    fi
fi

# ─────────────────────────────────────────────
#  11. LISTAR MONITORES
# ─────────────────────────────────────────────
section "6. Monitores"

STATUS=$(do_request GET "$BASE_URL/api/monitores" \
    -H "Authorization: Bearer $TOKEN")
BODY=$(read_body)
check "GET /api/monitores" 200 "$STATUS" "$BODY"

# ─────────────────────────────────────────────
#  12. LISTAR EMPRESAS
# ─────────────────────────────────────────────
section "7. Empresas"

STATUS=$(do_request GET "$BASE_URL/api/empresas" \
    -H "Authorization: Bearer $TOKEN")
BODY=$(read_body)
check "GET /api/empresas" 200 "$STATUS" "$BODY"

# ─────────────────────────────────────────────
#  13. LISTAR INSCRIÇÕES
# ─────────────────────────────────────────────
section "8. Inscrições"

STATUS=$(do_request GET "$BASE_URL/api/inscricoes" \
    -H "Authorization: Bearer $TOKEN")
BODY=$(read_body)
check "GET /api/inscricoes" 200 "$STATUS" "$BODY"

# ─────────────────────────────────────────────
#  14. FREQUÊNCIA — LISTAR
# ─────────────────────────────────────────────
section "9. Frequência"

STATUS=$(do_request GET "$BASE_URL/api/frequencia" \
    -H "Authorization: Bearer $TOKEN")
BODY=$(read_body)
check "GET /api/frequencia" 200 "$STATUS" "$BODY"

# ─────────────────────────────────────────────
#  15. SOFT-DELETE EVENTO
# ─────────────────────────────────────────────
section "10. Limpeza (soft-delete)"

if [ -n "$EVENT_ID" ]; then
    STATUS=$(do_request DELETE "$BASE_URL/api/eventos/$EVENT_ID" \
        -H "Authorization: Bearer $TOKEN")
    BODY=$(read_body)
    check "DELETE /api/eventos/$EVENT_ID → 204" 204 "$STATUS" "$BODY"
else
    skip "DELETE /api/eventos/:id — EVENT_ID não disponível"
fi

# ─────────────────────────────────────────────
#  16. VERIFICAR SOFT-DELETE (deve retornar 404)
# ─────────────────────────────────────────────
if [ -n "$EVENT_ID" ]; then
    STATUS=$(do_request GET "$BASE_URL/api/eventos/$EVENT_ID" \
        -H "Authorization: Bearer $TOKEN")
    BODY=$(read_body)
    check "GET /api/eventos/$EVENT_ID após delete → 404 (soft-delete OK)" 404 "$STATUS" "$BODY"
else
    skip "GET após DELETE — EVENT_ID não disponível"
fi

fi  # fim do bloco "if token disponível"

# ─────────────────────────────────────────────
#  SUMÁRIO FINAL
# ─────────────────────────────────────────────
TOTAL=$((PASS + FAIL + SKIP))
echo ""
echo -e "${BOLD}${CYAN}══════════════════════════════════════════════════${RESET}"
printf "  ${BOLD}Resultados:${RESET}  ${GREEN}✅ %d OK${RESET}   ${RED}❌ %d FALHAS${RESET}   ${YELLOW}⏭ %d PULADOS${RESET}\n" \
    "$PASS" "$FAIL" "$SKIP"
echo -e "  ${BOLD}API:${RESET} $BASE_URL"
echo -e "  ${BOLD}Total de verificações:${RESET} $TOTAL"
echo -e "${BOLD}${CYAN}══════════════════════════════════════════════════${RESET}"
echo ""

if [ "$FAIL" -gt 0 ]; then
    echo -e "${RED}${BOLD}Alguns testes falharam. Verifique os logs acima.${RESET}"
    echo ""
    exit 1
else
    echo -e "${GREEN}${BOLD}Todos os testes passaram!${RESET}"
    echo ""
    exit 0
fi
