Some checks failed
Deploy to Cloudflare Workers / deploy (push) Has been cancelled
104 lines
3.4 KiB
TypeScript
104 lines
3.4 KiB
TypeScript
import { createClient } from "@/lib/supabase/server";
|
|
import { PageHeader } from "@/components/dashboard/page-header";
|
|
import { StatCard } from "@/components/dashboard/stat-card";
|
|
import { GlassCard } from "@/components/ui/glass-card";
|
|
import { Trophy, Users, Inbox, Shield } from "lucide-react";
|
|
import Link from "next/link";
|
|
import { MasterAssignPanel } from "@/components/master/master-assign-panel";
|
|
|
|
export default async function MasterDashboardPage() {
|
|
const supabase = await createClient();
|
|
|
|
const [{ count: leagues }, { count: players }, { data: openIssues }] =
|
|
await Promise.all([
|
|
supabase.from("leagues").select("*", { count: "exact", head: true }),
|
|
supabase.from("players").select("*", { count: "exact", head: true }),
|
|
supabase
|
|
.from("support_issues")
|
|
.select("id, subject, status, created_at, leagues(name)")
|
|
.eq("status", "open")
|
|
.order("created_at", { ascending: false })
|
|
.limit(5),
|
|
]);
|
|
|
|
return (
|
|
<div className="space-y-6">
|
|
<PageHeader
|
|
title="League Master Dashboard"
|
|
description="Overview of leagues, players, and open issues"
|
|
actions={
|
|
<Link
|
|
href="/master/leagues"
|
|
className="inline-flex h-10 items-center rounded-lg bg-cyan-500 px-4 text-sm font-medium text-slate-950 hover:bg-cyan-400"
|
|
>
|
|
Manage leagues
|
|
</Link>
|
|
}
|
|
/>
|
|
|
|
<div className="grid gap-4 sm:grid-cols-2 xl:grid-cols-4">
|
|
<StatCard
|
|
title="Leagues"
|
|
value={leagues ?? 0}
|
|
subtitle="Total tournaments"
|
|
icon={Trophy}
|
|
accent="cyan"
|
|
/>
|
|
<StatCard
|
|
title="Players"
|
|
value={players ?? 0}
|
|
subtitle="Global registry"
|
|
icon={Users}
|
|
accent="green"
|
|
/>
|
|
<StatCard
|
|
title="Open issues"
|
|
value={openIssues?.length ?? 0}
|
|
subtitle="Needs attention"
|
|
icon={Inbox}
|
|
accent="amber"
|
|
/>
|
|
<StatCard
|
|
title="Portal"
|
|
value="Master"
|
|
subtitle="Full admin access"
|
|
icon={Shield}
|
|
accent="pink"
|
|
/>
|
|
</div>
|
|
|
|
<div className="grid gap-6 lg:grid-cols-2">
|
|
<MasterAssignPanel />
|
|
|
|
<GlassCard title="Recent issues">
|
|
<ul className="space-y-3">
|
|
{openIssues?.map((issue) => {
|
|
const league = issue.leagues as { name: string } | null;
|
|
return (
|
|
<li
|
|
key={issue.id}
|
|
className="rounded-lg border border-white/10 px-3 py-2 text-sm"
|
|
>
|
|
<p className="font-medium">{issue.subject}</p>
|
|
<p className="text-xs text-[var(--color-muted)]">
|
|
{league?.name} · {new Date(issue.created_at).toLocaleDateString()}
|
|
</p>
|
|
</li>
|
|
);
|
|
})}
|
|
{(!openIssues || openIssues.length === 0) && (
|
|
<p className="text-sm text-[var(--color-muted)]">No open issues</p>
|
|
)}
|
|
</ul>
|
|
<Link
|
|
href="/master/issues"
|
|
className="mt-4 inline-block text-sm text-cyan-400 hover:underline"
|
|
>
|
|
View all issues
|
|
</Link>
|
|
</GlassCard>
|
|
</div>
|
|
</div>
|
|
);
|
|
}
|