import { useMemo, useState } from "react";
import { useParams } from "react-router-dom";
import { useCourseDetail, useUpdateCourse } from "@/hooks/queries/useCourseGeneration";
import { courseGenerationService } from "@/services/course-generation.service";
import type { ModuleConfig } from "@/types";
import { Button } from "@/components/ui/button";
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card";
import { Collapsible, CollapsibleContent, CollapsibleTrigger } from "@/components/ui/collapsible";
import { Input } from "@/components/ui/input";
import { Label } from "@/components/ui/label";
import { Textarea } from "@/components/ui/textarea";
import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "@/components/ui/select";
import {
  Dialog,
  DialogContent,
  DialogFooter,
  DialogHeader,
  DialogTitle,
} from "@/components/ui/dialog";
import { ScrollArea } from "@/components/ui/scroll-area";
import { Separator } from "@/components/ui/separator";
import { Skeleton } from "@/components/ui/skeleton";
import { ChevronDown, GripVertical, Search, Sparkles } from "lucide-react";
import { cn } from "@/lib/utils";

export default function ModuleBuilder() {
  const { courseId: courseIdParam } = useParams();
  const courseId = Number(courseIdParam);
  const { data: course, isLoading } = useCourseDetail(courseId);
  const updateCourse = useUpdateCourse();

  const [modules, setModules] = useState<ModuleConfig[] | null>(null);
  const [resourceOpen, setResourceOpen] = useState(false);
  const [aiOpen, setAiOpen] = useState(false);
  const [aiForm, setAiForm] = useState({ topic: "", difficulty: "B2", type: "reading" });
  const [dragId, setDragId] = useState<number | null>(null);

  const mergedModules = modules ?? course?.modules ?? [];

  const bySkill = useMemo(() => {
    const map = new Map<string, ModuleConfig[]>();
    mergedModules.forEach((m) => {
      const k = m.skill || "General";
      if (!map.has(k)) map.set(k, []);
      map.get(k)!.push(m);
    });
    return map;
  }, [mergedModules]);

  const totalHours = mergedModules.reduce((s, m) => s + m.estimated_hours, 0);

  const syncModules = (next: ModuleConfig[]) => {
    setModules(next);
    if (course) {
      updateCourse.mutate({
        courseId,
        payload: { modules: next },
      });
    }
  };

  const onDragStart = (id: number) => setDragId(id);
  const onDrop = (targetId: number) => {
    if (dragId === null || dragId === targetId) return;
    const list = [...mergedModules];
    const from = list.findIndex((m) => m.id === dragId);
    const to = list.findIndex((m) => m.id === targetId);
    if (from < 0 || to < 0) return;
    const [item] = list.splice(from, 1);
    list.splice(to, 0, item);
    syncModules(list);
    setDragId(null);
  };

  const publish = () => {
    updateCourse.mutate({ courseId, payload: { status: "published" } });
  };

  if (isLoading) {
    return (
      <div className="p-6">
        <Skeleton className="mb-4 h-10 w-64" />
        <Skeleton className="h-96 w-full" />
      </div>
    );
  }

  return (
    <div className="mx-auto max-w-5xl space-y-6 p-6">
      <div className="flex flex-wrap items-center justify-between gap-4">
        <div>
          <h1 className="text-2xl font-bold">Module builder</h1>
          <p className="text-muted-foreground">
            {course?.title ?? `Course #${courseId}`} · {totalHours}h total · {mergedModules.length} modules
          </p>
        </div>
        <Button type="button" onClick={publish} disabled={updateCourse.isPending}>
          Publish Course
        </Button>
      </div>

      <div className="space-y-4">
        {mergedModules.length === 0 && (
          <Card>
            <CardContent className="flex flex-col items-center justify-center py-16 text-center">
              <Sparkles className="h-10 w-10 text-muted-foreground mb-4" />
              <h3 className="text-lg font-medium mb-1">No modules yet</h3>
              <p className="text-sm text-muted-foreground mb-4">
                Add modules manually or use the AI assistant to auto-generate a module structure.
              </p>
              <div className="flex gap-2">
                <Button
                  type="button"
                  onClick={() => {
                    const next: ModuleConfig[] = [
                      { id: Date.now(), title: "New Module", skill: "Listening", estimated_hours: 2, resources: [], assessment_type: "quiz" },
                    ];
                    syncModules(next);
                  }}
                >
                  Add Module
                </Button>
                <Button type="button" variant="outline" onClick={() => setAiOpen(true)}>
                  <Sparkles className="mr-2 h-4 w-4" />
                  AI Generate
                </Button>
              </div>
            </CardContent>
          </Card>
        )}
        {Array.from(bySkill.entries()).map(([skill, mods]) => (
          <Collapsible key={skill} defaultOpen>
            <Card>
              <CollapsibleTrigger asChild>
                <CardHeader className="flex cursor-pointer flex-row items-center justify-between">
                  <CardTitle className="text-lg">
                    {skill} · {mods.reduce((s, m) => s + m.estimated_hours, 0)}h · {mods.length} modules
                  </CardTitle>
                  <ChevronDown className="h-5 w-5" />
                </CardHeader>
              </CollapsibleTrigger>
              <CollapsibleContent>
                <CardContent className="space-y-4 pt-0">
                  {mods.map((mod, idx) => (
                    <div
                      key={mod.id}
                      draggable
                      onDragStart={() => onDragStart(mod.id)}
                      onDragOver={(e) => e.preventDefault()}
                      onDrop={() => onDrop(mod.id)}
                      className={cn("rounded-lg border p-4", dragId === mod.id && "opacity-60")}
                    >
                      <div className="mb-3 flex items-center gap-2">
                        <GripVertical className="h-5 w-5 text-muted-foreground" />
                        <span className="font-medium">
                          Module {idx + 1}: {mod.title}
                        </span>
                      </div>
                      <div className="grid gap-3 md:grid-cols-2">
                        <div className="space-y-2">
                          <Label htmlFor={`t-${mod.id}`}>Title</Label>
                          <Input
                            id={`t-${mod.id}`}
                            defaultValue={mod.title}
                            onBlur={(e) => {
                              const next = mergedModules.map((m) =>
                                m.id === mod.id ? { ...m, title: e.target.value } : m,
                              );
                              syncModules(next);
                            }}
                          />
                        </div>
                        <div className="space-y-2">
                          <Label htmlFor={`h-${mod.id}`}>Hours</Label>
                          <Input
                            id={`h-${mod.id}`}
                            type="number"
                            defaultValue={mod.estimated_hours}
                            onBlur={(e) => {
                              const v = Number(e.target.value);
                              const next = mergedModules.map((m) =>
                                m.id === mod.id ? { ...m, estimated_hours: v } : m,
                              );
                              syncModules(next);
                            }}
                          />
                        </div>
                      </div>
                      <div className="mt-3 space-y-2">
                        <Label>Resources</Label>
                        <div className="flex flex-wrap gap-2">
                          {mod.resources.map((r) => (
                            <span key={r.id} className="rounded-md bg-muted px-2 py-1 text-xs">
                              {r.title} ({r.type})
                            </span>
                          ))}
                          <Button type="button" size="sm" variant="outline" onClick={() => setResourceOpen(true)}>
                            <Search className="mr-1 h-3 w-3" />
                            Browse Resources
                          </Button>
                        </div>
                      </div>
                      <div className="mt-3 space-y-2">
                        <Label htmlFor={`ex-${mod.id}`}>Practice exercises</Label>
                        <Textarea id={`ex-${mod.id}`} placeholder="Describe linked exercises" rows={2} />
                      </div>
                        <div className="mt-3 grid gap-3 md:grid-cols-2">
                        <div className="space-y-2">
                          <Label>Completion criteria</Label>
                          <Select
                            defaultValue={mod.completion_criteria}
                            onValueChange={(val) => {
                              const v = val as ModuleConfig["completion_criteria"];
                              const next = mergedModules.map((m) =>
                                m.id === mod.id ? { ...m, completion_criteria: v } : m,
                              );
                              syncModules(next);
                            }}
                          >
                            <SelectTrigger>
                              <SelectValue placeholder="Criteria" />
                            </SelectTrigger>
                            <SelectContent>
                              <SelectItem value="complete_all">complete_all</SelectItem>
                              <SelectItem value="score_threshold">score_threshold</SelectItem>
                              <SelectItem value="teacher_approval">teacher_approval</SelectItem>
                            </SelectContent>
                          </Select>
                        </div>
                        <div className="space-y-2">
                          <Label htmlFor={`pre-${mod.id}`}>Prerequisite module id</Label>
                          <Input
                            id={`pre-${mod.id}`}
                            type="number"
                            defaultValue={mod.prerequisite_module_id ?? ""}
                            onBlur={(e) => {
                              const v = e.target.value ? Number(e.target.value) : undefined;
                              const next = mergedModules.map((m) =>
                                m.id === mod.id ? { ...m, prerequisite_module_id: v } : m,
                              );
                              syncModules(next);
                            }}
                          />
                        </div>
                      </div>
                      <Separator className="my-3" />
                      <Button
                        type="button"
                        size="sm"
                        variant="secondary"
                        onClick={() => setAiOpen(true)}
                      >
                        <Sparkles className="mr-1 h-3 w-3" />
                        Generate AI Content
                      </Button>
                    </div>
                  ))}
                </CardContent>
              </CollapsibleContent>
            </Card>
          </Collapsible>
        ))}
      </div>

      <Dialog open={resourceOpen} onOpenChange={setResourceOpen}>
        <DialogContent>
          <DialogHeader>
            <DialogTitle>Resource search</DialogTitle>
          </DialogHeader>
          <div className="space-y-2">
            <Input placeholder="Search title, skill, or tag" />
            <ScrollArea className="h-48 rounded-md border p-2 text-sm text-muted-foreground">
              Matching resources will list here from your library.
            </ScrollArea>
          </div>
          <DialogFooter>
            <Button type="button" variant="outline" onClick={() => setResourceOpen(false)}>
              Close
            </Button>
          </DialogFooter>
        </DialogContent>
      </Dialog>

      <Dialog open={aiOpen} onOpenChange={setAiOpen}>
        <DialogContent>
          <DialogHeader>
            <DialogTitle>Generate AI content</DialogTitle>
          </DialogHeader>
          <div className="space-y-3">
            <div className="space-y-2">
              <Label htmlFor="ai-topic">Topic</Label>
              <Input
                id="ai-topic"
                value={aiForm.topic}
                onChange={(e) => setAiForm((f) => ({ ...f, topic: e.target.value }))}
              />
            </div>
            <div className="space-y-2">
              <Label htmlFor="ai-diff">Difficulty</Label>
              <Input
                id="ai-diff"
                value={aiForm.difficulty}
                onChange={(e) => setAiForm((f) => ({ ...f, difficulty: e.target.value }))}
              />
            </div>
            <div className="space-y-2">
              <Label htmlFor="ai-type">Type</Label>
              <Input
                id="ai-type"
                value={aiForm.type}
                onChange={(e) => setAiForm((f) => ({ ...f, type: e.target.value }))}
              />
            </div>
          </div>
          <DialogFooter>
            <Button
              type="button"
              onClick={() => {
                void courseGenerationService
                  .generateAIResource({
                    topic: aiForm.topic,
                    difficulty: aiForm.difficulty,
                    type: aiForm.type,
                  })
                  .then(() => setAiOpen(false));
              }}
            >
              Generate
            </Button>
          </DialogFooter>
        </DialogContent>
      </Dialog>
    </div>
  );
}
