<?php

namespace Lc\SovBundle\Builder\Ticket;

use Doctrine\ORM\EntityManagerInterface;
use Lc\CaracoleBundle\Notification\MailMailjetNotification;
use Lc\SovBundle\Component\FormComponent;
use Lc\SovBundle\Factory\Ticket\TicketFactory;
use Lc\SovBundle\Model\Ticket\TicketInterface;
use Lc\SovBundle\Model\Ticket\TicketModel;
use Lc\SovBundle\Repository\User\UserStore;
use Symfony\Component\DependencyInjection\ParameterBag\ParameterBagInterface;
use Symfony\Component\Security\Core\Authorization\AuthorizationCheckerInterface;
use Symfony\Component\Security\Core\Security;

class TicketBuilder
{
    protected Security $security;
    protected EntityManagerInterface $entityManager;
    protected MailMailjetNotification $mailMailjetNotification;
    protected FormComponent $formComponent;
    protected ParameterBagInterface $parameterBag;
    protected TicketFactory $ticketFactory;
    protected AuthorizationCheckerInterface $authorizationChecker;
    protected UserStore $userStore;

    public function __construct(
            Security $security,
            EntityManagerInterface $entityManager,
            MailMailjetNotification $mailMailjetNotification,
            FormComponent $formComponent,
            ParameterBagInterface $parameterBag,
            AuthorizationCheckerInterface $authorizationChecker,
            TicketFactory $ticketFactory,
            UserStore $userStore
    ) {
        $this->security = $security;
        $this->entityManager = $entityManager;
        $this->mailMailjetNotification = $mailMailjetNotification;
        $this->formComponent = $formComponent;
        $this->parameterBag = $parameterBag;
        $this->ticketFactory = $ticketFactory;
        $this->userStore = $userStore;
        $this->authorizationChecker = $authorizationChecker;
    }

    public function create(array $params = []): TicketInterface
    {
        $ticket = $this->ticketFactory->create();

        $this->init($ticket, $params);

        $user = $ticket->getUser();
        if ($ticket->getUser()) {
            $email = $user->getEmail();
            $firstname = $user->getFirstname();
        } else {
            $email = $params['visitorEmail'];
            $firstname = $params['visitorFirstname'];
        }

        $this->entityManager->create($ticket);
        $this->entityManager->flush();

        if (isset($params['createByAdmin']) && $params['createByAdmin']) {
            // envoi email au client
            $this->mailMailjetNotification->send(
                    [
                            MailMailjetNotification::SUBJECT => 'Vous avez reçu un nouveau message',
                            MailMailjetNotification::TO_EMAIL => $email,
                            MailMailjetNotification::CONTENT_TEMPLATE => 'mail/ticket-new-by-admin',
                            MailMailjetNotification::CONTENT_DATA => [
                                    'firstname' => $firstname,
                                    'ticket' => $ticket,
                            ],
                    ]
            );
        } else {
            $this->mailMailjetNotification->send(
                    [
                            MailMailjetNotification::SUBJECT => 'Nouvelle demande',
                            MailMailjetNotification::TO_EMAIL => $email,
                            MailMailjetNotification::CONTENT_TEMPLATE => 'mail/ticket-new',
                            MailMailjetNotification::CONTENT_DATA => [
                                    'firstname' => $firstname,
                                    'ticket' => $ticket,
                            ],
                    ]
            );
        }

        // notifyAdmin
        $usersToNotify = $this->userStore->getByTicketTypesNotification($ticket->getType());

        foreach ($usersToNotify as $userToNotify) {
            if ($this->authorizationChecker->isGranted('ROLE_ADMIN', $userToNotify)) {
                $this->mailMailjetNotification->send(
                        [
                                MailMailjetNotification::SUBJECT => 'Nouveau ticket sur Place du Local',
                                MailMailjetNotification::TO_EMAIL => $userToNotify->getEmail(),
                                MailMailjetNotification::CONTENT_TEMPLATE => 'mail/ticket-notification',
                                MailMailjetNotification::CONTENT_DATA => [
                                        'firstname' => $userToNotify->getFirstname(),
                                        'ticket' => $ticket,
                                        'ticketMessage' => $ticket->getTicketMessages()[0],
                                ],
                        ]
                );
            }
        }

        return $ticket;
    }

    public function init(TicketInterface $ticket, array $params = []): void
    {
        $user = $this->security->getUser();
        if($user) {
            $ticket->setCreatedBy($user);
        }

        if (isset($params['user'])) {
            $ticket->setUser($params['user']);

        } else {
            $ticket->setVisitorFirstname($params['visitorFirstname']);
            $ticket->setVisitorLastname($params['visitorLastname']);
            $ticket->setVisitorEmail($params['visitorEmail']);
            $ticket->setVisitorToken(uniqid());
        }

        $ticket
                ->setStatus(TicketModel::TICKET_STATUS_OPEN)
                ->setType($params['type'])
                ->setSubject($params['subject']);

        $ticketMessageArray = $ticket->getTicketMessages();
        $ticketMessage = $ticketMessageArray[0];
        $ticketMessage->setMessage($params['message']);

        if (isset($params['imageFilename']) && $params['imageFilename']) {
            $ticketMessage->setImageFilename($params['imageFilename']);
        }

        if (isset($params['createByAdmin']) && $params['createByAdmin']) {
            $ticketMessage->setAnswerByAdmin(true);
        }
    }

    // uploadImageTicketMessage
    public function uploadImageTicketMessage($formTicket): ?string
    {
        return $this->formComponent->uploadFile(
                $formTicket,
                'image',
                $this->parameterBag->get('app.ticket_images_directory'),
                $this->parameterBag->get('app.ticket_images_subdirectory')
        );
    }
}
