"""Configuration management for SFTP pipeline"""

import os
from dataclasses import dataclass

# How consultation responses are delivered back to Amazon.
#   api  - (default) Shuttle ConsumeConsultation API only
#   both - every response goes to SFTP *and* the Shuttle API (Amazon dedupes
#          on primary/secondaryReferenceId)
#   sftp - legacy SEDI flow only (PGP zip uploaded to SFTP)
EGRESS_MODES = ("api", "both", "sftp")

# Env vars that must be set whenever responses can go out via the Shuttle API.
AMAZON_EGRESS_REQUIRED_VARS = (
    "AMAZON_COGNITO_TOKEN_URL",
    "AMAZON_CLIENT_ID",
    "AMAZON_CLIENT_SECRET",
    "AMAZON_OAUTH_SCOPE",
    "AMAZON_CONSULTATION_RESPONSE_URL",
    "S3_BUCKET",
)


@dataclass
class Config:
    """Complete configuration for SFTP pipeline"""

    # SFTP Settings
    sftp_host: str
    sftp_username: str
    outgoing_sftp_username: str
    sftp_private_key_path: str

    # PGP Settings
    pgp_private_key_path: str
    pgp_public_key_path: str

    # 1Rx API Settings
    rx_api_key: str

    # MySQL Settings
    mysql_username: str
    mysql_password: str

    # SFTP Settings
    sftp_port: int = 22
    incoming_sftp_path: str = "/consultationrequests"
    outgoing_sftp_path: str = "/consultationresponses"

    # 1Rx API Settings
    rx_api_base_url: str = "http://localhost:10000/api/1rx/v1"
    rx_api_retry_attempts: int = 3
    rx_api_retry_delay_seconds: float = 1.0
    rx_api_timeout_seconds: float = 10.0

    # Webhook Settings
    webhook_host: str = "0.0.0.0"
    webhook_port: int = 8080

    # MySQL Settings
    mysql_host: str = "localhost"
    mysql_port: int = 3306
    mysql_database: str = "sftp_pipeline"
    mysql_charset: str = "utf8mb4"
    mysql_pool_size: int = 10

    # Processing Settings
    poll_interval: int = 3
    max_retries: int = 3
    retry_delay_seconds: int = 300
    cleanup_days: int = 30
    max_parallel_files: int = 10
    scan_batch_size: int = 200
    use_local_scan: bool = False
    local_incoming_path: str = "connectivity_requests"
    APP_ENV = os.getenv("APP_ENV", "dev")

    # Ingress mode: "both" (default) = SFTP + API, "api" = API only, "sftp" = SFTP only
    ingress_mode: str = "both"

    # Egress (MyRX -> Amazon consultation responses), see EGRESS_MODES
    egress_mode: str = "api"
    # Amazon only accepts API responses for test orders for now: when true,
    # an order whose isTestData is not true is delivered over SFTP even if
    # EGRESS_MODE would otherwise send it to the Shuttle API. Flip to false
    # once Amazon opens the API to real orders.
    egress_api_test_orders_only: bool = True
    # Ramp-up of real orders onto the Shuttle API while the test-orders
    # gate above is on: the first N real orders (counted as API deliveries
    # Amazon acknowledged, persisted in the DB so restarts do not reset it)
    # go over the API, every real order after that goes over SFTP as before.
    # 0 (default) keeps real orders on SFTP. Ignored when the gate is off.
    egress_api_real_order_limit: int = 0

    # Amazon Shuttle ConsumeConsultation API
    amazon_provider_name: str = "myrx"
    amazon_cognito_token_url: str = ""
    amazon_client_id: str = ""
    amazon_client_secret: str = ""
    amazon_oauth_scope: str = ""
    amazon_consultation_response_url: str = ""
    amazon_api_timeout_seconds: float = 30.0
    amazon_api_retry_attempts: int = 3
    amazon_api_retry_delay_seconds: float = 1.0

    # S3 bucket holding prescription ZIPs that Amazon downloads via pre-signed
    # URL. AWS credentials are resolved by boto3's default chain (instance role
    # or AWS_ACCESS_KEY_ID / AWS_SECRET_ACCESS_KEY), never from this config.
    s3_bucket: str = ""
    s3_region: str = "ap-south-1"
    s3_prefix: str = "consultation-responses"
    s3_presign_ttl_seconds: int = 43200

    @property
    def egress_api_enabled(self) -> bool:
        return self.egress_mode in ("both", "api")

    @property
    def egress_sftp_enabled(self) -> bool:
        return self.egress_mode in ("sftp", "both")


def create_config_from_env() -> Config:
    """Create configuration from environment variables"""
    required_vars = [
        "SFTP_HOST",
        "SFTP_USERNAME",
        "RX_API_KEY",
        "MYSQL_USERNAME",
        "MYSQL_PASSWORD",
    ]

    SFTP_HOST = "in-sftp.amazonsedi.com"
    SFTP_PORT = 22
    SFTP_USERNAME = "2HRV5XSXT0JOV"
    OUTGOING_SFTP_USERNAME = "1A10E9TC5CYBE"

    SFTP_PRIVATE_KEY_PATH = "/mnt/c/keys/id_rsa_UAT"

    egress_mode = os.getenv("EGRESS_MODE", "api").lower()
    if egress_mode not in EGRESS_MODES:
        raise ValueError(
            f"Invalid EGRESS_MODE={egress_mode!r}; expected one of {EGRESS_MODES}"
        )
    if egress_mode != "sftp":
        required_vars.extend(AMAZON_EGRESS_REQUIRED_VARS)

    raw_limit = os.getenv("EGRESS_API_REAL_ORDER_LIMIT", "0").strip()
    try:
        egress_api_real_order_limit = int(raw_limit)
    except ValueError:
        raise ValueError(
            f"Invalid EGRESS_API_REAL_ORDER_LIMIT={raw_limit!r}; expected a whole number"
        )
    if egress_api_real_order_limit < 0:
        raise ValueError(
            f"Invalid EGRESS_API_REAL_ORDER_LIMIT={raw_limit!r}; must be 0 or greater"
        )

    missing_vars = [var for var in required_vars if not os.getenv(var)]
    if missing_vars:
        raise ValueError(f"Missing required environment variables: {missing_vars}")

    return Config(
        # SFTP
        rx_api_key=os.getenv(
            "RX_API_KEY", "amazon-6697f65c-8a8f-482e-bd27-7f4e075609d7"
        ),
        sftp_host=os.getenv("SFTP_HOST", SFTP_HOST),
        sftp_port=int(os.getenv("SFTP_PORT", SFTP_PORT)),
        sftp_username=os.getenv("SFTP_USERNAME", SFTP_USERNAME),
        outgoing_sftp_username=os.getenv(
            "OUTGOING_SFTP_USERNAME", OUTGOING_SFTP_USERNAME
        ),
        sftp_private_key_path=os.getenv("SFTP_PRIVATE_KEY_PATH", SFTP_PRIVATE_KEY_PATH),
        incoming_sftp_path=os.getenv("INCOMING_SFTP_PATH", "/consultationrequests"),
        outgoing_sftp_path=os.getenv("OUTGOING_SFTP_PATH", "/consultationresponses"),
        # PGP
        pgp_private_key_path=os.getenv(
            "PGP_PRIVATE_KEY_PATH", "/mnt/c/keys/pgp_private_key_UAT.asc"
        ),
        pgp_public_key_path=os.getenv(
            "PGP_PUBLIC_KEY_PATH", "/mnt/c/keys/PGPPublicKey.asc"
        ),
        # 1Rx API
        rx_api_base_url=os.getenv(
            "RX_API_BASE_URL", "http://localhost:10000/api/1rx/v1"
        ),
        rx_api_retry_attempts=int(os.getenv("RX_API_RETRY_ATTEMPTS", "3")),
        rx_api_retry_delay_seconds=float(os.getenv("RX_API_RETRY_DELAY_SECONDS", "1.0")),
        rx_api_timeout_seconds=float(os.getenv("RX_API_TIMEOUT_SECONDS", "10.0")),
        # Webhook
        webhook_host=os.getenv("WEBHOOK_HOST", "0.0.0.0"),
        webhook_port=int(os.getenv("WEBHOOK_PORT", "8080")),
        # MySQL
        mysql_host=os.getenv("MYSQL_HOST", "localhost"),
        mysql_port=int(os.getenv("MYSQL_PORT", "3306")),
        mysql_database=os.getenv("MYSQL_DATABASE", "rx_onerx"),
        mysql_username=os.getenv("MYSQL_USERNAME", "rx_prafull"),
        mysql_password=os.getenv("MYSQL_PASSWORD", "$rBr!2DTiAWv"),
        mysql_charset=os.getenv("MYSQL_CHARSET", "utf8mb4"),
        mysql_pool_size=int(os.getenv("MYSQL_POOL_SIZE", "10")),
        # Processing
        poll_interval=int(os.getenv("POLL_INTERVAL", "3")),
        max_retries=int(os.getenv("MAX_RETRIES", "3")),
        retry_delay_seconds=int(os.getenv("RETRY_DELAY_SECONDS", "300")),
        cleanup_days=int(os.getenv("CLEANUP_DAYS", "30")),
        max_parallel_files=int(os.getenv("MAX_PARALLEL_FILES", "10")),
        scan_batch_size=int(os.getenv("SCAN_BATCH_SIZE", "200")),
        use_local_scan=os.getenv("USE_LOCAL_SCAN", "false").lower() == "true",
        local_incoming_path=os.getenv("LOCAL_INCOMING_PATH", "connectivity_requests"),
        # Ingress mode: "both" (default), "api", or "sftp"
        ingress_mode=os.getenv("INGRESS_MODE", "both").lower(),
        # Egress
        egress_mode=egress_mode,
        egress_api_test_orders_only=os.getenv(
            "EGRESS_API_TEST_ORDERS_ONLY", "true"
        ).lower()
        == "true",
        egress_api_real_order_limit=egress_api_real_order_limit,
        amazon_provider_name=os.getenv("AMAZON_PROVIDER_NAME", "myrx").lower(),
        amazon_cognito_token_url=os.getenv("AMAZON_COGNITO_TOKEN_URL", ""),
        amazon_client_id=os.getenv("AMAZON_CLIENT_ID", ""),
        amazon_client_secret=os.getenv("AMAZON_CLIENT_SECRET", ""),
        amazon_oauth_scope=os.getenv("AMAZON_OAUTH_SCOPE", ""),
        amazon_consultation_response_url=os.getenv(
            "AMAZON_CONSULTATION_RESPONSE_URL", ""
        ),
        amazon_api_timeout_seconds=float(
            os.getenv("AMAZON_API_TIMEOUT_SECONDS", "30.0")
        ),
        amazon_api_retry_attempts=int(os.getenv("AMAZON_API_RETRY_ATTEMPTS", "3")),
        amazon_api_retry_delay_seconds=float(
            os.getenv("AMAZON_API_RETRY_DELAY_SECONDS", "1.0")
        ),
        # S3
        s3_bucket=os.getenv("S3_BUCKET", ""),
        s3_region=os.getenv("S3_REGION", "ap-south-1"),
        s3_prefix=os.getenv("S3_PREFIX", "consultation-responses").strip("/"),
        s3_presign_ttl_seconds=int(os.getenv("S3_PRESIGN_TTL_SECONDS", "43200")),
    )
