"""Input validators for API requests."""

import re
from typing import Any
from pydantic import field_validator
from agenticlypay.api.exceptions import ValidationError

# Stripe account ID pattern: acct_ followed by alphanumeric characters
STRIPE_ACCOUNT_ID_PATTERN = re.compile(r"^acct_[a-zA-Z0-9]+$")

# Valid ISO 4217 currency codes (common ones)
VALID_CURRENCIES = {
    "usd", "eur", "gbp", "jpy", "cad", "aud", "chf", "cny", "sek", "nzd",
    "mxn", "sgd", "hkd", "nok", "try", "rub", "inr", "brl", "zar", "krw"
}

# Maximum amount: 1 million dollars in cents
MAX_AMOUNT = 100_000_000  # $1,000,000.00

# Minimum amount: 1 cent
MIN_AMOUNT = 1


def validate_stripe_account_id(value: str) -> str:
    """Validate Stripe account ID format."""
    if not value:
        raise ValidationError("Account ID is required")
    if not STRIPE_ACCOUNT_ID_PATTERN.match(value):
        raise ValidationError(
            f"Invalid account ID format: {value}. Must start with 'acct_' followed by alphanumeric characters."
        )
    return value


def validate_amount(value: int) -> int:
    """Validate payment amount."""
    if value < MIN_AMOUNT:
        raise ValidationError(f"Amount must be at least {MIN_AMOUNT} cent(s)")
    if value > MAX_AMOUNT:
        raise ValidationError(f"Amount exceeds maximum of ${MAX_AMOUNT / 100:,.2f}")
    return value


def validate_currency(value: str) -> str:
    """Validate currency code."""
    if not value:
        raise ValidationError("Currency is required")
    value_lower = value.lower()
    if value_lower not in VALID_CURRENCIES:
        raise ValidationError(
            f"Unsupported currency: {value}. Supported currencies: {', '.join(sorted(VALID_CURRENCIES))}"
        )
    return value_lower


def validate_email(value: str) -> str:
    """Validate email format (basic check, Pydantic EmailStr does more)."""
    if not value or "@" not in value:
        raise ValidationError("Invalid email format")
    return value.lower().strip()

