"use client" import * as React from "react" import { zodResolver } from "@hookform/resolvers/zod" import { useForm } from "react-hook-form" import { Loader } from "lucide-react" import { toast } from "sonner" import { Button } from "@/components/ui/button" import { Form, FormControl, FormField, FormItem, FormLabel, FormMessage, } from "@/components/ui/form" import { Input } from "@/components/ui/input" import { Sheet, SheetClose, SheetContent, SheetDescription, SheetFooter, SheetHeader, SheetTitle, } from "@/components/ui/sheet" import { Select, SelectContent, SelectGroup, SelectItem, SelectTrigger, SelectValue, } from "@/components/ui/select" import { updateVendorInvestigationSchema, type UpdateVendorInvestigationSchema, } from "../validations" import { updateVendorInvestigationAction } from "../service" import { VendorInvestigationsViewWithContacts } from "@/config/vendorInvestigationsColumnsConfig" /** * The shape of `vendorInvestigation` * might come from your `vendorInvestigationsView` row * or your existing type for a single investigation. */ interface UpdateVendorInvestigationSheetProps extends React.ComponentPropsWithoutRef { investigation: VendorInvestigationsViewWithContacts | null } /** * A sheet for updating a vendor investigation (plus optional attachments). */ export function UpdateVendorInvestigationSheet({ investigation, ...props }: UpdateVendorInvestigationSheetProps) { const [isPending, startTransition] = React.useTransition() // RHF + Zod const form = useForm({ resolver: zodResolver(updateVendorInvestigationSchema), defaultValues: { investigationId: investigation?.investigationId ?? 0, investigationStatus: investigation?.investigationStatus ?? "PLANNED", scheduledStartAt: investigation?.scheduledStartAt ?? undefined, scheduledEndAt: investigation?.scheduledEndAt ?? undefined, completedAt: investigation?.completedAt ?? undefined, investigationNotes: investigation?.investigationNotes ?? "", }, }) React.useEffect(() => { if (investigation) { form.reset({ investigationId: investigation.investigationId, investigationStatus: investigation.investigationStatus || "PLANNED", scheduledStartAt: investigation.scheduledStartAt ?? undefined, scheduledEndAt: investigation.scheduledEndAt ?? undefined, completedAt: investigation.completedAt ?? undefined, investigationNotes: investigation.investigationNotes ?? "", }) } }, [investigation, form]) // Format date for form data const formatDateForFormData = (date: Date | undefined): string | null => { if (!date) return null; return date.toISOString(); } // Submit handler async function onSubmit(values: UpdateVendorInvestigationSchema) { if (!values.investigationId) return startTransition(async () => { // 1) Build a FormData object for the server action const formData = new FormData() // Add text fields formData.append("investigationId", String(values.investigationId)) formData.append("investigationStatus", values.investigationStatus) // Format dates properly before appending to FormData if (values.scheduledStartAt) { const formattedDate = formatDateForFormData(values.scheduledStartAt) if (formattedDate) formData.append("scheduledStartAt", formattedDate) } if (values.scheduledEndAt) { const formattedDate = formatDateForFormData(values.scheduledEndAt) if (formattedDate) formData.append("scheduledEndAt", formattedDate) } if (values.completedAt) { const formattedDate = formatDateForFormData(values.completedAt) if (formattedDate) formData.append("completedAt", formattedDate) } if (values.investigationNotes) { formData.append("investigationNotes", values.investigationNotes) } // Add attachments (if any) // Note: If you have multiple files in "attachments", we store them in the form under the same key. const attachmentValue = form.getValues("attachments"); if (attachmentValue instanceof FileList) { for (let i = 0; i < attachmentValue.length; i++) { formData.append("attachments", attachmentValue[i]); } } const { error } = await updateVendorInvestigationAction(formData) if (error) { toast.error(error) return } toast.success("Investigation updated!") form.reset() props.onOpenChange?.(false) }) } // Format date value for input field const formatDateForInput = (date: Date | undefined): string => { if (!date) return ""; return date instanceof Date ? date.toISOString().slice(0, 10) : ""; } // Handle date input change const handleDateChange = (e: React.ChangeEvent, onChange: (...event: any[]) => void) => { const val = e.target.value; if (val) { // Ensure proper date handling by setting to noon to avoid timezone issues const newDate = new Date(`${val}T12:00:00`); onChange(newDate); } else { onChange(undefined); } } return ( Update Investigation Change the investigation details & attachments
{/* investigationStatus */} ( Status )} /> {/* scheduledStartAt */} ( Scheduled Start handleDateChange(e, field.onChange)} /> )} /> {/* scheduledEndAt */} ( Scheduled End handleDateChange(e, field.onChange)} /> )} /> {/* completedAt */} ( Completed At handleDateChange(e, field.onChange)} /> )} /> {/* investigationNotes */} ( Notes )} /> {/* attachments: multiple file upload */} ( Attachments { onChange(e.target.files); // Store the FileList directly }} {...fieldProps} /> )} /> {/* Footer Buttons */}
) }