<?php

namespace App\Security;

use App\Entity\Product;
use App\Repository\FormulesRepository;
use App\Repository\OptionsRepository;
use App\Repository\ProductRepository;
use Doctrine\ORM\EntityManagerInterface;
use Presta\SitemapBundle\Event\SitemapPopulateEvent;
use Presta\SitemapBundle\Sitemap\Url\GoogleImage;
use Presta\SitemapBundle\Sitemap\Url\GoogleImageUrlDecorator;
use Presta\SitemapBundle\Sitemap\Url\GoogleVideo;
use Presta\SitemapBundle\Sitemap\Url\GoogleVideoUrlDecorator;
use Presta\SitemapBundle\Sitemap\Url\UrlConcrete;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\Routing\Generator\UrlGeneratorInterface;
use Vich\UploaderBundle\Templating\Helper\UploaderHelper;

class SiteMapListener implements EventSubscriberInterface
{
    public function __construct(
        private readonly UploaderHelper $uploaderHelper,
        private readonly OptionsRepository $optionsRepository,
        private readonly ProductRepository $productRepository,
        private readonly FormulesRepository $formulesRepository,
        private readonly EntityManagerInterface $entityManager
    ) {
    }

    public static function getSubscribedEvents(): array
    {
        return [
            SitemapPopulateEvent::class => 'populate',
        ];
    }

    public function populate(SitemapPopulateEvent $event): void
    {
        $urlGenerator = $event->getUrlGenerator();
        $urlContainer = $event->getUrlContainer();

        // Base URL pour les médias
        $baseUrl = $urlGenerator->generate('reservation', [], UrlGeneratorInterface::ABSOLUTE_URL);
        $rootUrl = rtrim($baseUrl, '/');

        $t = new \DateTime();

        // --- 1. PAGES STATIQUES & VIDÉO ---
        $reservationUrl = $urlGenerator->generate('reservation', [], UrlGeneratorInterface::ABSOLUTE_URL);
        $homeUrl = new UrlConcrete($reservationUrl, $t, UrlConcrete::CHANGEFREQ_DAILY, 1);

        // Décorateur Vidéo pour la page d'accueil
        $videoUrl = $rootUrl . '/provider/video/video.mp4';
        $videoTrumbs = $rootUrl . '/provider/video/video.jpg';
        $homeWithVideo = new GoogleVideoUrlDecorator($homeUrl);

        $video = new GoogleVideo(
            $videoTrumbs,
            "Découvrez nos produits en vidéo",
            "Découvrez nos produits en vidéo",
            ['content_location' => $videoUrl]
        );
        $homeWithVideo->addVideo($video);
        $urlContainer->addUrl($homeWithVideo, 'reservation');


        $catUrl = new UrlConcrete("https://reservation.ludikevent.fr", $t, UrlConcrete::CHANGEFREQ_DAILY, 0.7);
        $homeWithVideo = new GoogleVideoUrlDecorator($catUrl);
        $video = new GoogleVideo(
            $videoTrumbs,
            "Découvrez nos produits en vidéo",
            "Découvrez nos produits en vidéo",
            ['content_location' => $videoUrl]
        );
        $homeWithVideo->addVideo($video);
        $urlContainer->addUrl($homeWithVideo, 'reservation');

        // Autres routes statiques
        $staticRoutes = [
            'reservation_contact' => UrlConcrete::CHANGEFREQ_DAILY,
            'reservation_cookies' => UrlConcrete::CHANGEFREQ_WEEKLY,
            'reservation_mentions-legal' => UrlConcrete::CHANGEFREQ_WEEKLY,
            'reservation_rgpd' => UrlConcrete::CHANGEFREQ_WEEKLY,
            'reservation_hosting' => UrlConcrete::CHANGEFREQ_WEEKLY,
            'reservation_cgv' => UrlConcrete::CHANGEFREQ_WEEKLY,
        ];

        foreach ($staticRoutes as $route => $freq) {
            $url = $urlGenerator->generate($route, [], UrlGeneratorInterface::ABSOLUTE_URL);
            $urlContainer->addUrl(new UrlConcrete($url, $t, $freq, 0.5), 'reservation');
        }

        $reservationUrl = $urlGenerator->generate('reservation_catalogue', [], UrlGeneratorInterface::ABSOLUTE_URL);
        $catUrl = new UrlConcrete($reservationUrl, $t, UrlConcrete::CHANGEFREQ_DAILY, 0.7);
        $urlContainer->addUrl($catUrl, 'reservation');

        $reservationUrl = $urlGenerator->generate('reservation_formules', [], UrlGeneratorInterface::ABSOLUTE_URL);
        $catUrl = new UrlConcrete($reservationUrl, $t, UrlConcrete::CHANGEFREQ_DAILY, 0.7);
        $urlContainer->addUrl($catUrl, 'reservation');

        $reservationUrl = $urlGenerator->generate('reservation_login', [], UrlGeneratorInterface::ABSOLUTE_URL);
        $catUrl = new UrlConcrete($reservationUrl, $t, UrlConcrete::CHANGEFREQ_DAILY, 0.7);
        $urlContainer->addUrl($catUrl, 'reservation');



        foreach ($this->formulesRepository->findBy(['isPublish'=>true]) as $formule) {
            $formulesUrls = $urlGenerator->generate(
                'reservation_formule_show',
                ['slug' => $formule->slug()],
                UrlGeneratorInterface::ABSOLUTE_URL
            );
            $decoratedUrl = new GoogleImageUrlDecorator(
                new UrlConcrete($formulesUrls, $formule->getUpdatedAt(), UrlConcrete::CHANGEFREQ_WEEKLY, 0.5)
            );
            $imagePath = $this->uploaderHelper->asset($formule, 'imageFile');

            if ($imagePath) {
                $usedList = [];
                // Appel de votre fonction avec l'objet product
                $this->addImageToSitemap($decoratedUrl, $usedList, $rootUrl, $imagePath, $formule);
            }

            $urlContainer->addUrl($decoratedUrl, 'reservation_formules');
        }
        // --- 2. PRODUITS & IMAGES ---
        foreach ($this->productRepository->findBy(['isPublish' => true]) as $product) {
            $productUrl = $urlGenerator->generate(
                'reservation_product_show',
                ['id' => $product->slug()],
                UrlGeneratorInterface::ABSOLUTE_URL
            );

            $decoratedUrl = new GoogleImageUrlDecorator(
                new UrlConcrete($productUrl, $product->getUpdatedAt(), UrlConcrete::CHANGEFREQ_WEEKLY, 0.5)
            );

            $imagePath = $this->uploaderHelper->asset($product, 'imageFile');

            if ($imagePath) {
                $usedList = [];
                // Appel de votre fonction avec l'objet product
                $this->addImageToSitemap($decoratedUrl, $usedList, $rootUrl, $imagePath, $product);
            }

            $urlContainer->addUrl($decoratedUrl, 'reservation_product');
        }
        foreach ($this->optionsRepository->findBy(['isPublish' => true]) as $product) {
            $productUrl = $urlGenerator->generate(
                'reservation_options_show',
                ['id' => $product->slug()],
                UrlGeneratorInterface::ABSOLUTE_URL
            );

            $decoratedUrl = new GoogleImageUrlDecorator(
                new UrlConcrete($productUrl, $product->getUpdatedAt(), UrlConcrete::CHANGEFREQ_WEEKLY, 0.5)
            );

            $imagePath = $this->uploaderHelper->asset($product, 'imageFile');

            if ($imagePath) {
                $usedList = [];
                // Appel de votre fonction avec l'objet product
                $this->addImageToSitemap($decoratedUrl, $usedList, $rootUrl, $imagePath, $product);
            }

            $urlContainer->addUrl($decoratedUrl, 'reservation_options');
        }
    }

    /**
     * Votre fonction personnalisée avec gestion Base64 et Titre dynamique
     */
    private function addImageToSitemap(GoogleImageUrlDecorator $pathMenu, array &$usedList, string $rootUrl, string $image, object $object): void
    {
        // 1. Ignorer les images en base64
        if (str_starts_with($image, 'data:image/')) {
            return;
        }

        // 2. Éviter les doublons
        if (!isset($usedList[$image])) {
            $imageUrl = str_starts_with($image, 'http') ? $image : $rootUrl . $image;
            $gImage = new GoogleImage($imageUrl);

            if ($object instanceof Product) {
                // Utilisation du nom de l'objet pour le SEO de l'image
                $gImage->setTitle("Image du produit - " . $object->getName());
            }

            $pathMenu->addImage($gImage);
            $usedList[$image] = 1;
        }
    }
}
