<?php

declare(strict_types=1);

namespace TekDek\Employees\Tests;

use PDO;
use PHPUnit\Framework\TestCase;
use TekDek\Employees\EmployeeRepository;

/**
 * Tests for EmployeeRepository using SQLite in-memory.
 */
class EmployeeRepositoryTest extends TestCase
{
    private PDO $pdo;
    private EmployeeRepository $repo;

    protected function setUp(): void
    {
        $this->pdo = new PDO('sqlite::memory:');
        $this->pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
        $this->pdo->setAttribute(PDO::ATTR_DEFAULT_FETCH_MODE, PDO::FETCH_ASSOC);

        // Create table (SQLite-compatible schema)
        $this->pdo->exec("
            CREATE TABLE employees (
                id TEXT PRIMARY KEY,
                slug TEXT UNIQUE NOT NULL,
                name TEXT NOT NULL,
                title TEXT NOT NULL,
                role TEXT NOT NULL,
                tagline TEXT,
                bio TEXT NOT NULL,
                mythology TEXT NOT NULL,
                avatar_url TEXT,
                accent_color TEXT,
                symbol TEXT,
                skills TEXT,
                quote TEXT,
                sort_order INTEGER DEFAULT 0,
                created_at TEXT DEFAULT (datetime('now')),
                updated_at TEXT DEFAULT (datetime('now'))
            )
        ");

        $this->seedTestData();
        $this->repo = new EmployeeRepository($this->pdo);
    }

    private function seedTestData(): void
    {
        $employees = [
            [
                'id'           => 'uuid-daedalus',
                'slug'         => 'daedalus',
                'name'         => 'Daedalus',
                'title'        => 'Chief Architect',
                'role'         => 'Architecture & Systems Design',
                'tagline'      => 'The master builder.',
                'bio'          => 'Daedalus is the architectural mind behind TekDek.',
                'mythology'    => 'Named for the mythological master craftsman.',
                'avatar_url'   => null,
                'accent_color' => '#C4A24E',
                'symbol'       => 'labyrinth',
                'skills'       => '["System Architecture", "Database Design"]',
                'quote'        => 'A well-designed system is indistinguishable from inevitability.',
                'sort_order'   => 1,
            ],
            [
                'id'           => 'uuid-talos',
                'slug'         => 'talos',
                'name'         => 'Talos',
                'title'        => 'Lead Backend Engineer',
                'role'         => 'Backend Engineering & Implementation',
                'tagline'      => 'The bronze guardian.',
                'bio'          => 'Talos is the engine room of TekDek.',
                'mythology'    => 'Named for the giant bronze automaton.',
                'avatar_url'   => null,
                'accent_color' => '#7B8794',
                'symbol'       => 'gear',
                'skills'       => '["PHP", "MySQL", "REST APIs"]',
                'quote'        => 'If it compiles but can\'t survive production, it doesn\'t exist.',
                'sort_order'   => 2,
            ],
            [
                'id'           => 'uuid-icarus',
                'slug'         => 'icarus',
                'name'         => 'Icarus',
                'title'        => 'Lead Frontend Engineer',
                'role'         => 'Frontend & UI Design',
                'tagline'      => 'Flying close to the sun.',
                'bio'          => 'Icarus is the face of TekDek.',
                'mythology'    => 'Named for the son of Daedalus.',
                'avatar_url'   => null,
                'accent_color' => '#E07A2F',
                'symbol'       => 'wings',
                'skills'       => '["UI/UX Design", "React", "CSS/Animation"]',
                'quote'        => 'Users don\'t remember backends. They remember how it felt.',
                'sort_order'   => 3,
            ],
        ];

        $stmt = $this->pdo->prepare("
            INSERT INTO employees (id, slug, name, title, role, tagline, bio, mythology, avatar_url, accent_color, symbol, skills, quote, sort_order)
            VALUES (:id, :slug, :name, :title, :role, :tagline, :bio, :mythology, :avatar_url, :accent_color, :symbol, :skills, :quote, :sort_order)
        ");

        foreach ($employees as $emp) {
            $stmt->execute($emp);
        }
    }

    public function testGetAllReturnsAllEmployees(): void
    {
        $result = $this->repo->getAll();
        $this->assertCount(3, $result);
    }

    public function testGetAllReturnsSortedBySortOrder(): void
    {
        $result = $this->repo->getAll();
        $this->assertSame('daedalus', $result[0]['slug']);
        $this->assertSame('talos', $result[1]['slug']);
        $this->assertSame('icarus', $result[2]['slug']);
    }

    public function testGetAllDecodesSkillsJson(): void
    {
        $result = $this->repo->getAll();
        $this->assertIsArray($result[0]['skills']);
        $this->assertContains('System Architecture', $result[0]['skills']);
    }

    public function testGetAllCastsSortOrder(): void
    {
        $result = $this->repo->getAll();
        $this->assertSame(1, $result[0]['sort_order']);
        $this->assertSame(2, $result[1]['sort_order']);
    }

    public function testGetBySlugReturnsEmployee(): void
    {
        $result = $this->repo->getBySlug('talos');
        $this->assertNotNull($result);
        $this->assertSame('Talos', $result['name']);
        $this->assertSame('#7B8794', $result['accent_color']);
        $this->assertSame('gear', $result['symbol']);
    }

    public function testGetBySlugReturnsNullForMissing(): void
    {
        $result = $this->repo->getBySlug('nonexistent');
        $this->assertNull($result);
    }

    public function testGetBySlugDecodesSkills(): void
    {
        $result = $this->repo->getBySlug('icarus');
        $this->assertIsArray($result['skills']);
        $this->assertContains('React', $result['skills']);
    }

    public function testGetAllReturnsEmptyWhenNoData(): void
    {
        $this->pdo->exec('DELETE FROM employees');
        $result = $this->repo->getAll();
        $this->assertSame([], $result);
    }

    public function testGetBySlugReturnsAllFields(): void
    {
        $result = $this->repo->getBySlug('daedalus');
        $expectedKeys = ['id', 'slug', 'name', 'title', 'role', 'tagline', 'bio', 'mythology', 'avatar_url', 'accent_color', 'symbol', 'skills', 'quote', 'sort_order', 'created_at', 'updated_at'];
        foreach ($expectedKeys as $key) {
            $this->assertArrayHasKey($key, $result, "Missing key: {$key}");
        }
    }
}
