"""
Configuration module for S3Manager capability.

Supports loading values from environment variables.
"""

import os
from dataclasses import dataclass, field
from typing import Optional

from ..exceptions.s3_exceptions import ConfigurationError


@dataclass
class S3Config:
    """
    Configuration for S3 storage provider.

    Sensitive values can be set via environment variables:
        - AWS_ACCESS_KEY_ID
        - AWS_SECRET_ACCESS_KEY
        - AWS_SESSION_TOKEN
        - AWS_DEFAULT_REGION / NEURONOS_S3_REGION
        - NEURONOS_S3_ENDPOINT_URL
        - NEURONOS_S3_PROVIDER

    Attributes:
        provider: Storage provider name (e.g., "aws")
        region: AWS region (e.g., "us-east-1")
        access_key_id: AWS access key ID (optional if using IAM roles/profiles)
        secret_access_key: AWS secret access key
        session_token: AWS session token for temporary credentials
        endpoint_url: Custom endpoint URL (for MinIO, LocalStack, etc.)
        use_ssl: Whether to use SSL for connections
        verify_ssl: Whether to verify SSL certificates
        max_pool_connections: Maximum number of connections in the pool
        connect_timeout: Connection timeout in seconds
        read_timeout: Read timeout in seconds
        multipart_threshold: File size threshold (bytes) to trigger multipart upload
        multipart_chunksize: Chunk size (bytes) for multipart upload parts
    """

    provider: str = ""
    region: str = ""
    access_key_id: Optional[str] = None
    secret_access_key: Optional[str] = None
    session_token: Optional[str] = None
    endpoint_url: Optional[str] = None
    use_ssl: bool = True
    verify_ssl: bool = True
    max_pool_connections: int = 10
    connect_timeout: int = 60
    read_timeout: int = 60
    multipart_threshold: int = 100 * 1024 * 1024  # 100MB
    multipart_chunksize: int = 8 * 1024 * 1024  # 8MB

    def __post_init__(self):
        self.provider = self.provider or os.getenv("NEURONOS_S3_PROVIDER", "aws")
        self.region = self.region or os.getenv("AWS_DEFAULT_REGION") or os.getenv("NEURONOS_S3_REGION", "us-east-1")
        self.access_key_id = self.access_key_id or os.getenv("AWS_ACCESS_KEY_ID")
        self.secret_access_key = self.secret_access_key or os.getenv("AWS_SECRET_ACCESS_KEY")
        self.session_token = self.session_token or os.getenv("AWS_SESSION_TOKEN")
        self.endpoint_url = self.endpoint_url or os.getenv("NEURONOS_S3_ENDPOINT_URL")

        valid_providers = ["aws"]
        if self.provider.lower() not in valid_providers:
            raise ConfigurationError(
                f"Invalid provider '{self.provider}'. Supported: {', '.join(valid_providers)}"
            )
        self.provider = self.provider.lower()

    def to_dict(self) -> dict:
        return {
            "provider": self.provider,
            "region": self.region,
            "access_key_id": self.access_key_id,
            "secret_access_key": self.secret_access_key,
            "session_token": self.session_token,
            "endpoint_url": self.endpoint_url,
            "use_ssl": self.use_ssl,
            "verify_ssl": self.verify_ssl,
            "max_pool_connections": self.max_pool_connections,
            "connect_timeout": self.connect_timeout,
            "read_timeout": self.read_timeout,
            "multipart_threshold": self.multipart_threshold,
            "multipart_chunksize": self.multipart_chunksize,
        }

    @classmethod
    def from_dict(cls, config_dict: dict) -> "S3Config":
        return cls(**config_dict)
