<?php

declare(strict_types=1);

namespace App\Module\ProjectManagement\Infrastructure\Mcp\Tool\Task;

use App\Module\ProjectManagement\Domain\Entity\TaskRecurrence;
use App\Module\ProjectManagement\Domain\Enum\RecurrenceType;
use App\Module\ProjectManagement\Domain\Repository\TaskRepositoryInterface;
use App\Module\ProjectManagement\Infrastructure\Service\CalDavService;
use DateTimeImmutable;
use Doctrine\ORM\EntityManagerInterface;
use InvalidArgumentException;
use Mcp\Capability\Attribute\McpTool;
use Symfony\Bundle\SecurityBundle\Security;
use Symfony\Component\Security\Core\Exception\AccessDeniedException;

use function sprintf;

#[McpTool(name: 'create-task-recurrence', description: 'Create a recurrence pattern for a task. Type: daily, weekly, monthly, yearly. For weekly, provide daysOfWeek array (e.g. ["monday","wednesday"]). For monthly, provide dayOfMonth OR weekOfMonth.')]
class CreateTaskRecurrenceTool
{
    public function __construct(
        private readonly EntityManagerInterface $entityManager,
        private readonly TaskRepositoryInterface $taskRepository,
        private readonly Security $security,
        private readonly CalDavService $calDavService,
    ) {}

    public function __invoke(
        int $taskId,
        string $type,
        int $interval = 1,
        ?array $daysOfWeek = null,
        ?int $dayOfMonth = null,
        ?int $weekOfMonth = null,
        ?string $endDate = null,
        ?int $maxOccurrences = null,
    ): string {
        if (!$this->security->isGranted('ROLE_USER')) {
            throw new AccessDeniedException('Access denied: ROLE_USER required.');
        }

        $task = $this->taskRepository->findById($taskId);
        if (null === $task) {
            throw new InvalidArgumentException(sprintf('Task with ID %d not found.', $taskId));
        }

        $recurrenceType = RecurrenceType::from($type);

        $recurrence = new TaskRecurrence();
        $recurrence->setType($recurrenceType);
        $recurrence->setInterval($interval);

        if (null !== $daysOfWeek) {
            $recurrence->setDaysOfWeek($daysOfWeek);
        }
        if (null !== $dayOfMonth) {
            $recurrence->setDayOfMonth($dayOfMonth);
        }
        if (null !== $weekOfMonth) {
            $recurrence->setWeekOfMonth($weekOfMonth);
        }
        if (null !== $endDate) {
            $recurrence->setEndDate(new DateTimeImmutable($endDate));
        }
        if (null !== $maxOccurrences) {
            $recurrence->setMaxOccurrences($maxOccurrences);
        }

        $task->setRecurrence($recurrence);
        $this->entityManager->persist($recurrence);
        $this->entityManager->flush();

        $this->calDavService->syncTask($task);
        $this->entityManager->flush();

        return json_encode([
            'id'             => $recurrence->getId(),
            'type'           => $recurrence->getType()?->value,
            'interval'       => $recurrence->getInterval(),
            'daysOfWeek'     => $recurrence->getDaysOfWeek(),
            'dayOfMonth'     => $recurrence->getDayOfMonth(),
            'weekOfMonth'    => $recurrence->getWeekOfMonth(),
            'endDate'        => $recurrence->getEndDate()?->format('Y-m-d'),
            'maxOccurrences' => $recurrence->getMaxOccurrences(),
            'taskId'         => $task->getId(),
        ]);
    }
}
