"""
koci Visualize Controller

Visualizes pipeline structure as ASCII graph.
"""

import os
from cement import Controller, ex

from ..core import parse_pipeline, ParserError, ValidationError
from ..output import OutputFormatter, Verbosity


class Visualize(Controller):
    """Controller for the 'visualize' command."""

    class Meta:
        label = 'visualize'
        stacked_on = 'base'
        stacked_type = 'nested'
        description = 'Visualize pipeline structure'
        help = 'Show pipeline as ASCII graph'
        aliases = ['viz', 'graph']

        arguments = [
            (['-f', '--file'],
             {'help': 'Path to koci.yml file',
              'action': 'store',
              'dest': 'file',
              'default': None}),

            (['--format'],
             {'help': 'Output format (tree, graph, mermaid)',
              'action': 'store',
              'dest': 'format',
              'choices': ['tree', 'graph', 'mermaid'],
              'default': 'tree'}),

            (['--expanded'],
             {'help': 'Show expanded matrix jobs',
              'action': 'store_true',
              'dest': 'expanded',
              'default': False}),
        ]

    @ex(help='Visualize pipeline')
    def _default(self):
        """Show pipeline visualization."""
        verbosity = Verbosity.VERBOSE if self.app.pargs.expanded else Verbosity.NORMAL
        formatter = OutputFormatter(verbosity=verbosity)

        try:
            pipeline = parse_pipeline(
                filepath=self.app.pargs.file,
                directory=os.getcwd(),
            )
        except (ParserError, ValidationError) as e:
            formatter.error(str(e))
            self.app.exit_code = 1
            return

        output_format = self.app.pargs.format

        if output_format == 'tree':
            self._print_tree(pipeline, formatter)
        elif output_format == 'graph':
            self._print_graph(pipeline)
        elif output_format == 'mermaid':
            self._print_mermaid(pipeline)

    def _print_tree(self, pipeline, formatter):
        """Print tree visualization."""
        formatter.print_pipeline_graph(pipeline)

    def _print_graph(self, pipeline):
        """Print dependency graph."""
        print(f"\nPipeline: {pipeline.name}")
        print("=" * 60)

        # Print stages

        # Print stages
        for stage in pipeline.stages:
            print(f"\n┌─ Stage: {stage.name}")
            print("│")

            stage_jobs = [j for j in stage.jobs]

            for i, job in enumerate(stage_jobs):
                is_last = i == len(stage_jobs) - 1
                prefix = "└──" if is_last else "├──"
                cont = "   " if is_last else "│  "

                # Job line
                job_str = f" ⚙ {job.name}"
                if job.image:
                    job_str += f" [{job.image}]"
                print(f"│ {prefix}{job_str}")

                # Dependencies
                if job.needs:
                    for dep in job.needs:
                        print(f"│ {cont}    ← {dep}")

                # Matrix
                if job.matrix:
                    combos = len(job.matrix.expand())
                    print(f"│ {cont}    ⊕ matrix: {combos} variants")

                # Artifacts
                if job.artifacts:
                    if job.artifacts.paths:
                        print(f"│ {cont}    📦 produces: {', '.join(job.artifacts.paths)}")
                    if job.artifacts.consume:
                        print(f"│ {cont}    📥 consumes: {', '.join(job.artifacts.consume)}")

        print("\n" + "=" * 60)

        # Summary
        total_jobs = len(pipeline.get_all_jobs())
        matrix_jobs = sum(
            len(j.matrix.expand()) - 1
            for j in pipeline.get_all_jobs()
            if j.matrix
        )

        print(f"Stages: {len(pipeline.stages)}")
        print(f"Jobs: {total_jobs}" + (f" (+{matrix_jobs} from matrix)" if matrix_jobs else ""))

    def _print_mermaid(self, pipeline):
        """Print Mermaid diagram syntax."""
        print("```mermaid")
        print("graph LR")
        print(f"    subgraph {pipeline.name}")

        for stage in pipeline.stages:
            stage_id = stage.name.replace('-', '_').replace(' ', '_')
            print(f"        subgraph {stage_id}[{stage.name}]")

            for job in stage.jobs:
                job_id = job.name.replace('-', '_').replace(' ', '_')
                print(f"            {job_id}[{job.name}]")

            print("        end")

        # Add dependencies
        for job in pipeline.get_all_jobs():
            job_id = job.name.replace('-', '_').replace(' ', '_')
            for dep in job.needs:
                dep_id = dep.replace('-', '_').replace(' ', '_')
                print(f"    {dep_id} --> {job_id}")

        print("    end")
        print("```")
        print("\nCopy the above to a Mermaid renderer to visualize.")
