<?php

namespace NoahVet\Reef\Test\A_Unit\Infrastructure\Serialization\Json;

use NoahVet\Reef\Infrastructure\Serialization\Json\JsonSerializerFacade;
use NoahVet\Reef\Infrastructure\Serialization\Json\JsonSerializerFactory;
use PHPUnit\Framework\TestCase;

class JsonSerializerFacadeTest extends TestCase
{
    private JsonSerializerFacade $subject;

    protected function setUp(): void
    {
        $this->subject = new JsonSerializerFacade(new JsonSerializerFactory());
    }

    public function testNormalize(): void
    {
        $object = new \stdClass();

        $result = $this->subject->normalize(data: $object);

        $this->assertIsArray($result);
    }

    public function testDeserialize(): void
    {
        $result = $this->subject->deserialize(
            data: '{"name":"test"}',
            type: \stdClass::class,
        );

        $this->assertInstanceOf(\stdClass::class, $result);
    }

    public function testDenormalizeWithDefaults(): void
    {
        $result = $this->subject->denormalize(
            data: ['name' => 'test'],
            type: \stdClass::class,
        );

        $this->assertInstanceOf(\stdClass::class, $result);
    }

    public function testDenormalizeWithIgnoredAttributes(): void
    {
        $result = $this->subject->denormalize(
            data: ['name' => 'test'],
            type: \stdClass::class,
            ignoredAttributes: ['name'],
        );

        $this->assertInstanceOf(\stdClass::class, $result);
    }

    public function testDenormalizeWithObjectToPopulate(): void
    {
        $existing = new SerializerEntityFixture();
        $existing->name = 'original';
        $existing->code = 'preserved';

        $result = $this->subject->denormalize(
            data: ['name' => 'overridden'],
            type: SerializerEntityFixture::class,
            objectToPopulate: $existing,
        );

        $this->assertSame($existing, $result);
        $this->assertSame('overridden', $existing->name);
        $this->assertSame('preserved', $existing->code);
    }
}

class SerializerEntityFixture
{
    public string $name = '';

    public string $code = '';
}
