import { useState, useEffect, useCallback } from "react";
import { AxiosError } from "axios";

import { BytescaleUploader } from "@/components/BytescaleUploader/BytescaleUploader";

import {
	getDoctorsApi,
	createDoctorApi,
	updateDoctorApi,
	deleteDoctorApi,
	getDoctorTimingApi,
} from "@/api/doctor";
import { getDepartmentsApi } from "@/api/department";

import {
	Table,
	TableBody,
	TableCell,
	TableHead,
	TableHeader,
	TableRow,
} from "@/components/ui/table";
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card";
import { Button } from "@/components/ui/button";
import {
	Dialog,
	DialogContent,
	DialogHeader,
	DialogTitle,
	DialogFooter,
} from "@/components/ui/dialog";
import { Input } from "@/components/ui/input";
import { Badge } from "@/components/ui/badge";
import {
	Loader2,
	RefreshCw,
	Plus,
	Pencil,
	Trash,
	ChevronLeft,
	ChevronRight,
	User,
} from "lucide-react";

interface Department {
	departmentId: string;
	name: string;
}

const DAYS = [
	"monday",
	"tuesday",
	"wednesday",
	"thursday",
	"friday",
	"saturday",
	"sunday",
	"additional",
];

export default function DoctorPage() {
	const [doctors, setDoctors] = useState<any[]>([]);
	const [departments, setDepartments] = useState<Department[]>([]);
	const [loading, setLoading] = useState(true);
	const [error, setError] = useState("");

	const [openModal, setOpenModal] = useState(false);
	const [editing, setEditing] = useState<any>(null);

	const [searchText, setSearchText] = useState("");
	const [filterDepartment, setFilterDepartment] = useState("");

	const [currentPage, setCurrentPage] = useState(1);
	const itemsPerPage = 10;

	const [form, setForm] = useState<any>({
		doctorId: "",
		name: "",
		image: "",
		designation: "",
		workingStatus: "",
		qualification: "",
		departments: [],
	});

	const fetchAll = useCallback(async () => {
		setLoading(true);
		setError("");
		try {
			const [docRes, depRes] = await Promise.all([
				getDoctorsApi(),
				getDepartmentsApi(),
			]);
			setDoctors(docRes?.data || []);
			setDepartments(depRes?.data || []);
		} catch (err) {
			if (err instanceof AxiosError) {
				setError(err.response?.data?.message || "Failed to load data");
			} else {
				setError("Something went wrong");
			}
		} finally {
			setLoading(false);
		}
	}, []);

	useEffect(() => {
		fetchAll();
	}, [fetchAll]);

	const filteredDoctors = doctors.filter((doc) => {
		const matchesSearch =
			doc.name.toLowerCase().includes(searchText.toLowerCase()) ||
			doc.doctorId.toLowerCase().includes(searchText.toLowerCase());

		const matchesDepartment = filterDepartment
			? doc.departments?.some((d: any) => d.departmentId === filterDepartment)
			: true;

		return matchesSearch && matchesDepartment;
	});

	useEffect(() => {
		setCurrentPage(1);
	}, [searchText, filterDepartment]);

	const totalPages = Math.ceil(filteredDoctors.length / itemsPerPage);
	const indexOfLastItem = currentPage * itemsPerPage;
	const indexOfFirstItem = indexOfLastItem - itemsPerPage;
	const currentItems = filteredDoctors.slice(indexOfFirstItem, indexOfLastItem);

	function handleChange(e: any) {
		setForm({ ...form, [e.target.name]: e.target.value });
	}

	function handleDepartmentToggle(depId: string) {
		const exists = form.departments.find((d: any) => d.departmentId === depId);
		if (exists) {
			setForm({
				...form,
				departments: form.departments.filter(
					(d: any) => d.departmentId !== depId,
				),
			});
		} else {
			setForm({
				...form,
				departments: [...form.departments, { departmentId: depId, timing: {} }],
			});
		}
	}

	function handleTimingChange(depId: string, day: string, value: string) {
		setForm({
			...form,
			departments: form.departments.map((d: any) =>
				d.departmentId === depId
					? { ...d, timing: { ...d.timing, [day]: value } }
					: d,
			),
		});
	}

	function openAdd() {
		setEditing(null);
		setForm({
			doctorId: "",
			name: "",
			image: "",
			designation: "",
			workingStatus: "",
			qualification: "",
			departments: [],
		});
		setOpenModal(true);
	}

	async function openEdit(doc: any) {
		setEditing(doc);
		try {
			const timingRes = await getDoctorTimingApi(doc.doctorId);
			const timingData = timingRes?.data?.departments || [];
			setForm({
				doctorId: doc.doctorId,
				name: doc.name,
				image: doc.image || "",
				designation: doc.designation,
				workingStatus: doc.workingStatus,
				qualification: doc.qualification,
				departments: timingData.map((d: any) => ({
					departmentId: d.departmentId,
					timing: d.timing || {},
				})),
			});
			setOpenModal(true);
		} catch (err) {
			console.error(err);
		}
	}

	async function handleSubmit() {
		try {
			if (editing) {
				await updateDoctorApi(editing.doctorId, form);
			} else {
				await createDoctorApi(form);
			}
			setOpenModal(false);
			fetchAll();
		} catch (error) {
			console.error(error);
		}
	}

	async function handleDelete(id: string) {
		if (!confirm("Delete this doctor?")) return;
		try {
			await deleteDoctorApi(id);
			fetchAll();
		} catch (error) {
			console.error(error);
		}
	}

	return (
		<div className="p-6 space-y-6">
			<div className="flex flex-col md:flex-row md:justify-between md:items-center gap-4">
				<h1 className="text-3xl font-bold">Doctors</h1>

				<div className="flex flex-wrap gap-3">
					<Input
						placeholder="Search doctor..."
						value={searchText}
						onChange={(e) => setSearchText(e.target.value)}
						className="w-[250px] text-base"
					/>

					<select
						value={filterDepartment}
						onChange={(e) => setFilterDepartment(e.target.value)}
						className="flex h-10 w-[220px] rounded-md border border-input bg-background px-3 py-2 text-base ring-offset-background focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2"
					>
						<option value="">All Departments</option>
						{departments.map((dep) => (
							<option key={dep.departmentId} value={dep.departmentId}>
								{dep.name}
							</option>
						))}
					</select>

					<Button
						variant="outline"
						onClick={fetchAll}
						disabled={loading}
						className="text-base"
					>
						<RefreshCw className="mr-2 h-5 w-5" />
						Refresh
					</Button>

					<Button onClick={openAdd} className="text-base">
						<Plus className="mr-2 h-5 w-5" />
						Add Doctor
					</Button>
				</div>
			</div>

			{error && (
				<div className="p-4 text-red-600 bg-red-50 border rounded-md text-base">
					{error}
				</div>
			)}

			<Card>
				<CardHeader>
					<CardTitle className="text-xl">Doctor List</CardTitle>
				</CardHeader>

				<CardContent className="p-0 sm:p-6 space-y-4">
					<div className="rounded-md border overflow-x-auto overflow-y-auto max-h-[650px] relative">
						<Table className="w-full min-w-[900px] table-fixed border-separate border-spacing-0">
							<TableHeader className="sticky top-0 z-20 bg-background shadow-sm">
								<TableRow>
									<TableHead className="w-[100px] bg-background text-sm font-bold">
										ID
									</TableHead>
									<TableHead className="w-[200px] bg-background text-sm font-bold">
										Name
									</TableHead>
									<TableHead className="w-[180px] bg-background text-sm font-bold">
										Designation
									</TableHead>
									<TableHead className="w-[180px] bg-background text-sm font-bold">
										Qualification
									</TableHead>
									<TableHead className="w-[220px] bg-background text-sm font-bold">
										Departments
									</TableHead>
									<TableHead className="w-[120px] bg-background text-right text-sm font-bold">
										Actions
									</TableHead>
								</TableRow>
							</TableHeader>

							<TableBody>
								{loading ? (
									<TableRow>
										<TableCell colSpan={6} className="text-center py-10">
											<Loader2 className="h-8 w-8 animate-spin mx-auto" />
										</TableCell>
									</TableRow>
								) : currentItems.length === 0 ? (
									<TableRow>
										<TableCell
											colSpan={6}
											className="text-center text-muted-foreground py-10 text-base"
										>
											No doctors found
										</TableCell>
									</TableRow>
								) : (
									currentItems.map((doc) => (
										<TableRow key={doc.doctorId} className="hover:bg-muted/50">
											<TableCell className="truncate font-mono text-xs">
												{doc.doctorId}
											</TableCell>

											<TableCell>
												<div
													className="font-semibold text-base truncate"
													title={doc.name}
												>
													{doc.name}
												</div>
												<div className="text-xs text-muted-foreground truncate italic">
													{doc.workingStatus}
												</div>
											</TableCell>

											<TableCell>
												<div
													className="truncate text-sm"
													title={doc.designation}
												>
													{doc.designation || "-"}
												</div>
											</TableCell>

											<TableCell>
												<div
													className="truncate text-sm"
													title={doc.qualification}
												>
													{doc.qualification || "-"}
												</div>
											</TableCell>

											<TableCell>
												<div className="flex flex-wrap gap-1">
													{doc.departments?.map((d: any) => (
														<Badge
															key={d.departmentId}
															variant="secondary"
															className="text-xs px-2 h-5 leading-none"
														>
															{d.departmentName}
														</Badge>
													))}
													{doc.departments?.length === 0 && (
														<span className="text-muted-foreground">-</span>
													)}
												</div>
											</TableCell>

											<TableCell className="text-right">
												<div className="flex justify-end gap-2">
													<Button
														size="icon"
														variant="ghost"
														className="h-9 w-9"
														onClick={() => openEdit(doc)}
													>
														<Pencil className="h-4 w-4" />
													</Button>
													<Button
														size="icon"
														variant="ghost"
														className="h-9 w-9 text-destructive hover:text-destructive hover:bg-destructive/10"
														onClick={() => handleDelete(doc.doctorId)}
													>
														<Trash className="h-4 w-4" />
													</Button>
												</div>
											</TableCell>
										</TableRow>
									))
								)}
							</TableBody>
						</Table>
					</div>

					{!loading && filteredDoctors.length > 0 && (
						<div className="flex items-center justify-between px-2 py-6 border-t">
							<div className="text-base text-muted-foreground">
								Showing{" "}
								<span className="font-semibold">{indexOfFirstItem + 1}</span> to{" "}
								<span className="font-semibold">
									{Math.min(indexOfLastItem, filteredDoctors.length)}
								</span>{" "}
								of{" "}
								<span className="font-semibold">{filteredDoctors.length}</span>{" "}
								doctors
							</div>
							<div className="flex items-center gap-6">
								<div className="text-base font-semibold">
									Page {currentPage} of {totalPages}
								</div>
								<div className="flex gap-2">
									<Button
										variant="outline"
										size="icon"
										className="h-10 w-10"
										onClick={() =>
											setCurrentPage((prev) => Math.max(prev - 1, 1))
										}
										disabled={currentPage === 1}
									>
										<ChevronLeft className="h-5 w-5" />
									</Button>
									<Button
										variant="outline"
										size="icon"
										className="h-10 w-10"
										onClick={() =>
											setCurrentPage((prev) => Math.min(prev + 1, totalPages))
										}
										disabled={currentPage === totalPages || totalPages === 0}
									>
										<ChevronRight className="h-5 w-5" />
									</Button>
								</div>
							</div>
						</div>
					)}
				</CardContent>
			</Card>

			<Dialog open={openModal} onOpenChange={setOpenModal}>
				<DialogContent className="w-full !max-w-5xl h-[90vh] flex flex-col p-0 overflow-hidden">
					<DialogHeader className="p-6 border-b bg-background z-10">
						<DialogTitle className="text-2xl">
							{editing ? "Edit Doctor" : "Add Doctor"}
						</DialogTitle>
					</DialogHeader>

					<div className="flex-1 overflow-y-auto p-6">
						<div className="grid grid-cols-1 md:grid-cols-2 gap-8">
							<div className="space-y-6">
								<h3 className="font-bold text-base border-b pb-2">
									Basic Information
								</h3>
								<div className="space-y-4">
									<div className="space-y-2">
										<label className="text-sm font-semibold">
											Doctor Photo
										</label>
										<BytescaleUploader
											value={form.image}
											folderPath="/doctors"
											onChange={(url) => setForm({ ...form, image: url })}
										/>
									</div>

									<div className="space-y-1">
										<label className="text-sm font-semibold">Doctor ID</label>
										<Input
											name="doctorId"
											placeholder="GG-DOC-001"
											value={form.doctorId}
											onChange={handleChange}
											disabled={!!editing}
											className="text-base"
										/>
									</div>
									<div className="space-y-1">
										<label className="text-sm font-semibold">Full Name</label>
										<Input
											name="name"
											placeholder="Dr. John Doe"
											value={form.name}
											onChange={handleChange}
											className="text-base"
										/>
									</div>
									<div className="space-y-1">
										<label className="text-sm font-semibold">Designation</label>
										<Input
											name="designation"
											placeholder="Senior Consultant"
											value={form.designation}
											onChange={handleChange}
											className="text-base"
										/>
									</div>
									<div className="space-y-1">
										<label className="text-sm font-semibold">
											Working Status
										</label>
										<Input
											name="workingStatus"
											placeholder="Active / On Call"
											value={form.workingStatus}
											onChange={handleChange}
											className="text-base"
										/>
									</div>
									<div className="space-y-1">
										<label className="text-sm font-semibold">
											Qualification
										</label>
										<Input
											name="qualification"
											placeholder="MBBS, MD"
											value={form.qualification}
											onChange={handleChange}
											className="text-base"
										/>
									</div>
								</div>

								<div className="p-5 border rounded-md bg-muted/20">
									<p className="text-base font-bold mb-4">Assign Departments</p>
									<div className="grid grid-cols-2 gap-3">
										{departments.map((dep) => {
											const isSelected = form.departments.some(
												(d: any) => d.departmentId === dep.departmentId,
											);
											return (
												<Button
													key={dep.departmentId}
													type="button"
													variant={isSelected ? "default" : "outline"}
													size="sm"
													className="justify-start text-sm min-h-11 whitespace-normal break-words text-left py-2"
													onClick={() =>
														handleDepartmentToggle(dep.departmentId)
													}
												>
													{dep.name}
												</Button>
											);
										})}
									</div>
								</div>
							</div>

							<div className="space-y-6">
								<h3 className="font-bold text-base border-b pb-2">
									Working Hours / Timing
								</h3>
								{form.departments.length === 0 ? (
									<div className="text-base text-muted-foreground italic py-24 text-center border-2 border-dashed rounded-lg">
										Select a department to configure timing slots
									</div>
								) : (
									<div className="space-y-8">
										{form.departments.map((dep: any) => {
											const depName = departments.find(
												(d) => d.departmentId === dep.departmentId,
											)?.name;
											return (
												<div
													key={dep.departmentId}
													className="space-y-4 p-5 border rounded-lg bg-background shadow-sm"
												>
													<div className="flex items-center justify-between">
														<p className="font-bold text-base text-primary">
															{depName}
														</p>
														<Badge variant="outline" className="text-xs">
															Timing Slot
														</Badge>
													</div>
													<div className="grid grid-cols-1 sm:grid-cols-2 gap-x-6 gap-y-3">
														{DAYS.map((day) => (
															<div key={day} className="space-y-1">
																<label className="text-xs uppercase font-bold text-muted-foreground">
																	{day}
																</label>
																<Input
																	className="h-9 text-sm"
																	placeholder="e.g. 09:00 AM - 01:00 PM"
																	value={dep.timing?.[day] || ""}
																	onChange={(e) =>
																		handleTimingChange(
																			dep.departmentId,
																			day,
																			e.target.value,
																		)
																	}
																/>
															</div>
														))}
													</div>
												</div>
											);
										})}
									</div>
								)}
							</div>
						</div>
					</div>

					<DialogFooter className="p-6 border-t bg-background z-10 mt-0">
						<Button
							variant="ghost"
							onClick={() => setOpenModal(false)}
							className="text-base"
						>
							Cancel
						</Button>
						<Button onClick={handleSubmit} className="px-10 text-base">
							{editing ? "Save Changes" : "Create Doctor Profile"}
						</Button>
					</DialogFooter>
				</DialogContent>
			</Dialog>
		</div>
	);
}
