import { useQuery, useMutation } from "@tanstack/react-query";
import { News, insertNewsSchema } from "@shared/schema";
import { Button } from "@/components/ui/button";
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card";
import {
  AlertDialog,
  AlertDialogAction,
  AlertDialogCancel,
  AlertDialogContent,
  AlertDialogDescription,
  AlertDialogFooter,
  AlertDialogHeader,
  AlertDialogTitle,
  AlertDialogTrigger,
} from "@/components/ui/alert-dialog";
import {
  Form,
  FormControl,
  FormField,
  FormItem,
  FormLabel,
  FormMessage,
} from "@/components/ui/form";
import { Input } from "@/components/ui/input";
import { useForm } from "react-hook-form";
import { zodResolver } from "@hookform/resolvers/zod";
import { useToast } from "@/hooks/use-toast";
import { apiRequest, queryClient } from "@/lib/queryClient";
import { Loader2, Plus, Edit, Trash2 } from "lucide-react";
import { useState } from "react";
import { Textarea } from "@/components/ui/textarea";
import { format } from "date-fns";

export default function NewsPage() {
  const { toast } = useToast();
  const [isAdding, setIsAdding] = useState(false);
  const [editingNews, setEditingNews] = useState<News | null>(null);
  const [newsToDelete, setNewsToDelete] = useState<News | null>(null);

  const { data: news, isLoading } = useQuery<News[]>({
    queryKey: ["/api/news"],
  });

  // Set default date to now
  const defaultDate = new Date();
  const defaultDateString = defaultDate.toISOString().slice(0, 16);

  const form = useForm({
    resolver: zodResolver(insertNewsSchema),
    defaultValues: {
      title: "",
      titleAr: "",
      content: "",
      contentAr: "",
      image: "",
      publishDate: defaultDate,
      isPublished: false,
    },
  });

  // Reset form when switching between add/edit modes
  const resetForm = (newsItem?: News) => {
    if (newsItem) {
      form.reset({
        title: newsItem.title,
        titleAr: newsItem.titleAr,
        content: newsItem.content,
        contentAr: newsItem.contentAr,
        image: newsItem.image || "",
        publishDate: new Date(newsItem.publishDate),
        isPublished: newsItem.isPublished,
      });
    } else {
      form.reset({
        title: "",
        titleAr: "",
        content: "",
        contentAr: "",
        image: "",
        publishDate: defaultDate,
        isPublished: false,
      });
    }
  };

  const createNewsMutation = useMutation({
    mutationFn: async (data: any) => {
      const res = await apiRequest("POST", "/api/news", data);
      return res.json();
    },
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ["/api/news"] });
      toast({
        title: "News created",
        description: "The news article has been created successfully.",
      });
      setIsAdding(false);
      form.reset();
    },
    onError: (error: Error) => {
      toast({
        title: "Error",
        description: error.message,
        variant: "destructive",
      });
    },
  });

  const updateNewsMutation = useMutation({
    mutationFn: async (data: any) => {
      if (!editingNews?.id) throw new Error("No news ID provided");
      const res = await apiRequest("PATCH", `/api/news/${editingNews.id}`, data);
      return res.json();
    },
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ["/api/news"] });
      toast({
        title: "News updated",
        description: "The news article has been updated successfully.",
      });
      setEditingNews(null);
      form.reset();
    },
    onError: (error: Error) => {
      toast({
        title: "Error",
        description: error.message,
        variant: "destructive",
      });
    },
  });

  const deleteNewsMutation = useMutation({
    mutationFn: async (newsId: number) => {
      await apiRequest("DELETE", `/api/news/${newsId}`);
    },
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ["/api/news"] });
      toast({
        title: "News deleted",
        description: "The news article has been deleted successfully.",
      });
      setNewsToDelete(null);
    },
    onError: (error: Error) => {
      toast({
        title: "Error",
        description: error.message,
        variant: "destructive",
      });
    },
  });

  if (isLoading) {
    return (
      <div className="flex justify-center">
        <Loader2 className="h-8 w-8 animate-spin" />
      </div>
    );
  }

  return (
    <div className="space-y-8">
      <div className="flex justify-between items-center">
        <h1 className="text-3xl font-bold">News Management</h1>
        <Button
          onClick={() => {
            setIsAdding(true);
            setEditingNews(null);
            resetForm();
          }}
          disabled={isAdding || editingNews !== null}
        >
          <Plus className="h-4 w-4 mr-2" />
          Add News
        </Button>
      </div>

      {(isAdding || editingNews) && (
        <Card>
          <CardHeader>
            <CardTitle>{editingNews ? "Edit News Article" : "Add News Article"}</CardTitle>
          </CardHeader>
          <CardContent>
            <Form {...form}>
              <form
                onSubmit={form.handleSubmit((data) =>
                  editingNews
                    ? updateNewsMutation.mutate(data)
                    : createNewsMutation.mutate(data)
                )}
                className="space-y-4"
              >
                <div className="grid md:grid-cols-2 gap-4">
                  <FormField
                    control={form.control}
                    name="title"
                    render={({ field }) => (
                      <FormItem>
                        <FormLabel>Title (English)</FormLabel>
                        <FormControl>
                          <Input {...field} />
                        </FormControl>
                        <FormMessage />
                      </FormItem>
                    )}
                  />
                  <FormField
                    control={form.control}
                    name="titleAr"
                    render={({ field }) => (
                      <FormItem>
                        <FormLabel>Title (Arabic)</FormLabel>
                        <FormControl>
                          <Input {...field} dir="rtl" />
                        </FormControl>
                        <FormMessage />
                      </FormItem>
                    )}
                  />
                  <FormField
                    control={form.control}
                    name="content"
                    render={({ field }) => (
                      <FormItem>
                        <FormLabel>Content (English)</FormLabel>
                        <FormControl>
                          <Textarea {...field} />
                        </FormControl>
                        <FormMessage />
                      </FormItem>
                    )}
                  />
                  <FormField
                    control={form.control}
                    name="contentAr"
                    render={({ field }) => (
                      <FormItem>
                        <FormLabel>Content (Arabic)</FormLabel>
                        <FormControl>
                          <Textarea {...field} dir="rtl" />
                        </FormControl>
                        <FormMessage />
                      </FormItem>
                    )}
                  />
                  <FormField
                    control={form.control}
                    name="image"
                    render={({ field }) => (
                      <FormItem>
                        <FormLabel>Image</FormLabel>
                        <FormControl>
                          <div className="flex items-center space-x-2">
                            <Input
                              type="file"
                              accept="image/*"
                              onChange={async (e) => {
                                try {
                                  const file = e.target.files?.[0];
                                  if (file) {
                                    const formData = new FormData();
                                    formData.append("file", file);

                                    const res = await fetch("/api/upload", {
                                      method: "POST",
                                      body: formData,
                                    });

                                    if (!res.ok) {
                                      throw new Error(`Upload failed: ${res.status}`);
                                    }

                                    const { url } = await res.json();
                                    field.onChange(url);
                                    form.setValue("image", url, {
                                      shouldDirty: true,
                                      shouldValidate: true,
                                      shouldTouch: true
                                    });

                                    toast({
                                      title: "Upload successful",
                                      description: "News image has been uploaded. Click Update News to save changes.",
                                    });
                                  }
                                } catch (error) {
                                  console.error("Upload error:", error);
                                  toast({
                                    title: "Upload failed",
                                    description: error instanceof Error ? error.message : "Failed to upload image",
                                    variant: "destructive",
                                  });
                                }
                              }}
                            />
                            {field.value && (
                              <img
                                src={field.value}
                                alt="News preview"
                                className="w-10 h-10 rounded object-cover"
                              />
                            )}
                          </div>
                        </FormControl>
                        <FormMessage />
                      </FormItem>
                    )}
                  />
                  <FormField
                    control={form.control}
                    name="publishDate"
                    render={({ field }) => (
                      <FormItem>
                        <FormLabel>Publish Date</FormLabel>
                        <FormControl>
                          <Input
                            type="datetime-local"
                            value={field.value ? new Date(field.value).toISOString().slice(0, 16) : defaultDateString}
                            onChange={(e) => {
                              field.onChange(new Date(e.target.value));
                            }}
                          />
                        </FormControl>
                        <FormMessage />
                      </FormItem>
                    )}
                  />
                </div>
                <div className="flex justify-end gap-4">
                  <Button
                    type="button"
                    variant="outline"
                    onClick={() => {
                      setIsAdding(false);
                      setEditingNews(null);
                      form.reset();
                    }}
                  >
                    Cancel
                  </Button>
                  <Button
                    type="submit"
                    disabled={createNewsMutation.isPending || updateNewsMutation.isPending}
                  >
                    {(createNewsMutation.isPending || updateNewsMutation.isPending) && (
                      <Loader2 className="mr-2 h-4 w-4 animate-spin" />
                    )}
                    {editingNews ? "Update News" : "Create News"}
                  </Button>
                </div>
              </form>
            </Form>
          </CardContent>
        </Card>
      )}

      <div className="grid md:grid-cols-2 gap-4">
        {news?.map((item) => (
          <Card key={item.id}>
            <CardContent className="pt-6">
              <div className="flex justify-between items-start mb-4">
                <div>
                  <h3 className="font-semibold mb-1">{item.title}</h3>
                  <p className="text-sm text-muted-foreground mb-2" dir="rtl">
                    {item.titleAr}
                  </p>
                  <p className="text-sm mb-2">{item.content}</p>
                  <p className="text-sm text-muted-foreground" dir="rtl">
                    {item.contentAr}
                  </p>
                </div>
                <div className="flex gap-2">
                  <Button
                    variant="ghost"
                    size="icon"
                    onClick={() => {
                      setEditingNews(item);
                      setIsAdding(false);
                      resetForm(item);
                    }}
                  >
                    <Edit className="h-4 w-4" />
                  </Button>
                  <AlertDialog>
                    <AlertDialogTrigger asChild>
                      <Button
                        variant="ghost"
                        size="icon"
                        className="text-destructive"
                        onClick={() => setNewsToDelete(item)}
                      >
                        <Trash2 className="h-4 w-4" />
                      </Button>
                    </AlertDialogTrigger>
                    <AlertDialogContent>
                      <AlertDialogHeader>
                        <AlertDialogTitle>Delete News Article</AlertDialogTitle>
                        <AlertDialogDescription>
                          Are you sure you want to delete this news article? This action cannot be undone.
                        </AlertDialogDescription>
                      </AlertDialogHeader>
                      <AlertDialogFooter>
                        <AlertDialogCancel onClick={() => setNewsToDelete(null)}>
                          Cancel
                        </AlertDialogCancel>
                        <AlertDialogAction
                          onClick={() => item.id && deleteNewsMutation.mutate(item.id)}
                          className="bg-destructive text-destructive-foreground hover:bg-destructive/90"
                        >
                          {deleteNewsMutation.isPending ? (
                            <Loader2 className="h-4 w-4 animate-spin" />
                          ) : (
                            "Delete"
                          )}
                        </AlertDialogAction>
                      </AlertDialogFooter>
                    </AlertDialogContent>
                  </AlertDialog>
                </div>
              </div>
              {item.image && (
                <img
                  src={item.image}
                  alt={item.title}
                  className="mt-4 rounded-md w-full h-48 object-cover"
                />
              )}
              <div className="mt-4 text-sm text-muted-foreground">
                {format(new Date(item.publishDate), "PPP")}
              </div>
            </CardContent>
          </Card>
        ))}
      </div>
    </div>
  );
}