#!/bin/bash
set -e

# Colors for output (work in both local and CI environments)
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
NC='\033[0m' # No Color

# Counters
errors=0
warnings=0

echo "🔍 Bicep Solution Versioning Validation"
echo "========================================"
echo ""

# Check required commands
for cmd in jq find grep sed; do
  if ! command -v $cmd &> /dev/null; then
    echo -e "${RED}❌ ERROR: Required command '$cmd' not found${NC}"
    exit 1
  fi
done

# Get list of changed files
if [ -z "$GITHUB_BASE_REF" ]; then
  echo "ℹ️  Running in local mode - checking all solutions"
  changed_files=$(find . -name "metadata.json" | grep -E "(landing-zones|workload-solutions)" || echo "")
else
  echo "ℹ️  Running in PR mode - checking changed files only"
  echo "   Base branch: $GITHUB_BASE_REF"
  
  # Ensure we have the latest base branch
  git fetch origin "$GITHUB_BASE_REF" 2>/dev/null || echo "   Note: Branch already fetched"
  
  # Get changed files (handle case where grep finds nothing)
  changed_files=$(git diff --name-only "origin/$GITHUB_BASE_REF...HEAD" 2>/dev/null | grep "metadata.json" || echo "")
fi

if [ -z "$changed_files" ]; then
  echo "✅ No metadata.json files changed - skipping validation"
  exit 0
fi

echo "📋 Changed metadata.json files:"
echo "$changed_files"
echo ""

# Process each changed metadata.json
while IFS= read -r metadata_file; do
  if [ -z "$metadata_file" ]; then
    continue
  fi

  echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
  echo "📦 Validating: $metadata_file"
  echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
  
  solution_dir=$(dirname "$metadata_file")
  
  # Extract version from metadata.json
  if [ ! -f "$metadata_file" ]; then
    echo -e "${RED}❌ ERROR: metadata.json not found at $metadata_file${NC}"
    ((errors++))
    continue
  fi
  
  major=$(jq -r '.version.major' < "$metadata_file")
  minor=$(jq -r '.version.minor' < "$metadata_file")
  patch=$(jq -r '.version.patch' < "$metadata_file")
  
  if [ "$major" == "null" ] || [ "$minor" == "null" ] || [ "$patch" == "null" ]; then
    echo -e "${RED}❌ ERROR: Invalid version format in metadata.json${NC}"
    ((errors++))
    continue
  fi
  
  version="${major}.${minor}.${patch}"
  echo "📌 Version from metadata.json: $version"
  
  # Find main bicep file (alz.bicep or main.bicep)
  main_bicep=""
  if [ -f "$solution_dir/alz.bicep" ]; then
    main_bicep="$solution_dir/alz.bicep"
  elif [ -f "$solution_dir/main.bicep" ]; then
    main_bicep="$solution_dir/main.bicep"
  else
    echo -e "${RED}❌ ERROR: No main bicep file found (expected alz.bicep or main.bicep)${NC}"
    ((errors++))
    continue
  fi
  
  echo "📄 Main bicep file: $main_bicep"
  
  # Check 1: Validate CHANGELOG.md contains version section
  changelog="$solution_dir/CHANGELOG.md"
  echo ""
  echo "🔍 Checking CHANGELOG.md..."
  
  if [ ! -f "$changelog" ]; then
    echo -e "${RED}❌ ERROR: CHANGELOG.md not found${NC}"
    ((errors++))
  else
    # Look for version header in CHANGELOG (format: ## X.Y.Z - DD.MM.YYYY)
    if grep -qE "^## ${version} - [0-9]{2}\.[0-9]{2}\.[0-9]{4}" "$changelog"; then
      # Check if this version is the first entry (most recent)
      first_version=$(grep -m 1 -oE "^## [0-9]+\.[0-9]+\.[0-9]+" "$changelog" | sed 's/## //')
      if [ "$first_version" == "$version" ]; then
        echo -e "${GREEN}✅ CHANGELOG.md contains version $version at the top${NC}"
      else
        echo -e "${RED}❌ ERROR: Version $version found in CHANGELOG but not at the top (found: $first_version)${NC}"
        ((errors++))
      fi
    else
      echo -e "${RED}❌ ERROR: CHANGELOG.md missing version section for $version${NC}"
      echo -e "${YELLOW}   Expected format: ## $version - DD.MM.YYYY${NC}"
      ((errors++))
    fi
  fi
  
  # Check 2: Validate main bicep file contains metadata version
  echo ""
  echo "🔍 Checking main bicep file metadata..."
  
  if grep -q "metadata version" "$main_bicep"; then
    bicep_version=$(grep "metadata version" "$main_bicep" | sed -E "s/.*'([0-9]+\.[0-9]+\.[0-9]+)'.*/\1/")
    if [ "$bicep_version" == "$version" ]; then
      echo -e "${GREEN}✅ Main bicep metadata version matches: $version${NC}"
    else
      echo -e "${RED}❌ ERROR: Main bicep metadata version mismatch${NC}"
      echo -e "${YELLOW}   Expected: $version, Found: $bicep_version${NC}"
      ((errors++))
    fi
  else
    echo -e "${RED}❌ ERROR: metadata version not found in main bicep file${NC}"
    ((errors++))
  fi
  
  # Check 3: Check bicepparam files for version references
  echo ""
  echo "🔍 Checking .bicepparam files in configurations/ subfolder..."
  
  # Check if configurations folder exists
  if [ ! -d "$solution_dir/configurations" ]; then
    echo -e "${YELLOW}⚠️  WARNING: configurations/ subfolder not found${NC}"
    echo -e "${YELLOW}   Expected location: $solution_dir/configurations/${NC}"
    ((warnings++))
  else
    bicepparam_files=$(find "$solution_dir/configurations" -name "*.bicepparam" 2>/dev/null || echo "")
    
    if [ -z "$bicepparam_files" ]; then
      echo -e "${YELLOW}⚠️  WARNING: No .bicepparam files found in configurations/${NC}"
      ((warnings++))
    else
      bicepparam_count=$(echo "$bicepparam_files" | wc -l | xargs)
      echo "   Found $bicepparam_count .bicepparam file(s) in configurations/"
      
      # Extract solution path for ACR reference
      # Format: landing-zones/alz-platform or workload-solutions/vwan
      solution_path=$(echo "$solution_dir" | sed 's|^\./||')
      expected_acr_ref="bicep-solution/${solution_path}:v${version}"
      
      outdated_params=()
      
      while IFS= read -r param_file; do
        if [ -z "$param_file" ]; then
          continue
        fi
        
        param_name=$(basename "$param_file")
        
        # Verify file is actually in configurations/ subfolder (extra safety check)
        if [[ "$param_file" != *"/configurations/"* ]]; then
          echo -e "   ${RED}❌ ERROR: $param_name is not in configurations/ subfolder${NC}"
          ((errors++))
          continue
        fi
        
        # Check if file contains ACR reference with correct version
        if grep -q "using 'br:.*bicep-solution/${solution_path}:v" "$param_file"; then
          current_version=$(grep "using 'br:.*bicep-solution/${solution_path}:v" "$param_file" | sed -E "s/.*:v([0-9]+\.[0-9]+\.[0-9]+).*/\1/")
          if [ "$current_version" == "$version" ]; then
            echo -e "   ${GREEN}✅ $param_name references v$version${NC}"
          else
            echo -e "   ${YELLOW}⚠️  $param_name references v$current_version (not v$version)${NC}"
            outdated_params+=("$param_name")
          fi
        else
          echo -e "   ${YELLOW}⚠️  $param_name does not contain expected ACR reference${NC}"
          outdated_params+=("$param_name")
        fi
      done <<< "$bicepparam_files"
      
      if [ ${#outdated_params[@]} -gt 0 ]; then
        echo ""
        echo -e "${YELLOW}⚠️  WARNING: ${#outdated_params[@]} .bicepparam file(s) may need updating:${NC}"
        for param in "${outdated_params[@]}"; do
          echo -e "${YELLOW}   - $param${NC}"
        done
        echo -e "${YELLOW}   Expected ACR reference: br:pbagacr1csn.azurecr.io/${expected_acr_ref}${NC}"
        ((warnings++))
      fi
    fi
  fi
  
  echo ""
done <<< "$changed_files"

# Summary
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
echo "📊 Validation Summary"
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"

if [ $errors -eq 0 ] && [ $warnings -eq 0 ]; then
  echo -e "${GREEN}✅ All validation checks passed!${NC}"
  exit 0
elif [ $errors -eq 0 ]; then
  echo -e "${YELLOW}⚠️  Validation passed with $warnings warning(s)${NC}"
  echo -e "${YELLOW}   Please review .bicepparam files to ensure they reference the latest version${NC}"
  exit 0
else
  echo -e "${RED}❌ Validation failed with $errors error(s) and $warnings warning(s)${NC}"
  echo ""
  echo -e "${RED}Required fixes:${NC}"
  echo -e "${RED}1. Update CHANGELOG.md to include version section at the top${NC}"
  echo -e "${RED}   Format: ## X.Y.Z - DD.MM.YYYY${NC}"
  echo -e "${RED}2. Update main bicep file metadata version to match metadata.json${NC}"
  echo -e "${RED}   Format: metadata version = 'X.Y.Z'${NC}"
  exit 1
fi
