<?php

declare(strict_types=1);

namespace App\Service;

use App\Entity\Image;
use App\Entity\Token;
use App\Entity\User;
use App\Enum\TokenType;
use App\Repository\TokenRepository;
use Doctrine\ORM\EntityManagerInterface;

class TokenService
{
    public function __construct(
        private readonly TokenRepository        $tokenRepository,
        private readonly EntityManagerInterface $em,
    ) {}

    public function issue(
        TokenType $type,
        Image     $image,
        ?User     $recipient,
        ?string   $recipientEmail,
        int       $ttlDays,
    ): Token {
        $token = new Token($type, $image, $recipient, $recipientEmail, $ttlDays);
        $this->em->persist($token);
        return $token;
    }

    /** @throws \RuntimeException if token is not found, already used, or expired */
    public function consume(string $uuid, TokenType $type): Token
    {
        $token = $this->tokenRepository->findValidToken($uuid, $type);
        if (!$token) {
            throw new \RuntimeException('Token not found, already used, or expired.');
        }
        $token->consume();
        $this->em->flush();
        return $token;
    }

    /** Returns a valid token without consuming it, or null. */
    public function findValid(string $uuid, TokenType $type): ?Token
    {
        return $this->tokenRepository->findValidToken($uuid, $type);
    }
}
