"""Shared application settings."""

from __future__ import annotations

import re
from functools import lru_cache
from typing import List, Optional, Tuple

from pydantic_settings import BaseSettings, SettingsConfigDict


class Settings(BaseSettings):
    model_config = SettingsConfigDict(env_file=".env", env_file_encoding="utf-8", extra="ignore")

    app_env: str = "local"
    log_level: str = "INFO"
    artifacts_dir: str = "./data/artifacts"

    database_url: str = "postgresql+asyncpg://agent_nova:agent_nova@localhost:5432/agent_nova"
    redis_url: str = "redis://localhost:6379"

    jira_provider: str = "mock"
    jira_base_url: str = "https://example.atlassian.net"
    jira_email: str = ""
    jira_api_token: str = ""
    jira_webhook_secret: str = "dev-webhook-secret"
    jira_project_keys: str = "SALES"
    jira_agent_label: str = "agent-nova"
    jira_agent_status: str = "Ready for Agent"
    jira_issue_types: str = "Story,Task"
    jira_bot_account_id: str = ""
    jira_in_progress_status: str = "In Progress"

    confluence_provider: str = "mock"
    confluence_base_url: str = "https://example.atlassian.net/wiki"
    confluence_space_keys: str = "ENG,ARCH"
    confluence_write_space_key: str = ""
    confluence_email: str = ""
    confluence_api_token: str = ""

    git_provider: str = "mock"
    git_repo_url: str = ""
    git_default_branch: str = "main"
    github_token: str = ""
    github_api_base_url: str = "https://api.github.com"

    salesforce_provider: str = "mock"
    salesforce_org_alias: str = ""
    salesforce_deploy_check_only: bool = True

    static_analysis_provider: str = "mock"
    pmd_bin: str = "pmd"
    max_review_cycles: int = 3

    apex_test_provider: str = "mock"

    llm_provider: str = "mock"
    openai_api_key: str = ""
    openai_model: str = "gpt-4o"

    @property
    def jira_project_key_list(self) -> List[str]:
        return [p.strip() for p in self.jira_project_keys.split(",") if p.strip()]

    @property
    def jira_issue_type_list(self) -> List[str]:
        return [t.strip() for t in self.jira_issue_types.split(",") if t.strip()]

    @property
    def confluence_space_key_list(self) -> List[str]:
        return [s.strip() for s in self.confluence_space_keys.split(",") if s.strip()]

    @property
    def confluence_write_space(self) -> str:
        """Space key used when creating design docs (explicit write key or first search space)."""
        explicit = (self.confluence_write_space_key or "").strip()
        if explicit:
            return explicit
        spaces = self.confluence_space_key_list
        return spaces[0] if spaces else ""

    @property
    def github_owner_repo(self) -> Optional[Tuple[str, str]]:
        """Parse owner/repo from GIT_REPO_URL (HTTPS or SSH)."""
        url = (self.git_repo_url or "").strip()
        if not url:
            return None
        url = url.rstrip("/")
        if url.endswith(".git"):
            url = url[:-4]
        # https://github.com/owner/repo or git@github.com:owner/repo
        m = re.search(r"(?:github\.com[:/]|/)(?P<owner>[^/]+)/(?P<repo>[^/]+)$", url)
        if not m:
            # bare owner/repo
            parts = url.split("/")
            if len(parts) == 2 and parts[0] and parts[1]:
                return parts[0], parts[1]
            return None
        return m.group("owner"), m.group("repo")


@lru_cache
def get_settings() -> Settings:
    return Settings()
