<?php

namespace Tests\Feature;

use Illuminate\Foundation\Testing\RefreshDatabase;
use Illuminate\Http\UploadedFile;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Storage;
use App\Models\User;
use Tests\TestCase;

class AvatarUploadTest extends TestCase
{
    use RefreshDatabase;

    protected function setUp(): void
    {
        parent::setUp();

        config()->set('avatars.disk', 'public');
        Storage::fake('public');
    }

    public function test_upload_requires_authentication()
    {
        $response = $this->postJson(route('avatar.upload'));
        $response->assertStatus(401);
    }

    public function test_upload_rejects_invalid_avatar_type(): void
    {
        $user = User::factory()->create();

        $response = $this->actingAs($user)->postJson(route('avatar.upload'), [
            'avatar' => UploadedFile::fake()->create('avatar.txt', 50, 'text/plain'),
        ]);

        $response->assertStatus(422);
    }

    public function test_upload_processes_avatar_and_stores_webp_variants(): void
    {
        $user = User::factory()->create();

        $response = $this->actingAs($user)->postJson(route('avatar.upload'), [
            'avatar' => UploadedFile::fake()->image('avatar.png', 300, 180),
        ]);

        $response->assertOk()->assertJson(['success' => true]);

        $payload = $response->json();
        $this->assertMatchesRegularExpression('/^[a-f0-9]{64}$/', (string) ($payload['hash'] ?? ''));

        $this->assertTrue(Storage::disk('public')->exists("avatars/{$user->id}/32.webp"));
        $this->assertTrue(Storage::disk('public')->exists("avatars/{$user->id}/64.webp"));
        $this->assertTrue(Storage::disk('public')->exists("avatars/{$user->id}/128.webp"));
        $this->assertTrue(Storage::disk('public')->exists("avatars/{$user->id}/256.webp"));
        $this->assertTrue(Storage::disk('public')->exists("avatars/{$user->id}/512.webp"));

        $record = DB::table('user_profiles')->where('user_id', $user->id)->first();
        $this->assertNotNull($record);
        $this->assertSame('image/webp', $record->avatar_mime);
        $this->assertSame($payload['hash'], $record->avatar_hash);
        $this->assertNotNull($record->avatar_updated_at);
    }
}
