<?php

declare(strict_types=1);

/*
 * This file is part of the Ferienpass package.
 *
 * (c) Richard Henkenjohann <richard@ferienpass.online>
 *
 * For more information visit the project website <https://ferienpass.online>
 * or the documentation under <https://docs.ferienpass.online>.
 */

namespace Ferienpass\CmsBundle\Controller\Frontend;

use Contao\CoreBundle\Exception\PageNotFoundException;
use Ferienpass\CmsBundle\Controller\Page\EditionLandingController;
use Ferienpass\CoreBundle\Entity\Edition;
use Ferienpass\CoreBundle\Repository\OfferRepositoryInterface;
use Ferienpass\CoreBundle\Service\OfferPrivateLinkService;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\RedirectResponse;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\Routing\Attribute\Route;
use Symfony\Component\Uid\Uuid;

#[Route(path: '/p/{uuid}-{sig}', name: 'cms_offer_private_link', requirements: ['uuid' => '[1-9A-HJ-NP-Za-km-z]{22}', 'sig' => '[A-Za-z0-9_-]{1,32}'])]
class PrivateLinkController extends AbstractController
{
    public function __invoke(string $uuid, string $sig, OfferRepositoryInterface $offers, OfferPrivateLinkService $privateLinks): Response
    {
        try {
            $offerUuid = Uuid::fromBase58($uuid);
        } catch (\InvalidArgumentException) {
            throw new PageNotFoundException();
        }

        $offer = $offers->findByUuid($offerUuid);
        if (null === $offer || !$offer->getEdition() instanceof Edition || !$privateLinks->isValidSignature($offer, $sig)) {
            throw new PageNotFoundException();
        }

        [$route, $params] = EditionLandingController::offerRouteAndParams($offer);
        $params['k'] = $sig;

        return new RedirectResponse($this->generateUrl($route, $params), Response::HTTP_MOVED_PERMANENTLY);
    }
}
