shoc-frontend-new/src/domain/work-orders/utils/work-order-deep-link.ts
Codex Review Integration dcf944d7dc SH-292: Notification Center bell panel and feed page
Header bell panel and /notifications page share one feed from GET /api/notifications: labeled sections with live counts, unread styling, session-only dismiss and clear all (acknowledge rows excluded), and deep links to the unassigned queue and a work order's tab via ?wo=&tab=.
2026-09-18 12:55:54 -03:00

48 lines
1.5 KiB
TypeScript

import { WORK_ORDERS_ROUTE } from "@/domain/dashboard/utils/work-order-drilldown-links";
const WORK_ORDER_PARAM = "wo";
const TAB_PARAM = "tab";
export const WORK_ORDER_DEEP_LINK_TABS = [
"info",
"comments",
"audit",
"completion",
"extras",
] as const;
export type WorkOrderDeepLinkTab = (typeof WORK_ORDER_DEEP_LINK_TABS)[number];
export type WorkOrderDeepLink = {
workOrderId: string;
tab: WorkOrderDeepLinkTab;
};
function isDeepLinkTab(value: string | null): value is WorkOrderDeepLinkTab {
return WORK_ORDER_DEEP_LINK_TABS.some((tab) => tab === value);
}
/** `/workorders?wo=<id>&tab=<tab>` opens that work order's slide-over on the given tab. */
export function workOrderDeepLinkUrl(workOrderId: string | number, tab?: string | null): string {
const search = new URLSearchParams({ [WORK_ORDER_PARAM]: String(workOrderId) });
if (isDeepLinkTab(tab ?? null)) {
search.set(TAB_PARAM, String(tab));
}
return `${WORK_ORDERS_ROUTE}?${search.toString()}`;
}
export function parseWorkOrderDeepLink(params: URLSearchParams): WorkOrderDeepLink | null {
const workOrderId = (params.get(WORK_ORDER_PARAM) ?? "").trim();
if (!/^\d+$/.test(workOrderId)) {
return null;
}
const tab = params.get(TAB_PARAM);
return { workOrderId, tab: isDeepLinkTab(tab) ? tab : "info" };
}
export function withoutWorkOrderDeepLink(params: URLSearchParams): URLSearchParams {
const next = new URLSearchParams(params);
next.delete(WORK_ORDER_PARAM);
next.delete(TAB_PARAM);
return next;
}