<?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\DocStoreBundle\Tests\Controller;

use Chill\DocStoreBundle\Controller\StoredObjectVersionApiController;
use Chill\DocStoreBundle\Entity\StoredObject;
use Chill\DocStoreBundle\Security\Authorization\StoredObjectRoleEnum;
use Chill\DocStoreBundle\Serializer\Normalizer\StoredObjectVersionNormalizer;
use Chill\MainBundle\Pagination\Paginator;
use Chill\MainBundle\Pagination\PaginatorFactoryInterface;
use Chill\MainBundle\Serializer\Normalizer\CollectionNormalizer;
use Prophecy\Argument;
use Prophecy\PhpUnit\ProphecyTrait;
use Symfony\Component\Security\Core\Security;
use Symfony\Component\Serializer\Encoder\JsonEncoder;
use Symfony\Component\Serializer\Serializer;

/**
 * @internal
 *
 * @coversNothing
 */
class StoredObjectVersionApiControllerTest extends \PHPUnit\Framework\TestCase
{
    use ProphecyTrait;

    public function testListVersion(): void
    {
        $storedObject = new StoredObject();
        for ($i = 0; $i < 15; ++$i) {
            $storedObject->registerVersion();
        }

        // remove one version in the history
        $v5 = $storedObject->getVersions()->get(5);
        $storedObject->removeVersion($v5);

        $security = $this->prophesize(Security::class);
        $security->isGranted(StoredObjectRoleEnum::SEE->value, $storedObject)
            ->willReturn(true)
            ->shouldBeCalledOnce();

        $controller = $this->buildController($security->reveal());

        $response = $controller->listVersions($storedObject);
        $body = json_decode($response->getContent(), true, 512, JSON_THROW_ON_ERROR);

        self::assertEquals($response->getStatusCode(), 200);
        self::assertIsArray($body);
        self::assertArrayHasKey('results', $body);
        self::assertIsList($body['results']);
        self::assertCount(10, $body['results']);
    }

    private function buildController(Security $security): StoredObjectVersionApiController
    {
        $paginator = $this->prophesize(Paginator::class);
        $paginator->getCurrentPageFirstItemNumber()->willReturn(0);
        $paginator->getItemsPerPage()->willReturn(10);
        $paginator->getTotalItems()->willReturn(15);
        $paginator->hasNextPage()->willReturn(false);
        $paginator->hasPreviousPage()->willReturn(false);

        $paginatorFactory = $this->prophesize(PaginatorFactoryInterface::class);
        $paginatorFactory->create(Argument::type('int'))->willReturn($paginator);

        $serializer = new Serializer([
            new StoredObjectVersionNormalizer(), new CollectionNormalizer(),
        ], [new JsonEncoder()]);

        return new StoredObjectVersionApiController($paginatorFactory->reveal(), $serializer, $security);
    }
}
