<?php

namespace App\Livewire\Settings;

use App\Models\AuditEvent;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\RateLimiter;
use Illuminate\Validation\Rule;
use Illuminate\Validation\Rules\Password;
use Illuminate\Validation\ValidationException;
use Livewire\Component;

class Profile extends Component
{
    public string $name = '';

    public string $email = '';

    public string $current_password = '';

    public string $password = '';

    public string $password_confirmation = '';

    public function mount(): void
    {
        $this->name = Auth::user()->name;
        $this->email = Auth::user()->email;
    }

    public function updateProfile(): void
    {
        $data = $this->validate([
            'name' => ['required', 'string', 'max:255'],
            'email' => ['required', 'email', 'max:255', Rule::unique('users', 'email')->ignore(Auth::id())],
        ]);

        Auth::user()->update($data);
        $this->audit('profile.update', $data['email']);
        $this->dispatch('notify', message: __('settings.profile_saved'));
    }

    public function updatePassword(): void
    {
        // Throttle the current-password re-auth (hijacked-session brute-force protection).
        // User-id keyed + auto-expiring: only ever slows the user's own session briefly.
        $key = 'reauth:'.Auth::id();
        if (RateLimiter::tooManyAttempts($key, 5)) {
            throw ValidationException::withMessages([
                'current_password' => __('auth.too_many_attempts', ['seconds' => RateLimiter::availableIn($key)]),
            ]);
        }

        try {
            $this->validate([
                'current_password' => ['required', 'current_password'],
                'password' => ['required', 'confirmed', Password::min(6)],
            ]);
        } catch (ValidationException $e) {
            if (array_key_exists('current_password', $e->errors())) {
                RateLimiter::hit($key, 60);
            }
            throw $e;
        }

        RateLimiter::clear($key);

        Auth::user()->update(['password' => $this->password, 'must_change_password' => false]);
        $this->reset('current_password', 'password', 'password_confirmation');
        $this->audit('password.change', Auth::user()->email);
        $this->dispatch('notify', message: __('settings.password_changed'));
    }

    private function audit(string $action, string $target): void
    {
        AuditEvent::create([
            'user_id' => Auth::id(),
            'actor' => Auth::user()->name,
            'action' => $action,
            'target' => $target,
            'ip' => request()->ip(),
        ]);
    }

    public function render()
    {
        return view('livewire.settings.profile');
    }
}
