import React, { useEffect, useState } from 'react';
import axios from 'axios';
import { PageHeader, StatCard, Button, Badge, Avatar, PeriodPicker, Period } from './shared/ui';
import { CashflowChart, Donut, BarList } from './shared/charts';
import { pendingAction } from './shared/pendingAction';

const fmtHKD = (n: number) => 'HK$' + Math.round(n).toLocaleString('en-HK');
const fmtPct = (n: number | null | undefined, suffix = '%') =>
    n == null ? '—' : `${n >= 0 ? '+' : ''}${n.toFixed(1)}${suffix}`;
const fmtSigned = (n: number | null | undefined) =>
    n == null ? '—' : `${n >= 0 ? '+' : ''}${n}`;

type Summary = {
    year: number;
    available_years: number[];
    kpis: {
        cash_balance: number; outstanding: number;
        profit: number; operation_expense: number;
        salary: number; mpf: number;
        collection_rate: number;
        sales_income: number;
        bank_income: number; bank_expense: number;
        other_income: number; other_expense: number;
    };
    stats: {
        revenue: number; revenue_delta_pct: number | null;
        expense: number; expense_delta_pct: number | null;
        profit_margin: number; profit_margin_delta: number;
        active_clients: number; active_clients_delta: number;
    };
    cashflow: { m: string; income: number; expense: number }[];
    expense_mix: { name: string; value: number }[];
    recent_invoices: { id: string; client: string; amount: number; status: string; date: string }[];
    recent_receipts: { id: string; client: string; invoice_no: string; amount: number; date: string }[];
    top_clients: { name: string; value: number }[];
    ledger: { name: string; in: number; out: number; balance: number }[];
    series: Record<string, number[]>;
};

const statusKind: Record<string, 'good' | 'info' | 'bad' | 'neutral'> = {
    paid: 'good', sent: 'info', overdue: 'bad', draft: 'neutral',
};

const currentYear = new Date().getFullYear();
const currentMonth = new Date().getMonth() + 1;

type DashboardProps = { onNavigate?: (page: string) => void };

const HIDDEN = '••••••';

const Dashboard = ({ onNavigate }: DashboardProps = {}) => {
    const [period, setPeriod] = useState<Period>({ year: currentYear, month: currentMonth });
    const [recentTab, setRecentTab] = useState<'invoices' | 'receipts'>('invoices');
    const [revealed, setRevealed] = useState<boolean>(
        () => sessionStorage.getItem('dash_revealed') === '1'
    );
    useEffect(() => {
        sessionStorage.setItem('dash_revealed', revealed ? '1' : '0');
    }, [revealed]);
    const mask = (s: string) => (revealed ? s : HIDDEN);
    const maskSpark = (arr: number[] | undefined) => (revealed ? arr : undefined);
    const year = period.year === 'all' ? currentYear : period.year;

    const handleNewInvoice = () => {
        if (!onNavigate) return;
        pendingAction.current = 'invoice-add';
        onNavigate('IncomeInvoice');
    };
    const [data, setData] = useState<Summary | null>(null);
    const [error, setError] = useState<string | null>(null);

    useEffect(() => {
        setError(null);
        (async () => {
            try {
                const params: Record<string, any> = { year };
                if (period.month !== 'all') params.month = period.month;
                const r = await axios.get<Summary>('/dashboard/summary', { params });
                setData(r.data);
            } catch (e: any) {
                setError(e.response?.data?.message || 'Failed to load dashboard data');
            }
        })();
    }, [year, period.month]);

    if (error) return <div className="card card--pad" style={{ color: 'var(--bad)' }}>{error}</div>;
    if (!data) return <div className="card card--pad" style={{ color: 'var(--mute)' }}>Loading…</div>;

    const { kpis, stats, cashflow, expense_mix, recent_invoices, recent_receipts, top_clients, series, available_years } = data;
    const expenseTotal = expense_mix.reduce((s, d) => s + d.value, 0);
    const monthLabels = ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'];
    const isMonthScope = period.month !== 'all';
    const periodLabel = isMonthScope
        ? `${monthLabels[(period.month as number) - 1]} ${year}`
        : (year === currentYear ? 'YTD' : 'FY ' + year);
    const periodSubtitle = isMonthScope
        ? `${monthLabels[(period.month as number) - 1]} ${year}`
        : String(year);

    return (
        <>
            <PageHeader
                title="Overview"
                subtitle="A snapshot of your studio's financial health."
                actions={
                    <>
                        <Button
                            variant="default"
                            icon={revealed ? 'eyeOff' : 'eye'}
                            onClick={() => setRevealed(r => !r)}
                        >
                            {revealed ? 'Hide' : 'Show'}
                        </Button>
                        <PeriodPicker
                            period={period}
                            years={available_years.length ? available_years : [currentYear]}
                            onChange={p => setPeriod(p.year === 'all' ? { year: currentYear, month: 'all' } : p)}
                        />
                        <Button variant="primary" icon="plus" onClick={handleNewInvoice}>New invoice</Button>
                    </>
                }
            />

            {/* Liquidity */}
            <div className="stats3">
                <StatCard
                    label="Cash balance"
                    value={mask(fmtHKD(kpis.cash_balance))}
                    icon="wallet"
                    spark={maskSpark(series.cash_balance)}
                />
                <StatCard
                    label="Outstanding"
                    value={mask(fmtHKD(kpis.outstanding))}
                    icon="clock"
                    accent="var(--flame-d)"
                    spark={maskSpark(series.outstanding)}
                />
                <StatCard
                    label="Collection rate"
                    value={mask(`${kpis.collection_rate.toFixed(1)}%`)}
                    icon="check"
                    spark={maskSpark(series.collection_rate)}
                />
            </div>

            {/* Profitability & clients */}
            <div className="stats3">
                <StatCard
                    label="Profit"
                    value={mask(fmtHKD(kpis.profit))}
                    icon="trend"
                    accent={kpis.profit >= 0 ? 'var(--green-d)' : 'var(--bad)'}
                    spark={maskSpark(series.profit)}
                />
                <StatCard
                    label="Profit margin"
                    value={mask(`${stats.profit_margin.toFixed(1)}%`)}
                    delta={revealed ? fmtPct(stats.profit_margin_delta, 'pt') : undefined}
                    deltaDir={stats.profit_margin_delta >= 0 ? 'up' : 'down'}
                    icon="balance"
                    spark={maskSpark(series.profit_margin)}
                />
                <StatCard
                    label="Active clients"
                    value={mask(String(stats.active_clients))}
                    delta={revealed ? fmtSigned(stats.active_clients_delta) : undefined}
                    deltaDir={stats.active_clients_delta >= 0 ? 'up' : 'down'}
                    icon="contact"
                    spark={maskSpark(series.active_clients)}
                />
            </div>

            {/* Revenue group: total + components */}
            <div className="stats-flex">
                <StatCard
                    label={`Revenue (${periodLabel})`}
                    value={mask(fmtHKD(stats.revenue))}
                    delta={revealed ? fmtPct(stats.revenue_delta_pct) : undefined}
                    deltaDir={(stats.revenue_delta_pct ?? 0) >= 0 ? 'up' : 'down'}
                    icon="income"
                    spark={maskSpark(series.revenue)}
                />
                <StatCard
                    label="Sales Income"
                    value={mask(fmtHKD(kpis.sales_income))}
                    icon="receipt"
                    spark={maskSpark(series.sales_income)}
                />
                <StatCard
                    label="Bank Income"
                    value={mask(fmtHKD(kpis.bank_income))}
                    icon="income"
                    spark={maskSpark(series.bank_income)}
                />
                <StatCard
                    label="Other Income"
                    value={mask(fmtHKD(kpis.other_income))}
                    icon="income"
                    spark={maskSpark(series.other_income)}
                />
            </div>

            {/* Expense group: total + components */}
            <div className="stats-flex">
                <StatCard
                    label={`Expenses (${periodLabel})`}
                    value={mask(fmtHKD(stats.expense))}
                    delta={revealed ? fmtPct(stats.expense_delta_pct) : undefined}
                    deltaDir={(stats.expense_delta_pct ?? 0) >= 0 ? 'up' : 'down'}
                    icon="expense"
                    spark={maskSpark(series.expense)}
                />
                <StatCard
                    label="Operation Expense"
                    value={mask(fmtHKD(kpis.operation_expense))}
                    icon="wallet"
                    spark={maskSpark(series.operation_expense)}
                />
                <StatCard
                    label="Salary"
                    value={mask(fmtHKD(kpis.salary))}
                    icon="salary"
                    spark={maskSpark(series.salary)}
                />
                <StatCard
                    label="MPF"
                    value={mask(fmtHKD(kpis.mpf))}
                    icon="shareholder"
                    spark={maskSpark(series.mpf)}
                />
                <StatCard
                    label="Bank Expense"
                    value={mask(fmtHKD(kpis.bank_expense))}
                    icon="expense"
                    spark={maskSpark(series.bank_expense)}
                />
                <StatCard
                    label="Other Expense"
                    value={mask(fmtHKD(kpis.other_expense))}
                    icon="expense"
                    spark={maskSpark(series.other_expense)}
                />
            </div>

            <div className="grid2">
                <div className="card card--pad">
                    <div className="card__head">
                        <div>
                            <h3 className="card__title">Cashflow</h3>
                            <p className="card__sub">Income vs expense, {periodSubtitle}</p>
                        </div>
                        <div className="legend-inline">
                            <span><span className="dot dot--green" /> Income</span>
                            <span><span className="dot dot--flame" /> Expense</span>
                        </div>
                    </div>
                    <div className={revealed ? '' : 'dash-blur'}>
                        <CashflowChart data={cashflow} />
                    </div>
                </div>

                <div className="card card--pad">
                    <div className="card__head">
                        <div>
                            <h3 className="card__title">Operation Expense mix</h3>
                            <p className="card__sub">Top suppliers, {periodSubtitle}</p>
                        </div>
                    </div>
                    {expense_mix.length === 0
                        ? <div style={{ color: 'var(--mute)', padding: '20px 0' }}>No operation expenses recorded in {periodSubtitle}.</div>
                        : <div className={revealed ? '' : 'dash-blur'}>
                            <Donut data={expense_mix} centerLabel="Op. Expense" centerValue={revealed ? fmtHKD(expenseTotal) : HIDDEN} />
                          </div>
                    }
                </div>
            </div>

            <div className="grid2b">
                <div className="card card--pad">
                    <div className="card__head">
                        <div className="card-tabs">
                            <button
                                className={`card-tab ${recentTab === 'invoices' ? 'is-active' : ''}`}
                                onClick={() => setRecentTab('invoices')}>
                                Recent invoices
                            </button>
                            <button
                                className={`card-tab ${recentTab === 'receipts' ? 'is-active' : ''}`}
                                onClick={() => setRecentTab('receipts')}>
                                Recent receipts
                            </button>
                        </div>
                    </div>

                    {recentTab === 'invoices' ? (
                        recent_invoices.length === 0 ? (
                            <div style={{ color: 'var(--mute)', padding: '20px 0' }}>No invoices in {periodSubtitle}.</div>
                        ) : (
                            <table className="table table--compact">
                                <thead>
                                    <tr>
                                        <th style={{ textAlign: 'left' }}>Invoice</th>
                                        <th style={{ textAlign: 'left' }}>Client</th>
                                        <th style={{ textAlign: 'right' }}>Amount</th>
                                        <th style={{ textAlign: 'left' }}>Status</th>
                                        <th style={{ textAlign: 'right' }}>Date</th>
                                    </tr>
                                </thead>
                                <tbody>
                                    {recent_invoices.map(r => (
                                        <tr key={r.id}>
                                            <td className="mono">{r.id}</td>
                                            <td>
                                                <span style={{ display: 'inline-flex', alignItems: 'center', gap: 8 }}>
                                                    <Avatar name={r.client} size={24} />{r.client}
                                                </span>
                                            </td>
                                            <td className="mono" style={{ textAlign: 'right' }}>{mask(fmtHKD(r.amount))}</td>
                                            <td><Badge kind={statusKind[r.status] || 'neutral'}>{r.status}</Badge></td>
                                            <td style={{ textAlign: 'right', color: 'var(--mute)' }}>{r.date}</td>
                                        </tr>
                                    ))}
                                </tbody>
                            </table>
                        )
                    ) : (
                        recent_receipts.length === 0 ? (
                            <div style={{ color: 'var(--mute)', padding: '20px 0' }}>No receipts in {periodSubtitle}.</div>
                        ) : (
                            <table className="table table--compact">
                                <thead>
                                    <tr>
                                        <th style={{ textAlign: 'left' }}>Receipt</th>
                                        <th style={{ textAlign: 'left' }}>Client</th>
                                        <th style={{ textAlign: 'left' }}>Invoice</th>
                                        <th style={{ textAlign: 'right' }}>Amount</th>
                                        <th style={{ textAlign: 'right' }}>Date</th>
                                    </tr>
                                </thead>
                                <tbody>
                                    {recent_receipts.map(r => (
                                        <tr key={r.id}>
                                            <td className="mono">{r.id}</td>
                                            <td>
                                                <span style={{ display: 'inline-flex', alignItems: 'center', gap: 8 }}>
                                                    <Avatar name={r.client} size={24} />{r.client}
                                                </span>
                                            </td>
                                            <td className="mono" style={{ color: 'var(--mute)' }}>{r.invoice_no}</td>
                                            <td className="mono" style={{ textAlign: 'right' }}>{mask(fmtHKD(r.amount))}</td>
                                            <td style={{ textAlign: 'right', color: 'var(--mute)' }}>{r.date}</td>
                                        </tr>
                                    ))}
                                </tbody>
                            </table>
                        )
                    )}
                </div>

                <div className="card card--pad">
                    <div className="card__head">
                        <div>
                            <h3 className="card__title">Top clients</h3>
                            <p className="card__sub">By revenue in {periodSubtitle}</p>
                        </div>
                    </div>
                    {top_clients.length === 0
                        ? <div style={{ color: 'var(--mute)', padding: '20px 0' }}>No invoices in {periodSubtitle}.</div>
                        : <BarList data={top_clients} format={(v: number) => revealed ? fmtHKD(v) : HIDDEN} />
                    }
                </div>
            </div>
        </>
    );
};

export default Dashboard;
