import HeadingSmall from '@/components/heading-small';
import { Card, CardContent, CardHeader, CardTitle } from '@/components/ui/card';
import AppLayout from '@/layouts/app-layout';
import { formatDate } from '@/lib/format-date';
import admin from '@/routes/admin';
import { type BreadcrumbItem } from '@/types';
import { Head, router } from '@inertiajs/react';
import {
    Area,
    AreaChart,
    Bar,
    BarChart,
    CartesianGrid,
    Cell,
    ResponsiveContainer,
    Tooltip,
    XAxis,
    YAxis,
} from 'recharts';

type Totals = {
    total: number;
    today: number;
    last_7_days: number;
    avg_duration_ms: number | null;
};

type DailyPoint = { date: string; count: number };
type ZipcodeCount = { zipcode: string; count: number };
type CommodityCount = { commodity: string; count: number };
type AccountTypeCount = { account_type: string; count: number };
type ProductCount = { product_name: string; count: number };
type FormTypeCount = { web_form_type: string; count: number };

type Props = {
    totals: Totals;
    dailySeries: DailyPoint[];
    topZipcodes: ZipcodeCount[];
    commodityBreakdown: CommodityCount[];
    accountTypeBreakdown: AccountTypeCount[];
    days: number;
    webFormTotals: Totals;
    webFormDailySeries: DailyPoint[];
    topEnrollmentProducts: ProductCount[];
    webFormTypeBreakdown: FormTypeCount[];
};

const breadcrumbs: BreadcrumbItem[] = [{ title: 'Analytics', href: admin.analytics.index().url }];

const DAY_RANGES = [7, 30, 90] as const;

const CHART_TICK_STYLE = { fill: 'var(--muted-foreground)', fontSize: 12 };

export default function Analytics({
    totals,
    dailySeries,
    topZipcodes,
    commodityBreakdown,
    accountTypeBreakdown,
    days,
    webFormTotals,
    webFormDailySeries,
    topEnrollmentProducts,
    webFormTypeBreakdown,
}: Props) {
    const chartSeries = dailySeries.map((point) => ({
        ...point,
        label: formatDate(point.date).replace(/, \d{4}$/, ''),
    }));

    const webFormChartSeries = webFormDailySeries.map((point) => ({
        ...point,
        label: formatDate(point.date).replace(/, \d{4}$/, ''),
    }));

    return (
        <AppLayout breadcrumbs={breadcrumbs}>
            <Head title="Analytics" />

            <div className="space-y-6">
                <HeadingSmall
                    title="Search analytics"
                    description="Traffic to the public product search API."
                />

                <div className="grid gap-4 sm:grid-cols-2 lg:grid-cols-4">
                    <StatTile label="Total searches" value={totals.total.toLocaleString()} />
                    <StatTile label="Today" value={totals.today.toLocaleString()} />
                    <StatTile label="Last 7 days" value={totals.last_7_days.toLocaleString()} />
                    <StatTile
                        label="Avg. response time"
                        value={
                            totals.avg_duration_ms !== null
                                ? `${Math.round(totals.avg_duration_ms)} ms`
                                : '—'
                        }
                    />
                </div>

                <Card>
                    <CardHeader className="flex flex-row items-center justify-between">
                        <CardTitle>Search hits over time</CardTitle>
                        <div className="flex gap-1">
                            {DAY_RANGES.map((range) => (
                                <button
                                    key={range}
                                    type="button"
                                    onClick={() =>
                                        router.get(
                                            admin.analytics.index().url,
                                            { days: range },
                                            { preserveState: true, preserveScroll: true, replace: true },
                                        )
                                    }
                                    className={`rounded-md px-2.5 py-1 text-xs font-medium ${
                                        days === range
                                            ? 'bg-primary text-primary-foreground'
                                            : 'text-muted-foreground hover:bg-accent'
                                    }`}
                                >
                                    {range}d
                                </button>
                            ))}
                        </div>
                    </CardHeader>
                    <CardContent>
                        <div className="h-72">
                            <ResponsiveContainer width="100%" height="100%">
                                <AreaChart data={chartSeries} margin={{ left: -20, right: 12, top: 8 }}>
                                    <defs>
                                        <linearGradient id="searchHitsFill" x1="0" y1="0" x2="0" y2="1">
                                            <stop offset="0%" stopColor="var(--chart-1)" stopOpacity={0.35} />
                                            <stop offset="100%" stopColor="var(--chart-1)" stopOpacity={0.02} />
                                        </linearGradient>
                                    </defs>
                                    <CartesianGrid vertical={false} stroke="var(--border)" />
                                    <XAxis
                                        dataKey="label"
                                        tick={CHART_TICK_STYLE}
                                        axisLine={{ stroke: 'var(--border)' }}
                                        tickLine={false}
                                        minTickGap={24}
                                    />
                                    <YAxis
                                        allowDecimals={false}
                                        tick={CHART_TICK_STYLE}
                                        axisLine={false}
                                        tickLine={false}
                                        width={32}
                                    />
                                    <Tooltip
                                        contentStyle={{
                                            background: 'var(--popover)',
                                            border: '1px solid var(--border)',
                                            borderRadius: 8,
                                            color: 'var(--popover-foreground)',
                                            fontSize: 12,
                                        }}
                                        labelStyle={{ color: 'var(--muted-foreground)' }}
                                        formatter={(value) => [String(value), 'Searches']}
                                    />
                                    <Area
                                        type="monotone"
                                        dataKey="count"
                                        name="Searches"
                                        stroke="var(--chart-1)"
                                        strokeWidth={2}
                                        fill="url(#searchHitsFill)"
                                    />
                                </AreaChart>
                            </ResponsiveContainer>
                        </div>
                    </CardContent>
                </Card>

                <div className="grid gap-4 lg:grid-cols-3">
                    <Card className="lg:col-span-2">
                        <CardHeader>
                            <CardTitle>Zip codes searched</CardTitle>
                        </CardHeader>
                        <CardContent>
                            {topZipcodes.length > 0 ? (
                                <div className="max-h-96 overflow-y-auto">
                                    <div style={{ height: Math.max(topZipcodes.length * 28, 100) }}>
                                        <ResponsiveContainer width="100%" height="100%">
                                            <BarChart
                                                data={topZipcodes}
                                                layout="vertical"
                                                margin={{ left: 8, right: 16 }}
                                            >
                                                <CartesianGrid horizontal={false} stroke="var(--border)" />
                                                <XAxis
                                                    type="number"
                                                    allowDecimals={false}
                                                    tick={CHART_TICK_STYLE}
                                                    axisLine={false}
                                                    tickLine={false}
                                                />
                                                <YAxis
                                                    type="category"
                                                    dataKey="zipcode"
                                                    tick={CHART_TICK_STYLE}
                                                    axisLine={false}
                                                    tickLine={false}
                                                    interval={0}
                                                    width={56}
                                                />
                                                <Tooltip
                                                    cursor={{ fill: 'var(--accent)' }}
                                                    contentStyle={{
                                                        background: 'var(--popover)',
                                                        border: '1px solid var(--border)',
                                                        borderRadius: 8,
                                                        color: 'var(--popover-foreground)',
                                                        fontSize: 12,
                                                    }}
                                                    formatter={(value) => [String(value), 'Searches']}
                                                />
                                                <Bar dataKey="count" name="Searches" fill="var(--chart-1)" radius={4} />
                                            </BarChart>
                                        </ResponsiveContainer>
                                    </div>
                                </div>
                            ) : (
                                <p className="text-sm text-muted-foreground">No search data yet.</p>
                            )}
                        </CardContent>
                    </Card>

                    <div className="space-y-4">
                        <BreakdownCard
                            title="By commodity"
                            data={commodityBreakdown}
                            labelKey="commodity"
                        />
                        <BreakdownCard
                            title="By account type"
                            data={accountTypeBreakdown}
                            labelKey="account_type"
                        />
                    </div>
                </div>

                <HeadingSmall
                    title="Enrollment starts"
                    description="Traffic to the public web form API, hit when a customer selects a product and begins enrollment."
                />

                <div className="grid gap-4 sm:grid-cols-2 lg:grid-cols-4">
                    <StatTile label="Total starts" value={webFormTotals.total.toLocaleString()} />
                    <StatTile label="Today" value={webFormTotals.today.toLocaleString()} />
                    <StatTile label="Last 7 days" value={webFormTotals.last_7_days.toLocaleString()} />
                    <StatTile
                        label="Avg. response time"
                        value={
                            webFormTotals.avg_duration_ms !== null
                                ? `${Math.round(webFormTotals.avg_duration_ms)} ms`
                                : '—'
                        }
                    />
                </div>

                <Card>
                    <CardHeader>
                        <CardTitle>Enrollment starts over time</CardTitle>
                    </CardHeader>
                    <CardContent>
                        <div className="h-72">
                            <ResponsiveContainer width="100%" height="100%">
                                <AreaChart data={webFormChartSeries} margin={{ left: -20, right: 12, top: 8 }}>
                                    <defs>
                                        <linearGradient id="webFormHitsFill" x1="0" y1="0" x2="0" y2="1">
                                            <stop offset="0%" stopColor="var(--chart-2)" stopOpacity={0.35} />
                                            <stop offset="100%" stopColor="var(--chart-2)" stopOpacity={0.02} />
                                        </linearGradient>
                                    </defs>
                                    <CartesianGrid vertical={false} stroke="var(--border)" />
                                    <XAxis
                                        dataKey="label"
                                        tick={CHART_TICK_STYLE}
                                        axisLine={{ stroke: 'var(--border)' }}
                                        tickLine={false}
                                        minTickGap={24}
                                    />
                                    <YAxis
                                        allowDecimals={false}
                                        tick={CHART_TICK_STYLE}
                                        axisLine={false}
                                        tickLine={false}
                                        width={32}
                                    />
                                    <Tooltip
                                        contentStyle={{
                                            background: 'var(--popover)',
                                            border: '1px solid var(--border)',
                                            borderRadius: 8,
                                            color: 'var(--popover-foreground)',
                                            fontSize: 12,
                                        }}
                                        labelStyle={{ color: 'var(--muted-foreground)' }}
                                        formatter={(value) => [String(value), 'Enrollment starts']}
                                    />
                                    <Area
                                        type="monotone"
                                        dataKey="count"
                                        name="Enrollment starts"
                                        stroke="var(--chart-2)"
                                        strokeWidth={2}
                                        fill="url(#webFormHitsFill)"
                                    />
                                </AreaChart>
                            </ResponsiveContainer>
                        </div>
                    </CardContent>
                </Card>

                <div className="grid gap-4 lg:grid-cols-3">
                    <Card className="lg:col-span-2">
                        <CardHeader>
                            <CardTitle>Top products started</CardTitle>
                        </CardHeader>
                        <CardContent>
                            {topEnrollmentProducts.length > 0 ? (
                                <div className="h-64">
                                    <ResponsiveContainer width="100%" height="100%">
                                        <BarChart
                                            data={topEnrollmentProducts}
                                            layout="vertical"
                                            margin={{ left: 8, right: 16 }}
                                        >
                                            <CartesianGrid horizontal={false} stroke="var(--border)" />
                                            <XAxis
                                                type="number"
                                                allowDecimals={false}
                                                tick={CHART_TICK_STYLE}
                                                axisLine={false}
                                                tickLine={false}
                                            />
                                            <YAxis
                                                type="category"
                                                dataKey="product_name"
                                                tick={CHART_TICK_STYLE}
                                                axisLine={false}
                                                tickLine={false}
                                                width={140}
                                            />
                                            <Tooltip
                                                cursor={{ fill: 'var(--accent)' }}
                                                contentStyle={{
                                                    background: 'var(--popover)',
                                                    border: '1px solid var(--border)',
                                                    borderRadius: 8,
                                                    color: 'var(--popover-foreground)',
                                                    fontSize: 12,
                                                }}
                                                formatter={(value) => [String(value), 'Enrollment starts']}
                                            />
                                            <Bar dataKey="count" name="Enrollment starts" fill="var(--chart-2)" radius={4} />
                                        </BarChart>
                                    </ResponsiveContainer>
                                </div>
                            ) : (
                                <p className="text-sm text-muted-foreground">No enrollment data yet.</p>
                            )}
                        </CardContent>
                    </Card>

                    <BreakdownCard
                        title="By form type"
                        data={webFormTypeBreakdown}
                        labelKey="web_form_type"
                    />
                </div>
            </div>
        </AppLayout>
    );
}

function StatTile({ label, value }: { label: string; value: string }) {
    return (
        <Card>
            <CardHeader>
                <CardTitle className="text-sm font-medium text-muted-foreground">{label}</CardTitle>
            </CardHeader>
            <CardContent>
                <p className="text-2xl font-semibold">{value}</p>
            </CardContent>
        </Card>
    );
}

const BREAKDOWN_COLORS = ['var(--chart-1)', 'var(--chart-2)', 'var(--chart-3)', 'var(--chart-4)'];

function BreakdownCard<K extends string>({
    title,
    data,
    labelKey,
}: {
    title: string;
    data: Array<Record<K, string> & { count: number }>;
    labelKey: K;
}) {
    return (
        <Card>
            <CardHeader>
                <CardTitle>{title}</CardTitle>
            </CardHeader>
            <CardContent>
                {data.length > 0 ? (
                    <div className="h-40">
                        <ResponsiveContainer width="100%" height="100%">
                            <BarChart data={data} margin={{ left: -20 }}>
                                <XAxis
                                    dataKey={labelKey}
                                    tick={CHART_TICK_STYLE}
                                    axisLine={{ stroke: 'var(--border)' }}
                                    tickLine={false}
                                />
                                <YAxis
                                    allowDecimals={false}
                                    tick={CHART_TICK_STYLE}
                                    axisLine={false}
                                    tickLine={false}
                                    width={32}
                                />
                                <Tooltip
                                    cursor={{ fill: 'var(--accent)' }}
                                    contentStyle={{
                                        background: 'var(--popover)',
                                        border: '1px solid var(--border)',
                                        borderRadius: 8,
                                        color: 'var(--popover-foreground)',
                                        fontSize: 12,
                                    }}
                                    formatter={(value) => [String(value), 'Searches']}
                                />
                                <Bar dataKey="count" name="Searches" radius={4}>
                                    {data.map((entry, index) => (
                                        <Cell
                                            key={String(entry[labelKey])}
                                            fill={BREAKDOWN_COLORS[index % BREAKDOWN_COLORS.length]}
                                        />
                                    ))}
                                </Bar>
                            </BarChart>
                        </ResponsiveContainer>
                    </div>
                ) : (
                    <p className="text-sm text-muted-foreground">No data yet.</p>
                )}
            </CardContent>
        </Card>
    );
}
