#!/usr/bin/env bash

# Pre-deployment wallet balance checker
# Ensures wallet has necessary tokens and amounts before deployment

set -e

SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
source "$SCRIPT_DIR/../lib/init.sh"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/../.." && pwd)"
if [[ -f "$SCRIPT_DIR/../lib/deployment/dotenv.sh" ]]; then
  # shellcheck disable=SC1090
  source "$SCRIPT_DIR/../lib/deployment/dotenv.sh"
  load_deployment_env --repo-root "${PROJECT_ROOT:-$REPO_ROOT}"
elif [[ -n "${PROJECT_ROOT:-}" && -f "$PROJECT_ROOT/.env" ]]; then
  set -a
  # shellcheck disable=SC1090
  source "$PROJECT_ROOT/.env"
  set +a
elif [[ -n "${REPO_ROOT:-}" && -f "$REPO_ROOT/.env" ]]; then
  set -a
  # shellcheck disable=SC1090
  source "$REPO_ROOT/.env"
  set +a
fi

log_info "=== Pre-Deployment Wallet Balance Check ==="

: "${MAINNET_ETH_REQUIRED:=25000000000000000}"  # 0.025 ETH
: "${MAINNET_LINK_REQUIRED:=0}"
: "${CHAIN138_ETH_REQUIRED:=0}"
: "${CHAIN138_LINK_REQUIRED:=0}"

# Required amounts (in wei, then converted)

# Check if cast is available
if ! command -v cast &> /dev/null; then
    log_error "Error: cast (Foundry) not found. Please install Foundry."
    exit 1
fi

# Get wallet address from private key
if ! require_private_key_env; then
    exit 1
fi

WALLET_ADDRESS="$(derive_deployer_address || true)"
if [ -z "$WALLET_ADDRESS" ]; then
    log_error "ERROR: Could not derive DEPLOYER_ADDRESS from PRIVATE_KEY."
    exit 1
fi

log_info "Wallet Address: $WALLET_ADDRESS"

# Function to check balance
check_balance() {
    local rpc_url=$1
    local address=$2
    local token_address=$3
    local token_name=$4
    local required=$5
    local chain_name=$6
    
    if [ -z "$token_address" ] || [ "$token_address" == "0x0000000000000000000000000000000000000000" ]; then
        # Check native ETH balance
        balance=$(cast balance "$address" --rpc-url "$rpc_url" 2>/dev/null || echo "0")
    else
        # Check ERC20 token balance
        balance=$(cast call "$token_address" "balanceOf(address)(uint256)" "$address" --rpc-url "$rpc_url" 2>/dev/null || echo "0")
    fi

    if [[ "$balance" =~ ^0x ]]; then
        balance=$(cast --to-dec "$balance" 2>/dev/null || echo "0")
    fi
    balance="$(printf '%s' "$balance" | tr -d '\r\n[:space:]')"
    if [[ -z "$balance" || ! "$balance" =~ ^[0-9]+$ ]]; then
        balance="0"
    fi

    if [ "$balance" == "0" ] || [ -z "$balance" ]; then
        balance="0"
    fi
    
    # Convert to human readable
    if [ -z "$token_address" ] || [ "$token_address" == "0x0000000000000000000000000000000000000000" ]; then
        balance_eth=$(cast --to-unit "$balance" ether 2>/dev/null || echo "0")
        required_eth=$(cast --to-unit "$required" ether 2>/dev/null || echo "0")
        
        log_info "$chain_name - $token_name:"
        echo "  Balance: $balance_eth ETH"
        echo "  Required: $required_eth ETH"
        
        if [ "$(echo "$balance >= $required" | bc 2>/dev/null || echo "0")" == "1" ]; then
            echo -e "  Status: ${GREEN}✅ Sufficient${NC}"
            return 0
        else
            echo -e "  Status: ${RED}❌ Insufficient${NC}"
            deficit=$(echo "$required - $balance" | bc 2>/dev/null || echo "$required")
            deficit_eth=$(cast --to-unit "$deficit" ether 2>/dev/null || echo "0")
            echo -e "  ${YELLOW}Need: $deficit_eth ETH more${NC}"
            return 1
        fi
    else
        balance_eth=$(cast --to-unit "$balance" ether 2>/dev/null || echo "0")
        required_eth=$(cast --to-unit "$required" ether 2>/dev/null || echo "0")
        
        log_info "$chain_name - $token_name:"
        echo "  Balance: $balance_eth tokens"
        echo "  Required: $required_eth tokens"
        
        if [ "$required" == "0" ]; then
            echo -e "  Status: ${GREEN}✅ Not required for deployment${NC}"
            return 0
        elif [ "$(echo "$balance >= $required" | bc 2>/dev/null || echo "0")" == "1" ]; then
            echo -e "  Status: ${GREEN}✅ Sufficient${NC}"
            return 0
        else
            echo -e "  Status: ${RED}❌ Insufficient${NC}"
            return 1
        fi
    fi
}

# Check Mainnet balances
log_info "=== Ethereum Mainnet Balances ==="

MAINNET_RPC_URL="${MAINNET_RPC_URL:-${ETHEREUM_MAINNET_RPC:-}}"
if [ -z "$MAINNET_RPC_URL" ]; then
    MAINNET_RPC_URL="https://eth.llamarpc.com"
    log_warn "Using default Mainnet RPC: $MAINNET_RPC_URL"
fi

MAINNET_PASS=true

# Check Mainnet ETH
if ! check_balance "$MAINNET_RPC_URL" "$WALLET_ADDRESS" "" "ETH" "$MAINNET_ETH_REQUIRED" "Mainnet"; then
    MAINNET_PASS=false
fi

# Check Mainnet LINK (if address provided)
if [ -n "$MAINNET_LINK_TOKEN" ] && [ "$MAINNET_LINK_TOKEN" != "0x0000000000000000000000000000000000000000" ]; then
    if ! check_balance "$MAINNET_RPC_URL" "$WALLET_ADDRESS" "$MAINNET_LINK_TOKEN" "LINK" "$MAINNET_LINK_REQUIRED" "Mainnet"; then
        echo -e "  ${YELLOW}Note: LINK not required for deployment, only for CCIP fees${NC}"
    fi
else
    log_info "Mainnet - LINK:"
    echo -e "  Status: ${YELLOW}⚠️  Address not configured${NC}"
    echo -e "  ${YELLOW}Note: LINK not required for deployment, only for CCIP fees${NC}"
fi


# Check ChainID 138 balances
log_info "=== ChainID 138 Balances ==="

RPC_URL="${RPC_URL:-${RPC_URL_138:-${CHAIN138_RPC_URL:-}}}"
if [ -z "$RPC_URL" ]; then
    log_error "ERROR: Chain 138 RPC not available. Set RPC_URL, RPC_URL_138, or CHAIN138_RPC_URL."
    exit 1
fi

CHAIN138_PASS=true

# Check ChainID 138 ETH
if ! check_balance "$RPC_URL" "$WALLET_ADDRESS" "" "ETH" "$CHAIN138_ETH_REQUIRED" "ChainID 138"; then
    CHAIN138_PASS=false
fi

# Check ChainID 138 LINK (if address provided)
if [ -n "$LINK_TOKEN" ] && [ "$LINK_TOKEN" != "0x0000000000000000000000000000000000000000" ]; then
    if ! check_balance "$RPC_URL" "$WALLET_ADDRESS" "$LINK_TOKEN" "LINK" "$CHAIN138_LINK_REQUIRED" "ChainID 138"; then
        echo -e "  ${YELLOW}Note: LINK not required for deployment, only for CCIP fees${NC}"
    fi
else
    log_info "ChainID 138 - LINK:"
    echo -e "  Status: ${YELLOW}⚠️  Address not configured${NC}"
    echo -e "  ${YELLOW}Note: LINK not required for deployment, only for CCIP fees${NC}"
fi


# Summary
log_info "=== Summary ==="

if [ "$MAINNET_PASS" == "true" ] && [ "$CHAIN138_PASS" == "true" ]; then
    log_success "✅ All balances sufficient for deployment"
    echo "You can proceed with deployment:"
    echo "  • Mainnet: ./scripts/deployment/deploy-bridges-mainnet.sh"
    echo "  • ChainID 138: ./scripts/deployment/deploy-bridges-chain138.sh"
    exit 0
else
    log_error "❌ Insufficient balances detected"
    echo "Please fund your wallet before deployment:"
    if [ "$MAINNET_PASS" == "false" ]; then
        echo -e "  ${RED}• Mainnet: Need more ETH for gas fees${NC}"
    fi
    if [ "$CHAIN138_PASS" == "false" ]; then
        echo -e "  ${RED}• ChainID 138: Need more ETH for gas fees${NC}"
    fi
    exit 1
fi
