<?php

/**
 * Todo Reminder System - Usage Examples
 */

namespace App\Examples;

use App\Models\Todo;
use App\Models\User;
use App\Notifications\TodoReminderNotification;
use Carbon\Carbon;

class TodoReminderExamples
{
    /**
     * Example 1: Create a simple todo with 1-hour reminder
     */
    public function createSimpleTodo()
    {
        $userId = auth()->id();

        $todo = Todo::create([
            'user_id' => $userId,
            'title' => 'Team Meeting',
            'description' => 'Discuss project milestones for Q4',
            'todo_time' => '2025-11-10 14:00:00', // Meeting at 2 PM
            'reminder_before' => 60, // Remind 1 hour before (at 1 PM)
            'priority' => 'high',
        ]);

        return $todo;
    }

    /**
     * Example 2: Create todo for tomorrow with 2-hour reminder
     */
    public function createTomorrowTodo()
    {
        $todo = Todo::create([
            'user_id' => auth()->id(),
            'title' => 'Submit Monthly Report',
            'description' => 'Complete and submit financial report to management',
            'todo_time' => Carbon::tomorrow()->setTime(17, 0), // Tomorrow at 5 PM
            'reminder_before' => 120, // Remind 2 hours before (at 3 PM)
            'priority' => 'medium',
        ]);

        return $todo;
    }

    /**
     * Example 3: Create todo for next week with 5-hour reminder
     */
    public function createNextWeekTodo()
    {
        $todo = Todo::create([
            'user_id' => auth()->id(),
            'title' => 'Client Presentation',
            'description' => 'Present new product features to key stakeholders',
            'todo_time' => Carbon::now()->addWeek()->setTime(10, 0), // Next week at 10 AM
            'reminder_before' => 300, // Remind 5 hours before (at 5 AM)
            'priority' => 'high',
        ]);

        return $todo;
    }

    /**
     * Example 4: Bulk create todos for a workday
     */
    public function createWorkdayTodos()
    {
        $userId = auth()->id();
        $tomorrow = Carbon::tomorrow();

        $todos = [
            [
                'title' => 'Morning Stand-up',
                'time' => $tomorrow->copy()->setTime(9, 0),
                'reminder' => 60, // 1 hour
                'priority' => 'medium',
            ],
            [
                'title' => 'Review Code PRs',
                'time' => $tomorrow->copy()->setTime(11, 0),
                'reminder' => 60,
                'priority' => 'medium',
            ],
            [
                'title' => 'Client Call',
                'time' => $tomorrow->copy()->setTime(14, 0),
                'reminder' => 120, // 2 hours
                'priority' => 'high',
            ],
            [
                'title' => 'Team Retrospective',
                'time' => $tomorrow->copy()->setTime(16, 30),
                'reminder' => 60,
                'priority' => 'low',
            ],
        ];

        $created = [];
        foreach ($todos as $todoData) {
            $created[] = Todo::create([
                'user_id' => $userId,
                'title' => $todoData['title'],
                'todo_time' => $todoData['time'],
                'reminder_before' => $todoData['reminder'],
                'priority' => $todoData['priority'],
            ]);
        }

        return $created;
    }

    /**
     * Example 5: Get user's dashboard statistics
     */
    public function getDashboardStats($userId)
    {
        return [
            'total' => Todo::where('user_id', $userId)->count(),
            'pending' => Todo::where('user_id', $userId)->pending()->count(),
            'completed' => Todo::where('user_id', $userId)->completed()->count(),
            'overdue' => Todo::where('user_id', $userId)->overdue()->count(),
            'today' => Todo::where('user_id', $userId)
                ->whereDate('todo_time', today())
                ->pending()
                ->count(),
            'this_week' => Todo::where('user_id', $userId)
                ->whereBetween('todo_time', [
                    Carbon::now()->startOfWeek(),
                    Carbon::now()->endOfWeek()
                ])
                ->pending()
                ->count(),
        ];
    }

    /**
     * Example 6: Get upcoming todos for next 24 hours
     */
    public function getUpcomingTodos($userId)
    {
        return Todo::where('user_id', $userId)
            ->upcoming(24)
            ->orderBy('todo_time', 'asc')
            ->get()
            ->map(function ($todo) {
                return [
                    'id' => $todo->id,
                    'title' => $todo->title,
                    'time' => $todo->todo_time->format('M d, h:i A'),
                    'time_until' => $todo->todo_time->diffForHumans(),
                    'priority' => $todo->priority,
                    'reminder_label' => $todo->reminder_label,
                ];
            });
    }

    /**
     * Example 7: Mark todo as completed
     */
    public function completeTodo($todoId)
    {
        $todo = Todo::findOrFail($todoId);
        
        // Check authorization
        if ($todo->user_id !== auth()->id()) {
            abort(403, 'Unauthorized');
        }

        $todo->markAsCompleted();

        return [
            'success' => true,
            'message' => 'Todo completed!',
            'completed_at' => $todo->completed_at->format('M d, Y h:i A'),
        ];
    }

    /**
     * Example 8: Update todo and reset reminder
     */
    public function updateTodoTime($todoId, $newTime)
    {
        $todo = Todo::findOrFail($todoId);
        
        if ($todo->user_id !== auth()->id()) {
            abort(403, 'Unauthorized');
        }

        $todo->update([
            'todo_time' => $newTime,
            'reminder_sent' => false, // Reset reminder
            'reminder_sent_at' => null,
        ]);

        return [
            'success' => true,
            'message' => 'Todo updated. New reminder will be sent ' . $todo->reminder_label,
            'new_reminder_time' => $todo->reminder_time->format('M d, Y h:i A'),
        ];
    }

    /**
     * Example 9: Get todos grouped by date
     */
    public function getTodosGroupedByDate($userId)
    {
        $todos = Todo::where('user_id', $userId)
            ->pending()
            ->orderBy('todo_time', 'asc')
            ->get();

        return $todos->groupBy(function ($todo) {
            return $todo->todo_time->format('Y-m-d');
        })->map(function ($dateTodos, $date) {
            return [
                'date' => Carbon::parse($date)->format('l, M d, Y'),
                'is_today' => Carbon::parse($date)->isToday(),
                'is_tomorrow' => Carbon::parse($date)->isTomorrow(),
                'todos' => $dateTodos->map(function ($todo) {
                    return [
                        'id' => $todo->id,
                        'title' => $todo->title,
                        'time' => $todo->todo_time->format('h:i A'),
                        'priority' => $todo->priority,
                        'reminder_sent' => $todo->reminder_sent,
                    ];
                }),
            ];
        });
    }

    /**
     * Example 10: Get overdue todos with details
     */
    public function getOverdueTodos($userId)
    {
        return Todo::where('user_id', $userId)
            ->overdue()
            ->orderBy('todo_time', 'desc')
            ->get()
            ->map(function ($todo) {
                return [
                    'id' => $todo->id,
                    'title' => $todo->title,
                    'description' => $todo->description,
                    'was_scheduled' => $todo->todo_time->format('M d, Y h:i A'),
                    'overdue_by' => $todo->todo_time->diffForHumans(),
                    'priority' => $todo->priority,
                ];
            });
    }

    /**
     * Example 11: Manually send reminder for a todo
     */
    public function sendManualReminder($todoId)
    {
        $todo = Todo::findOrFail($todoId);
        
        if ($todo->user_id !== auth()->id()) {
            abort(403, 'Unauthorized');
        }

        // Send notification
        $todo->user->notify(new TodoReminderNotification($todo));

        return [
            'success' => true,
            'message' => 'Reminder sent successfully',
        ];
    }

    /**
     * Example 12: Get todos by priority
     */
    public function getTodosByPriority($userId)
    {
        $priorities = ['high', 'medium', 'low'];
        $result = [];

        foreach ($priorities as $priority) {
            $result[$priority] = Todo::where('user_id', $userId)
                ->pending()
                ->where('priority', $priority)
                ->orderBy('todo_time', 'asc')
                ->get();
        }

        return $result;
    }

    /**
     * Example 13: Search todos
     */
    public function searchTodos($userId, $keyword)
    {
        return Todo::where('user_id', $userId)
            ->where(function ($query) use ($keyword) {
                $query->where('title', 'like', "%{$keyword}%")
                    ->orWhere('description', 'like', "%{$keyword}%");
            })
            ->orderBy('todo_time', 'desc')
            ->get();
    }

    /**
     * Example 14: Clone/duplicate a todo
     */
    public function cloneTodo($todoId, $newTime)
    {
        $original = Todo::findOrFail($todoId);
        
        if ($original->user_id !== auth()->id()) {
            abort(403, 'Unauthorized');
        }

        $clone = Todo::create([
            'user_id' => $original->user_id,
            'title' => $original->title . ' (Copy)',
            'description' => $original->description,
            'todo_time' => $newTime,
            'reminder_before' => $original->reminder_before,
            'priority' => $original->priority,
        ]);

        return $clone;
    }

    /**
     * Example 15: Get calendar events for a month
     */
    public function getCalendarEvents($userId, $year, $month)
    {
        $startDate = Carbon::create($year, $month, 1)->startOfMonth();
        $endDate = Carbon::create($year, $month, 1)->endOfMonth();

        $todos = Todo::where('user_id', $userId)
            ->whereBetween('todo_time', [$startDate, $endDate])
            ->get();

        return $todos->map(function ($todo) {
            return [
                'id' => $todo->id,
                'title' => $todo->title,
                'start' => $todo->todo_time->toIso8601String(),
                'allDay' => false,
                'backgroundColor' => $this->getPriorityColor($todo->priority),
                'borderColor' => $this->getPriorityColor($todo->priority),
                'extendedProps' => [
                    'description' => $todo->description,
                    'priority' => $todo->priority,
                    'status' => $todo->status,
                    'completed' => $todo->is_completed,
                ],
            ];
        });
    }

    /**
     * Example 16: Test reminder system with a quick todo
     */
    public function createTestTodo()
    {
        // Create a todo that will trigger in 10 minutes
        $todo = Todo::create([
            'user_id' => auth()->id(),
            'title' => 'TEST: Quick Reminder',
            'description' => 'This is a test todo to verify the reminder system',
            'todo_time' => Carbon::now()->addMinutes(15), // 15 minutes from now
            'reminder_before' => 5, // Remind 5 minutes before (so in 10 minutes)
            'priority' => 'high',
        ]);

        return [
            'todo' => $todo,
            'reminder_will_send_at' => $todo->reminder_time->format('Y-m-d H:i:s'),
            'minutes_until_reminder' => Carbon::now()->diffInMinutes($todo->reminder_time, false),
        ];
    }

    private function getPriorityColor($priority)
    {
        $colors = [
            'high' => '#dc3545',   // Red
            'medium' => '#ffc107', // Yellow
            'low' => '#17a2b8',    // Blue
        ];

        return $colors[$priority] ?? '#6c757d';
    }
}
