import { useState, ReactNode } from "react";
import { Head } from '@inertiajs/react';
import { useAuth } from "@/hooks/useAuth";
import { useQuery, useMutation, useQueryClient } from "@tanstack/react-query";
import AdminLayout from '@/layouts/AdminLayout';
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card";
import { Badge } from "@/components/ui/badge";
import { Table, TableBody, TableCell, TableHead, TableHeader, TableRow } from "@/components/ui/table";
import { Calendar, Clock, MapPin, Users, BookOpen, AlertCircle, ShoppingCart, Building2, XCircle, CalendarClock } from "lucide-react";
import { format, addDays, isAfter, isBefore, startOfDay } from "date-fns";
import { Button } from "@/components/ui/button";
import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogFooter, DialogDescription } from "@/components/ui/dialog";
import { Input } from "@/components/ui/input";
import { Label } from "@/components/ui/label";
import { Textarea } from "@/components/ui/textarea";
import { toast } from "sonner";
import TrainerAvailabilityPanel from "@/components/admin/TrainerAvailabilityPanel";

const csrfToken = () =>
  (document.querySelector('meta[name="csrf-token"]') as HTMLMetaElement | null)?.content ?? '';

/* ─── Purchasing-company view ───────────────────────────────── */
const PurchasingCompanySchedule = ({ companyId, companyName }: { companyId: string; companyName: string }) => {
  const today = startOfDay(new Date());
  const queryClient = useQueryClient();
  const [cancelDialog, setCancelDialog] = useState<{ open: boolean; order: any | null }>({ open: false, order: null });
  const [rescheduleDialog, setRescheduleDialog] = useState<{ open: boolean; order: any | null }>({ open: false, order: null });
  const [newDate, setNewDate] = useState("");
  const [reason, setReason] = useState("");
  const [processing, setProcessing] = useState(false);

  const { data: orders, isLoading } = useQuery({
    queryKey: ["purchasing-company-orders", companyId],
    queryFn: async () => {
      const res = await fetch(`/api/admin/companies/${companyId}/orders?status=paid,confirmed`);
      if (!res.ok) return [];
      return res.json();
    },
  });

  // Fetch pending/approved reschedule requests for this company's orders
  const orderIds = orders?.map((o: any) => o.id) || [];
  const { data: rescheduleRequests } = useQuery({
    queryKey: ["purchasing-reschedule-requests", orderIds],
    enabled: orderIds.length > 0,
    queryFn: async () => {
      const res = await fetch(`/api/admin/companies/${companyId}/reschedule-requests`);
      if (!res.ok) return [];
      return res.json();
    },
  });

  // Map order_id → latest reschedule request
  const rescheduleByOrder = new Map<string, { status: string; requested_date: string }>();
  rescheduleRequests?.forEach((r: any) => {
    if (!rescheduleByOrder.has(r.order_id)) {
      rescheduleByOrder.set(r.order_id, { status: r.status, requested_date: r.requested_date });
    }
  });

  const upcoming = orders?.filter((o: any) => isAfter(new Date(o.start_date), addDays(today, -1))) || [];
  const thisMonth = upcoming.filter((o: any) => isBefore(new Date(o.start_date), addDays(today, 30)));
  const totalDelegates = upcoming.reduce((s: number, o: any) => s + (o.booking_delegates?.length || o.num_delegates || 0), 0);

  const handleCancel = async () => {
    if (!cancelDialog.order) return;
    setProcessing(true);
    try {
      const res = await fetch(`/api/admin/orders/${cancelDialog.order.id}/cancel`, {
        method: 'POST',
        headers: { 'Content-Type': 'application/json', 'X-CSRF-TOKEN': csrfToken() },
        body: JSON.stringify({}),
      });
      if (!res.ok) throw new Error('Failed to cancel');
      toast.success("Booking cancelled successfully");
      queryClient.invalidateQueries({ queryKey: ["purchasing-company-orders"] });
      setCancelDialog({ open: false, order: null });
    } catch (e: any) {
      toast.error(e.message || "Failed to cancel booking");
    } finally {
      setProcessing(false);
    }
  };

  const handleReschedule = async () => {
    if (!rescheduleDialog.order || !newDate) return;
    const order = rescheduleDialog.order;
    setProcessing(true);
    try {
      const res = await fetch('/api/admin/date-change-requests', {
        method: 'POST',
        headers: { 'Content-Type': 'application/json', 'X-CSRF-TOKEN': csrfToken() },
        body: JSON.stringify({
          order_id: order.id,
          requested_date: newDate,
          reason: reason || null,
          status: "pending",
          trainer_id: order.trainer_id || null,
          company_name: companyName,
          course_title: (order as any).courses?.title || "a course",
        }),
      });
      if (!res.ok) {
        const err = await res.json().catch(() => ({ message: 'Failed' }));
        throw new Error(err.message || 'Failed to submit request');
      }

      toast.success("Reschedule request submitted — you can track it in the Status column");
      queryClient.invalidateQueries({ queryKey: ["purchasing-reschedule-requests"] });
      queryClient.invalidateQueries({ queryKey: ["notif-pending-reschedules"] });
      setRescheduleDialog({ open: false, order: null });
      setNewDate("");
      setReason("");
    } catch (e: any) {
      toast.error(e.message || "Failed to submit request");
    } finally {
      setProcessing(false);
    }
  };

  return (
    <div>
      <div className="flex items-center gap-3 mb-6">
        <Building2 className="h-6 w-6 text-primary" />
        <div>
          <h1 className="text-2xl font-bold text-foreground">{companyName}</h1>
          <p className="text-sm text-muted-foreground">Purchasing Company — Booked Training</p>
        </div>
      </div>

      {/* KPI Cards */}
      <div className="grid grid-cols-1 sm:grid-cols-3 gap-4 mb-8">
        <Card>
          <CardContent className="pt-6">
            <div className="flex items-center gap-3">
              <ShoppingCart className="h-8 w-8 text-primary" />
              <div>
                <p className="text-2xl font-bold text-foreground">{upcoming.length}</p>
                <p className="text-sm text-muted-foreground">Upcoming bookings</p>
              </div>
            </div>
          </CardContent>
        </Card>
        <Card>
          <CardContent className="pt-6">
            <div className="flex items-center gap-3">
              <Calendar className="h-8 w-8 text-primary" />
              <div>
                <p className="text-2xl font-bold text-foreground">{thisMonth.length}</p>
                <p className="text-sm text-muted-foreground">Next 30 days</p>
              </div>
            </div>
          </CardContent>
        </Card>
        <Card>
          <CardContent className="pt-6">
            <div className="flex items-center gap-3">
              <Users className="h-8 w-8 text-primary" />
              <div>
                <p className="text-2xl font-bold text-foreground">{totalDelegates}</p>
                <p className="text-sm text-muted-foreground">Delegates booked</p>
              </div>
            </div>
          </CardContent>
        </Card>
      </div>

      {/* Bookings Table */}
      <Card>
        <CardHeader>
          <CardTitle className="text-lg">Upcoming Bookings</CardTitle>
        </CardHeader>
        <CardContent>
          {isLoading ? (
            <p className="text-muted-foreground text-xs">Loading...</p>
          ) : upcoming.length === 0 ? (
            <p className="text-muted-foreground text-center py-8 text-xs">No upcoming bookings.</p>
          ) : (
            <Table>
              <TableHeader>
                <TableRow>
                  <TableHead className="text-xs">Date</TableHead>
                  <TableHead className="text-xs">Course</TableHead>
                  <TableHead className="text-xs">Location</TableHead>
                  <TableHead className="text-xs">Delegates</TableHead>
                  <TableHead className="text-xs">Status</TableHead>
                  <TableHead className="text-xs text-right">Actions</TableHead>
                </TableRow>
              </TableHeader>
              <TableBody>
                {upcoming.map((order: any) => {
                  const course = (order as any).courses;
                  const venue = (order as any).venues;
                  const delegates = (order as any).booking_delegates || [];
                  const daysUntil = Math.ceil((new Date(order.start_date).getTime() - today.getTime()) / 86400000);

                  return (
                    <TableRow key={order.id} className={`text-xs ${daysUntil <= 3 ? "bg-amber-50/50 dark:bg-amber-950/10" : ""}`}>
                      <TableCell className="py-2">
                        <div className="font-medium text-xs">
                          {format(new Date(order.start_date + "T00:00:00"), "EEE d MMM yyyy")}
                        </div>
                        <div className="text-[10px] text-muted-foreground">
                          {course?.days || 1} day{(course?.days || 1) > 1 ? "s" : ""}
                          {daysUntil <= 7 && (
                            <Badge variant={daysUntil <= 1 ? "destructive" : "secondary"} className="ml-1 text-[9px] px-1 py-0">
                              {daysUntil <= 0 ? "Today" : `${daysUntil}d`}
                            </Badge>
                          )}
                        </div>
                      </TableCell>
                      <TableCell className="py-2 font-medium text-xs">{course?.title || "—"}</TableCell>
                      <TableCell className="py-2">
                        <div className="flex items-center gap-1 text-xs">
                          <MapPin className="h-3 w-3 text-muted-foreground" />
                          {venue?.name ? `${venue.name}, ${venue.city || ""}` : course?.location_name || "TBC"}
                        </div>
                      </TableCell>
                      <TableCell className="py-2">
                        <div className="text-xs">
                          {delegates.length > 0 ? (
                            <details className="cursor-pointer">
                              <summary className="text-primary">{delegates.length} delegate{delegates.length !== 1 ? "s" : ""}</summary>
                              <ul className="mt-1 text-[10px] text-muted-foreground space-y-0.5">
                                {delegates.map((d: any) => (
                                  <li key={d.id}>{d.first_name} {d.last_name}</li>
                                ))}
                              </ul>
                            </details>
                          ) : (
                            <span className="text-muted-foreground">{order.num_delegates || "—"}</span>
                          )}
                        </div>
                      </TableCell>
                      <TableCell className="py-2">
                        {(() => {
                          const rr = rescheduleByOrder.get(order.id);
                          if (rr?.status === "pending") {
                            return (
                              <div>
                                <Badge variant="secondary" className="text-[10px] px-1.5 py-0 bg-amber-100 text-amber-800 border-amber-300">
                                  Reschedule Pending
                                </Badge>
                                <div className="text-[9px] text-muted-foreground mt-0.5">
                                  Requested: {format(new Date(rr.requested_date + "T00:00:00"), "d MMM yyyy")}
                                </div>
                              </div>
                            );
                          }
                          if (rr?.status === "approved") {
                            return (
                              <Badge variant="secondary" className="text-[10px] px-1.5 py-0 bg-green-100 text-green-800 border-green-300">
                                Rescheduled
                              </Badge>
                            );
                          }
                          return <Badge variant="default" className="capitalize text-[10px] px-1.5 py-0">{order.status}</Badge>;
                        })()}
                      </TableCell>
                      <TableCell className="py-2 text-right">
                        <div className="flex items-center justify-end gap-1">
                          <Button
                            variant="ghost"
                            size="sm"
                            className="h-6 px-2 text-[10px]"
                            disabled={rescheduleByOrder.has(order.id)}
                            onClick={() => { setRescheduleDialog({ open: true, order }); setNewDate(""); setReason(""); }}
                          >
                            <CalendarClock className="h-3 w-3 mr-1" />
                            {rescheduleByOrder.has(order.id) ? "Pending" : "Reschedule"}
                          </Button>
                          <Button
                            variant="ghost"
                            size="sm"
                            className="h-6 px-2 text-[10px] text-destructive hover:bg-destructive hover:text-destructive-foreground"
                            onClick={() => setCancelDialog({ open: true, order })}
                          >
                            <XCircle className="h-3 w-3 mr-1" />
                            Cancel
                          </Button>
                        </div>
                      </TableCell>
                    </TableRow>
                  );
                })}
              </TableBody>
            </Table>
          )}
        </CardContent>
      </Card>

      {/* Cancel Dialog */}
      <Dialog open={cancelDialog.open} onOpenChange={(o) => !o && setCancelDialog({ open: false, order: null })}>
        <DialogContent>
          <DialogHeader>
            <DialogTitle>Cancel Booking</DialogTitle>
            <DialogDescription>
              Are you sure you want to cancel <strong>{(cancelDialog.order as any)?.courses?.title}</strong> on{" "}
              {cancelDialog.order && format(new Date(cancelDialog.order.start_date + "T00:00:00"), "d MMM yyyy")}?
            </DialogDescription>
          </DialogHeader>
          <DialogFooter>
            <Button variant="outline" onClick={() => setCancelDialog({ open: false, order: null })}>Keep Booking</Button>
            <Button variant="destructive" onClick={handleCancel} disabled={processing}>
              {processing ? "Cancelling…" : "Confirm Cancel"}
            </Button>
          </DialogFooter>
        </DialogContent>
      </Dialog>

      {/* Reschedule Dialog */}
      <Dialog open={rescheduleDialog.open} onOpenChange={(o) => !o && setRescheduleDialog({ open: false, order: null })}>
        <DialogContent>
          <DialogHeader>
            <DialogTitle>Request Reschedule</DialogTitle>
            <DialogDescription>
              Request a new date for <strong>{(rescheduleDialog.order as any)?.courses?.title}</strong> (currently{" "}
              {rescheduleDialog.order && format(new Date(rescheduleDialog.order.start_date + "T00:00:00"), "d MMM yyyy")}).
            </DialogDescription>
          </DialogHeader>
          <div className="space-y-3 py-2">
            <div>
              <Label className="text-xs">New Preferred Date</Label>
              <Input type="date" value={newDate} onChange={(e) => setNewDate(e.target.value)} />
            </div>
            <div>
              <Label className="text-xs">Reason (optional)</Label>
              <Textarea value={reason} onChange={(e) => setReason(e.target.value)} rows={2} placeholder="Why do you need to reschedule?" />
            </div>
          </div>
          <DialogFooter>
            <Button variant="outline" onClick={() => setRescheduleDialog({ open: false, order: null })}>Cancel</Button>
            <Button onClick={handleReschedule} disabled={processing || !newDate}>
              {processing ? "Submitting…" : "Submit Request"}
            </Button>
          </DialogFooter>
        </DialogContent>
      </Dialog>
    </div>
  );
};

/* ─── Trainer schedule view (training companies) ────────────── */
const TrainerScheduleView = ({ userEmail }: { userEmail: string }) => {
  const { data: trainer } = useQuery({
    queryKey: ["my-trainer-profile", userEmail],
    queryFn: async () => {
      const res = await fetch(`/api/admin/trainers/by-email?email=${encodeURIComponent(userEmail)}`);
      if (!res.ok) return null;
      return res.json();
    },
  });

  const { data: bookings, isLoading } = useQuery({
    queryKey: ["trainer-bookings", trainer?.id],
    enabled: !!trainer?.id,
    queryFn: async () => {
      const res = await fetch(`/api/admin/trainers/${trainer!.id}/bookings`);
      if (!res.ok) return [];
      return res.json();
    },
  });

  const { data: overrides } = useQuery({
    queryKey: ["trainer-overrides", trainer?.id],
    enabled: !!trainer?.id,
    queryFn: async () => {
      const res = await fetch(`/api/admin/trainers/${trainer!.id}/overrides?upcoming=true`);
      if (!res.ok) return [];
      return res.json();
    },
  });

  const today = startOfDay(new Date());
  const upcoming = bookings?.filter((b: any) => isAfter(new Date(b.start_date), addDays(today, -1))) || [];
  const thisWeek = upcoming.filter((b: any) => isBefore(new Date(b.start_date), addDays(today, 7)));
  const thisMonth = upcoming.filter((b: any) => isBefore(new Date(b.start_date), addDays(today, 30)));

  if (!trainer) {
    return (
      <div className="flex flex-col items-center justify-center py-20 text-center">
        <AlertCircle className="h-12 w-12 text-muted-foreground mb-4" />
        <h2 className="text-xl font-bold text-foreground mb-2">Trainer Profile Not Found</h2>
        <p className="text-muted-foreground max-w-md">
          Your email ({userEmail}) is not linked to a trainer record. Please contact your administrator.
        </p>
      </div>
    );
  }

  return (
    <div>
      <h1 className="text-2xl font-bold text-foreground mb-6">My Schedule</h1>

      <div className="grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-4 gap-4 mb-8">
        <Card>
          <CardContent className="pt-6">
            <div className="flex items-center gap-3">
              <Calendar className="h-8 w-8 text-primary" />
              <div>
                <p className="text-2xl font-bold text-foreground">{thisWeek.length}</p>
                <p className="text-sm text-muted-foreground">This week</p>
              </div>
            </div>
          </CardContent>
        </Card>
        <Card>
          <CardContent className="pt-6">
            <div className="flex items-center gap-3">
              <BookOpen className="h-8 w-8 text-primary" />
              <div>
                <p className="text-2xl font-bold text-foreground">{thisMonth.length}</p>
                <p className="text-sm text-muted-foreground">Next 30 days</p>
              </div>
            </div>
          </CardContent>
        </Card>
        <Card>
          <CardContent className="pt-6">
            <div className="flex items-center gap-3">
              <Users className="h-8 w-8 text-primary" />
              <div>
                <p className="text-2xl font-bold text-foreground">
                  {upcoming.reduce((sum: number, b: any) => sum + (b.booking_delegates?.length || b.num_delegates || 0), 0)}
                </p>
                <p className="text-sm text-muted-foreground">Upcoming delegates</p>
              </div>
            </div>
          </CardContent>
        </Card>
        <Card>
          <CardContent className="pt-6">
            <div className="flex items-center gap-3">
              <Clock className="h-8 w-8 text-muted-foreground" />
              <div>
                <p className="text-2xl font-bold text-foreground">
                  {overrides?.filter((o: any) => !o.is_available).length || 0}
                </p>
                <p className="text-sm text-muted-foreground">Days blocked</p>
              </div>
            </div>
          </CardContent>
        </Card>
      </div>

      <Card className="mb-6">
        <CardHeader>
          <CardTitle className="text-lg">Upcoming Sessions</CardTitle>
        </CardHeader>
        <CardContent>
          {isLoading ? (
            <p className="text-muted-foreground">Loading...</p>
          ) : upcoming.length === 0 ? (
            <p className="text-muted-foreground text-center py-8">No upcoming sessions scheduled.</p>
          ) : (
            <Table>
              <TableHeader>
                <TableRow>
                  <TableHead>Date</TableHead>
                  <TableHead>Course</TableHead>
                  <TableHead>Location</TableHead>
                  <TableHead>Delegates</TableHead>
                  <TableHead>Status</TableHead>
                </TableRow>
              </TableHeader>
              <TableBody>
                {upcoming.map((booking: any) => {
                  const course = (booking as any).courses;
                  const venue = (booking as any).venues;
                  const delegates = (booking as any).booking_delegates || [];
                  const daysUntil = Math.ceil((new Date(booking.start_date).getTime() - today.getTime()) / 86400000);

                  return (
                    <TableRow key={booking.id} className={daysUntil <= 3 ? "bg-amber-50/50 dark:bg-amber-950/10" : ""}>
                      <TableCell>
                        <div className="font-medium">
                          {format(new Date(booking.start_date + "T00:00:00"), "EEE d MMM yyyy")}
                        </div>
                        <div className="text-xs text-muted-foreground">
                          {course?.days || 1} day{(course?.days || 1) > 1 ? "s" : ""}
                          {daysUntil <= 7 && (
                            <Badge variant={daysUntil <= 1 ? "destructive" : "secondary"} className="ml-2 text-[10px]">
                              {daysUntil <= 0 ? "Today" : `${daysUntil}d away`}
                            </Badge>
                          )}
                        </div>
                      </TableCell>
                      <TableCell className="font-medium">{course?.title || "—"}</TableCell>
                      <TableCell>
                        <div className="flex items-center gap-1 text-sm">
                          <MapPin className="h-3 w-3 text-muted-foreground" />
                          {venue?.name ? `${venue.name}, ${venue.city || ""}` : course?.location_name || "TBC"}
                        </div>
                      </TableCell>
                      <TableCell>
                        <div className="text-sm">
                          {delegates.length > 0 ? (
                            <details className="cursor-pointer">
                              <summary className="text-primary">{delegates.length} delegate{delegates.length !== 1 ? "s" : ""}</summary>
                              <ul className="mt-1 text-xs text-muted-foreground space-y-0.5">
                                {delegates.map((d: any) => (
                                  <li key={d.id}>{d.first_name} {d.last_name} {d.email ? `(${d.email})` : ""}</li>
                                ))}
                              </ul>
                            </details>
                          ) : (
                            <span className="text-muted-foreground">{booking.num_delegates || "—"}</span>
                          )}
                        </div>
                      </TableCell>
                      <TableCell>
                        <Badge variant="default" className="capitalize">{booking.status}</Badge>
                      </TableCell>
                    </TableRow>
                  );
                })}
              </TableBody>
            </Table>
          )}
        </CardContent>
      </Card>

      {overrides && overrides.filter((o: any) => !o.is_available).length > 0 && (
        <Card className="mb-6">
          <CardHeader>
            <CardTitle className="text-lg">Blocked Days</CardTitle>
          </CardHeader>
          <CardContent>
            <div className="flex flex-wrap gap-2">
              {overrides
                .filter((o: any) => !o.is_available)
                .map((o: any) => (
                  <Badge key={o.id} variant="outline" className="text-sm py-1 px-3">
                    {format(new Date(o.override_date + "T00:00:00"), "EEE d MMM")}
                    {o.reason && <span className="ml-1 text-muted-foreground">— {o.reason}</span>}
                  </Badge>
                ))}
            </div>
          </CardContent>
        </Card>
      )}

      <TrainerAvailabilityPanel
        trainerId={trainer.id}
        trainerName={`${trainer.first_name} ${trainer.last_name}`}
      />
    </div>
  );
};

/* ─── Main page — routes to the correct view ────────────────── */
const TrainerSchedule = () => {
  const { user, companyId } = useAuth();

  const { data: company } = useQuery({
    queryKey: ["my-company-type", companyId],
    enabled: !!companyId,
    queryFn: async () => {
      const res = await fetch(`/api/admin/companies/${companyId}`);
      if (!res.ok) return null;
      return res.json();
    },
  });

  if (!user) return null;

  const isPurchasing = company?.company_type === "customer_company";

  if (isPurchasing && companyId && company) {
    return (
      <>
        <Head title={company.name} />
        <PurchasingCompanySchedule companyId={companyId} companyName={company.name} />
      </>
    );
  }

  return (
    <>
      <Head title="My Schedule" />
      <TrainerScheduleView userEmail={user.email!} />
    </>
  );
};

TrainerSchedule.layout = (page: ReactNode) => <AdminLayout>{page}</AdminLayout>;

export default TrainerSchedule;
