<?php

namespace App\Http\Controllers\Admin;

use App\Http\Controllers\Controller;
use App\Http\Controllers\Concerns\LogsAdminActions;
use Illuminate\Http\Request;
use App\Models\User;

class AdminUserController extends Controller
{
    use LogsAdminActions;

    public function index(Request $request)
    {
        if ($request->status === 'deleted') {
            $query = User::onlyTrashed()->withCount(['items', 'soldTransactions', 'boughtTransactions']);
        } else {
            $query = User::withCount(['items', 'soldTransactions', 'boughtTransactions']);
        }

        if ($request->filled('search')) {
            $search = $request->search;
            $query->where(function($q) use ($search) {
                $q->where('name', 'like', "%{$search}%")
                  ->orWhere('email', 'like', "%{$search}%");
            });
        }

        // Default to 'pending' (unreviewed queue) when no status param given
        $status = $request->filled('status') ? $request->status : 'pending';

        if ($status === 'active') {
            $query->where('is_active', true);
        } elseif ($status === 'inactive') {
            $query->where('is_active', false);
        } elseif ($status === 'admin') {
            $query->where('is_admin', true);
        } elseif ($status === 'pending') {
            $query->where('review_status', 'pending')->where('is_active', true);
        } elseif ($status === 'flagged') {
            $query->where('review_status', 'flagged');
        }
        // 'deleted' already handled above via onlyTrashed(); '' (all) has no filter

        $users = $query->latest()->paginate(20)->withQueryString();

        return view('admin.users.index', compact('users'));
    }

    public function show($id)
    {
        // Find user including soft deleted ones for admin view
        $user = User::withTrashed()->findOrFail($id);
        $user->load(['items.category', 'soldTransactions.item', 'boughtTransactions.item', 'givenFeedback', 'receivedFeedback', 'reviewer']);
        return view('admin.users.show', compact('user'));
    }

    public function update(Request $request, User $user)
    {
        $validated = $request->validate([
            'is_active' => 'boolean',
            'admin_notes' => 'nullable|string|max:5000',
        ]);

        $changes = array_intersect_key($validated, array_flip(array_keys($validated)));

        if (array_key_exists('is_active', $validated)) {
            $user->is_active = $validated['is_active'];
        }
        if (array_key_exists('admin_notes', $validated)) {
            $user->admin_notes = $validated['admin_notes'];
        }
        $user->save();

        $this->auditLog('update_user', $user, ['changes' => $changes]);

        return back()->with('success', 'User updated successfully');
    }

    public function ban(User $user)
    {
        if ($user->is_admin) {
            return back()->with('error', 'Cannot ban admin users');
        }

        $user->is_active = false;
        $user->save();
        $user->items()->update(['status' => 'archived']);

        $this->auditLog('ban_user', $user, [
            'user_name'  => $user->name,
            'user_email' => $user->email,
        ]);

        return back()->with('success', 'User banned successfully');
    }

    public function unban(User $user)
    {
        $user->is_active = true;
        $user->save();

        $this->auditLog('unban_user', $user, [
            'user_name'  => $user->name,
            'user_email' => $user->email,
        ]);

        return back()->with('success', 'User unbanned successfully');
    }

    public function approve(User $user)
    {
        $previousStatus = $user->review_status;

        $user->review_status = 'approved';
        $user->reviewed_at   = now();
        $user->reviewed_by   = auth()->id();
        $user->save();

        $this->auditLog('approve_user', $user, [
            'user_name'       => $user->name,
            'user_email'      => $user->email,
            'previous_status' => $previousStatus,
        ]);

        return back()->with('success', 'User approved.');
    }

    public function flag(User $user)
    {
        $previousStatus = $user->review_status;

        $user->review_status = 'flagged';
        $user->reviewed_at   = now();
        $user->reviewed_by   = auth()->id();
        $user->save();

        $this->auditLog('flag_user', $user, [
            'user_name'       => $user->name,
            'user_email'      => $user->email,
            'previous_status' => $previousStatus,
        ]);

        return back()->with('success', 'User flagged for attention.');
    }

    public function impersonate(User $user)
    {
        if ($user->id === auth()->id()) {
            return back()->with('error', 'You cannot impersonate yourself');
        }

        $this->auditLog('impersonate_start', $user, [
            'target_name'  => $user->name,
            'target_email' => $user->email,
        ]);

        session(['impersonator_id' => auth()->id()]);
        auth()->login($user);

        return redirect()->route('marketplace.index')->with('success', "You are now viewing the site as {$user->name}");
    }

    public function stopImpersonating()
    {
        $originalAdminId = session('impersonator_id');

        if (!$originalAdminId) {
            return redirect()->route('marketplace.index')->with('error', 'You are not currently impersonating anyone');
        }

        $originalAdmin = User::find($originalAdminId);

        if (!$originalAdmin || !$originalAdmin->is_admin) {
            session()->forget('impersonator_id');
            return redirect()->route('login')->with('error', 'Original admin account not found');
        }

        $impersonatedUser = auth()->user();

        session()->forget('impersonator_id');
        auth()->login($originalAdmin);

        // Log as the original admin now that we've switched back
        $this->auditLog('impersonate_stop', $impersonatedUser, [
            'target_name'  => $impersonatedUser->name,
            'target_email' => $impersonatedUser->email,
        ]);

        return redirect()->route('admin.users.index')->with('success', 'Stopped impersonating user. You are now back to your admin account');
    }
}
