Improve dashboard prefetching and analytics charts
All checks were successful
Build Frontend / build (push) Successful in 1m14s

Removed dashboard prefetching from the login page to avoid unnecessary middleware redirects for unauthenticated users. Added delayed prefetching of dashboard routes after initial load for better navigation performance. Updated AdminAnalytics to use AreaChart instead of BarChart for daily metrics, improving visual clarity. Enhanced middleware to allow prefetch requests through without redirecting to login, supporting better caching and navigation.
This commit is contained in:
g
2026-01-13 05:49:14 +00:00
parent 4c15f433d9
commit a07ca55a1e
5 changed files with 132 additions and 58 deletions

View File

@@ -42,6 +42,8 @@ import {
LineChart,
Line,
ComposedChart,
AreaChart,
Area,
} from "recharts";
import { formatGBP, formatNumber } from "@/lib/utils/format";
import { PieChart, Pie, Cell, Legend } from "recharts";
@@ -376,34 +378,38 @@ export default function AdminAnalytics() {
data.count === undefined);
return (
<div className="bg-background border border-border p-3 rounded-lg shadow-lg">
<p className="text-sm font-medium mb-2">
<div className="bg-[#050505]/90 p-4 rounded-xl shadow-xl border border-white/10 backdrop-blur-md ring-1 ring-white/5">
<p className="font-bold text-[10px] uppercase tracking-wide text-muted-foreground mb-3 border-b border-white/5 pb-2">
{data.formattedDate || label}
</p>
{isDualAxis ? (
<div className="space-y-1">
<p className="text-sm text-blue-600">
Orders: <span className="font-semibold">{data.orders}</span>
</p>
<p className="text-sm text-green-600">
Revenue:{" "}
<span className="font-semibold">{formatGBP(data.revenue)}</span>
</p>
<div className="space-y-2">
<div className="flex items-center justify-between gap-8">
<span className="text-[11px] font-semibold text-blue-400">Orders</span>
<span className="text-[11px] font-bold text-foreground tabular-nums">{data.orders}</span>
</div>
<div className="flex items-center justify-between gap-8">
<span className="text-[11px] font-semibold text-emerald-400">Revenue</span>
<span className="text-[11px] font-bold text-foreground tabular-nums">{formatGBP(data.revenue)}</span>
</div>
{data.avgOrderValue !== undefined && data.avgOrderValue > 0 && (
<p className="text-sm text-purple-600">
Avg Order Value:{" "}
<span className="font-semibold">
{formatGBP(data.avgOrderValue)}
</span>
</p>
<div className="flex items-center justify-between gap-8 pt-2 border-t border-white/5">
<span className="text-[10px] font-medium text-purple-400">Avg Order Value</span>
<span className="text-[10px] font-bold text-foreground tabular-nums">{formatGBP(data.avgOrderValue)}</span>
</div>
)}
</div>
) : (
<p className="text-sm text-primary">
{isAmount
? formatGBP(data.value || data.amount || 0)
: `${data.value || data.count || 0}`}
</p>
<div className="flex items-center justify-between gap-8">
<span className={`text-[11px] font-semibold ${isAmount ? "text-emerald-400" : "text-blue-400"}`}>
{isAmount ? "Revenue" : "Count"}
</span>
<span className="text-[11px] font-bold text-foreground tabular-nums">
{isAmount
? formatGBP(data.value || data.amount || 0)
: `${data.value || data.count || 0}`}
</span>
</div>
)}
</div>
);
@@ -449,7 +455,7 @@ export default function AdminAnalytics() {
};
// Calculate best month from daily data (for YTD, full year, or previous years)
const calculateBestMonth = () => {
const calculateBestMonth = (): { month: string; revenue: number; orders: number } | null => {
// Show best month for YTD, full year view, or when viewing previous years
const showBestMonth =
dateRange === "ytd" || dateRange === "year" || !isViewingCurrentYear;
@@ -734,16 +740,30 @@ export default function AdminAnalytics() {
analyticsData.orders.dailyOrders.length > 0 ? (
<div className="mt-4 h-14 -mx-2">
<ResponsiveContainer width="100%" height="100%">
<RechartsBarChart
<AreaChart
data={transformChartData(
analyticsData.orders.dailyOrders,
"count",
)}
margin={{ top: 0, right: 0, left: 0, bottom: 0 }}
margin={{ top: 5, right: 0, left: 0, bottom: 0 }}
>
<Bar dataKey="value" fill="#3b82f6" fillOpacity={0.8} radius={[2, 2, 0, 0]} />
<Tooltip content={<CustomTooltip />} cursor={{ fill: 'transparent' }} />
</RechartsBarChart>
<defs>
<linearGradient id="colorOrdersAdmin" x1="0" y1="0" x2="0" y2="1">
<stop offset="5%" stopColor="#3b82f6" stopOpacity={0.3} />
<stop offset="95%" stopColor="#3b82f6" stopOpacity={0} />
</linearGradient>
</defs>
<Area
type="monotone"
dataKey="value"
stroke="#3b82f6"
fillOpacity={1}
fill="url(#colorOrdersAdmin)"
strokeWidth={2}
activeDot={{ r: 4, strokeWidth: 0, fill: "#3b82f6" }}
/>
<Tooltip content={<CustomTooltip />} cursor={{ stroke: 'rgba(255,255,255,0.1)', strokeWidth: 1 }} />
</AreaChart>
</ResponsiveContainer>
</div>
) : (
@@ -788,16 +808,30 @@ export default function AdminAnalytics() {
analyticsData.revenue.dailyRevenue.length > 0 ? (
<div className="mt-4 h-14 -mx-2">
<ResponsiveContainer width="100%" height="100%">
<RechartsBarChart
<AreaChart
data={transformChartData(
analyticsData.revenue.dailyRevenue,
"amount",
)}
margin={{ top: 0, right: 0, left: 0, bottom: 0 }}
margin={{ top: 5, right: 0, left: 0, bottom: 0 }}
>
<Bar dataKey="value" fill="#10b981" fillOpacity={0.8} radius={[2, 2, 0, 0]} />
<Tooltip content={<CustomTooltip />} cursor={{ fill: 'transparent' }} />
</RechartsBarChart>
<defs>
<linearGradient id="colorRevenueAdmin" x1="0" y1="0" x2="0" y2="1">
<stop offset="5%" stopColor="#10b981" stopOpacity={0.3} />
<stop offset="95%" stopColor="#10b981" stopOpacity={0} />
</linearGradient>
</defs>
<Area
type="monotone"
dataKey="value"
stroke="#10b981"
fillOpacity={1}
fill="url(#colorRevenueAdmin)"
strokeWidth={2}
activeDot={{ r: 4, strokeWidth: 0, fill: "#10b981" }}
/>
<Tooltip content={<CustomTooltip />} cursor={{ stroke: 'rgba(255,255,255,0.1)', strokeWidth: 1 }} />
</AreaChart>
</ResponsiveContainer>
</div>
) : (
@@ -844,16 +878,30 @@ export default function AdminAnalytics() {
analyticsData.vendors.dailyGrowth.length > 0 ? (
<div className="mt-2 h-12 -mx-2">
<ResponsiveContainer width="100%" height="100%">
<RechartsBarChart
<AreaChart
data={transformChartData(
analyticsData.vendors.dailyGrowth,
"count",
)}
margin={{ top: 0, right: 0, left: 0, bottom: 0 }}
margin={{ top: 5, right: 0, left: 0, bottom: 0 }}
>
<Bar dataKey="value" fill="#8b5cf6" fillOpacity={0.8} radius={[2, 2, 0, 0]} />
<Tooltip content={<CustomTooltip />} cursor={{ fill: 'transparent' }} />
</RechartsBarChart>
<defs>
<linearGradient id="colorVendorsAdmin" x1="0" y1="0" x2="0" y2="1">
<stop offset="5%" stopColor="#8b5cf6" stopOpacity={0.3} />
<stop offset="95%" stopColor="#8b5cf6" stopOpacity={0} />
</linearGradient>
</defs>
<Area
type="monotone"
dataKey="value"
stroke="#8b5cf6"
fillOpacity={1}
fill="url(#colorVendorsAdmin)"
strokeWidth={2}
activeDot={{ r: 4, strokeWidth: 0, fill: "#8b5cf6" }}
/>
<Tooltip content={<CustomTooltip />} cursor={{ stroke: 'rgba(255,255,255,0.1)', strokeWidth: 1 }} />
</AreaChart>
</ResponsiveContainer>
</div>
) : (