#!/bin/bash

# validate-env-backups.sh - Validate .env file backups
# Author: Shell Repository
# Description: Verify integrity and consistency of .env file backups

set -e

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

# Configuration
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
DOCKER_DIR="$HOME/docker"
BACKUP_DIR="$HOME/.env-backup"
LOG_FILE="$SCRIPT_DIR/logs/env-backup-validation.log"

# Ensure logs directory exists
mkdir -p "$(dirname "$LOG_FILE")"

# Logging function
log() {
    echo "$(date '+%Y-%m-%d %H:%M:%S') - $1" | tee -a "$LOG_FILE"
}

# Display usage information
usage() {
    echo "Usage: $0 [OPTIONS]"
    echo ""
    echo "Validate .env file backups against source files"
    echo ""
    echo "Options:"
    echo "  -h, --help              Show this help message"
    echo "  -v, --verbose           Verbose output"
    echo "  -s, --summary-only      Show only summary"
    echo "  -m, --missing-only      Show only missing files"
    echo "  -d, --diff              Show differences between files"
    echo ""
    echo "Examples:"
    echo "  $0                      # Basic validation"
    echo "  $0 --verbose            # Detailed validation"
    echo "  $0 --missing-only       # Show only missing backups"
    echo "  $0 --diff               # Show file differences"
}

# Validate backups
validate_backups() {
    local verbose="$1"
    local summary_only="$2"
    local missing_only="$3"
    local show_diff="$4"
    
    echo -e "${BLUE}=== .env Backup Validation ===${NC}"
    echo "Source: $DOCKER_DIR"
    echo "Backup: $BACKUP_DIR"
    echo ""
    
    if [ ! -d "$BACKUP_DIR" ]; then
        echo -e "${RED}Error: Backup directory not found at $BACKUP_DIR${NC}"
        echo "Run backup-env-files.sh --init first"
        exit 1
    fi
    
    local total_source=0
    local total_backup=0
    local missing_backup=0
    local outdated_backup=0
    local identical_files=0
    local different_files=0
    local backup_only=0
    
    # Arrays to store file lists
    declare -a missing_files=()
    declare -a outdated_files=()
    declare -a different_files_list=()
    declare -a backup_only_files=()
    
    # Count and validate source files
    echo -e "${YELLOW}Scanning source files...${NC}"
    while IFS= read -r source_file; do
        if [ -n "$source_file" ]; then
            ((total_source++))
            
            # Determine backup path
            local rel_path="${source_file#$DOCKER_DIR/}"
            local backup_file="$BACKUP_DIR/docker-containers/$rel_path"
            
            if [ ! -f "$backup_file" ]; then
                ((missing_backup++))
                missing_files+=("$rel_path")
                [ "$summary_only" != true ] && [ "$missing_only" != true ] && echo -e "${RED}✗ Missing backup: $rel_path${NC}"
            else
                # Compare files
                if cmp -s "$source_file" "$backup_file"; then
                    ((identical_files++))
                    [ "$verbose" = true ] && [ "$summary_only" != true ] && [ "$missing_only" != true ] && echo -e "${GREEN}✓ Identical: $rel_path${NC}"
                else
                    # Check if backup is older
                    if [ "$source_file" -nt "$backup_file" ]; then
                        ((outdated_backup++))
                        outdated_files+=("$rel_path")
                        [ "$summary_only" != true ] && [ "$missing_only" != true ] && echo -e "${YELLOW}⚠ Outdated backup: $rel_path${NC}"
                    else
                        ((different_files++))
                        different_files_list+=("$rel_path")
                        [ "$summary_only" != true ] && [ "$missing_only" != true ] && echo -e "${BLUE}△ Different: $rel_path${NC}"
                    fi
                    
                    # Show diff if requested
                    if [ "$show_diff" = true ] && [ "$summary_only" != true ] && [ "$missing_only" != true ]; then
                        echo -e "${YELLOW}  Differences:${NC}"
                        diff -u "$backup_file" "$source_file" | head -20 || true
                        echo ""
                    fi
                fi
            fi
        fi
    done < <(find "$DOCKER_DIR" -type f \( -name "*.env" -o -name ".env*" -o -name "env.*" \) 2>/dev/null | sort)
    
    # Check for backup-only files
    echo -e "${YELLOW}Scanning backup files...${NC}"
    if [ -d "$BACKUP_DIR/docker-containers" ]; then
        while IFS= read -r backup_file; do
            if [ -n "$backup_file" ]; then
                ((total_backup++))
                
                # Determine source path
                local rel_path="${backup_file#$BACKUP_DIR/docker-containers/}"
                local source_file="$DOCKER_DIR/$rel_path"
                
                if [ ! -f "$source_file" ]; then
                    ((backup_only++))
                    backup_only_files+=("$rel_path")
                    [ "$summary_only" != true ] && [ "$missing_only" != true ] && echo -e "${BLUE}⚡ Backup only: $rel_path${NC}"
                fi
            fi
        done < <(find "$BACKUP_DIR/docker-containers" -type f \( -name "*.env" -o -name ".env*" -o -name "env.*" \) 2>/dev/null | sort)
    fi
    
    # Display missing files if requested
    if [ "$missing_only" = true ] && [ ${#missing_files[@]} -gt 0 ]; then
        echo -e "${RED}=== Missing Backup Files ===${NC}"
        for file in "${missing_files[@]}"; do
            echo -e "${RED}✗ $file${NC}"
        done
        echo ""
    fi
    
    # Summary
    echo -e "${BLUE}=== Validation Summary ===${NC}"
    echo -e "Source files:      ${BLUE}$total_source${NC}"
    echo -e "Backup files:      ${BLUE}$total_backup${NC}"
    echo -e "Identical:         ${GREEN}$identical_files${NC}"
    echo -e "Missing backups:   ${RED}$missing_backup${NC}"
    echo -e "Outdated backups:  ${YELLOW}$outdated_backup${NC}"
    echo -e "Different files:   ${BLUE}$different_files${NC}"
    echo -e "Backup only:       ${BLUE}$backup_only${NC}"
    echo ""
    
    # Recommendations
    if [ $missing_backup -gt 0 ] || [ $outdated_backup -gt 0 ]; then
        echo -e "${YELLOW}=== Recommendations ===${NC}"
        if [ $missing_backup -gt 0 ]; then
            echo -e "${YELLOW}• Run backup-env-files.sh to backup missing files${NC}"
        fi
        if [ $outdated_backup -gt 0 ]; then
            echo -e "${YELLOW}• Run backup-env-files.sh to update outdated backups${NC}"
        fi
        echo ""
    fi
    
    # Log summary
    log "Validation completed - Source: $total_source, Backup: $total_backup, Missing: $missing_backup, Outdated: $outdated_backup"
    
    # Exit with error code if issues found
    if [ $missing_backup -gt 0 ] || [ $outdated_backup -gt 0 ]; then
        exit 1
    fi
}

# Main function
main() {
    local verbose=false
    local summary_only=false
    local missing_only=false
    local show_diff=false
    
    # Parse command line arguments
    while [[ $# -gt 0 ]]; do
        case $1 in
            -h|--help)
                usage
                exit 0
                ;;
            -v|--verbose)
                verbose=true
                shift
                ;;
            -s|--summary-only)
                summary_only=true
                shift
                ;;
            -m|--missing-only)
                missing_only=true
                shift
                ;;
            -d|--diff)
                show_diff=true
                shift
                ;;
            *)
                echo "Unknown option: $1"
                usage
                exit 1
                ;;
        esac
    done
    
    validate_backups "$verbose" "$summary_only" "$missing_only" "$show_diff"
}

# Run main function with all arguments
main "$@"
