import { render, screen } from '@testing-library/react'; import { describe, it, expect, vi, beforeEach } from 'vitest'; import DailySummary from '../../../../src/components/stats/DailySummary'; import { useStats } from '../../../../src/hooks/useStats'; import { XAxis, Tooltip } from 'recharts'; import { formatMinutes } from '../../../../src/utils/time'; vi.mock('../../../../src/hooks/useStats', () => ({ useStats: vi.fn(), })); vi.mock('recharts', async () => { const actual = await vi.importActual('recharts'); return { ...actual, ResponsiveContainer: ({ children }: any) =>
{children}
, BarChart: ({ children }: any) =>
{children}
, XAxis: vi.fn(({ tickFormatter }) =>
), YAxis: vi.fn(() =>
), CartesianGrid: vi.fn(), Tooltip: vi.fn(({ formatter }) =>
), Bar: vi.fn(), }; }); describe('DailySummary', () => { const props = { from_date: '2024-01-01', to_date: '2024-01-02', day_start: '07:00', day_end: '20:00', }; beforeEach(() => { vi.clearAllMocks(); }); it('renders loading state', () => { vi.mocked(useStats).mockReturnValue({ dailySummary: undefined, isLoading: true, } as any); render(); expect(screen.getByText(/Loading summary.../i)).toBeInTheDocument(); }); it('renders empty state when dailySummary.days is undefined', () => { vi.mocked(useStats).mockReturnValue({ dailySummary: undefined, isLoading: false, } as any); render(); expect(screen.getByText(/No data available for this period./i)).toBeInTheDocument(); }); it('renders empty state when dailySummary.days is an empty array', () => { vi.mocked(useStats).mockReturnValue({ dailySummary: { days: [] }, isLoading: false, } as any); render(); expect(screen.getByText(/No data available for this period./i)).toBeInTheDocument(); }); it('renders chart and average stats correctly with multiple days', () => { vi.mocked(useStats).mockReturnValue({ dailySummary: { days: [ { date: '2024-01-01', total_minutes: 480, day_minutes: 240, night_minutes: 240 }, { date: '2024-01-02', total_minutes: 540, day_minutes: 300, night_minutes: 240 }, ], }, isLoading: false, } as any); render(); expect(screen.getByText(/Daily Summary/i)).toBeInTheDocument(); // Totals: (480 + 540) / 2 = 510 mins -> 8h 30m // Day: (240 + 300) / 2 = 270 mins -> 4h 30m // Night: (240 + 240) / 2 = 240 mins -> 4h 0m expect(screen.getByText(/8h 30m/i)).toBeInTheDocument(); expect(screen.getByText(/4h 30m/i)).toBeInTheDocument(); expect(screen.getByText(/4h 0m/i)).toBeInTheDocument(); }); it('handles single day data correctly', () => { vi.mocked(useStats).mockReturnValue({ dailySummary: { days: [ { date: '2024-01-01', total_minutes: 600, day_minutes: 300, night_minutes: 300 }, ], }, isLoading: false, } as any); render(); expect(screen.getByText(/10h 0m/i)).toBeInTheDocument(); const avgTimes = screen.getAllByText(/5h 0m/i); expect(avgTimes).toHaveLength(2); }); it('uses correct formatters for XAxis and Tooltip', () => { vi.mocked(useStats).mockReturnValue({ dailySummary: { days: [ { date: '2024-01-01', total_minutes: 480, day_minutes: 240, night_minutes: 240 }, ], }, isLoading: false, } as any); render(); // Check XAxis tickFormatter const xAxisCall = vi.mocked(XAxis).mock.calls[0][0]; expect(xAxisCall.tickFormatter).toBeDefined(); expect(xAxisCall.tickFormatter(10)).toBe('10h'); expect(xAxisCall.tickFormatter(5.5)).toBe('6h'); // Check Tooltip formatter const tooltipCall = vi.mocked(Tooltip).mock.calls[0][0]; expect(tooltipCall.formatter).toBeDefined(); // Test Tooltip formatter with a single number (e.g., daySleep) const [val1, name1] = tooltipCall.formatter(8, 'daySleep'); expect(val1).toBe('8h 0m'); expect(name1).toBe('Day'); const [val2, name2] = tooltipCall.formatter(7, 'nightSleep'); expect(val2).toBe('7h 0m'); expect(name2).toBe('Night'); // Test Tooltip formatter with an array const [val3, name3] = tooltipCall.formatter([10], 'daySleep'); expect(val3).toBe('10h 0m'); expect(name3).toBe('Day'); // Test Tooltip formatter with undefined/null const [val4, name4] = tooltipCall.formatter(undefined, 'daySleep'); expect(val4).toBe('0m'); expect(name4).toBe('Day'); }); });