<?php

namespace Tests\Feature;

use App\Models\User;
use Database\Seeders\PermissionsSeeder;
use Illuminate\Foundation\Testing\RefreshDatabase;
use Spatie\Permission\Models\Role;
use Tests\TestCase;

class AdminPanelSmokeTest extends TestCase
{
    use RefreshDatabase;

    private function admin(): User
    {
        Role::findOrCreate('admin');
        $admin = User::factory()->create();
        $admin->assignRole('admin');

        return $admin;
    }

    public function test_admin_dashboard_renders_with_branded_widgets(): void
    {
        $this->actingAs($this->admin())
            ->get('/admin')
            ->assertOk()
            ->assertSee('View live site')   // welcome banner
            ->assertSee('At a glance')      // stats heading
            ->assertSee('Recent activity'); // activity feed
    }

    public function test_roles_resource_renders(): void
    {
        $this->seed(PermissionsSeeder::class);

        $this->actingAs($this->admin())
            ->get('/admin/roles')
            ->assertOk();
    }

    public function test_permissions_seeder_grants_admin_access(): void
    {
        $this->seed(PermissionsSeeder::class);

        $admin = Role::findByName('admin');
        $this->assertTrue($admin->hasPermissionTo('access_admin'));
        $this->assertCount(count(PermissionsSeeder::PERMISSIONS), $admin->permissions);
    }

    public function test_login_event_updates_last_seen(): void
    {
        $user = User::factory()->create(['last_login_at' => null]);

        event(new \Illuminate\Auth\Events\Login('web', $user, false));

        $this->assertNotNull($user->fresh()->last_login_at);
        $this->assertEquals(1, $user->fresh()->login_count);
    }

    public function test_users_table_renders(): void
    {
        $this->actingAs($this->admin())
            ->get('/admin/users')
            ->assertOk();
    }

    public function test_admin_can_impersonate_member_and_return(): void
    {
        $admin = $this->admin();
        $member = User::factory()->create();

        $this->actingAs($admin)
            ->get(route('impersonate.start', $member))
            ->assertRedirect(route('dashboard'));

        $this->assertEquals($admin->id, session('impersonator_id'));
        $this->assertEquals($member->id, auth()->id());

        $this->get(route('impersonate.leave'))
            ->assertRedirect('/admin/users');

        $this->assertNull(session('impersonator_id'));
        $this->assertEquals($admin->id, auth()->id());
    }

    public function test_non_admin_cannot_impersonate(): void
    {
        $member = User::factory()->create();
        $target = User::factory()->create();

        $this->actingAs($member)
            ->get(route('impersonate.start', $target))
            ->assertForbidden();
    }

    public function test_cannot_impersonate_an_admin(): void
    {
        $admin = $this->admin();
        $otherAdmin = $this->admin();

        $this->actingAs($admin)
            ->get(route('impersonate.start', $otherAdmin))
            ->assertForbidden();
    }
}
