adminFront/src/pages/dashboard/Content/PromocodeManagement/StatisticsModal.tsx
2024-04-12 03:02:26 +03:00

286 lines
8.0 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

import { useEffect, useState } from "react";
import {
Box,
Button,
Typography,
Modal,
TextField,
useTheme,
useMediaQuery,
IconButton,
} from "@mui/material";
import { DataGrid, GridLoadingOverlay, GridToolbar } from "@mui/x-data-grid";
import { DatePicker } from "@mui/x-date-pickers/DatePicker";
import { fadeIn } from "@root/utils/style/keyframes";
import ContentCopyIcon from "@mui/icons-material/ContentCopy";
import type { GridColDef } from "@mui/x-data-grid";
import type { Promocode, PromocodeStatistics } from "@root/model/promocodes";
type StatisticsModalProps = {
id: string;
to: number;
from: number;
setId: (id: string) => void;
setTo: (date: number) => void;
setFrom: (date: number) => void;
promocodes: Promocode[];
promocodeStatistics: PromocodeStatistics | null | undefined;
createFastLink: (id: string) => Promise<void>;
};
type Row = {
id: number;
link: string;
useCount: number;
};
const COLUMNS: GridColDef<Row, string>[] = [
{
field: "copy",
headerName: "копировать",
width: 50,
sortable: false,
valueGetter: ({ row }) => String(row.useCount),
renderCell: (params) => {
return (
<IconButton
onClick={() => navigator.clipboard.writeText(`https://hub.pena.digital/?fl=${params.row.link}`)}
>
<ContentCopyIcon />
</IconButton>
);
},
},
{
field: "link",
headerName: "Ссылка",
width: 320,
sortable: false,
valueGetter: ({ row }) => row.link,
renderCell: ({ value }) =>
value?.split("|").map((link) => <Typography>{link}</Typography>),
},
{
field: "useCount",
headerName: "Использований",
width: 120,
sortable: false,
valueGetter: ({ row }) => String(row.useCount),
},
{
field: "purchasesCount",
headerName: "Покупок",
width: 70,
sortable: false,
valueGetter: ({ row }) => String(0),
},
];
export const StatisticsModal = ({
id,
setId,
setFrom,
from,
to,
setTo,
promocodeStatistics,
promocodes,
createFastLink,
}: StatisticsModalProps) => {
const [startDate, setStartDate] = useState<Date>(new Date());
const [endDate, setEndDate] = useState<Date>(new Date());
const theme = useTheme();
const isMobile = useMediaQuery(theme.breakpoints.down(550));
const [rows, setRows] = useState<Row[]>([]);
const createFastlink = async () => {
await createFastLink(id);
getParseData();
};
const getParseData = async () => {
const rows = promocodes
.find((promocode) => promocode.id === id)
?.fastLinks?.map((link, index) => ({
link,
id: index,
useCount: promocodeStatistics?.usageMap[link] ?? 0,
})) as Row[];
setRows(rows);
};
useEffect(() => {
if (id.length > 0) {
getParseData();
}
if (!id) {
setRows([]);
}
}, [id]);
// const formatTo = to === null ? 0 : moment(to).unix()
// const formatFrom = from === null ? 0 : moment(from).unix()
// useEffect(() => {
// (async () => {
// const gottenGeneral = await promocodeStatistics(id, startDate, endDate)
// setGeneral(gottenGeneral[0])
// })()
// }, [to, from]);
return (
<Modal
open={Boolean(id)}
onClose={() => {
setId("");
setStartDate(new Date());
setEndDate(new Date());
}}
sx={{ "& > .MuiBox-root": { outline: "none" } }}
>
<Box
sx={{
position: "absolute",
top: "50%",
left: "50%",
transform: "translate(-50%, -50%)",
width: "95%",
maxWidth: "600px",
background: "#1F2126",
border: "2px solid gray",
borderRadius: "6px",
boxShadow: 24,
p: 4,
}}
>
<Box
sx={{
display: "flex",
gap: "30px",
justifyContent: "center",
alignItems: "center",
flexDirection: isMobile ? "column" : "row",
}}
>
<Box
sx={{
display: "flex",
gap: "30px",
justifyContent: "center",
alignItems: "center",
}}
>
<Button sx={{ maxWidth: "100px" }} onClick={createFastlink}>
Создать короткую ссылку
</Button>
<Button sx={{ maxWidth: "100px" }} onClick={getParseData}>
Обновить статистику
</Button>
</Box>
<Box sx={{ minWidth: "200px" }}>
<Box sx={{ display: "flex", alignItems: "center", gap: "10px" }}>
<Typography sx={{ minWidth: "20px", color: "#FFFFFF" }}>
от
</Typography>
<DatePicker
inputFormat="DD/MM/YYYY"
value={startDate}
onChange={(date) => date && setStartDate(date)}
renderInput={(params) => (
<TextField
{...params}
sx={{ background: "#1F2126", borderRadius: "5px" }}
/>
)}
InputProps={{
sx: {
height: "40px",
color: theme.palette.secondary.main,
border: "1px solid",
borderColor: theme.palette.secondary.main,
"& .MuiSvgIcon-root": {
color: theme.palette.secondary.main,
},
},
}}
/>
</Box>
<Box
sx={{
display: "flex",
alignItems: "center",
gap: "10px",
marginTop: "10px",
}}
>
<Typography sx={{ minWidth: "20px", color: "#FFFFFF" }}>
до
</Typography>
<DatePicker
inputFormat="DD/MM/YYYY"
value={endDate}
onChange={(date) => date && setEndDate(date)}
renderInput={(params) => (
<TextField
{...params}
sx={{ background: "#1F2126", borderRadius: "5px" }}
/>
)}
InputProps={{
sx: {
height: "40px",
color: theme.palette.secondary.main,
border: "1px solid",
borderColor: theme.palette.secondary.main,
"& .MuiSvgIcon-root": {
color: theme.palette.secondary.main,
},
},
}}
/>
</Box>
</Box>
</Box>
<DataGrid
disableSelectionOnClick={true}
rows={rows}
columns={COLUMNS}
sx={{
marginTop: "30px",
background: "#1F2126",
color: theme.palette.secondary.main,
"& .MuiDataGrid-iconSeparator": { display: "none" },
"& .css-levciy-MuiTablePagination-displayedRows": {
color: theme.palette.secondary.main,
},
"& .MuiSvgIcon-root": { color: theme.palette.secondary.main },
"& .MuiTablePagination-selectLabel": {
color: theme.palette.secondary.main,
},
"& .MuiInputBase-root": { color: theme.palette.secondary.main },
"& .MuiButton-text": { color: theme.palette.secondary.main },
"& .MuiDataGrid-overlay": {
backgroundColor: "rgba(255, 255, 255, 0.1)",
animation: `${fadeIn} 0.5s ease-out`,
},
"& .MuiDataGrid-virtualScrollerContent": { maxHeight: "200px" },
"& .MuiDataGrid-virtualScrollerRenderZone": {
maxHeight: "200px",
overflowY: "auto",
},
}}
components={{
Toolbar: GridToolbar,
LoadingOverlay: GridLoadingOverlay,
}}
rowsPerPageOptions={[10, 25, 50, 100]}
autoHeight
/>
</Box>
</Modal>
);
};