3
3
// @mui
import {
Container,
Grid,
Card,
Paper,
Typography,
styled,
Button,
TableRow,
TableCell,
Table,
TableHead,
TableBody,
Pagination,
TableContainer,
CardContent,
} from "@mui/material";
import axiosInstance from "../../utils/axios";
import { API_ENDPOINT } from "../../utils/constant";
import { RefreshOutlined, RefreshTwoTone } from "@mui/icons-material";
import ActiveUserCard from "../../components/ActiveUserCard";
import UserMetricsCard from "../../components/UserMetricsCard";
import ChartCard from "../../components/ChartCard";
import { List as BaseList } from "../../layouts/list/List";
import { fi } from "date-fns/locale";
// ----------------------------------------------------------------------
const NOTIFICATION_ROWS = [
{ id: "empty1", label: "" },
{ id: "title", label: "Title" },
{ id: "empty2", label: "" },
{ id: "type", label: "Type" },
{ id: "empty3", label: "" },
{ id: "createdAt", label: "Created At" },
{ id: "status", label: "Status" },
];
const ROWS = [
{ id: "username", label: "Username" },
{ id: "", label: "" },
{ id: "mobileNumber", label: "Mobile Number" },
{ id: "", label: "" },
{ id: "lastActiveAt", label: "Last Active" },
];
const [
audiosByCategoryResponse,
audiosByLanguageResponse,
activeUsersResponse,
userGrowthStatsResponse,
audiosCreatedByMonthResponse,
audiosCreatedLast30DaysResponse,
unprocessedAudiosResponse,
userMatricesResponse,
] = await Promise.all([
axiosInstance.get(API_ENDPOINT.DASHBOARD.AUDIOS_BY_CATEGORY),
axiosInstance.get(API_ENDPOINT.DASHBOARD.AUDIOS_BY_LANGUAGE),
axiosInstance.get(API_ENDPOINT.DASHBOARD.ACTIVE_USERS),
axiosInstance.get(API_ENDPOINT.DASHBOARD.USER_GROWTH),
axiosInstance.get(API_ENDPOINT.DASHBOARD.AUDIOS_CREATED_BY_MONTH),
axiosInstance.get(API_ENDPOINT.DASHBOARD.AUDIOS_CREATED_30_DAYS),
axiosInstance.get(API_ENDPOINT.DASHBOARD.UNPROCESSED_AUDIOS),
axiosInstance.get(API_ENDPOINT.METRICS.USER_METRICS),
]);
const audiosCreatedMonthWiseDates =
audiosCreatedByMonthResponse?.data?.map((item) => item.month) || [];
const audiosCreatedMonthWiseCounts =
audiosCreatedByMonthResponse?.data?.map((item) => item.count) || [];
setAudiosCreatedMonthwise({
series: [
{ name: "Audios Created Count", data: audiosCreatedMonthWiseCounts },
],
options: {
...audiosCreatedMonthwiseBarChart.options,
xaxis: { categories: audiosCreatedMonthWiseDates },
},
});
const audiosCreatedLast30Dates =
audiosCreatedLast30DaysResponse?.data?.map((item) => item.date) || [];
const audiosCreatedLast30Counts =
audiosCreatedLast30DaysResponse?.data?.map((item) => item.count) || [];
setAudiosCreatedLast30Dayswise({
series: [
{ name: "Audios Created Count", data: audiosCreatedLast30Counts },
],
options: {
...audiosCreatedMonthwiseBarChart.options,
xaxis: { categories: audiosCreatedLast30Dates },
},
});
setError(false);
} catch (error) {
console.error(error);
setError(true);
} finally {
setIsLoading(false);
}
};
useEffect(() => {
getStatsData();
getActiveUserData(duration, pageMeta?.limit, pageMeta?.page);
}, []);
useEffect(() => {
setUserDataLoading(true);
getActiveUserData(duration, pageMeta?.limit, pageMeta?.page);
setUserDataLoading(false);
}, [pageMeta]);
try {
setIsButtonLoading(true); // Disable button
const response = await axiosInstance.post(url, null, {
headers: {
"Content-Type": "multipart/form-data",
},
});
useEffect(() => {
if (!isInitialRender.current) {
setUserDataLoading(true);
getActiveUserData(duration, pageMeta?.limit, pageMeta?.page);
setUserDataLoading(false);
}
}, [pageMeta, duration]);
return (
<Page title="Audioshots | Admin">
{isLoading ? (
<Loader />
) : (
<>
<Container maxWidth="xl">
<Grid
container
alignItems="center"
justifyContent="space-between"
sx={{ mb: 3 }}
>
<Typography
variant="h5"
sx={{ fontWeight: "bold", color: "#34bf49" }}
>
{unprocessedCount}
</Typography>
<RefreshOutlined
onClick={handleRefresh}
color="primary"
sx={{
fontSize: 30,
cursor: "pointer",
"&:hover": {
color: "#1565c0",
},
}}
/>
</Grid>
<Typography
variant="h5"
sx={{
mb: 3,
fontWeight: "bold",
pb: 1,
}}
>
User Metrics
</Typography>
<Grid container spacing={2} sx={{ mb: 3 }}>
<Grid item xs={6} sm={3}>
<UserMetricsCard label="DAU" value={userMetrics?.DAU} />
</Grid>
<Grid item xs={6} sm={3}>
<UserMetricsCard label="WAU" value={userMetrics?.WAU} />
</Grid>
<Grid item xs={6} sm={3}>
<UserMetricsCard label="MAU" value={userMetrics?.MAU} />
</Grid>
</Grid>
<Grid item>
<Button
onClick={handleClick}
disabled={unprocessedCount <= 0}
style={{
padding: "12px 24px",
backgroundColor:
unprocessedCount > 0 ? "#28a745" : "#e0e0e0",
color: unprocessedCount > 0 ? "#ffffff" : "#9e9e9e",
fontSize: "16px",
fontWeight: "500",
border: "1px solid",
borderColor: unprocessedCount > 0 ? "#28a745" : "#ccc",
borderRadius: "8px",
cursor: unprocessedCount > 0 ? "pointer" : "not-allowed",
transition: "all 0.1s ease",
boxShadow:
unprocessedCount > 0
? "0 2px 4px rgba(0, 0, 0, 0.2)"
: "none",
}}
onMouseOver={(e) => {
if (unprocessedCount > 0) {
e.target.style.backgroundColor = "#218838";
e.target.style.boxShadow = "0 4px 8px rgba(0, 0, 0, 0.2)";
}
}}
onMouseOut={(e) => {
if (unprocessedCount > 0) {
e.target.style.backgroundColor = "#28a745";
e.target.style.boxShadow = "0 2px 4px rgba(0, 0, 0, 0.2)";
}
}}
>
{isButtonLoading ? "Processing..." : "Trigger Request"}{" "}
</Button>
</Grid>
</Grid>
pb: 1,
}}
>
Audios Analytics
</Typography>
<Grid container spacing={4} sx={{ mb: 3 }}>
<Grid item xs={12} sm={6}>
<ChartCard
title="Audios by Language"
chartData={languageBarChart}
/>
</Grid>
{userDataLoading ? (
<Loader />
) : (
<>
<BaseList
title="Active Users"
countries={[]}
hideSearch={true}
elements={activeUsersData?.users || []}
rows={ROWS}
onChange={(newMeta) => {
setPageMeta(newMeta);
if (newMeta.duration !== duration) {
setDuration(newMeta.duration);
getActiveUserData(
newMeta.duration,
newMeta.limit,
newMeta.page
);
}
}}
meta={pageMeta}
total={activeUsersData?.total || 0}
showUserFilter={false}
durationFilter={true}
renderBody={(elements) => (
<>
{elements.map((user) => (
<TableRow hover key={user._id}>
<TableCell>{}</TableCell>
<TableCell>{user?.userName}</TableCell>
<TableCell>{}</TableCell>
<TableCell>{user?.mobileNumber}</TableCell>
<TableCell>{}</TableCell>
<TableCell>
{user?.lastActiveAt
? new Date(user.lastActiveAt).toLocaleString()
: "N/A"}
</TableCell>
</TableRow>
))}
</>
)}
/>
</>
)}
<div>
<Typography variant="h5" sx={{ mb: 3, fontWeight: "bold" }}>
Notifications
</Typography>
<Button
onClick={markAllAsRead}
disabled={
!Array.isArray(notificationsData) ||
notificationsData.length === 0 ||
!notificationsData.some((n) => !n.hasBeenRead)
}
sx={{ ml: 2 }}
variant="contained"
color="primary"
>
Mark All as Read
</Button>