//! Command-line interface for the makima CLI.

pub mod chain;
pub mod config;
pub mod contract;
pub mod daemon;
pub mod directive;
pub mod server;
pub mod supervisor;
pub mod view;

use clap::{Parser, Subcommand};

pub use chain::ChainArgs;
pub use config::CliConfig;
pub use contract::ContractArgs;
pub use daemon::DaemonArgs;
pub use directive::DirectiveArgs;
pub use server::ServerArgs;
pub use supervisor::SupervisorArgs;
pub use view::ViewArgs;

/// Makima - unified CLI for server, daemon, and task management.
#[derive(Parser, Debug)]
#[command(name = "makima")]
#[command(version, about = "Makima CLI - server, daemon, and task management", long_about = None)]
pub struct Cli {
    #[command(subcommand)]
    pub command: Commands,
}

#[derive(Subcommand, Debug)]
pub enum Commands {
    /// Run the makima server
    Server(ServerArgs),

    /// Run the daemon (connect to server, manage tasks)
    Daemon(DaemonArgs),

    /// Supervisor commands for contract orchestration
    #[command(subcommand)]
    Supervisor(SupervisorCommand),

    /// Contract commands for task-contract interaction
    #[command(subcommand)]
    Contract(ContractCommand),

    /// Interactive TUI browser for contracts and tasks
    ///
    /// Provides a drill-down interface for browsing contracts, viewing their
    /// tasks, and streaming real-time task output.
    ///
    /// Keyboard shortcuts:
    ///   ↑/k: Move up    ↓/j: Move down    Enter/l: Drill in
    ///   Esc/h: Go back  /: Search         q: Quit
    ///   e: Edit         d: Delete         c: cd to worktree
    ///   n: New contract
    View(ViewArgs),

    /// Configure CLI settings (API key, server URL)
    ///
    /// Saves configuration to ~/.makima/config.toml for use by CLI commands.
    #[command(subcommand)]
    Config(ConfigCommand),

    /// Chain commands for multi-contract orchestration
    ///
    /// Chains are DAGs (directed acyclic graphs) of contracts that work together
    /// to achieve a larger goal. Contracts can depend on each other, and run
    /// in parallel when no dependencies exist.
    #[command(subcommand)]
    Chain(ChainCommand),

    /// Directive commands for autonomous goal-driven orchestration
    ///
    /// Directives are top-level goals that generate chains of steps executed
    /// autonomously with configurable guardrails. Steps spawn contracts with
    /// supervisors and are verified with programmatic and LLM evaluation.
    #[command(subcommand)]
    Directive(DirectiveCommand),
}

/// Config subcommands for CLI configuration.
#[derive(Subcommand, Debug)]
pub enum ConfigCommand {
    /// Set the API key
    ///
    /// Saves the API key to ~/.makima/config.toml
    SetKey(config::SetKeyArgs),

    /// Set the API URL
    ///
    /// Saves the API URL to ~/.makima/config.toml
    SetUrl(config::SetUrlArgs),

    /// Show current configuration
    Show,

    /// Show the config file path
    Path,
}

/// Supervisor subcommands for contract orchestration.
#[derive(Subcommand, Debug)]
pub enum SupervisorCommand {
    /// List all tasks in the contract
    Tasks(SupervisorArgs),

    /// Get the task tree structure
    Tree(SupervisorArgs),

    /// Create and start a new task
    Spawn(supervisor::SpawnArgs),

    /// Wait for a task to complete
    Wait(supervisor::WaitArgs),

    /// Read a file from a task's worktree
    ReadFile(supervisor::ReadFileArgs),

    /// Create a git branch
    Branch(supervisor::BranchArgs),

    /// Merge a task's changes to a branch
    Merge(supervisor::MergeArgs),

    /// Create a pull request
    Pr(supervisor::PrArgs),

    /// View task diff
    Diff(supervisor::DiffArgs),

    /// Create a checkpoint
    Checkpoint(supervisor::CheckpointArgs),

    /// List checkpoints
    Checkpoints(SupervisorArgs),

    /// Get contract status
    Status(SupervisorArgs),

    /// Advance the contract to the next phase
    AdvancePhase(supervisor::AdvancePhaseArgs),

    /// Ask a question and wait for user feedback
    Ask(supervisor::AskArgs),

    /// Get individual task details
    Task(supervisor::GetTaskArgs),

    /// Get task output/claude log
    Output(supervisor::GetTaskOutputArgs),

    /// View task conversation history
    TaskHistory(supervisor::TaskHistoryArgs),

    /// List task checkpoints (with optional diff)
    TaskCheckpoints(supervisor::TaskCheckpointsArgs),

    /// Resume supervisor after interruption
    Resume(supervisor::ResumeArgs),

    /// Resume task from checkpoint
    TaskResumeFrom(supervisor::TaskResumeFromArgs),

    /// Rewind task code to checkpoint
    TaskRewind(supervisor::TaskRewindArgs),

    /// Fork task from historical point
    TaskFork(supervisor::TaskForkArgs),

    /// Rewind supervisor conversation
    RewindConversation(supervisor::ConversationRewindArgs),

    /// Mark the contract as complete and stop the supervisor
    Complete(supervisor::CompleteArgs),

    /// Resume a completed contract (reactivate it)
    ResumeContract(supervisor::ResumeContractArgs),

    /// Mark a deliverable as complete
    MarkDeliverable(supervisor::MarkDeliverableArgs),
}

/// Contract subcommands for task-contract interaction.
#[derive(Subcommand, Debug)]
pub enum ContractCommand {
    /// Get contract status
    Status(ContractArgs),

    /// Get the phase checklist
    Checklist(ContractArgs),

    /// Get contract goals
    Goals(ContractArgs),

    /// List contract files
    Files(ContractArgs),

    /// Get a specific file's content
    File(contract::FileArgs),

    /// Report progress on the contract
    Report(contract::ReportArgs),

    /// Get suggested next action
    SuggestAction(ContractArgs),

    /// Get completion recommendation
    CompletionAction(contract::CompletionActionArgs),

    /// Update a file (reads content from stdin)
    UpdateFile(contract::UpdateFileArgs),

    /// Create a new file (reads content from stdin)
    CreateFile(contract::CreateFileArgs),
}

/// Chain subcommands for multi-contract orchestration.
#[derive(Subcommand, Debug)]
pub enum ChainCommand {
    /// Create a chain from a YAML file
    ///
    /// Parses the chain definition, validates the DAG, and creates
    /// contracts in the correct dependency order.
    Run(chain::RunArgs),

    /// Get chain status and progress
    Status(chain::StatusArgs),

    /// List all chains
    List(chain::ListArgs),

    /// List contracts in a chain
    Contracts(chain::ContractsArgs),

    /// Display ASCII DAG visualization
    ///
    /// Shows the chain structure as an ASCII graph with
    /// contracts as nodes and dependencies as edges.
    Graph(chain::GraphArgs),

    /// Validate a chain YAML file without creating
    ///
    /// Checks syntax, validates the DAG (no cycles), and
    /// reports any errors.
    Validate(chain::ValidateArgs),

    /// Preview what would be created from a chain file
    ///
    /// Shows execution order and contract details without
    /// actually creating anything.
    Preview(chain::PreviewArgs),

    /// Archive a chain
    ///
    /// Marks the chain as archived. Does not delete contracts.
    Archive(chain::ArchiveArgs),
}

/// Directive subcommands for autonomous goal-driven orchestration.
#[derive(Subcommand, Debug)]
pub enum DirectiveCommand {
    /// Create a new directive from a goal
    Create(directive::CreateArgs),

    /// Get directive status and progress
    Status(directive::StatusArgs),

    /// List all directives
    List(directive::ListArgs),

    /// List steps in the directive's chain
    Steps(directive::StepsArgs),

    /// Display ASCII DAG visualization
    ///
    /// Shows the directive's chain structure as an ASCII graph with
    /// steps as nodes and dependencies as edges.
    Graph(directive::GraphArgs),

    /// Show recent events for a directive
    Events(directive::EventsArgs),

    /// Approve a pending approval request
    Approve(directive::ApproveArgs),

    /// Deny a pending approval request
    Deny(directive::DenyArgs),

    /// Start a directive (generates chain and begins execution)
    Start(directive::StartArgs),

    /// Pause a running directive
    Pause(directive::PauseArgs),

    /// Resume a paused directive
    Resume(directive::ResumeArgs),

    /// Stop a directive
    Stop(directive::StopArgs),

    /// Archive a directive
    Archive(directive::ArchiveArgs),
}

impl Cli {
    /// Parse command-line arguments
    pub fn parse_args() -> Self {
        Self::parse()
    }
}
