"use client"; import { useState } from "react"; import { useRouter } from "next/navigation"; import { Badge, Button, Card, ErrorBanner, Field, Input, Modal, PageHeader, Select, Textarea } from "@/components/ui"; import { apiFetch, ApiClientError } from "@/lib/client-api"; interface MachineRow { id: string; name: string; kind: string; location: string | null; notes: string | null; active: boolean; createdAt: string; updatedAt: string; } const KINDS = ["NCT_PUNCH", "PRESS_BRAKE", "RIVET", "WELD", "LASER", "SHEAR", "ASSEMBLY", "OTHER"] as const; const KIND_LABEL: Record = { NCT_PUNCH: "NCT punch", PRESS_BRAKE: "Press brake", RIVET: "Rivet", WELD: "Weld", LASER: "Laser", SHEAR: "Shear", ASSEMBLY: "Assembly", OTHER: "Other", }; export default function MachinesClient({ initial }: { initial: MachineRow[] }) { const router = useRouter(); const [edit, setEdit] = useState(null); const [newOpen, setNewOpen] = useState(false); return (
setNewOpen(true)}>New machine} /> {initial.map((m) => ( ))} {initial.length === 0 && ( )}
Name Type Location Status
{m.name} {KIND_LABEL[m.kind] ?? m.kind} {m.location ?? "—"} {m.active ? "active" : "inactive"}
No machines yet.
{newOpen && setNewOpen(false)} onSaved={() => router.refresh()} />} {edit && setEdit(null)} onSaved={() => router.refresh()} />}
); } function MachineModal({ machine, onClose, onSaved, }: { machine?: MachineRow; onClose: () => void; onSaved: () => void; }) { const editing = !!machine; const [name, setName] = useState(machine?.name ?? ""); const [kind, setKind] = useState(machine?.kind ?? "OTHER"); const [location, setLocation] = useState(machine?.location ?? ""); const [notes, setNotes] = useState(machine?.notes ?? ""); const [active, setActive] = useState(machine?.active ?? true); const [busy, setBusy] = useState(false); const [error, setError] = useState(null); async function submit(e: React.FormEvent) { e.preventDefault(); setBusy(true); setError(null); try { if (editing) { await apiFetch(`/api/v1/machines/${machine!.id}`, { method: "PATCH", body: JSON.stringify({ name, kind, location, notes, active }), }); } else { await apiFetch("/api/v1/machines", { method: "POST", body: JSON.stringify({ name, kind, location, notes }), }); } onSaved(); onClose(); } catch (err) { setError(err instanceof ApiClientError ? err.message : "Save failed"); } finally { setBusy(false); } } async function deactivate() { if (!machine || !confirm(`Deactivate ${machine.name}?`)) return; setBusy(true); setError(null); try { await apiFetch(`/api/v1/machines/${machine.id}`, { method: "DELETE" }); onSaved(); onClose(); } catch (err) { setError(err instanceof ApiClientError ? err.message : "Deactivate failed"); setBusy(false); } } return ( {editing && machine!.active && ( )}
} >
setName(e.target.value)} required maxLength={200} /> setLocation(e.target.value)} />