seahaven-ap/src/dashboard/columns.tsx

118 lines
3.2 KiB
TypeScript
Raw Normal View History

import { Link as MuiLink } from "@mui/material";
import type { GridColDef, GridRenderCellParams } from "@mui/x-data-grid";
import type { MockInvoice } from "@/mocks";
import { Link } from "@/router";
const currencyFormatter = new Intl.NumberFormat("en-US", {
style: "currency",
currency: "USD",
});
const dateFormatter = new Intl.DateTimeFormat("en-US", {
year: "numeric",
month: "short",
day: "numeric",
});
function formatIsoDate(value: string | null | undefined): string {
if (!value) {
return "—";
}
const parsed = new Date(`${value}T00:00:00`);
if (Number.isNaN(parsed.getTime())) {
return value;
}
return dateFormatter.format(parsed);
}
function formatCurrency(value: number | null | undefined): string {
if (value == null) {
return "—";
}
return currencyFormatter.format(value);
}
const moneyColumn = (field: keyof MockInvoice, headerName: string): GridColDef<MockInvoice> => ({
field,
headerName,
flex: 1,
minWidth: 120,
type: "number",
valueFormatter: (value: number | null | undefined) => formatCurrency(value),
});
const dateColumn = (
field: keyof MockInvoice,
headerName: string,
editable = false,
): GridColDef<MockInvoice> => ({
field,
headerName,
flex: 1,
minWidth: 130,
editable,
valueFormatter: (value: string | null | undefined) => formatIsoDate(value),
});
function invoiceNumberLink(params: GridRenderCellParams<MockInvoice, string>) {
return (
<MuiLink
component={Link}
to="/invoices/:id"
params={{ id: params.row.id }}
underline="hover"
data-testid={`invoice-link-${params.row.id}`}
onClick={(event) => event.stopPropagation()}
>
{params.value}
</MuiLink>
);
}
export const pendingApprovalColumns: GridColDef<MockInvoice>[] = [
{
field: "invoiceNumbers",
headerName: "Invoice #",
flex: 1,
minWidth: 120,
renderCell: invoiceNumberLink,
},
{ field: "vendorName", headerName: "Vendor", flex: 1.4, minWidth: 160 },
dateColumn("dueDate", "Due Date"),
dateColumn("sendPaymentOn", "Send Payment On"),
{ field: "paymentMethod", headerName: "Payment Method", flex: 1, minWidth: 130 },
moneyColumn("amountDue", "Amount Due"),
moneyColumn("amount", "Amount"),
];
export const readyToPayColumns: GridColDef<MockInvoice>[] = [
dateColumn("dueDate", "Due Date"),
dateColumn("payDate", "Pay Date", true),
{ field: "vendorName", headerName: "Vendor", flex: 1.4, minWidth: 160 },
{
field: "invoiceNumber",
headerName: "Invoice #",
flex: 1,
minWidth: 120,
renderCell: invoiceNumberLink,
},
moneyColumn("amountDue", "Amount Due"),
];
export const allInvoicesColumns: GridColDef<MockInvoice>[] = [
{
field: "invoiceNumber",
headerName: "Invoice #",
flex: 1,
minWidth: 120,
renderCell: invoiceNumberLink,
},
{ field: "vendorName", headerName: "Vendor", flex: 1.4, minWidth: 160 },
{ field: "status", headerName: "Status", flex: 1, minWidth: 140 },
dateColumn("dueDate", "Due Date"),
dateColumn("payDate", "Pay Date"),
{ field: "paymentMethod", headerName: "Payment Method", flex: 1, minWidth: 130 },
moneyColumn("amountDue", "Amount Due"),
moneyColumn("amount", "Amount"),
];