mirror of
https://github.com/Sea-Haven-Industries/shoc-frontend-new.git
synced 2026-10-05 14:12:05 +00:00
233 lines
6.8 KiB
TypeScript
233 lines
6.8 KiB
TypeScript
import { render, screen } from "@testing-library/react";
|
|
import userEvent from "@testing-library/user-event";
|
|
import { useState } from "react";
|
|
import { describe, expect, it, vi } from "vitest";
|
|
import { AssignedToCell } from "@/app/(protected)/workorders/_components/list/table/cells/assigned-to-cell";
|
|
import { WoTableBody } from "@/app/(protected)/workorders/_components/list/table/wo-table-body";
|
|
import type { ReturnTypeOfUseWorkOrdersTableData } from "@/app/(protected)/workorders/_components/list/table/wo-table-types";
|
|
import { expandTablePatchToBoardFieldOps } from "@/domain/work-orders/mappers/work-order-board-patch-mapper";
|
|
import type { WorkOrderTableRow } from "@/domain/work-orders/types/work-order-table-row";
|
|
|
|
function makeRow(overrides: Partial<WorkOrderTableRow> = {}): WorkOrderTableRow {
|
|
return {
|
|
id: "1",
|
|
woNumber: "24991",
|
|
site: "CLV2",
|
|
type: "PM",
|
|
severity: null,
|
|
dispatcherId: "",
|
|
dispatcherName: "",
|
|
scheduledOn: "2026-06-02",
|
|
completedDate: "",
|
|
targetWeek: "",
|
|
dayGroup: "06/02",
|
|
dayLabel: "TUE · 06/02",
|
|
location: "Cleveland, OH",
|
|
locationId: "",
|
|
pm: "Backflow",
|
|
serviceNotes: "",
|
|
extraServices: [],
|
|
company: "",
|
|
tech: "",
|
|
techPhone: "",
|
|
apptStart: "",
|
|
apptEnd: "",
|
|
apptTime: "—",
|
|
status: "Incomplete",
|
|
docStatus: "No",
|
|
pocName: "",
|
|
pocPhone: "",
|
|
pocNotes: "",
|
|
dueDate: "",
|
|
rescheduleCount: 0,
|
|
carriedOver: 0,
|
|
isAddOn: false,
|
|
originalWeek: "",
|
|
originalDate: "",
|
|
isPastDue: false,
|
|
scheduleWeekOnly: false,
|
|
mediaCount: 0,
|
|
title: "",
|
|
priority: "",
|
|
vendorId: "",
|
|
primaryDispatchId: null,
|
|
rowVersion: "",
|
|
dispatchRowVersion: "",
|
|
flagColor: null,
|
|
additionalContacts: [],
|
|
...overrides,
|
|
};
|
|
}
|
|
|
|
function baseTableData(
|
|
overrides: Partial<ReturnTypeOfUseWorkOrdersTableData> = {},
|
|
): ReturnTypeOfUseWorkOrdersTableData {
|
|
return {
|
|
rows: [],
|
|
isLoading: false,
|
|
isFetching: false,
|
|
error: null,
|
|
refetch: vi.fn(),
|
|
advActive: false,
|
|
advResults: [],
|
|
unassigned: [],
|
|
unassignedError: null,
|
|
unassignedLoading: false,
|
|
unscheduled: [],
|
|
displayGroups: [],
|
|
searchActive: false,
|
|
noSearchResults: false,
|
|
isEmptyWeek: false,
|
|
todayKey: null,
|
|
draftDayKey: null,
|
|
draft: null,
|
|
setDraft: vi.fn(),
|
|
unassignedOpen: true,
|
|
setUnassignedOpen: vi.fn(),
|
|
unschedOpen: true,
|
|
setUnschedOpen: vi.fn(),
|
|
selectedId: null,
|
|
setSelectedId: vi.fn(),
|
|
selectedRow: null,
|
|
flashId: null,
|
|
triggerFlash: vi.fn(),
|
|
dragViz: null,
|
|
setDragViz: vi.fn(),
|
|
dragState: null,
|
|
patchRow: vi.fn(),
|
|
clearRowPatch: vi.fn(),
|
|
reorderRows: vi.fn(),
|
|
endDrag: vi.fn(),
|
|
startDayDraft: vi.fn(),
|
|
cancelDraft: vi.fn(),
|
|
addRow: vi.fn(),
|
|
scopeTotalCount: 0,
|
|
totalCount: 0,
|
|
search: "",
|
|
...overrides,
|
|
} as ReturnTypeOfUseWorkOrdersTableData;
|
|
}
|
|
|
|
const DISPATCHER = { id: "sarah", name: "Sarah Chen", initials: "SC", color: "#3366cc" };
|
|
|
|
function DayAssignHarness({
|
|
initialRow,
|
|
patchBoardField,
|
|
}: {
|
|
initialRow: WorkOrderTableRow;
|
|
patchBoardField: (
|
|
id: string | number,
|
|
payload: { field: string; value?: string | null },
|
|
) => Promise<WorkOrderTableRow>;
|
|
}) {
|
|
const [row, setRow] = useState(initialRow);
|
|
const tableData = baseTableData({
|
|
displayGroups: [
|
|
{
|
|
key: "06/02",
|
|
label: "TUE · 06/02",
|
|
date: "2026-06-02",
|
|
items: [row],
|
|
totalCount: 1,
|
|
},
|
|
],
|
|
});
|
|
|
|
return (
|
|
<table>
|
|
<WoTableBody
|
|
tableData={tableData}
|
|
renderRow={(item) => (
|
|
<tr key={String(item.id)} data-testid={`row-${item.id}`}>
|
|
<td>{item.woNumber}</td>
|
|
<td>
|
|
<AssignedToCell
|
|
dispatcherId={item.dispatcherId}
|
|
users={[DISPATCHER]}
|
|
highlight={!item.dispatcherId}
|
|
onSave={async (id, name) => {
|
|
const ops = expandTablePatchToBoardFieldOps({
|
|
dispatcherId: id,
|
|
dispatcherName: name,
|
|
});
|
|
const patched = await patchBoardField(item.id, ops[0]!);
|
|
setRow({ ...patched, dispatcherId: id, dispatcherName: name });
|
|
}}
|
|
/>
|
|
</td>
|
|
</tr>
|
|
)}
|
|
renderInlineRow={() => null}
|
|
/>
|
|
</table>
|
|
);
|
|
}
|
|
|
|
describe("WoTableBody weekly board (AAP day view)", () => {
|
|
it("renders the selected day and keeps dated-unassigned inline, with no Unassigned pin", () => {
|
|
const datedUnassigned = makeRow({ id: "u-dated", woNumber: "24991" });
|
|
const datedAssigned = makeRow({
|
|
id: "day-assigned",
|
|
woNumber: "25023",
|
|
dispatcherId: "sarah",
|
|
dispatcherName: "Sarah",
|
|
});
|
|
|
|
render(
|
|
<table>
|
|
<WoTableBody
|
|
tableData={baseTableData({
|
|
displayGroups: [
|
|
{
|
|
key: "06/02",
|
|
label: "TUE · 06/02",
|
|
date: "2026-06-02",
|
|
items: [datedUnassigned, datedAssigned],
|
|
totalCount: 2,
|
|
},
|
|
],
|
|
})}
|
|
renderRow={(row) => (
|
|
<tr key={String(row.id)} data-testid={`row-${row.id}`}>
|
|
<td>{row.woNumber}</td>
|
|
</tr>
|
|
)}
|
|
renderInlineRow={() => null}
|
|
/>
|
|
</table>,
|
|
);
|
|
|
|
expect(screen.getByText("TUE · 06/02")).toBeInTheDocument();
|
|
expect(screen.getByText("2 WOs")).toBeInTheDocument();
|
|
expect(screen.queryByRole("button", { name: /Unassigned/ })).not.toBeInTheDocument();
|
|
expect(screen.queryByRole("button", { name: /Unscheduled/ })).not.toBeInTheDocument();
|
|
expect(screen.getByTestId("row-u-dated")).toBeInTheDocument();
|
|
expect(screen.getByTestId("row-day-assigned")).toBeInTheDocument();
|
|
});
|
|
|
|
it("assigns a dated-unassigned row in the day group without a pin section", async () => {
|
|
const user = userEvent.setup();
|
|
const pinned = makeRow({
|
|
id: "u-pin",
|
|
woNumber: "24991",
|
|
dispatcherId: "",
|
|
dispatcherName: "",
|
|
rowVersion: "AAAAAAA=",
|
|
});
|
|
const patchBoardField = vi.fn(async (_id: string | number, payload: { field: string }) => {
|
|
expect(payload.field).toBe("assignTo");
|
|
return { ...pinned, dispatcherId: DISPATCHER.id, dispatcherName: DISPATCHER.name };
|
|
});
|
|
|
|
render(<DayAssignHarness initialRow={pinned} patchBoardField={patchBoardField} />);
|
|
|
|
expect(screen.getByTestId("row-u-pin")).toBeInTheDocument();
|
|
await user.click(screen.getByRole("button", { name: /Select/ }));
|
|
await user.click(screen.getByRole("button", { name: /Sarah Chen/ }));
|
|
|
|
expect(patchBoardField).toHaveBeenCalled();
|
|
expect(screen.queryByRole("button", { name: /Unassigned/ })).not.toBeInTheDocument();
|
|
expect(screen.getByTestId("row-u-pin")).toBeInTheDocument();
|
|
expect(screen.getByText("TUE · 06/02")).toBeInTheDocument();
|
|
});
|
|
});
|