"use client" import { useState, useRef } from "react" import { useMutation, useQuery } from "@tanstack/react-query" import { useAuthApi } from "@/shared/useApi" import { useRouter } from "next/navigation" import { Button } from "@/shared/components/ui/button" import { DropdownMenu, DropdownMenuContent, DropdownMenuItem, DropdownMenuSeparator, DropdownMenuTrigger, } from "@/shared/components/ui/dropdown-menu" import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogDescription, } from "@/shared/components/ui/dialog" import { Combobox, ComboboxInput, ComboboxContent, ComboboxList, ComboboxItem, ComboboxEmpty, } from "@/shared/components/ui/combobox" import { Popover, PopoverContent, PopoverTrigger, } from "@/shared/components/ui/popover" import { Calendar } from "@/shared/components/ui/calendar" import { confirm } from "@/shared/components/confirm-dialog" import { toast } from "sonner" import { Ellipsis, Pencil, Trash2, CalendarIcon, UserCog, UserCheck, Loader2 } from "lucide-react" import { format } from "date-fns" import { EMPLOYEE_ROUTES } from "@garage/api" type JobCardActionsProps = { jobCardId: string } type Employee = { id: number first_name?: string last_name?: string name?: string } function getEmployeeName(emp: Employee) { return emp.name || [emp.first_name, emp.last_name].filter(Boolean).join(" ") || `Employee #${emp.id}` } // ── Employee Picker Dialog ── type EmployeePickerDialogProps = { open: boolean onOpenChange: (open: boolean) => void title: string description: string employees: Employee[] loading: boolean isPending: boolean onSelect: (employeeId: number) => void } function EmployeePickerDialog({ open, onOpenChange, title, description, employees, loading, isPending, onSelect, }: EmployeePickerDialogProps) { const anchorRef = useRef(null) const handleSelect = (emp: Employee | null) => { if (!emp) return onSelect(emp.id) } return ( {title} {description}
{loading && (
)} {!loading && employees.map((emp) => ( {getEmployeeName(emp)} ))} {!loading && employees.length === 0 && ( No employees found )}
) } // ── Main Component ── export function JobCardActions({ jobCardId }: JobCardActionsProps) { const api = useAuthApi() const router = useRouter() const [datePickerOpen, setDatePickerOpen] = useState(false) const [serviceWriterDialogOpen, setServiceWriterDialogOpen] = useState(false) const [salesPersonDialogOpen, setSalesPersonDialogOpen] = useState(false) const { data: employeesData, isLoading: employeesLoading } = useQuery({ queryKey: [EMPLOYEE_ROUTES.INDEX], queryFn: () => api.employees.list(), }) const employees: Employee[] = (employeesData as any)?.data ?? [] const handleEdit = () => { router.push(`/sales/job-cards/${jobCardId}/edit`) } const handleDelete = async () => { const confirmed = await confirm({ title: "Delete Job Card", description: "Are you sure you want to delete this job card? This action cannot be undone.", confirmLabel: "Delete", variant: "destructive", }) if (confirmed) { const promise = api.jobCards.destroy(jobCardId) toast.promise(promise, { loading: "Deleting job card...", success: "Job card deleted successfully", error: "Failed to delete job card", }) await promise router.push("/sales/job-cards") } } const changeDateMutation = useMutation({ mutationFn: (date: Date) => { const order_date = format(date, "yyyy-MM-dd") const promise = api.jobCards.changeDate(jobCardId, { order_date }) toast.promise(promise, { loading: "Updating date...", success: "Date updated successfully", error: "Failed to update date", }) return promise }, onSuccess: () => { setDatePickerOpen(false) router.refresh() }, }) const changeServiceWriterMutation = useMutation({ mutationFn: (employeeId: number) => { const promise = api.jobCards.changeServiceWriter(jobCardId, { service_writer_id: employeeId }) toast.promise(promise, { loading: "Updating service writer...", success: "Service writer updated successfully", error: "Failed to update service writer", }) return promise }, onSuccess: () => { setServiceWriterDialogOpen(false) router.refresh() }, }) const changeSalesPersonMutation = useMutation({ mutationFn: (employeeId: number) => { const promise = api.jobCards.changeSalesPerson(jobCardId, { sales_person_id: employeeId }) toast.promise(promise, { loading: "Updating sales person...", success: "Sales person updated successfully", error: "Failed to update sales person", }) return promise }, onSuccess: () => { setSalesPersonDialogOpen(false) router.refresh() }, }) return (
{ if (date) changeDateMutation.mutate(date) }} disabled={changeDateMutation.isPending} /> Edit Delete changeServiceWriterMutation.mutate(id)} /> changeSalesPersonMutation.mutate(id)} />
) }