2026-08-19 14:45:59 -03:00
|
|
|
|
import type {
|
|
|
|
|
|
WorkOrderDayGroup,
|
|
|
|
|
|
WorkOrderTableRow,
|
|
|
|
|
|
} from "@/domain/work-orders/types/work-order-table-row";
|
2026-09-01 14:16:52 -03:00
|
|
|
|
import { rowMatchesCarryOverDay } from "@/domain/work-orders/utils/carry-over-display";
|
2026-08-19 14:45:59 -03:00
|
|
|
|
import { isLiveWeek } from "@/domain/work-orders/utils/list-week-utils";
|
|
|
|
|
|
import { isDateInWeek } from "@/domain/work-orders/utils/table-day-utils";
|
2026-08-20 09:21:45 -03:00
|
|
|
|
import { addDaysIso, mondayOf, todayIso } from "@/domain/work-orders/utils/wizard-date-utils";
|
2026-08-19 14:45:59 -03:00
|
|
|
|
|
|
|
|
|
|
const DAY_TAB_WEEKDAYS = ["Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"] as const;
|
|
|
|
|
|
|
|
|
|
|
|
export function weekdaysMonFri(weekMonday: string): string[] {
|
|
|
|
|
|
return Array.from({ length: 5 }, (_, index) => addDaysIso(weekMonday, index));
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
export function firstWeekday(weekMonday: string): string {
|
|
|
|
|
|
return weekMonday;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2026-08-20 09:21:45 -03:00
|
|
|
|
/** Maps a scheduled date onto the Mon–Fri tab that can show it (weekends fall back to Monday). */
|
|
|
|
|
|
export function scheduledDayTab(dateIso: string): { weekMonday: string; selectedDayIso: string } {
|
|
|
|
|
|
const day = dateIso.slice(0, 10);
|
|
|
|
|
|
const weekMonday = mondayOf(day);
|
|
|
|
|
|
const days = weekdaysMonFri(weekMonday);
|
|
|
|
|
|
return {
|
|
|
|
|
|
weekMonday,
|
|
|
|
|
|
selectedDayIso: days.includes(day) ? day : firstWeekday(weekMonday),
|
|
|
|
|
|
};
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2026-08-20 10:28:04 -03:00
|
|
|
|
export function isUnassignedQueueReady(
|
|
|
|
|
|
unassignedLoading: boolean,
|
|
|
|
|
|
unassignedError: Error | null,
|
|
|
|
|
|
): boolean {
|
|
|
|
|
|
return !unassignedLoading && unassignedError == null;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
2026-08-20 09:21:45 -03:00
|
|
|
|
export function isDayScopedSearchEmpty(args: {
|
|
|
|
|
|
searchActive: boolean;
|
|
|
|
|
|
unassignedCount: number;
|
|
|
|
|
|
dayItemCount: number;
|
2026-08-20 10:28:04 -03:00
|
|
|
|
unassignedQueueReady: boolean;
|
2026-08-20 09:21:45 -03:00
|
|
|
|
}): boolean {
|
2026-08-20 10:28:04 -03:00
|
|
|
|
return (
|
|
|
|
|
|
args.searchActive &&
|
|
|
|
|
|
args.unassignedQueueReady &&
|
|
|
|
|
|
args.unassignedCount === 0 &&
|
|
|
|
|
|
args.dayItemCount === 0
|
|
|
|
|
|
);
|
2026-08-20 09:21:45 -03:00
|
|
|
|
}
|
|
|
|
|
|
|
2026-08-19 14:45:59 -03:00
|
|
|
|
export function initialSelectedDay(weekMonday: string, today = todayIso()): string {
|
|
|
|
|
|
if (isLiveWeek(weekMonday) && isDateInWeek(today, weekMonday)) {
|
|
|
|
|
|
return today;
|
|
|
|
|
|
}
|
|
|
|
|
|
return firstWeekday(weekMonday);
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
export function formatDayTabLabel(iso: string): string {
|
|
|
|
|
|
if (!/^\d{4}-\d{2}-\d{2}$/.test(iso)) {
|
|
|
|
|
|
return "";
|
|
|
|
|
|
}
|
|
|
|
|
|
const day = new Date(`${iso}T12:00:00`);
|
|
|
|
|
|
const [, month, date] = iso.split("-");
|
|
|
|
|
|
return `${DAY_TAB_WEEKDAYS[day.getDay()]} · ${month}/${date}`;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
export function rowMatchesSelectedDay(
|
2026-09-01 14:16:52 -03:00
|
|
|
|
row: Pick<WorkOrderTableRow, "scheduledOn" | "status" | "carriedOver">,
|
2026-08-19 14:45:59 -03:00
|
|
|
|
selectedDayIso: string,
|
2026-09-01 14:16:52 -03:00
|
|
|
|
weekMonday?: string,
|
2026-08-19 14:45:59 -03:00
|
|
|
|
): boolean {
|
2026-09-01 14:16:52 -03:00
|
|
|
|
if (Boolean(row.scheduledOn) && row.scheduledOn.slice(0, 10) === selectedDayIso) {
|
|
|
|
|
|
return true;
|
|
|
|
|
|
}
|
|
|
|
|
|
if (!weekMonday) {
|
|
|
|
|
|
return false;
|
|
|
|
|
|
}
|
|
|
|
|
|
return rowMatchesCarryOverDay(row, selectedDayIso, weekMonday);
|
2026-08-19 14:45:59 -03:00
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
export function buildSelectedDayGroup(
|
|
|
|
|
|
weekMonday: string,
|
|
|
|
|
|
selectedDayIso: string,
|
|
|
|
|
|
scheduled: WorkOrderTableRow[],
|
|
|
|
|
|
): WorkOrderDayGroup {
|
|
|
|
|
|
const days = weekdaysMonFri(weekMonday);
|
|
|
|
|
|
const date = days.includes(selectedDayIso) ? selectedDayIso : firstWeekday(weekMonday);
|
|
|
|
|
|
const [, month, day] = date.split("-");
|
|
|
|
|
|
return {
|
|
|
|
|
|
key: `${month}/${day}`,
|
|
|
|
|
|
label: formatDayTabLabel(date),
|
|
|
|
|
|
date,
|
2026-09-01 14:16:52 -03:00
|
|
|
|
items: scheduled.filter((row) => rowMatchesSelectedDay(row, date, weekMonday)),
|
2026-08-19 14:45:59 -03:00
|
|
|
|
};
|
|
|
|
|
|
}
|