#!/usr/bin/env bash
# Dry run: Simulate bridging WETH9 from ChainID 138 to Ethereum Mainnet
# This script checks everything without sending any transactions
# Usage: ./dry-run-bridge-to-ethereum.sh [amount_in_eth] [private_key_or_address]

set -euo pipefail

SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
PROJECT_ROOT="$(cd "$SCRIPT_DIR/.." && pwd)"
source "$PROJECT_ROOT/scripts/lib/address-inventory.sh"
source "$PROJECT_ROOT/scripts/lib/ccip-destinations.sh"

# Colors
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
CYAN='\033[0;36m'
NC='\033[0m'

log_info() { echo -e "${BLUE}[INFO]${NC} $1"; }
log_success() { echo -e "${GREEN}[✓]${NC} $1"; }
log_warn() { echo -e "${YELLOW}[WARN]${NC} $1"; }
log_error() { echo -e "${RED}[ERROR]${NC} $1"; }
log_dryrun() { echo -e "${CYAN}[DRY RUN]${NC} $1"; }

load_explorer_runtime_env

# Configuration
RPC_URL="${RPC_URL_138:-http://192.168.11.250:8545}"
WETH9_ADDRESS="$(resolve_address_value WETH9_ADDRESS WETH9_ADDRESS 0xC02aaA39b223FE8D0A0e5C4F27eAD9083C756Cc2)"
WETH9_BRIDGE="$(resolve_address_value CCIPWETH9_BRIDGE CCIPWETH9_BRIDGE 0xcacfd227A040002e49e2e01626363071324f820a)"
ETHEREUM_MAINNET_SELECTOR="${ETHEREUM_MAINNET_SELECTOR:-$(ccip_destination_selector_by_name "Ethereum Mainnet")}"

# Parse arguments
AMOUNT="${1:-1.0}"
PRIVATE_KEY_OR_ADDRESS="${2:-}"

log_info "========================================="
log_info "DRY RUN: Bridge WETH9 to Ethereum Mainnet"
log_info "========================================="
log_info ""
log_info "This is a DRY RUN - no transactions will be sent"
log_info ""

# Determine if input is private key or address
if [ -n "$PRIVATE_KEY_OR_ADDRESS" ]; then
    if echo "$PRIVATE_KEY_OR_ADDRESS" | grep -qE "^0x[0-9a-fA-F]{40}$"; then
        # It's an address
        DEPLOYER="$PRIVATE_KEY_OR_ADDRESS"
        log_info "Using provided address: $DEPLOYER"
    else
        # Try as private key
        DEPLOYER=$(cast wallet address --private-key "$PRIVATE_KEY_OR_ADDRESS" 2>/dev/null || echo "")
        if [ -z "$DEPLOYER" ]; then
            log_error "Invalid private key or address: $PRIVATE_KEY_OR_ADDRESS"
            exit 1
        fi
        log_info "Using address from private key: $DEPLOYER"
    fi
elif [ -n "${PRIVATE_KEY:-}" ]; then
    DEPLOYER=$(cast wallet address --private-key "$PRIVATE_KEY" 2>/dev/null || echo "")
    if [ -z "$DEPLOYER" ]; then
        log_error "Failed to get address from PRIVATE_KEY in effective environment"
        exit 1
    fi
    log_info "Using address from effective PRIVATE_KEY: $DEPLOYER"
else
    log_error "No address or private key provided"
    log_info "Usage: $0 [amount_in_eth] [private_key_or_address]"
    log_info "Or export PRIVATE_KEY before running"
    exit 1
fi

log_info ""
log_info "Configuration:"
log_info "  Amount to Bridge: $AMOUNT ETH"
log_info "  Source Address: $DEPLOYER"
log_info "  Destination: Ethereum Mainnet (Selector: $ETHEREUM_MAINNET_SELECTOR)"
log_info "  WETH9 Address: $WETH9_ADDRESS"
log_info "  Bridge Address: $WETH9_BRIDGE"
log_info "  RPC URL: $RPC_URL"
log_info ""

# Convert amount to wei
AMOUNT_WEI=$(cast --to-wei "$AMOUNT" ether 2>/dev/null || echo "")
if [ -z "$AMOUNT_WEI" ]; then
    log_error "Failed to convert amount to wei"
    exit 1
fi

log_dryrun "========================================="
log_dryrun "Step 1: Check ETH Balance"
log_dryrun "========================================="

ETH_BALANCE=$(cast balance "$DEPLOYER" --rpc-url "$RPC_URL" 2>/dev/null || echo "0")
ETH_BALANCE_ETH=$(echo "scale=18; $ETH_BALANCE / 1000000000000000000" | bc 2>/dev/null || echo "0")

log_info "Current ETH Balance: $ETH_BALANCE_ETH ETH ($ETH_BALANCE wei)"

# Estimate gas costs (approximate)
ESTIMATED_GAS_WRAP=50000
ESTIMATED_GAS_APPROVE=50000
ESTIMATED_GAS_BRIDGE=300000
GAS_PRICE=5000000000  # 5 gwei
TOTAL_GAS_ESTIMATE=$((ESTIMATED_GAS_WRAP + ESTIMATED_GAS_APPROVE + ESTIMATED_GAS_BRIDGE))
GAS_COST_WEI=$(echo "$TOTAL_GAS_ESTIMATE * $GAS_PRICE" | bc 2>/dev/null || echo "0")
GAS_COST_ETH=$(echo "scale=18; $GAS_COST_WEI / 1000000000000000000" | bc 2>/dev/null || echo "0")

REQUIRED_ETH=$(echo "scale=18; $AMOUNT + $GAS_COST_ETH + 0.01" | bc 2>/dev/null || echo "$AMOUNT")

log_info "Estimated Gas Costs:"
log_info "  Wrap: ~$ESTIMATED_GAS_WRAP gas"
log_info "  Approve: ~$ESTIMATED_GAS_APPROVE gas"
log_info "  Bridge: ~$ESTIMATED_GAS_BRIDGE gas"
log_info "  Total: ~$TOTAL_GAS_ESTIMATE gas"
log_info "  Gas Cost: ~$GAS_COST_ETH ETH (at 5 gwei)"

if (( $(echo "$ETH_BALANCE_ETH < $REQUIRED_ETH" | bc -l 2>/dev/null || echo 1) )); then
    log_error "✗ Insufficient ETH balance"
    log_error "  Required: $REQUIRED_ETH ETH (amount + gas + buffer)"
    log_error "  Available: $ETH_BALANCE_ETH ETH"
    log_warn "  Action needed: Add more ETH to address"
else
    log_success "✓ Sufficient ETH balance"
    log_info "  Available: $ETH_BALANCE_ETH ETH"
    log_info "  Required: $REQUIRED_ETH ETH"
    log_info "  Remaining after: $(echo "scale=18; $ETH_BALANCE_ETH - $REQUIRED_ETH" | bc) ETH"
fi

log_info ""

log_dryrun "========================================="
log_dryrun "Step 2: Check WETH9 Balance"
log_dryrun "========================================="

WETH9_BAL=$(cast call "$WETH9_ADDRESS" "balanceOf(address)" "$DEPLOYER" --rpc-url "$RPC_URL" 2>/dev/null || echo "0")
    # Convert hex to decimal if needed
    if echo "$WETH9_BAL" | grep -q "^0x"; then
        WETH9_BAL_DEC=$(cast --to-dec "$WETH9_BAL" 2>/dev/null || echo "0")
    else
        WETH9_BAL_DEC="$WETH9_BAL"
    fi
    
    WETH9_BAL_ETH=$(echo "scale=18; $WETH9_BAL_DEC / 1000000000000000000" | bc 2>/dev/null || echo "0")

log_info "Current WETH9 Balance: $WETH9_BAL_ETH WETH ($WETH9_BAL_DEC wei)"

if [ "$WETH9_BAL_DEC" = "0" ] || (( $(echo "$WETH9_BAL_DEC < $AMOUNT_WEI" | bc -l 2>/dev/null || echo 1) )); then
    log_warn "⚠ Insufficient WETH9 balance"
    log_info "  Required: $AMOUNT WETH"
    log_info "  Available: $WETH9_BAL_ETH WETH"
    
    if [ "$WETH9_BAL_DEC" = "0" ]; then
        NEEDED_ETH="$AMOUNT"
    else
        NEEDED_ETH=$(echo "scale=18; $AMOUNT - $WETH9_BAL_ETH" | bc 2>/dev/null || echo "$AMOUNT")
    fi
    
    log_dryrun "  Would need to wrap: $NEEDED_ETH ETH"
    log_info "  Action needed: Wrap ETH to WETH9 first"
else
    log_success "✓ Sufficient WETH9 balance"
    log_info "  Available: $WETH9_BAL_ETH WETH"
    log_info "  Required: $AMOUNT WETH"
    log_info "  Remaining after: $(echo "scale=18; $WETH9_BAL_ETH - $AMOUNT" | bc) WETH"
fi

log_info ""

log_dryrun "========================================="
log_dryrun "Step 3: Check Bridge Allowance"
log_dryrun "========================================="

ALLOW=$(cast call "$WETH9_ADDRESS" "allowance(address,address)" "$DEPLOYER" "$WETH9_BRIDGE" --rpc-url "$RPC_URL" 2>/dev/null || echo "0")

# Convert hex to decimal if needed
if echo "$ALLOW" | grep -q "^0x"; then
    ALLOW_DEC=$(cast --to-dec "$ALLOW" 2>/dev/null || echo "0")
else
    ALLOW_DEC="$ALLOW"
fi

ALLOW_ETH=$(echo "scale=18; $ALLOW_DEC / 1000000000000000000" | bc 2>/dev/null || echo "0")

log_info "Current Bridge Allowance: $ALLOW_ETH WETH ($ALLOW_DEC wei)"

if [ "$ALLOW_DEC" = "0" ] || (( $(echo "$ALLOW_DEC < $AMOUNT_WEI" | bc -l 2>/dev/null || echo 1) )); then
    log_warn "⚠ Insufficient bridge allowance"
    log_info "  Required: $AMOUNT WETH"
    log_info "  Current: $ALLOW_ETH WETH"
    log_dryrun "  Would need to approve: $AMOUNT WETH (or max uint256)"
    log_info "  Action needed: Approve bridge to spend WETH9"
else
    log_success "✓ Sufficient bridge allowance"
    log_info "  Current: $ALLOW_ETH WETH"
    log_info "  Required: $AMOUNT WETH"
fi

log_info ""

log_dryrun "========================================="
log_dryrun "Step 4: Calculate CCIP Bridge Fee"
log_dryrun "========================================="

FEE=$(cast call "$WETH9_BRIDGE" "calculateFee(uint64,uint256)" "$ETHEREUM_MAINNET_SELECTOR" "$AMOUNT_WEI" --rpc-url "$RPC_URL" 2>/dev/null || echo "0")

if [ "$FEE" = "0" ] || [ -z "$FEE" ]; then
    log_warn "⚠ Could not calculate CCIP fee"
    log_info "  This may require LINK tokens for fees"
    log_info "  Check bridge contract for fee requirements"
else
    FEE_ETH=$(echo "scale=18; $FEE / 1000000000000000000" | bc 2>/dev/null || echo "0")
    log_info "CCIP Bridge Fee: $FEE_ETH ETH ($FEE wei)"
    
    # Check if fee is in native token or LINK
    if (( $(echo "$FEE_ETH > 0" | bc -l 2>/dev/null || echo 0) )); then
        log_info "  Fee will be paid in native ETH"
    else
        log_warn "  Fee may be paid in LINK tokens"
        log_info "  Check LINK balance if required"
    fi
fi

log_info ""

log_dryrun "========================================="
log_dryrun "Step 5: Verify Bridge Configuration"
log_dryrun "========================================="

# Check if Ethereum Mainnet is configured as destination
DESTINATION=$(cast call "$WETH9_BRIDGE" "destinations(uint64)" "$ETHEREUM_MAINNET_SELECTOR" --rpc-url "$RPC_URL" 2>&1 || echo "ERROR")

# Clean up the result (remove any error messages, get just the address)
DESTINATION_CLEAN=$(echo "$DESTINATION" | grep -oE "^0x[0-9a-fA-F]{40}$" | head -1 || echo "")

if [ -n "$DESTINATION_CLEAN" ] && ! echo "$DESTINATION_CLEAN" | grep -qE "^0x0+$"; then
    log_success "✓ Ethereum Mainnet is configured as destination"
    log_info "  Destination Bridge: $DESTINATION_CLEAN"
else
    log_error "✗ Ethereum Mainnet is NOT configured as destination"
    log_info "  Current value: ${DESTINATION_CLEAN:-Not configured}"
    log_info "  Action needed: Configure destination bridge address"
    log_info "  Fix script: ./scripts/fix-bridge-errors.sh [private_key] [bridge_address]"
fi

log_info ""

log_dryrun "========================================="
log_dryrun "Step 6: Transaction Simulation"
log_dryrun "========================================="

log_info "Simulated Transaction Sequence:"
log_info ""

# Transaction 1: Wrap ETH (if needed)
if [ "$WETH9_BAL_DEC" = "0" ] || (( $(echo "$WETH9_BAL_DEC < $AMOUNT_WEI" | bc -l 2>/dev/null || echo 1) )); then
    log_dryrun "1. Wrap ETH to WETH9"
    log_info "   Function: deposit()"
    log_info "   Value: $NEEDED_ETH ETH"
    log_info "   Gas: ~$ESTIMATED_GAS_WRAP"
    log_info "   Status: ⏳ Would execute"
else
    log_info "1. Wrap ETH to WETH9"
    log_info "   Status: ⏭️  Skipped (sufficient balance)"
fi

# Transaction 2: Approve Bridge (if needed)
if [ "$ALLOW_DEC" = "0" ] || (( $(echo "$ALLOW_DEC < $AMOUNT_WEI" | bc -l 2>/dev/null || echo 1) )); then
    log_dryrun "2. Approve Bridge"
    log_info "   Function: approve(address,uint256)"
    log_info "   Spender: $WETH9_BRIDGE"
    log_info "   Amount: $AMOUNT WETH (or max)"
    log_info "   Gas: ~$ESTIMATED_GAS_APPROVE"
    log_info "   Status: ⏳ Would execute"
else
    log_info "2. Approve Bridge"
    log_info "   Status: ⏭️  Skipped (already approved)"
fi

# Transaction 3: Bridge
log_dryrun "3. Bridge to Ethereum Mainnet"
log_info "   Function: sendCrossChain(uint64,address,uint256)"
log_info "   Destination: Ethereum Mainnet ($ETHEREUM_MAINNET_SELECTOR)"
log_info "   Recipient: $DEPLOYER"
log_info "   Amount: $AMOUNT WETH"
log_info "   Gas: ~$ESTIMATED_GAS_BRIDGE"
log_info "   Status: ⏳ Would execute"

log_info ""

log_dryrun "========================================="
log_dryrun "Step 7: Cost Summary"
log_dryrun "========================================="

log_info "Estimated Total Costs:"
log_info "  Amount to Bridge: $AMOUNT WETH"
log_info "  Gas Costs: ~$GAS_COST_ETH ETH"
if [ -n "$FEE" ] && [ "$FEE" != "0" ]; then
    FEE_ETH=$(echo "scale=18; $FEE / 1000000000000000000" | bc 2>/dev/null || echo "0")
    log_info "  CCIP Fee: $FEE_ETH ETH"
    TOTAL_COST=$(echo "scale=18; $AMOUNT + $GAS_COST_ETH + $FEE_ETH" | bc 2>/dev/null || echo "$AMOUNT")
else
    TOTAL_COST=$(echo "scale=18; $AMOUNT + $GAS_COST_ETH" | bc 2>/dev/null || echo "$AMOUNT")
fi
log_info "  Total Cost: ~$TOTAL_COST ETH"
log_info ""

log_dryrun "========================================="
log_dryrun "Step 8: Final Checks"
log_dryrun "========================================="

ALL_CHECKS_PASS=true

# Check 1: ETH Balance
if (( $(echo "$ETH_BALANCE_ETH < $REQUIRED_ETH" | bc -l 2>/dev/null || echo 1) )); then
    log_error "✗ Check 1: Insufficient ETH balance"
    ALL_CHECKS_PASS=false
else
    log_success "✓ Check 1: Sufficient ETH balance"
fi

# Check 2: WETH9 Balance or ability to wrap
if [ "$WETH9_BAL_DEC" = "0" ] || (( $(echo "$WETH9_BAL_DEC < $AMOUNT_WEI" | bc -l 2>/dev/null || echo 1) )); then
    if (( $(echo "$ETH_BALANCE_ETH >= $NEEDED_ETH" | bc -l 2>/dev/null || echo 0) )); then
        log_success "✓ Check 2: Can wrap sufficient ETH to WETH9"
    else
        log_error "✗ Check 2: Cannot wrap sufficient ETH to WETH9"
        ALL_CHECKS_PASS=false
    fi
else
    log_success "✓ Check 2: Sufficient WETH9 balance"
fi

# Check 3: Bridge Allowance
if [ "$ALLOW_DEC" = "0" ] || (( $(echo "$ALLOW_DEC < $AMOUNT_WEI" | bc -l 2>/dev/null || echo 1) )); then
    log_warn "⚠ Check 3: Bridge allowance needed (will be approved)"
else
    log_success "✓ Check 3: Bridge already approved"
fi

# Check 4: Destination Configuration
DESTINATION_CLEAN=$(echo "$DESTINATION" | grep -oE "^0x[0-9a-fA-F]{40}$" | head -1 || echo "")
if [ -n "$DESTINATION_CLEAN" ] && ! echo "$DESTINATION_CLEAN" | grep -qE "^0x0+$"; then
    log_success "✓ Check 4: Destination configured"
else
    log_error "✗ Check 4: Destination not configured"
    ALL_CHECKS_PASS=false
fi

log_info ""

log_dryrun "========================================="
log_dryrun "DRY RUN SUMMARY"
log_dryrun "========================================="
log_info ""

if [ "$ALL_CHECKS_PASS" = true ]; then
    log_success "✓ All checks passed!"
    log_info ""
    log_info "Ready to bridge:"
    log_info "  Amount: $AMOUNT WETH"
    log_info "  Destination: Ethereum Mainnet"
    log_info "  Recipient: $DEPLOYER"
    log_info ""
    log_info "To execute (not dry run), use:"
    log_info "  ./scripts/wrap-and-bridge-to-ethereum.sh $AMOUNT [private_key]"
else
    log_error "✗ Some checks failed"
    log_info ""
    log_info "Issues to resolve:"
    if (( $(echo "$ETH_BALANCE_ETH < $REQUIRED_ETH" | bc -l 2>/dev/null || echo 1) )); then
        log_info "  - Add more ETH to address"
    fi
    if [ "$WETH9_BAL_DEC" = "0" ] || (( $(echo "$WETH9_BAL_DEC < $AMOUNT_WEI" | bc -l 2>/dev/null || echo 1) )); then
        if (( $(echo "$ETH_BALANCE_ETH < $NEEDED_ETH" | bc -l 2>/dev/null || echo 1) )); then
            log_info "  - Add more ETH to wrap to WETH9"
        fi
    fi
    if [ -z "$DESTINATION_CLEAN" ] || echo "$DESTINATION_CLEAN" | grep -qE "^0x0+$" || [ "$DESTINATION_CLEAN" = "0x0000000000000000000000000000000000000000" ]; then
        log_info "  - Configure Ethereum Mainnet destination in bridge"
    fi
fi

log_info ""
log_info "This was a DRY RUN - no transactions were sent"
log_info ""
