"""Tiered context generator — produces CLAUDE.md + .agents/ directory."""

from __future__ import annotations

from dataclasses import dataclass
from pathlib import Path

from agentmd.detectors.subsystem import SubsystemInfo
from agentmd.generators.base import BaseGenerator
from agentmd.types import ProjectAnalysis


@dataclass
class TieredOutput:
    """Result of a tiered generation run."""

    tier1_path: str  # e.g. "CLAUDE.md"
    tier1_content: str
    tier2_files: dict[str, str]  # e.g. {".agents/api.md": "content..."}

    @property
    def all_files(self) -> dict[str, str]:
        """Return all generated files as {relative_path: content}."""
        result = {self.tier1_path: self.tier1_content}
        result.update(self.tier2_files)
        return result

    @property
    def file_count(self) -> int:
        return 1 + len(self.tier2_files)


class TieredGenerator:
    """Generates a directory of context files instead of a single file."""

    def __init__(self, analysis: ProjectAnalysis, subsystems: list[SubsystemInfo]) -> None:
        self.analysis = analysis
        self.subsystems = subsystems

    def generate(self) -> TieredOutput:
        """Generate Tier 1 + Tier 2 context files."""
        tier2_files: dict[str, str] = {}
        for subsystem in self.subsystems:
            filename = f".agents/{subsystem.name}.md"
            tier2_files[filename] = self._generate_tier2(subsystem)

        tier1_content = self._generate_tier1(tier2_files)
        return TieredOutput(
            tier1_path="CLAUDE.md",
            tier1_content=tier1_content,
            tier2_files=tier2_files,
        )

    def _generate_tier1(self, tier2_files: dict[str, str]) -> str:
        """Generate the Tier 1 CLAUDE.md — minimal style with trigger table."""
        a = self.analysis
        sections: list[str] = []

        # Header
        sections.append(
            "# CLAUDE.md\n\n"
            "Agent context for Claude Code. "
            "Generated by agentmd with `--tiered` mode."
        )

        # Build/test/lint commands — reuse base generator logic
        gen = _Tier1Helper(a)
        sections.append(gen._section_commands())

        # Directory structure (minimal)
        sections.append(gen._section_directory_structure_minimal())

        # Trigger table
        sections.append(self._section_trigger_table(tier2_files))

        return "\n\n".join(s.strip() for s in sections if s.strip()) + "\n"

    def _section_trigger_table(self, tier2_files: dict[str, str]) -> str:
        """Generate the trigger table mapping directories to context files."""
        lines = [
            "## Context Files (load when working in these areas)",
            "| Directory | Context File |",
            "|-----------|-------------|",
        ]
        for subsystem in self.subsystems:
            filename = f".agents/{subsystem.name}.md"
            if filename in tier2_files:
                lines.append(f"| {subsystem.path}/ | {filename} |")
        return "\n".join(lines)

    def _generate_tier2(self, subsystem: SubsystemInfo) -> str:
        """Generate a Tier 2 per-subsystem context file."""
        sections: list[str] = []

        # Header
        sections.append(f"# {subsystem.name}\n\nSubsystem context for `{subsystem.path}/`.")

        # Detected stack
        stack_lines = ["## Detected Stack"]
        if subsystem.languages:
            stack_lines.append(f"**Languages:** {', '.join(subsystem.languages)}")
        if subsystem.frameworks:
            stack_lines.append(f"**Frameworks:** {', '.join(subsystem.frameworks)}")
        stack_lines.append(f"**Source files:** {subsystem.file_count}")
        sections.append("\n".join(stack_lines))

        # Key files
        sections.append(
            "## Key Files\n"
            "_(Add important files and their purposes here.)_"
        )

        # Test conventions
        sections.append(
            "## Test Conventions\n"
            "_(Add test file patterns, fixtures, and conventions for this subsystem.)_"
        )

        # Common failure modes
        sections.append(
            "## Common Failure Modes\n"
            "_(Document recurring issues and their fixes here.)_"
        )

        return "\n\n".join(s.strip() for s in sections if s.strip()) + "\n"

    def write(self, root: Path, *, force: bool = False) -> list[str]:
        """Write all generated files to disk. Returns list of written paths."""
        output = self.generate()
        written: list[str] = []

        for rel_path, content in output.all_files.items():
            full_path = root / rel_path
            if full_path.exists() and not force:
                continue
            full_path.parent.mkdir(parents=True, exist_ok=True)
            full_path.write_text(content, encoding="utf-8")
            written.append(rel_path)

        return written


class _Tier1Helper(BaseGenerator):
    """Internal helper to reuse BaseGenerator section builders for Tier 1."""

    output_filename = "CLAUDE.md"

    def __init__(self, analysis: ProjectAnalysis) -> None:
        super().__init__(analysis, minimal=True)

    def _build_sections(self) -> list[str]:
        return []  # Not used directly
