<?php

namespace DMD\LaLigaApi\Service\Season\createSeason;

use DMD\LaLigaApi\Dto\SeasonDto;
use DMD\LaLigaApi\Dto\TeamDto;
use DMD\LaLigaApi\Entity\Season;
use DMD\LaLigaApi\Entity\Team;
use DMD\LaLigaApi\Exception\ValidationException;
use DMD\LaLigaApi\Repository\LeagueRepository;
use DMD\LaLigaApi\Repository\SeasonRepository;
use DMD\LaLigaApi\Service\Common\AuthorizeRequest;
use DMD\LaLigaApi\Service\Common\TeamFactory;
use DMD\LaLigaApi\Service\Season\SeasonFactory;
use Doctrine\ORM\EntityManagerInterface;
use Symfony\Component\HttpFoundation\JsonResponse;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpKernel\Exception\HttpException;

class HandleCreateSeason
{
    public function __construct(
        public SeasonFactory          $seasonFactory,
        public TeamFactory          $teamFactory,
        public AuthorizeRequest       $authorizeRequest,
        public LeagueRepository       $leagueRepository,
        public SeasonRepository       $seasonRepository,
        public EntityManagerInterface $entityManager,
    ){}

    /**
     * @throws ValidationException
     */
    public function __invoke(Request $request, int $leagueId): JsonResponse
    {
        $this->authorizeRequest->authorizeLeaguePresident($leagueId);
        $leagueEntity = $this->leagueRepository->find($leagueId);
        if (is_null($leagueEntity))
        {
            throw new HttpException(Response::HTTP_NOT_FOUND, 'League not found');
        }
        $seasonCount = $this->seasonRepository->count([
            'league' => $leagueId
        ]);
        $seasonDto = new SeasonDto();
        $seasonDto->seasonNumber = $seasonCount + 1;
        $seasonDto->leagueId = $leagueEntity->getId();
        $seasonDto->leagueName = $leagueEntity->getName();
        $seasonDto->fillFromArray($request->toArray());
        $seasonDto->validate();

        $numberOfTeams = $request->toArray()['numberOfTeams'];
        $seasonEntity = $this->seasonFactory::create($seasonDto);
        $seasonEntity->setLeague($leagueEntity);

        if (!empty($numberOfTeams))
        {
            $this->createTeams($numberOfTeams, $seasonEntity);
        }

        $this->entityManager->persist($seasonEntity);
        $this->entityManager->flush();

        $seasonDto->id = $seasonEntity->getId();
        return new JsonResponse(
            data: [
                'success' => true,
                'season' => $seasonDto->createSeasonArray()
            ],
            status: Response::HTTP_OK
        );
    }

    private function createTeams(int $numberOfTeams, Season $seasonEntity): void
    {
        if (!empty($numberOfTeams))
        {
            for ($i = 0; $i < $numberOfTeams; $i++)
            {
                $teamEntity = new Team();
                $teamEntity->addSeason($seasonEntity);
                $teamEntity->setName('Equipo '. $i+1);
                $this->entityManager->persist($teamEntity);
            }
        }
    }
}