{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "invoices-table",
  "title": "Invoices Table",
  "description": "Billing history with mono invoice numbers, status pills and a per-row PDF download.",
  "registryDependencies": [
    "@spectrumui/data-table"
  ],
  "files": [
    {
      "path": "components/spectrumui/blocks/tables/invoices-table.tsx",
      "content": "'use client';\n\nimport * as React from 'react';\nimport { DataTable, type DataTableColumn } from '@/components/spectrumui/data-table';\n\ntype IconProps = React.SVGProps<SVGSVGElement>;\n\nfunction IconDownload(props: IconProps) {\n  return (\n    <svg viewBox=\"0 0 24 24\" fill=\"currentColor\" aria-hidden=\"true\" {...props}>\n      <path\n        transform=\"translate(2, 2.5)\"\n        d=\"M9.23,4.791 L9.23,0.782 C9.23,0.355 9.57,0 10,0 C10.385,0 10.711,0.298 10.763,0.677 L10.77,0.782 L10.77,4.791 L15.55,4.791 C17.93,4.791 19.885,6.74 19.995,9.17 L20,9.386 L20,14.425 C20,16.873 18.113,18.882 15.768,18.995 L15.56,19 L4.44,19 C2.06,19 0.114,17.061 0.005,14.621 L0,14.405 L0,9.376 C0,6.928 1.878,4.909 4.222,4.796 L4.43,4.791 L9.23,4.791 L9.23,11.193 L7.63,9.541 C7.33,9.231 6.84,9.231 6.54,9.541 C6.39,9.696 6.32,9.902 6.32,10.109 C6.32,10.266 6.365,10.429 6.46,10.568 L6.54,10.667 L9.45,13.682 C9.59,13.837 9.79,13.919 10,13.919 C10.167,13.919 10.333,13.862 10.465,13.753 L10.54,13.682 L13.45,10.667 C13.75,10.357 13.75,9.851 13.45,9.541 C13.177,9.259 12.748,9.234 12.446,9.464 L12.36,9.541 L10.77,11.193 L10.77,4.791 L9.23,4.791 Z\"\n      />\n    </svg>\n  );\n}\n\ntype Status = 'paid' | 'due' | 'overdue';\n\ninterface Invoice {\n  id: string;\n  number: string;\n  period: string;\n  issued: string;\n  status: Status;\n  amount: number;\n}\n\nconst INVOICES: Invoice[] = [\n  {\n    id: 'i1',\n    number: 'INV-2041',\n    period: 'Aug 2026',\n    issued: 'Sep 1',\n    status: 'due',\n    amount: 1140,\n  },\n  {\n    id: 'i2',\n    number: 'INV-2033',\n    period: 'Jul 2026',\n    issued: 'Aug 1',\n    status: 'paid',\n    amount: 1140,\n  },\n  {\n    id: 'i3',\n    number: 'INV-2025',\n    period: 'Jun 2026',\n    issued: 'Jul 1',\n    status: 'paid',\n    amount: 980,\n  },\n  {\n    id: 'i4',\n    number: 'INV-2017',\n    period: 'May 2026',\n    issued: 'Jun 1',\n    status: 'paid',\n    amount: 980,\n  },\n  {\n    id: 'i5',\n    number: 'INV-2009',\n    period: 'Apr 2026',\n    issued: 'May 1',\n    status: 'overdue',\n    amount: 860,\n  },\n  {\n    id: 'i6',\n    number: 'INV-2001',\n    period: 'Mar 2026',\n    issued: 'Apr 1',\n    status: 'paid',\n    amount: 860,\n  },\n];\n\nconst STATUS_STYLE: Record<Status, string> = {\n  paid: 'bg-emerald-50 text-emerald-700 ring-emerald-600/20 dark:bg-emerald-400/10 dark:text-emerald-300 dark:ring-emerald-300/25',\n  due: 'bg-amber-50 text-amber-800 ring-amber-600/20 dark:bg-amber-400/10 dark:text-amber-300 dark:ring-amber-300/25',\n  overdue:\n    'bg-rose-50 text-rose-700 ring-rose-600/20 dark:bg-rose-400/10 dark:text-rose-300 dark:ring-rose-300/25',\n};\n\nconst money = new Intl.NumberFormat('en-US', {\n  style: 'currency',\n  currency: 'USD',\n  maximumFractionDigits: 0,\n});\n\nconst columns: DataTableColumn<Invoice>[] = [\n  {\n    id: 'number',\n    header: 'Invoice',\n    sortable: true,\n    value: (row) => row.number,\n    cell: (row) => <span className=\"font-mono text-[13px]\">{row.number}</span>,\n  },\n  { id: 'period', header: 'Billing period', value: (row) => row.period },\n  { id: 'issued', header: 'Issued', hideBelow: 'sm', value: (row) => row.issued },\n  {\n    id: 'status',\n    header: 'Status',\n    sortable: true,\n    value: (row) => row.status,\n    cell: (row) => (\n      <span\n        className={`inline-flex items-center gap-1.5 rounded-full px-2 py-0.5 text-xs font-medium capitalize ring-1 ring-inset ${STATUS_STYLE[row.status]}`}\n      >\n        <span aria-hidden=\"true\" className=\"size-1.5 rounded-full bg-current\" />\n        {row.status}\n      </span>\n    ),\n  },\n  {\n    id: 'amount',\n    header: 'Amount',\n    sortable: true,\n    numeric: true,\n    value: (row) => row.amount,\n    formatTotal: (sum) => money.format(sum),\n    cell: (row) => (\n      <span className=\"font-medium text-neutral-900 dark:text-neutral-100\">\n        {money.format(row.amount)}\n      </span>\n    ),\n  },\n];\n\nexport function InvoicesTable({ variant = 'Panel' }: { variant?: 'Panel' | 'Minimal' }) {\n  return (\n    <div className=\"mx-auto w-full max-w-3xl px-4 py-10 sm:px-6\">\n      <DataTable\n        data={INVOICES}\n        columns={columns}\n        rowId={(row) => row.id}\n        rowLabel={(row) => `invoice ${row.number}`}\n        caption=\"Billing history with period, status and amount.\"\n        variant={variant === 'Minimal' ? 'minimal' : 'panel'}\n        title=\"Invoices\"\n        totals={['amount']}\n        rowActions={(row) => (\n          <button\n            type=\"button\"\n            aria-label={`Download ${row.number} as PDF`}\n            className=\"grid size-8 place-items-center rounded-xl text-neutral-400 transition-colors duration-100 ease-out hover:bg-neutral-100 hover:text-neutral-900 focus-visible:ring-1 focus-visible:ring-neutral-950 focus-visible:outline-hidden dark:hover:bg-neutral-800 dark:hover:text-neutral-100 dark:focus-visible:ring-neutral-300\"\n          >\n            <IconDownload className=\"size-4\" />\n          </button>\n        )}\n      />\n    </div>\n  );\n}\n",
      "type": "registry:block",
      "target": "components/spectrumui/blocks/tables/invoices-table.tsx"
    }
  ],
  "type": "registry:block"
}
