import React, { useState, FC } from "react";

import { useRouter } from "next/router";

import useSWR, { mutate } from "swr";

// icons
import { PlusIcon } from "@heroicons/react/24/outline";
// hooks
import useToast from "hooks/use-toast";
import useTheme from "hooks/use-theme";
// services
import projectService from "services/project.service";
// components
import { CreateProjectModal, DeleteProjectModal, SingleSidebarProject } from "components/project";
// ui
import { Loader } from "components/ui";
// helpers
import { copyTextToClipboard } from "helpers/string.helper";
// types
import { IFavoriteProject, IProject } from "types";
// fetch-keys
import { FAVORITE_PROJECTS_LIST, PROJECTS_LIST } from "constants/fetch-keys";

export const ProjectSidebarList: FC = () => {
  const [deleteProjectModal, setDeleteProjectModal] = useState(false);
  const [projectToDelete, setProjectToDelete] = useState<IProject | null>(null);

  // router
  const router = useRouter();
  const { workspaceSlug } = router.query;
  // states
  const [isCreateProjectModal, setCreateProjectModal] = useState(false);
  // theme
  const { collapsed: sidebarCollapse } = useTheme();
  // toast handler
  const { setToastAlert } = useToast();

  const { data: favoriteProjects } = useSWR(
    workspaceSlug ? FAVORITE_PROJECTS_LIST(workspaceSlug as string) : null,
    () => (workspaceSlug ? projectService.getFavoriteProjects(workspaceSlug as string) : null)
  );

  const { data: projects } = useSWR(
    workspaceSlug ? PROJECTS_LIST(workspaceSlug as string) : null,
    () => (workspaceSlug ? projectService.getProjects(workspaceSlug as string) : null)
  );
  const normalProjects = projects?.filter((p) => !p.is_favorite) ?? [];

  const handleAddToFavorites = (project: IProject) => {
    if (!workspaceSlug) return;

    projectService
      .addProjectToFavorites(workspaceSlug as string, {
        project: project.id,
      })
      .then(() => {
        mutate<IProject[]>(
          PROJECTS_LIST(workspaceSlug as string),
          (prevData) =>
            (prevData ?? []).map((p) => ({
              ...p,
              is_favorite: p.id === project.id ? true : p.is_favorite,
            })),
          false
        );
        mutate(FAVORITE_PROJECTS_LIST(workspaceSlug as string));

        setToastAlert({
          type: "success",
          title: "Success!",
          message: "Successfully added the project to favorites.",
        });
      })
      .catch(() => {
        setToastAlert({
          type: "error",
          title: "Error!",
          message: "Couldn't remove the project from favorites. Please try again.",
        });
      });
  };

  const handleRemoveFromFavorites = (project: IProject) => {
    if (!workspaceSlug) return;

    projectService
      .removeProjectFromFavorites(workspaceSlug as string, project.id)
      .then(() => {
        mutate<IProject[]>(
          PROJECTS_LIST(workspaceSlug as string),
          (prevData) =>
            (prevData ?? []).map((p) => ({
              ...p,
              is_favorite: p.id === project.id ? false : p.is_favorite,
            })),
          false
        );
        mutate<IFavoriteProject[]>(
          FAVORITE_PROJECTS_LIST(workspaceSlug as string),
          (prevData) => (prevData ?? []).filter((p) => p.project !== project.id),
          false
        );

        setToastAlert({
          type: "success",
          title: "Success!",
          message: "Successfully removed the project from favorites.",
        });
      })
      .catch(() => {
        setToastAlert({
          type: "error",
          title: "Error!",
          message: "Couldn't remove the project from favorites. Please try again.",
        });
      });
  };

  const handleDeleteProject = (project: IProject) => {
    setProjectToDelete(project);
    setDeleteProjectModal(true);
  };

  const handleCopyText = (projectId: string) => {
    const originURL =
      typeof window !== "undefined" && window.location.origin ? window.location.origin : "";
    copyTextToClipboard(`${originURL}/${workspaceSlug}/projects/${projectId}/issues`).then(() => {
      setToastAlert({
        type: "success",
        title: "Link Copied!",
        message: "Project link copied to clipboard.",
      });
    });
  };

  return (
    <>
      <CreateProjectModal isOpen={isCreateProjectModal} setIsOpen={setCreateProjectModal} />
      <DeleteProjectModal
        isOpen={deleteProjectModal}
        onClose={() => setDeleteProjectModal(false)}
        data={projectToDelete}
      />
      <div className="mt-2.5 h-full overflow-y-auto border-t bg-white pt-2.5">
        {favoriteProjects && favoriteProjects.length > 0 && (
          <div className="mt-3 flex flex-col space-y-2 px-6">
            {!sidebarCollapse && <h5 className="text-sm font-semibold text-gray-400">Favorites</h5>}
            {favoriteProjects.map((favoriteProject) => {
              const project = favoriteProject.project_detail;

              return (
                <SingleSidebarProject
                  key={project.id}
                  project={project}
                  sidebarCollapse={sidebarCollapse}
                  handleDeleteProject={() => handleDeleteProject(project)}
                  handleCopyText={() => handleCopyText(project.id)}
                  handleRemoveFromFavorites={() => handleRemoveFromFavorites(project)}
                />
              );
            })}
          </div>
        )}
        <div className="mt-3 flex flex-col space-y-2 px-6 pb-3">
          {!sidebarCollapse && <h5 className="text-sm font-semibold text-gray-400">Projects</h5>}
          {projects ? (
            <>
              {normalProjects.length > 0 ? (
                normalProjects.map((project) => (
                  <SingleSidebarProject
                    key={project.id}
                    project={project}
                    sidebarCollapse={sidebarCollapse}
                    handleDeleteProject={() => handleDeleteProject(project)}
                    handleCopyText={() => handleCopyText(project.id)}
                    handleAddToFavorites={() => handleAddToFavorites(project)}
                  />
                ))
              ) : (
                <div className="space-y-3 text-center">
                  {!sidebarCollapse && (
                    <h4 className="text-sm text-gray-700">You don{"'"}t have any project yet</h4>
                  )}
                  <button
                    type="button"
                    className="group flex w-full items-center justify-center gap-2 rounded-md bg-gray-200 p-2 text-xs text-gray-900"
                    onClick={() => setCreateProjectModal(true)}
                  >
                    <PlusIcon className="h-4 w-4" />
                    {!sidebarCollapse && "Create Project"}
                  </button>
                </div>
              )}
            </>
          ) : (
            <div className="w-full">
              <Loader className="space-y-5">
                <div className="space-y-2">
                  <Loader.Item height="30px" />
                  <Loader.Item height="15px" width="80%" light />
                  <Loader.Item height="15px" width="80%" light />
                  <Loader.Item height="15px" width="80%" light />
                </div>
                <div className="space-y-2">
                  <Loader.Item height="30px" />
                  <Loader.Item height="15px" width="80%" light />
                  <Loader.Item height="15px" width="80%" light />
                  <Loader.Item height="15px" width="80%" light />
                </div>
              </Loader>
            </div>
          )}
        </div>
      </div>
    </>
  );
};