<?php

namespace App\Tests\Feature\Manga;

use App\Entity\Chapter;
use App\Entity\Manga;
use App\Tests\Feature\AbstractApiTestCase;
use Zenstruck\Foundry\Test\ResetDatabase;

class GetMangaChaptersTest extends AbstractApiTestCase
{
    use ResetDatabase;

    public function testGetChaptersOfNonExistentManga(): void
    {
        // When
        $client = static::createClient();
        $response = $client->request('GET', '/api/mangas/999/chapters');

        // Then
        $this->assertResponseStatusCodeSame(404);
    }

    public function testGetEmptyChapterList(): void
    {
        // Given
        $manga = $this->createManga();

        // When
        $client = static::createClient();
        $response = $client->request('GET', '/api/mangas/' . $manga->getId() . '/chapters');

        // Then
        $this->assertResponseIsSuccessful();
        $this->assertJsonContains([
            'total' => 0,
            'page' => 1,
            'limit' => 20,
            'hasNextPage' => false,
            'hasPreviousPage' => false,
            'items' => []
        ]);
    }

    public function testGetChaptersWithPagination(): void
    {
        // Given
        $manga = $this->createManga();
        $this->createChapters($manga, 25);

        // When
        $client = static::createClient();
        $response = $client->request('GET', '/api/mangas/' . $manga->getId() . '/chapters', [
            'query' => [
                'page' => 2,
                'limit' => 10,
                'sortOrder' => 'desc'
            ]
        ]);

        // Then
        $this->assertResponseIsSuccessful();
        $data = $response->toArray();
        
        $this->assertCount(10, $data['items']);
        $this->assertEquals(25, $data['total']);
        $this->assertEquals(2, $data['page']);
        $this->assertEquals(10, $data['limit']);
        $this->assertTrue($data['hasNextPage']);
        $this->assertTrue($data['hasPreviousPage']);

        $numbers = array_map(fn($item) => $item['number'], $data['items']);

        $expectedNumbers = $numbers;
        rsort($expectedNumbers);
        $this->assertEquals($expectedNumbers, $numbers);
    }

    private function createManga(): Manga
    {
        $manga = new Manga();
        $manga->setTitle('One Piece')
            ->setSlug('one-piece')
            ->setDescription('Test description')
            ->setAuthor('Eiichiro Oda')
            ->setPublicationYear(1997)
            ->setGenres(['action', 'adventure'])
            ->setStatus('ongoing')
            ->setMonitored(true);

        $entityManager = static::getContainer()->get('doctrine')->getManager();
        $entityManager->persist($manga);
        $entityManager->flush();

        return $manga;
    }

    private function createChapters(Manga $manga, int $count): void
    {
        $entityManager = static::getContainer()->get('doctrine')->getManager();

        for ($i = 1; $i <= $count; $i++) {
            $chapter = new Chapter();
            $chapter->setManga($manga)
                ->setNumber($i)
                ->setTitle("Chapter $i")
                ->setVolume((int)ceil($i / 10))
                ->setVisible(true);

            $entityManager->persist($chapter);
        }

        $entityManager->flush();
    }
} 