//! Deadline picker component
//!
//! Allows users to set and update task deadlines with date/time selection.
//! Provides visual indicators for overdue and upcoming deadlines.

/// Generate HTML for the deadline picker component
///
/// # Arguments
///
/// * `task_id` - ID of the task to set deadline for
/// * `current_deadline` - Current deadline (ISO 8601 format, optional)
/// * `auth_token` - Authentication token for API calls (optional)
///
/// # Returns
///
/// HTML string for the deadline picker component
pub fn deadline_picker_html(
    task_id: &str,
    current_deadline: Option<&str>,
    auth_token: Option<&str>,
) -> String {
    let (deadline_value, deadline_display, status_class, status_icon) =
        format_deadline_info(current_deadline);

    let auth_header = auth_token
        .map(|token| format!(r#"headers.set('Authorization', 'Bearer {}');"#, token))
        .unwrap_or_default();

    format!(
        r#"<div class="bg-white dark:bg-gray-800 rounded-lg shadow-md p-4">
    <div class="flex items-center justify-between mb-4">
        <h3 class="text-lg font-bold text-gray-900 dark:text-white">Deadline</h3>
        {}
    </div>

    <!-- Current Deadline Display -->
    <div id="deadline-display-{}" class="mb-4 p-3 rounded-md {}">
        <p class="text-sm text-gray-700 dark:text-gray-300">{}</p>
    </div>

    <!-- Deadline Picker -->
    <div class="space-y-3">
        <label class="block text-sm font-medium text-gray-700 dark:text-gray-300">
            Set Deadline
        </label>
        <input
            type="datetime-local"
            id="deadline-input-{}"
            value="{}"
            class="w-full px-3 py-2 border border-gray-300 dark:border-gray-600 rounded-md shadow-sm dark:bg-gray-700 dark:text-white focus:outline-none focus:ring-blue-500 focus:border-blue-500"
        />

        <div class="flex justify-end space-x-2">
            <button
                id="clear-deadline-{}"
                class="px-3 py-2 border border-gray-300 dark:border-gray-600 rounded-md text-gray-700 dark:text-gray-300 hover:bg-gray-50 dark:hover:bg-gray-700 transition-colors">
                Clear
            </button>
            <button
                id="save-deadline-{}"
                class="px-3 py-2 bg-blue-600 hover:bg-blue-700 text-white rounded-md transition-colors">
                Save
            </button>
        </div>
    </div>

    <!-- Quick Actions -->
    <div class="mt-4 pt-4 border-t border-gray-200 dark:border-gray-700">
        <p class="text-xs text-gray-500 dark:text-gray-400 mb-2">Quick Set:</p>
        <div class="flex flex-wrap gap-2">
            <button class="quick-deadline-btn text-xs px-2 py-1 bg-gray-100 dark:bg-gray-700 rounded hover:bg-gray-200 dark:hover:bg-gray-600 transition-colors" data-hours="24">
                Tomorrow
            </button>
            <button class="quick-deadline-btn text-xs px-2 py-1 bg-gray-100 dark:bg-gray-700 rounded hover:bg-gray-200 dark:hover:bg-gray-600 transition-colors" data-hours="72">
                3 Days
            </button>
            <button class="quick-deadline-btn text-xs px-2 py-1 bg-gray-100 dark:bg-gray-700 rounded hover:bg-gray-200 dark:hover:bg-gray-600 transition-colors" data-hours="168">
                1 Week
            </button>
            <button class="quick-deadline-btn text-xs px-2 py-1 bg-gray-100 dark:bg-gray-700 rounded hover:bg-gray-200 dark:hover:bg-gray-600 transition-colors" data-hours="336">
                2 Weeks
            </button>
        </div>
    </div>
</div>

<script>
    (function() {{
        const taskId = '{}';
        const deadlineInput = document.getElementById('deadline-input-' + taskId);
        const saveBtn = document.getElementById('save-deadline-' + taskId);
        const clearBtn = document.getElementById('clear-deadline-' + taskId);
        const quickBtns = document.querySelectorAll('.quick-deadline-btn');

        // Save deadline
        saveBtn?.addEventListener('click', async function() {{
            const deadline = deadlineInput?.value;
            if (!deadline) {{
                alert('Please select a deadline');
                return;
            }}

            // Convert to ISO 8601
            const isoDeadline = new Date(deadline).toISOString();

            try {{
                const headers = new Headers();
                headers.set('Content-Type', 'application/json');
                {}

                const response = await fetch(`/api/tasks/${{taskId}}/deadline`, {{
                    method: 'PUT',
                    headers: headers,
                    body: JSON.stringify({{ deadline: isoDeadline }})
                }});

                if (response.ok) {{
                    window.location.reload();
                }} else {{
                    const error = await response.json();
                    alert('Failed to save deadline: ' + (error.error || 'Unknown error'));
                }}
            }} catch (err) {{
                console.error('Save deadline error:', err);
                alert('Network error. Please try again.');
            }}
        }});

        // Clear deadline
        clearBtn?.addEventListener('click', async function() {{
            if (!confirm('Remove the deadline for this task?')) {{
                return;
            }}

            try {{
                const headers = new Headers();
                {}

                const response = await fetch(`/api/tasks/${{taskId}}/deadline`, {{
                    method: 'DELETE',
                    headers: headers
                }});

                if (response.ok) {{
                    window.location.reload();
                }} else {{
                    alert('Failed to clear deadline');
                }}
            }} catch (err) {{
                console.error('Clear deadline error:', err);
                alert('Network error. Please try again.');
            }}
        }});

        // Quick deadline buttons
        quickBtns.forEach(btn => {{
            btn.addEventListener('click', function() {{
                const hours = parseInt(this.getAttribute('data-hours') || '24');
                const deadline = new Date();
                deadline.setHours(deadline.getHours() + hours);

                // Format for datetime-local input
                const year = deadline.getFullYear();
                const month = String(deadline.getMonth() + 1).padStart(2, '0');
                const day = String(deadline.getDate()).padStart(2, '0');
                const hour = String(deadline.getHours()).padStart(2, '0');
                const minute = String(deadline.getMinutes()).padStart(2, '0');

                deadlineInput.value = `${{year}}-${{month}}-${{day}}T${{hour}}:${{minute}}`;
            }});
        }});

        // Enter key saves
        deadlineInput?.addEventListener('keypress', function(e) {{
            if (e.key === 'Enter') {{
                saveBtn?.click();
            }}
        }});
    }})();
</script>"#,
        status_icon,
        task_id,
        status_class,
        deadline_display,
        task_id,
        deadline_value,
        task_id,
        task_id,
        task_id,
        auth_header,
        auth_header
    )
}

/// Format deadline information for display
///
/// Returns a tuple of (input_value, display_text, css_class, status_icon)
fn format_deadline_info(deadline: Option<&str>) -> (String, String, &'static str, &'static str) {
    if let Some(dt) = deadline {
        // Parse and format the deadline
        let display = format_deadline_display(dt);
        let input_value = format_for_input(dt);

        // Determine status
        let (status_class, status_icon) = get_deadline_status(dt);

        (input_value, display, status_class, status_icon)
    } else {
        (
            String::new(),
            "No deadline set".to_string(),
            "bg-gray-50 dark:bg-gray-700",
            "",
        )
    }
}

/// Format deadline for display
fn format_deadline_display(dt: &str) -> String {
    // Parse ISO 8601 and format nicely
    if let Some(datetime_str) = dt.split('T').next() {
        if let Some(time_str) = dt.split('T').nth(1) {
            if let Some(time_part) = time_str.split('.').next() {
                if let Some(hm) = time_part.get(..5) {
                    return format!("Due: {} at {}", datetime_str, hm);
                }
            }
        }
        return format!("Due: {}", datetime_str);
    }
    dt.to_string()
}

/// Format deadline for datetime-local input
fn format_for_input(dt: &str) -> String {
    // Convert ISO 8601 to datetime-local format (YYYY-MM-DDTHH:MM)
    if let Some((date, time)) = dt.split_once('T') {
        if let Some(time_part) = time.split('.').next() {
            if let Some(hm) = time_part.get(..5) {
                return format!("{}T{}", date, hm);
            }
        }
    }
    String::new()
}

/// Get deadline status (overdue, upcoming, etc.)
///
/// Returns (css_class, status_icon)
fn get_deadline_status(_dt: &str) -> (&'static str, &'static str) {
    // In a real implementation, compare with current time
    // For now, assume it's upcoming
    ("bg-blue-50 dark:bg-blue-900", "⏰")
}

#[cfg(test)]
mod tests {
    use super::*;

    #[test]
    fn test_format_deadline_display() {
        assert_eq!(
            format_deadline_display("2023-11-14T10:30:00Z"),
            "Due: 2023-11-14 at 10:30"
        );
        assert_eq!(
            format_deadline_display("2023-11-14T10:30:45.123Z"),
            "Due: 2023-11-14 at 10:30"
        );
        assert_eq!(format_deadline_display("2023-11-14"), "Due: 2023-11-14");
    }

    #[test]
    fn test_format_for_input() {
        assert_eq!(format_for_input("2023-11-14T10:30:00Z"), "2023-11-14T10:30");
        assert_eq!(
            format_for_input("2023-11-14T10:30:45.123Z"),
            "2023-11-14T10:30"
        );
        assert_eq!(format_for_input("invalid"), "");
    }

    #[test]
    fn test_format_deadline_info_none() {
        let (value, display, class, icon) = format_deadline_info(None);
        assert_eq!(value, "");
        assert_eq!(display, "No deadline set");
        assert!(class.contains("gray"));
        assert_eq!(icon, "");
    }

    #[test]
    fn test_format_deadline_info_with_deadline() {
        let (value, display, class, icon) = format_deadline_info(Some("2023-11-14T10:30:00Z"));
        assert_eq!(value, "2023-11-14T10:30");
        assert!(display.contains("Due"));
        assert!(!class.is_empty());
        assert_eq!(icon, "⏰");
    }

    #[test]
    fn test_deadline_picker_html_no_deadline() {
        let html = deadline_picker_html("task-123", None, None);
        assert!(html.contains("task-123"));
        assert!(html.contains("No deadline set"));
        assert!(html.contains("Quick Set"));
    }

    #[test]
    fn test_deadline_picker_html_with_deadline() {
        let html = deadline_picker_html("task-123", Some("2023-11-14T10:30:00Z"), Some("token"));
        assert!(html.contains("task-123"));
        assert!(html.contains("Due"));
        assert!(html.contains("2023-11-14T10:30"));
        assert!(html.contains("Authorization"));
    }
}
