243 lines
5.8 KiB
TypeScript
243 lines
5.8 KiB
TypeScript
import type { ColumnDef } from "@tanstack/react-table";
|
|
import { CircleCheck, ExternalLink } from "lucide-react";
|
|
import Link from "next/link";
|
|
import { useState } from "react";
|
|
import { OrdiniModal } from "~/components/area-riservata/ordini";
|
|
import { DataTable } from "~/components/custom_ui/data-table";
|
|
import { DataTableColumnHeader } from "~/components/custom_ui/dataTable-header";
|
|
import type {
|
|
PinnedFiltro,
|
|
SearchFiltro,
|
|
} from "~/components/custom_ui/dataTable-toolbar";
|
|
import { Button } from "~/components/ui/button";
|
|
import OrderTypeEnum from "~/schemas/public/OrderTypeEnum";
|
|
import type { OrdiniOrdineId } from "~/schemas/public/Ordini";
|
|
import PaymentStatusEnum from "~/schemas/public/PaymentStatusEnum";
|
|
import type { UsersId } from "~/schemas/public/Users";
|
|
import type { OrdiniWPagamenti } from "~/server/controllers/ordini.controller";
|
|
|
|
type PaymentsTableProps = {
|
|
data: OrdiniWPagamenti[];
|
|
isAdmin: boolean;
|
|
userId?: UsersId;
|
|
};
|
|
|
|
export const OrdiniTable = ({ data, isAdmin, userId }: PaymentsTableProps) => {
|
|
const tabledata = data.map((row) => {
|
|
return {
|
|
actions: "Azioni",
|
|
created_at: row.created_at,
|
|
id: row.ordine_id,
|
|
isActive: row.isActive,
|
|
isPaid: row.pagamenti.some(
|
|
(p) => p.paymentstatus === PaymentStatusEnum.success,
|
|
),
|
|
packid: row.packid,
|
|
tipo: row.type,
|
|
userId: row.userid,
|
|
username: row.username,
|
|
};
|
|
});
|
|
|
|
const columns_titles = {
|
|
actions: "Azioni",
|
|
created_at: "Creato il",
|
|
isPaid: "Pagato",
|
|
packid: "ID Pacchetto",
|
|
tipo: "Tipo",
|
|
username: "Utente",
|
|
};
|
|
const isPaidOptions = [
|
|
{ label: "Pagato", value: "true" },
|
|
{ label: "Non pagato", value: "false" },
|
|
];
|
|
|
|
const type_options = [
|
|
{ label: "Acconto", value: OrderTypeEnum.Acconto },
|
|
{ label: "Saldo", value: OrderTypeEnum.Saldo },
|
|
{ label: "Consulenza", value: OrderTypeEnum.Consulenza },
|
|
{ label: "Altro", value: OrderTypeEnum.Altro },
|
|
];
|
|
|
|
const [modalOpen, setModalOpen] = useState(false);
|
|
const [selectedOrdine, setSelectedOrdine] = useState<OrdiniOrdineId | null>(
|
|
null,
|
|
);
|
|
|
|
type Column = (typeof tabledata)[number];
|
|
|
|
const columns: ColumnDef<Column>[] = [
|
|
{
|
|
accessorKey: "username",
|
|
cell: ({ row }) => {
|
|
if (isAdmin) {
|
|
return (
|
|
<Link
|
|
aria-label="Visualizza Utente"
|
|
href={`/area-riservata/admin/user-view/ricerca/${row.original.userId}`}
|
|
>
|
|
<Button size="sm">{row.original.username}</Button>
|
|
</Link>
|
|
);
|
|
}
|
|
return <span>{row.original.username}</span>;
|
|
},
|
|
enableHiding: false,
|
|
header: ({ column }) => (
|
|
<DataTableColumnHeader
|
|
column={column}
|
|
title={columns_titles.username}
|
|
/>
|
|
),
|
|
},
|
|
{
|
|
accessorKey: "created_at",
|
|
cell: ({ row }) => {
|
|
const date = row.getValue("created_at");
|
|
return new Date(date as Date).toLocaleDateString();
|
|
},
|
|
enableHiding: false,
|
|
header: ({ column }) => (
|
|
<DataTableColumnHeader
|
|
column={column}
|
|
title={columns_titles.created_at}
|
|
/>
|
|
),
|
|
sortingFn: "datetime",
|
|
},
|
|
{
|
|
accessorKey: "tipo",
|
|
cell: ({ row }) => {
|
|
return row.original.tipo.toString();
|
|
},
|
|
filterFn: (row, id, value) => {
|
|
return value.includes(row.getValue(id));
|
|
},
|
|
header: ({ column }) => (
|
|
<DataTableColumnHeader column={column} title={columns_titles.tipo} />
|
|
),
|
|
},
|
|
|
|
{
|
|
accessorKey: "packid",
|
|
header: ({ column }) => (
|
|
<DataTableColumnHeader column={column} title={columns_titles.packid} />
|
|
),
|
|
},
|
|
{
|
|
accessorKey: "isPaid",
|
|
cell: ({ row }) => {
|
|
const isPaid = row.original.isPaid;
|
|
const isActive = row.original.isActive;
|
|
if (isActive) {
|
|
return (
|
|
<span className="inline-flex items-center gap-1 text-green-500">
|
|
<CircleCheck className="size-5" />
|
|
{isPaid ? "Pagato" : "Attivato da Admin"}
|
|
</span>
|
|
);
|
|
}
|
|
if (isPaid) {
|
|
return (
|
|
<span className="inline-flex items-center gap-1 text-green-500">
|
|
<CircleCheck className="size-5" />
|
|
Pagato
|
|
</span>
|
|
);
|
|
} else {
|
|
return (
|
|
<span className="inline-flex items-center gap-1 text-red-500">
|
|
<CircleCheck className="size-5" />
|
|
Non pagato
|
|
</span>
|
|
);
|
|
}
|
|
},
|
|
|
|
filterFn: (row, id, value) => {
|
|
return value.includes(row.getValue(id));
|
|
},
|
|
header: ({ column }) => (
|
|
<DataTableColumnHeader column={column} title={columns_titles.isPaid} />
|
|
),
|
|
},
|
|
|
|
{
|
|
cell: ({ row }) => {
|
|
return (
|
|
<Button
|
|
aria-label="Apri Dettagli Ordine"
|
|
className="flex items-center gap-2"
|
|
onClick={() => {
|
|
setSelectedOrdine(row.original.id);
|
|
setModalOpen(true);
|
|
}}
|
|
size="sm"
|
|
variant="outline"
|
|
>
|
|
<ExternalLink className="size-6" />
|
|
Apri Dettagli
|
|
</Button>
|
|
);
|
|
},
|
|
enableHiding: false,
|
|
id: "actions",
|
|
},
|
|
];
|
|
|
|
const searchFiltro: SearchFiltro =
|
|
isAdmin && !userId
|
|
? {
|
|
columnName: "username",
|
|
placeholder: "Cerca utente...",
|
|
}
|
|
: {
|
|
columnName: "packid",
|
|
placeholder: "Cerca pagamento...",
|
|
};
|
|
|
|
const pinnedFiltri: PinnedFiltro[] = [
|
|
{
|
|
columnName: "isPaid",
|
|
|
|
options: isPaidOptions,
|
|
title: "Stato Pagamento",
|
|
},
|
|
{
|
|
columnName: "tipo",
|
|
options: type_options,
|
|
title: "Tipo Ordine",
|
|
},
|
|
];
|
|
|
|
return (
|
|
<div className="mx-auto w-full py-10">
|
|
<DataTable
|
|
columns={columns}
|
|
columns_titles={columns_titles}
|
|
data={tabledata}
|
|
defaultColumnVisibility={{
|
|
actions: true,
|
|
amount: true,
|
|
packid: true,
|
|
paid_at: true,
|
|
status: true,
|
|
tipo: true,
|
|
username: isAdmin && !userId,
|
|
}}
|
|
defaultSort={[{ desc: true, id: "created_at" }]}
|
|
pinnedFiltri={pinnedFiltri}
|
|
searchColumn={searchFiltro}
|
|
/>
|
|
{selectedOrdine && (
|
|
<OrdiniModal
|
|
isAdmin={isAdmin}
|
|
open={modalOpen}
|
|
ordineId={selectedOrdine}
|
|
setModalOpen={setModalOpen}
|
|
userId={userId}
|
|
/>
|
|
)}
|
|
</div>
|
|
);
|
|
};
|