import { useState, useEffect } from "react" import { BarChart, Bar, XAxis, YAxis, Tooltip, ResponsiveContainer, PieChart, Pie, Cell, LineChart, Line, } from "recharts" import { financeApi } from "../../api/finance" const COLORS = [ "#0D4F4F", "#F7B538", "#6366f1", "#22c55e", "#ef4444", "#8b5cf6", "#0ea5e9", "#f97316", "#ec4899", "#14b8a6", "#64748b", "#a855f7", "#78716c", ] const fmt = (n) => Number(n).toLocaleString("ru-RU") + " ₽" const MONTH_NAMES = [ "", "Янв", "Фев", "Мар", "Апр", "Май", "Июн", "Июл", "Авг", "Сен", "Окт", "Ноя", "Дек", ] export default function FinanceAnalytics({ month, year }) { const [analytics, setAnalytics] = useState(null) const [summary, setSummary] = useState(null) const [loading, setLoading] = useState(true) useEffect(() => { setLoading(true) Promise.all([ financeApi.getAnalytics({ months: 6 }), financeApi.getSummary({ month, year }), ]) .then(([a, s]) => { setAnalytics(a) setSummary(s) }) .catch(console.error) .finally(() => setLoading(false)) }, [month, year]) if (loading) { return (
{[1, 2, 3].map((i) => (
))}
) } if (!analytics || !summary) return null const expenseCategories = (summary.by_category || []).filter( (c) => c.type === "expense" ) const barData = expenseCategories.map((c) => ({ name: c.category_emoji + " " + c.category_name, value: c.amount, })) const pieData = barData const monthlyData = (analytics.monthly_trend || []).map((m) => ({ month: MONTH_NAMES[parseInt(m.month.slice(5))] || m.month, income: m.income, expense: m.expense, })) const comp = analytics.comparison_prev_month const diffPct = Math.abs(Math.round(comp.diff_percent)) const isUp = comp.diff_percent > 0 return (

Всего расходов

{fmt(summary.total_expense)}

{isUp ? "↑" : "↓"} {diffPct}% vs пред. месяц

В среднем / день

{fmt(Math.round(analytics.avg_daily_expense))}

{barData.length > 0 && (

Расходы по категориям

v / 1000 + "к"} /> fmt(v)} /> {barData.map((_, i) => ( ))}
)} {pieData.length > 0 && (

Доля категорий

{pieData.map((_, i) => ( ))} fmt(v)} />
{pieData.map((c, i) => (
{c.name} {Math.round( (c.value / summary.total_expense) * 100 )} %
))}
)} {monthlyData.length > 0 && (

Тренд по месяцам

v / 1000 + "к"} /> fmt(v)} />
Доходы
Расходы
)}
) }