"use client" import { AlertTriangle, Plus, Save } from "lucide-react" import { Button } from "@/shared/components/ui/button" import { Alert, AlertTitle } from "@/shared/components/ui/alert" import { FieldGroup } from "@/shared/components/ui/field" import { Rhform, RhfTextField, RhfTextareaField, RhfSelectField, RhfAsyncSelectField, RhfDateField, RhfTimeField, } from "@/shared/components/form" import { toast } from "sonner" import { useAuthApi } from "@/shared/useApi" import { useResourceForm } from "@/shared/hooks/use-resource-form" import { useFormMutation } from "@/shared/hooks/use-form-mutation" import { toRelation, toId } from "@/shared/lib/utils" import { InspectionCategoryInlineForm } from "./inline-forms/inspection-category-inline-form" import { DepartmentInlineForm } from "@/modules/services/inline-forms/department-inline-form" import { inspectionFormSchema, type InspectionFormValues, } from "./inspection.schema" import { INSPECTION_ROUTES, DEPARTMENT_ROUTES, JOB_CARD_ROUTES, InspectionStatus, RateType, } from "@garage/api" import { RhfVehicleSelectField } from "@/modules/vehicles/rhf-vehicle-select-field" import { RhfCustomerSelectField } from "@/modules/customers/rhf-customer-select-field" import { RhfEmployeeSelectField } from "@/modules/employees/rhf-employee-select-field" // ── Props ── export type InspectionFormProps = { resourceId?: string | null initialData?: unknown onSuccess?: () => void } // ── Default values ── const DEFAULT_VALUES: InspectionFormValues = { customer: null, vehicle: null, department: null, inspection_category: null, employee: null, job_card: null, labor_rate: null, title: "", order_number: "", date: "", time: "", status: "in_progress", note: "", description: "", rate_type: "flat_rate", quantity: 1, rate: 0, working_hours: 0, labor_hours: 0, tax: "", chart_of_account: "", } // ── Mapping helpers ── function mapToFormValues(data: unknown): InspectionFormValues { const d = (data as any)?.data ?? data ?? {} return { customer: toRelation(d.customer_id, d.customer?.first_name ? `${d.customer.first_name} ${d.customer.last_name ?? ""}`.trim() : undefined), vehicle: toRelation(d.vehicle_id, d.vehicle?.make ? `${d.vehicle.make} ${d.vehicle.model ?? ""}`.trim() : undefined), department: toRelation(d.department_id, d.department?.name), inspection_category: toRelation(d.inspection_category_id, d.inspection_category?.name), employee: toRelation(d.employee_id, d.employee?.first_name ? `${d.employee.first_name} ${d.employee.last_name ?? ""}`.trim() : undefined), job_card: d.job_card_id ? { value: String(d.job_card_id), label: d.job_card?.title ?? d.job_card?.order_number ?? String(d.job_card_id) } : null, labor_rate: d.labor_rate_id ? { value: String(d.labor_rate_id), label: d.labor_rate?.title ?? String(d.labor_rate_id) } : null, title: d.title ?? "", order_number: d.order_number ?? "", date: d.date ? d.date.split("T")[0] : "", time: d.time ?? "", status: d.status ?? "in_progress", note: d.note ?? "", description: d.description ?? "", rate_type: d.rate_type ?? "flat_rate", quantity: d.quantity != null ? Number(d.quantity) : 1, rate: d.rate != null ? Number(d.rate) : 0, working_hours: d.working_hours != null ? Number(d.working_hours) : 0, labor_hours: d.labor_hours != null ? Number(d.labor_hours) : 0, tax: d.tax ?? "", chart_of_account: d.chart_of_account ?? "", } } function mapFormToPayload(values: InspectionFormValues) { return { customer_id: toId(values.customer), vehicle_id: toId(values.vehicle), department_id: toId(values.department), inspection_category_id: toId(values.inspection_category), employee_id: toId(values.employee), job_card_id: toId(values.job_card) ?? null, labor_rate_id: values.labor_rate ? Number(values.labor_rate.value) : undefined, title: values.title, order_number: values.order_number || undefined, date: values.date || undefined, time: values.time || undefined, status: values.status || undefined, note: values.note || undefined, description: values.description || undefined, rate_type: values.rate_type || undefined, quantity: values.quantity ?? undefined, rate: values.rate ?? undefined, working_hours: values.working_hours ?? undefined, labor_hours: values.labor_hours ?? undefined, tax: values.tax || undefined, chart_of_account: values.chart_of_account || undefined, } } // ── Select options ── const STATUS_OPTIONS = InspectionStatus.map((v) => ({ value: v, label: v.replace(/_/g, " ").replace(/\b\w/g, (c) => c.toUpperCase()), })) const RATE_TYPE_OPTIONS = RateType.map((v) => ({ value: v, label: v === "flat_rate" ? "Flat Rate" : "Hourly", })) const mapLookupOption = (item: any) => ({ value: String(item.id), label: item.name ?? item.title ?? String(item.id), }) const STORE_OBJECT = { getOptionValue: (o: any) => o, getOptionLabel: (o: any) => o.label } // ── Component ── export function InspectionForm({ resourceId, initialData, onSuccess }: InspectionFormProps) { const api = useAuthApi() const { form, isEditing } = useResourceForm({ schema: inspectionFormSchema, defaultValues: DEFAULT_VALUES, resourceId, initialData, queryKey: [INSPECTION_ROUTES.BY_ID, resourceId], mapToFormValues: mapToFormValues, }) const { mutate, error, isPending } = useFormMutation(form, { mutationFn: (values: InspectionFormValues) => { const payload = mapFormToPayload(values) const promise = (isEditing && resourceId ? api.inspections.update(resourceId, payload) : api.inspections.create(payload)) as any toast.promise(promise, { loading: isEditing ? "Updating inspection..." : "Creating inspection...", success: isEditing ? "Inspection updated successfully" : "Inspection created successfully", error: isEditing ? "Failed to update inspection" : "Failed to create inspection", }) return promise }, onSuccess: () => { form.reset() onSuccess?.() }, }) return ( mutate(values)}> {error && ( {isEditing ? "Failed to update inspection" : "Failed to create inspection"} {error.message} )}
api.departments.list()} mapOption={mapLookupOption} createForm={(props) => } createLabel="Department" {...STORE_OBJECT} /> api.inspections.listCategories()} mapOption={mapLookupOption} createForm={(props) => } createLabel="Inspection Category" {...STORE_OBJECT} />
api.jobCards.list()} mapOption={(item: any) => ({ value: String(item.id), label: item.title ?? item.order_number ?? String(item.id), })} {...STORE_OBJECT} />
api.inventory.listLaborRates()} mapOption={(item: any) => ({ value: String(item.id), label: item.title ?? String(item.id), })} {...STORE_OBJECT} />
) }