<?php

namespace Detektivo\Command;

use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Input\InputArgument;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\Console\Helper\Table;

class Status extends Command {

    protected static $defaultName = 'detektivo:status';
    protected ?\Lime\App $app = null;

    public function __construct(\Lime\App $app) {
        $this->app = $app;
        parent::__construct();
    }

    protected function configure(): void {
        $this
            ->setDescription('Show status of Detektivo search indexes')
            ->setHelp('This command displays the status of all configured search indexes')
            ->addArgument('name', InputArgument::OPTIONAL, 'Show detailed status for a specific index');
    }

    protected function execute(InputInterface $input, OutputInterface $output): int {

        $detektivo = $this->app->module('detektivo');
        $indexName = $input->getArgument('name');
        $indexes = $detektivo->indexes();

        if (!count($indexes)) {
            $output->writeln('<comment>[!] No indexes configured</comment>');
            return Command::SUCCESS;
        }

        $output->writeln('');
        $output->writeln('<info>Detektivo Search Indexes</info>');
        $output->writeln(str_repeat('=', 60));

        // Show detailed status for a specific index
        if ($indexName) {

            if (!isset($indexes[$indexName])) {
                $output->writeln("<error>[x] Index '{$indexName}' not found</error>");
                return Command::FAILURE;
            }

            $index = $indexes[$indexName];
            $this->showIndexDetails($output, $detektivo, $indexName, $index);

            return Command::SUCCESS;
        }

        // Show summary table of all indexes
        $table = new Table($output);
        $table->setHeaders(['Name', 'Type', 'Label', 'Status', 'Documents']);

        foreach ($indexes as $name => $index) {

            $status = $detektivo->isIndexerRunning($name) ? '<comment>Indexing</comment>' : '<info>Ready</info>';
            $docCount = $this->getDocumentCount($detektivo, $name);

            $table->addRow([
                $name,
                $index['type'] ?? 'unknown',
                $index['label'] ?? $name,
                $status,
                $docCount
            ]);
        }

        $table->render();

        $output->writeln('');
        $output->writeln('<comment>Tip:</comment> Use ./tower detektivo:status <name> for detailed info');
        $output->writeln('');

        return Command::SUCCESS;
    }

    protected function showIndexDetails(OutputInterface $output, $detektivo, string $name, array $index): void {

        $output->writeln('');
        $output->writeln("<info>Index:</info> {$name}");
        $output->writeln(str_repeat('-', 40));

        // Basic info
        $output->writeln("<comment>Label:</comment>    " . ($index['label'] ?? $name));
        $output->writeln("<comment>Type:</comment>     " . ($index['type'] ?? 'unknown'));
        $output->writeln("<comment>Info:</comment>     " . ($index['info'] ?? '-'));
        $output->writeln("<comment>Group:</comment>    " . ($index['group'] ?? '-'));
        $output->writeln("<comment>Created:</comment>  " . (isset($index['_created']) ? date('Y-m-d H:i:s', $index['_created']) : '-'));

        // Status
        $isRunning = $detektivo->isIndexerRunning($name);
        $status = $isRunning ? '<comment>Indexing in progress</comment>' : '<info>Ready</info>';
        $output->writeln("<comment>Status:</comment>   {$status}");

        // Document count
        $docCount = $this->getDocumentCount($detektivo, $name);
        $output->writeln("<comment>Documents:</comment> {$docCount}");

        // Fields
        if (!empty($index['fields'])) {
            $output->writeln('');
            $output->writeln('<info>Indexed Fields:</info>');
            foreach ($index['fields'] as $field) {
                $fieldName = is_array($field) ? ($field['name'] ?? json_encode($field)) : $field;
                $output->writeln("  - {$fieldName}");
            }
        }

        // Meta configuration
        if (!empty($index['meta'])) {
            $output->writeln('');
            $output->writeln('<info>Configuration:</info>');
            foreach ($index['meta'] as $key => $value) {
                if (is_scalar($value)) {
                    $output->writeln("  {$key}: {$value}");
                } else {
                    $output->writeln("  {$key}: " . json_encode($value));
                }
            }
        }

        // Indexer log (if running)
        if ($isRunning) {
            $log = $detektivo->getIndexerLog($name);
            if (!empty($log)) {
                $output->writeln('');
                $output->writeln('<info>Recent Log:</info>');
                $recentLogs = array_slice($log, -5);
                foreach ($recentLogs as $entry) {
                    $time = isset($entry['time']) ? date('H:i:s', $entry['time']) : '';
                    $msg = $entry['msg'] ?? '';
                    $type = $entry['type'] ?? 'info';
                    $output->writeln("  [{$time}] {$msg}");
                }
            }
        }

        $output->writeln('');
    }

    protected function getDocumentCount($detektivo, string $name): string {

        try {
            $idx = $detektivo->index($name);
            if ($idx && method_exists($idx, 'count')) {
                return (string) $idx->count();
            }
            if ($idx && method_exists($idx, 'search')) {
                $result = $idx->search('*', ['limit' => 0]);
                if (isset($result['estimatedTotalHits'])) {
                    return (string) $result['estimatedTotalHits'];
                }
                if (isset($result['totalHits'])) {
                    return (string) $result['totalHits'];
                }
            }
        } catch (\Throwable $e) {
            return '<error>error</error>';
        }

        return '-';
    }
}
