#!/bin/bash
# Deployment script for {{ project_name }}
# Generated by Prism
#
# Usage: ./deploy.sh [IMAGE_TAG]
#   IMAGE_TAG: Docker image tag to deploy (default: latest)

set -euo pipefail

# Configuration
PROJECT_NAME="{{ project_name }}"
APP_DIR="/opt/${PROJECT_NAME}"
COMPOSE_FILE="docker-compose.prod.yml"
IMAGE_TAG="${1:-latest}"

# Colors for output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
NC='\033[0m' # No Color

log() {
    echo -e "${GREEN}[$(date +'%Y-%m-%d %H:%M:%S')]${NC} $1"
}

warn() {
    echo -e "${YELLOW}[$(date +'%Y-%m-%d %H:%M:%S')] WARNING:${NC} $1"
}

error() {
    echo -e "${RED}[$(date +'%Y-%m-%d %H:%M:%S')] ERROR:${NC} $1"
    exit 1
}

# Check if running as deploy user
if [ "$(whoami)" != "deploy" ]; then
    warn "Not running as deploy user. Some operations may fail."
fi

cd "${APP_DIR}" || error "Failed to change to ${APP_DIR}"

log "Starting deployment of ${PROJECT_NAME} (tag: ${IMAGE_TAG})"

# Backup current deployment info
if [ -f .env ]; then
    cp .env .env.backup.$(date +%Y%m%d_%H%M%S)
    log "Backed up current .env file"
fi

# Update IMAGE_TAG in .env
if [ -f .env ]; then
    sed -i "s/^IMAGE_TAG=.*/IMAGE_TAG=${IMAGE_TAG}/" .env
    log "Updated IMAGE_TAG to ${IMAGE_TAG}"
else
    error ".env file not found. Please configure environment first."
fi

# Pull new images
log "Pulling Docker images..."
docker compose -f "${COMPOSE_FILE}" pull || error "Failed to pull images"

# Stop old containers gracefully
log "Stopping current containers..."
docker compose -f "${COMPOSE_FILE}" down --timeout 30 || warn "Some containers may not have stopped cleanly"

# Start new containers
log "Starting new containers..."
docker compose -f "${COMPOSE_FILE}" up -d --remove-orphans || error "Failed to start containers"

# Wait for health check
log "Waiting for application to be healthy..."
sleep 10

# Check health
HEALTH_CHECK_URL="http://localhost/health"
MAX_RETRIES=30
RETRY_COUNT=0

while [ $RETRY_COUNT -lt $MAX_RETRIES ]; do
    if curl -sf "${HEALTH_CHECK_URL}" > /dev/null 2>&1; then
        log "Health check passed!"
        break
    fi
    RETRY_COUNT=$((RETRY_COUNT + 1))
    log "Waiting for application... (attempt ${RETRY_COUNT}/${MAX_RETRIES})"
    sleep 2
done

if [ $RETRY_COUNT -eq $MAX_RETRIES ]; then
    error "Health check failed after ${MAX_RETRIES} attempts"
fi

# Cleanup old images
log "Cleaning up old Docker images..."
docker image prune -f || warn "Failed to prune images"

log "Deployment completed successfully!"
log "Application is running at: http://$(hostname -I | awk '{print $1}')"
