"use client";

import { useState } from "react";
import { VacationStatus, VacationType } from "@capakraken/shared";
import { trpc } from "~/lib/trpc/client.js";
import { VacationModal } from "./VacationModal.js";
import { InfoTooltip } from "~/components/ui/InfoTooltip.js";
import { BalanceCard } from "./BalanceCard.js";
import { VacationCalendar } from "./VacationCalendar.js";
import { VACATION_STATUS_BADGE as STATUS_BADGE, VACATION_TYPE_LABELS as TYPE_LABELS, VACATION_TYPE_BADGE } from "~/lib/status-styles.js";
import { getHolidayBasis, getHolidayBreakdown, getRequestedDays, type VacationExplainabilityEntry } from "./vacationExplainability.js";

type VacationListItem = VacationExplainabilityEntry & {
  id: string;
  startDate: Date | string;
  endDate: Date | string;
  status: string;
  type: string;
  note?: string | null;
  rejectionReason?: string | null;
};

export function MyVacationsClient() {
  const [showModal, setShowModal] = useState(false);

  const utils = trpc.useUtils();

  // Find resource linked to current user
  const { data: myResource } = trpc.resource.getMyResource.useQuery(undefined, {
    staleTime: 60_000,
  });

  const resourceId = myResource?.id;

  const vacationListQuery = trpc.vacation.list.useQuery as unknown as (
    input: { limit: number; resourceId?: string | undefined },
    options: { enabled: boolean; staleTime: number },
  ) => {
    data: VacationListItem[] | undefined;
    isLoading: boolean;
    refetch: () => Promise<unknown>;
  };

  const { data: vacations, isLoading, refetch } = vacationListQuery(
    { limit: 200, ...(resourceId ? { resourceId } : {}) },
    { enabled: !!resourceId, staleTime: 15_000 },
  );

  const cancelMutation = trpc.vacation.cancel.useMutation({
    onSuccess: async () => {
      await utils.vacation.list.invalidate();
      await utils.entitlement.getBalance.invalidate();
    },
  });

  const vacationList: VacationListItem[] = vacations ?? [];

  return (
    <div className="p-6 max-w-4xl mx-auto space-y-6">
      {/* Header */}
      <div className="flex items-center justify-between">
        <div>
          <h1 className="text-2xl font-bold text-gray-900 dark:text-gray-100">My Vacations</h1>
          <p className="text-sm text-gray-500 dark:text-gray-400 mt-1">Manage your personal vacation requests</p>
        </div>
        <button
          type="button"
          onClick={() => setShowModal(true)}
          disabled={!resourceId}
          className="px-4 py-2 bg-brand-600 text-white rounded-lg hover:bg-brand-700 text-sm font-medium disabled:opacity-50"
        >
          + Request Vacation
        </button>
      </div>

      {!resourceId && (
        <div className="rounded-xl border border-amber-200 bg-amber-50 dark:bg-amber-950/20 dark:border-amber-800 p-8 flex flex-col items-center text-center gap-3">
          <svg className="h-10 w-10 text-amber-400" fill="none" stroke="currentColor" viewBox="0 0 24 24">
            <path strokeLinecap="round" strokeLinejoin="round" strokeWidth={1.5} d="M12 9v3.75m-9.303 3.376c-.866 1.5.217 3.374 1.948 3.374h14.71c1.73 0 2.813-1.874 1.948-3.374L13.949 3.378c-.866-1.5-3.032-1.5-3.898 0L2.697 16.126ZM12 15.75h.007v.008H12v-.008Z" />
          </svg>
          <div>
            <p className="text-sm font-semibold text-amber-800 dark:text-amber-300">Account not linked to a resource</p>
            <p className="text-sm text-amber-700 dark:text-amber-400 mt-1">
              Your user account has not been connected to a resource record yet. Vacation tracking requires this link.<br />
              Please ask an administrator to open your resource profile and link it to your account.
            </p>
          </div>
        </div>
      )}

      {/* Balance card */}
      {resourceId && (
        <BalanceCard resourceId={resourceId} />
      )}

      {/* Calendar */}
      {resourceId && vacationList.length > 0 && (
        <VacationCalendar vacations={vacationList} />
      )}

      {/* Vacation list */}
      <div className="bg-white dark:bg-gray-800 rounded-xl border border-gray-200 dark:border-gray-700 overflow-hidden">
        {isLoading ? (
          <div className="p-8 text-center text-sm text-gray-400">Loading…</div>
        ) : vacationList.length === 0 ? (
          <div className="p-8 text-center text-sm text-gray-400">No vacation requests yet.</div>
        ) : (
          <table className="w-full text-sm">
            <thead>
              <tr className="border-b border-gray-100 dark:border-gray-700 bg-gray-50 dark:bg-gray-900">
                <th className="text-left px-4 py-3 font-medium text-gray-500 dark:text-gray-400 text-xs uppercase tracking-wider">
                  Type <InfoTooltip content="ANNUAL = paid annual leave · SICK = sick leave · PUBLIC_HOLIDAY = public holiday · OTHER = other leave types." />
                </th>
                <th className="text-left px-4 py-3 font-medium text-gray-500 dark:text-gray-400 text-xs uppercase tracking-wider">Start</th>
                <th className="text-left px-4 py-3 font-medium text-gray-500 dark:text-gray-400 text-xs uppercase tracking-wider">End</th>
                <th className="text-right px-4 py-3 font-medium text-gray-500 dark:text-gray-400 text-xs uppercase tracking-wider">
                  <span className="inline-flex items-center justify-end gap-0.5">
                    Days <InfoTooltip content="Calendar days from start to end date (inclusive). Shows 0.5 for half-day requests (½ indicator on start date)." />
                  </span>
                </th>
                <th className="text-left px-4 py-3 font-medium text-gray-500 dark:text-gray-400 text-xs uppercase tracking-wider">
                  Status <InfoTooltip content="PENDING = awaiting manager approval · APPROVED = confirmed leave · REJECTED = declined by manager · CANCELLED = withdrawn by employee." />
                </th>
                <th className="text-left px-4 py-3 font-medium text-gray-500 dark:text-gray-400 text-xs uppercase tracking-wider">
                  Note <InfoTooltip content="Your note on the request, or the manager's rejection reason if declined." />
                </th>
                <th className="px-4 py-3" />
              </tr>
            </thead>
            <tbody className="divide-y divide-gray-50 dark:divide-gray-700">
              {vacationList.map((v) => {
                const start = new Date(v.startDate);
                const end = new Date(v.endDate);
                const requestedDays = getRequestedDays(v);
                const deductedDays = typeof v.deductedDays === "number" ? v.deductedDays : null;
                const holidayBasis = getHolidayBasis(v);
                const holidayBreakdown = getHolidayBreakdown(v);
                const status = v.status as string;
                const type = v.type as string;
                const affectsBalance = type === VacationType.ANNUAL || type === VacationType.OTHER;

                return (
                  <tr key={v.id} className="hover:bg-gray-50 dark:hover:bg-gray-700/50">
                    <td className="px-4 py-3">
                      <span className={`inline-flex px-2 py-0.5 rounded-full text-xs font-medium ${VACATION_TYPE_BADGE[type] ?? "bg-gray-100 text-gray-600"}`}>
                        {TYPE_LABELS[type] ?? type}
                      </span>
                    </td>
                    <td className="px-4 py-3 text-gray-600 dark:text-gray-400">{start.toLocaleDateString("en-GB")}</td>
                    <td className="px-4 py-3 text-gray-600 dark:text-gray-400">{end.toLocaleDateString("en-GB")}</td>
                    <td className="px-4 py-3 text-right text-gray-600 dark:text-gray-400">
                      <div className="space-y-1">
                        <div>{requestedDays}</div>
                        {affectsBalance && deductedDays !== null && (
                          <div className="text-[11px] text-gray-400 dark:text-gray-500">
                            Deducted: {deductedDays}
                          </div>
                        )}
                        {affectsBalance && deductedDays === 0 && holidayBreakdown.length > 0 && (
                          <div className="text-[11px] text-emerald-600 dark:text-emerald-400">
                            Fully covered by holidays
                          </div>
                        )}
                      </div>
                    </td>
                    <td className="px-4 py-3">
                      <span className={`inline-flex px-2 py-0.5 rounded-full text-xs font-medium ${STATUS_BADGE[status] ?? ""}`}>
                        {status}
                      </span>
                    </td>
                    <td className="px-4 py-3 text-gray-400 dark:text-gray-500 text-xs max-w-[280px]">
                      {v.rejectionReason ? (
                        <span className="text-red-500">{v.rejectionReason}</span>
                      ) : (
                        <div className="space-y-1">
                          <div>{v.note ?? "—"}</div>
                          {affectsBalance && holidayBasis.length > 0 && (
                            <div className="text-[11px] text-gray-500 dark:text-gray-400">
                              Holiday basis: {holidayBasis.join(" / ")}
                            </div>
                          )}
                          {affectsBalance && holidayBreakdown.length > 0 && (
                            <div className="text-[11px] text-gray-500 dark:text-gray-400">
                              Excluded holidays: {holidayBreakdown.map((holiday) => `${holiday.date} (${holiday.source})`).join(", ")}
                            </div>
                          )}
                        </div>
                      )}
                      {!v.rejectionReason && affectsBalance && deductedDays !== null && deductedDays !== requestedDays && holidayBreakdown.length === 0 && (
                        <div className="mt-1 text-[11px] text-gray-500 dark:text-gray-400">
                          Local holiday-adjusted deduction snapshot applied.
                        </div>
                      )}
                      {!v.rejectionReason && !affectsBalance && (
                        <div className="mt-1 text-[11px] text-gray-500 dark:text-gray-400">
                          This leave type does not reduce annual vacation entitlement.
                        </div>
                      )}
                    </td>
                    <td className="px-4 py-3 text-right">
                      {(status === VacationStatus.PENDING || status === VacationStatus.APPROVED) && (
                        <button
                          type="button"
                          onClick={() => cancelMutation.mutate({ id: v.id })}
                          disabled={cancelMutation.isPending}
                          className="text-xs text-gray-400 hover:text-red-600 underline disabled:opacity-50"
                        >
                          Cancel
                        </button>
                      )}
                    </td>
                  </tr>
                );
              })}
            </tbody>
          </table>
        )}
      </div>

      {showModal && resourceId && (
        <VacationModal
          resourceId={resourceId}
          onClose={() => setShowModal(false)}
          onSuccess={() => {
            setShowModal(false);
            void refetch();
            void utils.entitlement.getBalance.invalidate();
          }}
        />
      )}
    </div>
  );
}
