import type { LogsHistogramResponse } from "@/lib/types/logs"; import { useMemo } from "react"; import { Area, AreaChart, Bar, BarChart, CartesianGrid, ResponsiveContainer, Tooltip, XAxis, YAxis, } from "recharts"; import { CHART_COLORS, formatFullTimestamp, formatTimestamp, } from "../../utils/chartUtils"; import { ChartErrorBoundary } from "./chartErrorBoundary"; import type { ChartType } from "./chartTypeToggle"; interface LogVolumeChartProps { data: LogsHistogramResponse | null; chartType: ChartType; startTime: number; endTime: number; } type LogVolumeDataPoint = { timestamp: string; count: number; success: number; error: number; index: number; formattedTime: string; }; interface CustomTooltipProps { active?: boolean; payload?: Array<{ payload?: LogVolumeDataPoint }>; } function CustomTooltip({ active, payload }: CustomTooltipProps) { if (!active || !payload || !payload.length) return null; const data = payload[0]?.payload; if (!data) return null; return (
{formatFullTimestamp(data.timestamp)}
Success {data.success.toLocaleString()}
Error {data.error.toLocaleString()}
); } export function LogVolumeChart({ data, chartType, startTime, endTime, }: LogVolumeChartProps) { const chartData = useMemo(() => { if (!data?.buckets || !data.bucket_size_seconds) { return []; } return data.buckets.map((bucket, index) => ({ ...bucket, index, formattedTime: formatTimestamp( bucket.timestamp, data.bucket_size_seconds, ), })); }, [data]); if (!data?.buckets || chartData.length === 0) { return (
No data available
); } const commonProps = { data: chartData, margin: { top: 6, right: 4, left: 12, bottom: 0 }, }; return ( {chartType === "bar" ? ( chartData[Math.round(idx)]?.formattedTime || "" } interval="preserveStartEnd" /> v.toLocaleString()} domain={[0, (dataMax: number) => Math.max(dataMax, 1)]} allowDataOverflow={false} /> } cursor={{ fill: "#8c8c8f", fillOpacity: 0.15 }} /> ) : ( chartData[Math.round(idx)]?.formattedTime || "" } interval="preserveStartEnd" /> v.toLocaleString()} domain={[0, (dataMax: number) => Math.max(dataMax, 1)]} allowDataOverflow={false} /> } /> )} ); }