<?php

namespace App\Http\Controllers;

use App\Models\Attendance;
use App\Models\Employee;
use Illuminate\Http\Request;
use Yajra\DataTables\DataTables;
use Carbon\Carbon;
use Illuminate\Support\Facades\Auth;

class AttendanceController extends Controller
{
    public function index()
    {
        $user = Auth::user();
        $query = Employee::query();
        
        if (!$user->hasRole('Admin')) {
            $subordinateIds = $user->employee ? $user->employee->subordinates->pluck('id') : collect([]);
            $query->where(function($q) use ($user, $subordinateIds) {
                $q->where('id', $user->employee_id)
                  ->orWhereIn('id', $subordinateIds);
            });
        }

        $employees = $query->get();
        return view('attendance.index', compact('employees'));
    }

    public function getData(Request $request)
    {
        $user = Auth::user();
        $query = Attendance::with('employee')->orderBy('date', 'desc')->orderBy('punch_in', 'desc');

        // Mandatory Scoping for non-admins
        if (!$user->hasRole('Admin')) {
            $subordinateIds = $user->employee ? $user->employee->subordinates->pluck('id') : collect([]);
            $query->whereIn('employee_id', $subordinateIds->push($user->employee_id));
        }

        // Contextual filters from UI
        if ($request->has('mine')) {
            $query->where('employee_id', $user->employee_id);
        } elseif ($request->has('subordinates')) {
            $subordinateIds = $user->employee ? $user->employee->subordinates->pluck('id') : collect([]);
            $query->whereIn('employee_id', $subordinateIds);
        }

        // Advanced Filters
        $query->when($request->start_date, function ($q) use ($request) {
            return $q->where('date', '>=', $request->start_date);
        })
        ->when($request->end_date, function ($q) use ($request) {
            return $q->where('date', '<=', $request->end_date);
        })
        ->when($request->employee_id, function ($q) use ($request) {
            return $q->where('employee_id', $request->employee_id);
        });

        return DataTables::of($query)
            ->addColumn('employee', function ($attendance) {
                return $attendance->employee->name;
            })
            ->editColumn('punch_in', function ($attendance) {
                return $attendance->punch_in ? Carbon::parse($attendance->punch_in)->format('H:i') : '-';
            })
            ->editColumn('punch_out', function ($attendance) {
                return $attendance->punch_out ? Carbon::parse($attendance->punch_out)->format('H:i') : 'Still In';
            })
            ->addColumn('duration', function ($attendance) {
                return $attendance->working_hours;
            })
            ->make(true);
    }

    public function punch(Request $request)
    {
        // If admin provides employee_id, use it. Otherwise use logged in user's employee_id
        $employee_id = (Auth::user()->hasRole('Admin') && $request->employee_id) 
            ? $request->employee_id 
            : Auth::user()->employee_id;

        if (!$employee_id) {
            return response()->json(['error' => 'No employee record linked to this user.'], 422);
        }

        $today = Carbon::today()->toDateString();
        $attendance = Attendance::where('employee_id', $employee_id)
            ->where('date', $today)
            ->whereNull('punch_out')
            ->first();

        if ($attendance) {
            // Punch Out
            $punchOut = Carbon::now();
            $attendance->update([
                'punch_out' => $punchOut,
            ]);

            // Get business settings for validation
            $settings = \App\Models\BusinessSetting::first();
            $messages = ['Punched out successfully.'];
            $warnings = [];

            // Check for late punch in
            if ($settings && $settings->standard_punch_in_time) {
                $standardPunchIn = Carbon::parse($today . ' ' . $settings->standard_punch_in_time);
                $actualPunchIn = Carbon::parse($attendance->punch_in);
                
                if ($actualPunchIn->gt($standardPunchIn)) {
                    $lateMinutes = $actualPunchIn->diffInMinutes($standardPunchIn);
                    $warnings[] = "⚠️ Late arrival: You were " . $lateMinutes . " minutes late.";
                }
            }

            // Check for low working hours
            if ($settings && $settings->minimum_working_hours) {
                $punchIn = Carbon::parse($attendance->punch_in);
                $workedHours = $punchIn->diffInHours($punchOut, true);
                $minimumHours = (float) $settings->minimum_working_hours;

                if ($workedHours < $minimumHours) {
                    $shortfall = round($minimumHours - $workedHours, 2);
                    $warnings[] = "⚠️ Low attendance: You worked " . round($workedHours, 2) . " hours. Short by " . $shortfall . " hours.";
                }
            }

            // Combine messages
            if (!empty($warnings)) {
                $messages = array_merge($messages, $warnings);
            }

            return response()->json([
                'success' => implode(' ', $messages),
                'has_warnings' => !empty($warnings),
                'warnings' => $warnings
            ]);
        } else {
            // Punch In
            $punchIn = Carbon::now();
            Attendance::create([
                'employee_id' => $employee_id,
                'date' => $today,
                'punch_in' => $punchIn,
            ]);

            // Check if late on punch in
            $settings = \App\Models\BusinessSetting::first();
            $message = 'Punched in successfully.';
            
            if ($settings && $settings->standard_punch_in_time) {
                $standardPunchIn = Carbon::parse($today . ' ' . $settings->standard_punch_in_time);
                
                if ($punchIn->gt($standardPunchIn)) {
                    $lateMinutes = $punchIn->diffInMinutes($standardPunchIn);
                    $message .= " ⚠️ Note: You are " . $lateMinutes . " minutes late.";
                }
            }

            return response()->json(['success' => $message]);
        }
    }

    public function myAttendance()
    {
        return view('attendance.my_attendance');
    }

    public function getStatus()
    {
        $employee_id = Auth::user()->employee_id;
        if (!$employee_id) return response()->json(['status' => 'out']);

        $attendance = Attendance::where('employee_id', $employee_id)
            ->where('date', Carbon::today()->toDateString())
            ->whereNull('punch_out')
            ->first();

        return response()->json([
            'status' => $attendance ? 'in' : 'out',
            'punch_in' => $attendance ? Carbon::parse($attendance->punch_in)->format('H:i') : null
        ]);
    }

    public function teamAttendance()
    {
        return view('attendance.team_attendance');
    }
}
