from pydantic import Field from pydantic_settings import BaseSettings, SettingsConfigDict class PostgresSettings(BaseSettings): model_config = SettingsConfigDict(env_prefix="POSTGRES_", extra="ignore") host: str = "127.0.0.1" port: int = 5433 user: str = "chatbot" password: str = "chatbot" db: str = "chatbot" @property def dsn(self) -> str: return f"postgresql+asyncpg://{self.user}:{self.password}@{self.host}:{self.port}/{self.db}" class MinioSettings(BaseSettings): model_config = SettingsConfigDict(env_prefix="MINIO_", extra="ignore") endpoint: str = "127.0.0.1:9100" access_key: str = "chatbot" secret_key: str = "chatbot-secret" secure: bool = False bucket: str = "chatbot-source-files" class IngestionSettings(BaseSettings): """Bounds on inline ingestion (ADR-0017). `timeout_seconds` must stay below the proxy/load-balancer/client read timeouts, or callers give up on work that is still succeeding. """ model_config = SettingsConfigDict(env_prefix="INGESTION_", extra="ignore") max_concurrency: int = 4 thread_pool_size: int = 8 timeout_seconds: float = 120.0 max_chunks_per_file: int = 5000 embed_batch_size: int = 128 embed_concurrency: int = 4 class QdrantSettings(BaseSettings): model_config = SettingsConfigDict(env_prefix="QDRANT_", extra="ignore") url: str = "http://127.0.0.1:6343" api_key: str | None = None class AppLimitSettings(BaseSettings): model_config = SettingsConfigDict(env_prefix="APP_", extra="ignore") env: str = "local" max_upload_size_mb: int = 25 readiness_check_timeout_seconds: float = 2.0 class LoggingSettings(BaseSettings): model_config = SettingsConfigDict(env_prefix="LOG_", extra="ignore") level: str = "INFO" json_format: bool = False class Settings(BaseSettings): model_config = SettingsConfigDict(env_file=".env", extra="ignore") postgres: PostgresSettings = Field(default_factory=PostgresSettings) minio: MinioSettings = Field(default_factory=MinioSettings) ingestion: IngestionSettings = Field(default_factory=IngestionSettings) qdrant: QdrantSettings = Field(default_factory=QdrantSettings) app: AppLimitSettings = Field(default_factory=AppLimitSettings) logging: LoggingSettings = Field(default_factory=LoggingSettings)