'use client'; import Link from 'next/link'; import { format } from 'date-fns'; import { MoreHorizontal, Pencil, Archive, Eye } from 'lucide-react'; import type { ColumnDef } from '@tanstack/react-table'; import { Button } from '@/components/ui/button'; import { Badge } from '@/components/ui/badge'; import { DropdownMenu, DropdownMenuContent, DropdownMenuItem, DropdownMenuTrigger, } from '@/components/ui/dropdown-menu'; export interface ExpenseRow { id: string; establishmentName: string | null; amount: string; currency: string; amountUsd: string | null; category: string | null; paymentStatus: string | null; paymentMethod: string | null; expenseDate: string; description: string | null; payer: string | null; receiptFileIds: string[] | null; archivedAt: string | null; createdAt: string; } const PAYMENT_STATUS_COLORS: Record = { unpaid: 'bg-red-100 text-red-700 border-red-200', paid: 'bg-green-100 text-green-700 border-green-200', partial: 'bg-yellow-100 text-yellow-700 border-yellow-200', }; interface GetColumnsOptions { portSlug: string; onEdit: (expense: ExpenseRow) => void; onArchive: (expense: ExpenseRow) => void; } export function getExpenseColumns({ portSlug, onEdit, onArchive, }: GetColumnsOptions): ColumnDef[] { return [ { id: 'expenseDate', accessorKey: 'expenseDate', header: 'Date', cell: ({ getValue }) => ( {format(new Date(getValue() as string), 'MMM d, yyyy')} ), }, { id: 'establishmentName', accessorKey: 'establishmentName', header: 'Establishment', cell: ({ row }) => ( e.stopPropagation()} > {row.original.establishmentName ?? '—'} ), }, { id: 'amount', header: 'Amount', enableSorting: false, cell: ({ row }) => ( {Number(row.original.amount).toLocaleString('en-US', { minimumFractionDigits: 2, maximumFractionDigits: 2, })}{' '} {row.original.currency} ), }, { id: 'amountUsd', header: 'USD Equiv.', enableSorting: false, cell: ({ row }) => row.original.amountUsd ? ( ${Number(row.original.amountUsd).toLocaleString('en-US', { minimumFractionDigits: 2, maximumFractionDigits: 2, })} ) : ( N/A ), }, { id: 'category', accessorKey: 'category', header: 'Category', cell: ({ getValue }) => { const cat = getValue() as string | null; if (!cat) return ; return ( {cat.replace(/_/g, ' ')} ); }, }, { id: 'paymentStatus', accessorKey: 'paymentStatus', header: 'Status', cell: ({ getValue }) => { const status = (getValue() as string | null) ?? 'unpaid'; const colorClass = PAYMENT_STATUS_COLORS[status] ?? ''; return ( {status} ); }, }, { id: 'actions', header: '', enableSorting: false, size: 48, cell: ({ row }) => ( View onEdit(row.original)}> Edit onArchive(row.original)} > Archive ), }, ]; }