<?php

namespace App\Command;

use Symfony\Component\Console\Attribute\AsCommand;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
use Symfony\Component\Console\Style\SymfonyStyle;
use Symfony\Component\Filesystem\Filesystem;
use Symfony\Component\HttpKernel\KernelInterface;

#[AsCommand(
    name: 'app:process-communes',
    description: 'Processes communes-france-avec-polygon-2025.json to create a simplified JSON file.',
)]
class ProcessCommunesCommand extends Command
{
    private string $projectDir;

    public function __construct(KernelInterface $kernel)
    {
        parent::__construct();
        $this->projectDir = $kernel->getProjectDir();
    }

    protected function execute(InputInterface $input, OutputInterface $output): int
    {
        $io = new SymfonyStyle($input, $output);
        $filesystem = new Filesystem();

        $inputFilePath = $this->projectDir . '/public/communes-france-avec-polygon-2025.json';
        $outputFilePath = $this->projectDir . '/public/simplified_communes_by_zip.json'; // New output file name

        if (!$filesystem->exists($inputFilePath)) {
            $io->error(sprintf('Input file not found: %s', $inputFilePath));
            return Command::FAILURE;
        }

        $io->info(sprintf('Reading input file: %s', $inputFilePath));
        $fileContent = file_get_contents($inputFilePath);

        if ($fileContent === false) {
            $io->error(sprintf('Failed to read content from file: %s', $inputFilePath));
            return Command::FAILURE;
        }

        $decodedJson = json_decode($fileContent, true);

        if (json_last_error() !== JSON_ERROR_NONE) {
            $io->error(sprintf('Failed to decode JSON from file: %s. Error: %s', $inputFilePath, json_last_error_msg()));
            return Command::FAILURE;
        }

        if (!isset($decodedJson['data']) || !is_array($decodedJson['data'])) {
            $io->error('JSON structure invalid: "data" key not found or not an array.');
            return Command::FAILURE;
        }

        $simplifiedData = [];
        $processedCount = 0;

        $io->progressStart(count($decodedJson['data']));

        foreach ($decodedJson['data'] as $commune) {
            $io->progressAdvance();
            if (!isset($commune['codes_postaux']) || !isset($commune['nom_standard'])) {
                $io->warning(sprintf('Skipping commune due to missing "codes_postaux" or "nom_standard": %s', json_encode($commune)));
                continue;
            }

            $city = $commune['nom_standard'];
            $zipCodes = explode(',', $commune['codes_postaux']);

            foreach ($zipCodes as $zipCode) {
                $zipCode = trim($zipCode);
                if (!empty($zipCode)) {
                    if (!isset($simplifiedData[$zipCode])) {
                        $simplifiedData[$zipCode] = [];
                    }
                    if (!in_array($city, $simplifiedData[$zipCode])) {
                        $simplifiedData[$zipCode][] = $city;
                    }
                }
            }
            $processedCount++;
        }

        $io->progressFinish();
        $io->info(sprintf('Processed %d communes.', $processedCount));

        // Sort cities within each postal code array
        foreach ($simplifiedData as $zipCode => $cities) {
            sort($simplifiedData[$zipCode]);
        }
        // Optionally sort by zip code for consistent output
        ksort($simplifiedData);


        $outputJsonContent = json_encode($simplifiedData, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE);

        if ($outputJsonContent === false) {
            $io->error(sprintf('Failed to encode simplified data to JSON. Error: %s', json_last_error_msg()));
            return Command::FAILURE;
        }

        if ($filesystem->dumpFile($outputFilePath, $outputJsonContent) === false) {
            $io->error(sprintf('Failed to write simplified JSON to file: %s', $outputFilePath));
            return Command::FAILURE;
        }

        $io->success(sprintf('Simplified JSON file created successfully at: %s', $outputFilePath));

        return Command::SUCCESS;
    }
}
