<?php

declare(strict_types=1);

/*
 * Chill is a software for social workers
 *
 * For the full copyright and license information, please view
 * the LICENSE file that was distributed with this source code.
 */

namespace Chill\TaskBundle\Event\Lifecycle;

use Chill\TaskBundle\Entity\Task\SingleTaskPlaceEvent;
use Chill\TaskBundle\Event\TaskEvent;
use Doctrine\ORM\EntityManagerInterface;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
use Symfony\Component\Security\Core\Authentication\Token\Storage\TokenStorageInterface;
use Symfony\Component\Workflow\Event\Event as WorkflowEvent;

class TaskLifecycleEvent implements EventSubscriberInterface
{
    /**
     * @var EntityManagerInterface
     */
    protected $em;

    /**
     * @var TokenStorageInterface
     */
    protected $tokenStorage;

    public function __construct(
        TokenStorageInterface $tokenStorage,
        EntityManagerInterface $em,
    ) {
        $this->tokenStorage = $tokenStorage;
        $this->em = $em;
    }

    public static function getSubscribedEvents(): array
    {
        return [
            TaskEvent::PERSIST => [
                'onTaskPersist',
            ],
        ];
    }

    public function onTaskPersist(TaskEvent $e)
    {
        $task = $e->getTask();
        $user = $this->tokenStorage->getToken()->getUser();

        $event = (new SingleTaskPlaceEvent())
            ->setTask($task)
            ->setAuthor($user)
            ->setTransition('_creation')
            ->setData([
                'new_states' => $task->getCurrentStates(),
            ]);

        $task->getTaskPlaceEvents()->add($event);

        $this->em->persist($event);
    }

    public function onTransition(WorkflowEvent $e)
    {
        $task = $e->getSubject();
        $user = $this->tokenStorage->getToken()->getUser();

        $event = (new SingleTaskPlaceEvent())
            ->setTask($task)
            ->setAuthor($user)
            ->setTransition($e->getTransition()->getName())
            ->setData([
                'old_states' => $e->getTransition()->getFroms(),
                'new_states' => $e->getTransition()->getTos(),
                'workflow' => $e->getWorkflowName(),
            ]);

        $task->getTaskPlaceEvents()->add($event);

        $this->em->persist($event);
    }
}
