UNPKG

bananas-commerce-admin

Version:

What's this, an admin for apes?

94 lines 4.58 kB
import React, { useCallback, useMemo } from "react"; import { Button, Stack, TableBody, TableRow } from "@mui/material"; import { useDashboardFilter } from "../contexts/DashboardFilterContext"; import { formatDate } from "../util/format_date"; import { TableCell } from "./Table/TableCell"; import TableHead from "./Table/TableHead"; import TableHeading from "./Table/TableHeading"; import Table from "./Table"; export default function StatsDataTable({ data, dateKey, csvFileName }) { const { filter } = useDashboardFilter(); const mappedData = useMemo(() => { return data .map((item) => { const dateEntry = getDateEntry(item, dateKey); if (dateEntry === undefined) return undefined; const [key, date] = dateEntry; const { [key]: _, ...rest } = item; return { [key]: date, ...rest }; }) .filter((item) => item !== undefined); }, [data, dateKey]); const handleExportToCSV = useCallback(() => { if (mappedData.length === 0) return; const headers = Object.keys(mappedData[0]); const csvRows = [ headers.join(","), // Header row ...mappedData.map((row) => headers .map((key) => { const value = row[key]; if (value instanceof Date) return `"${value.toISOString()}"`; if (typeof value === "string") return `"${value.replace(/"/g, '""')}"`; // Escape quotes return value; }) .join(",")), ]; const csvContent = csvRows.join("\n"); const blob = new Blob([csvContent], { type: "text/csv" }); const url = URL.createObjectURL(blob); const link = document.createElement("a"); link.href = url; link.download = `${csvFileName || "data"}_${filter.startDate.toISO()?.split("T")[0]}_${filter.endDate.toISO()?.split("T")[0]}.csv`; document.body.appendChild(link); link.click(); document.body.removeChild(link); URL.revokeObjectURL(url); }, [mappedData, filter.startDate, filter.endDate, filter.granularity]); return (React.createElement(Stack, { maxHeight: 300 }, React.createElement(Table, { count: mappedData.length }, React.createElement(TableHead, { tableRowProps: { sx: { position: "sticky", top: 0, bgcolor: "background.paper", backgroundImage: "var(--Paper-overlay)", boxShadow: "inset 0 -1px var(--mui-palette-divider)", }, } }, mappedData.length > 0 && Object.keys(mappedData[0]).map((key) => { return React.createElement(TableHeading, { key: key }, formatKey(key)); })), React.createElement(TableBody, { sx: { overflowY: "auto" } }, mappedData.map((item, i) => (React.createElement(TableRow, { key: i }, Object.entries(item).map(([key, value]) => (React.createElement(TableCell, { key: key, sx: { borderBottomWidth: i === mappedData.length - 1 ? 0 : 1 } }, value instanceof Date ? formatDate(value, filter.granularity) : value.toString())))))))), React.createElement(Stack, { alignItems: "flex-end", pt: 2, px: 2, spacing: 1, sx: { borderTop: "1px solid", borderColor: "divider" } }, React.createElement(Button, { color: "inherit", variant: "outlined", onClick: handleExportToCSV }, "Export to CSV")))); } function formatKey(key) { return key .split("_") .map((word) => word.charAt(0).toUpperCase() + word.slice(1)) .join(" "); } function getDateEntry(item, dateKey) { if (dateKey !== undefined && item.hasOwnProperty(dateKey)) { let date = item[dateKey]; date = typeof date === "string" ? new Date(date) : date; if (!(date instanceof Date)) return undefined; return [dateKey, date]; } const dateEntry = Object.entries(item).find(([_, value]) => isDateOrString(value)); if (dateEntry === undefined) { return undefined; } const dateObj = dateEntry[1] instanceof Date ? dateEntry[1] : new Date(dateEntry[1]); return [dateEntry[0], dateObj]; } function isDateOrString(value) { return ((value instanceof Date && !Number.isNaN(value.getTime())) || (typeof value === "string" && !Number.isNaN(Date.parse(value)))); } //# sourceMappingURL=StatsDataTable.js.map