Files
gemini-nexus/src/tests/unit/components/usage/StatCard.test.tsx
T
Gemini Nexus Bot 6e568dd866 fix: resolve type-check and unit test failures for CI
- vite.renderer.config: remove deprecated babel option from @vitejs/plugin-react v6
- server/main.ts: cast fastify instance to fix version mismatch TS error
- proxy-tool-streaming.test: pass 3 args to ProxyService constructor (added TokenUsageService mock)
- input.test: update expected classes (rounded-lg, bg-muted/50)
- StatCard.test: update selectors and accent classes to match component (rounded-lg, /8 opacity, bg-white/[0.04])
- paths.test: relax executable path assertion for CI environments
- cloud-repo.test: add fs mock to prevent EACCES on /mock/db
- cloudHandler-sync.test: add traffic-logger mock to prevent EACCES on /mock/
2026-04-29 02:56:03 -03:00

127 lines
4.3 KiB
TypeScript

import { screen } from '@testing-library/react';
import { renderWithProviders } from '@/tests/unit/test-utils';
import { StatCard } from '@/components/usage/StatCard';
import { Activity, TrendingUp, Users, Zap } from 'lucide-react';
import { vi, beforeAll, afterAll } from 'vitest';
describe('StatCard', () => {
beforeAll(() => {
vi.spyOn(Number.prototype, 'toLocaleString').mockImplementation(function (this: number) {
return this.toString().replace(/\B(?=(\d{3})+(?!\d))/g, ',');
});
});
afterAll(() => {
vi.restoreAllMocks();
});
it('renders label and value', () => {
renderWithProviders(
<StatCard label="Total Tokens" value={12345} icon={Activity} />,
);
expect(screen.getByText('Total Tokens')).toBeInTheDocument();
expect(screen.getByText('12,345')).toBeInTheDocument();
});
it('renders string values correctly', () => {
renderWithProviders(
<StatCard label="Status" value="Active" icon={Zap} />,
);
expect(screen.getByText('Active')).toBeInTheDocument();
});
it('formats number values with locale string', () => {
renderWithProviders(
<StatCard label="Requests" value={1000000} icon={TrendingUp} />,
);
expect(screen.getByText('1,000,000')).toBeInTheDocument();
});
it('shows skeleton when isLoading is true', () => {
renderWithProviders(
<StatCard label="Loading" value={0} icon={Users} isLoading />,
);
expect(screen.queryByText('0')).not.toBeInTheDocument();
expect(document.querySelector('.animate-pulse')).toBeInTheDocument();
});
it('does not show skeleton when isLoading is false', () => {
renderWithProviders(
<StatCard label="Loaded" value={42} icon={Activity} isLoading={false} />,
);
expect(screen.getByText('42')).toBeInTheDocument();
expect(document.querySelector('.animate-pulse')).not.toBeInTheDocument();
});
it('renders icon element', () => {
renderWithProviders(
<StatCard label="With Icon" value={100} icon={Zap} />,
);
expect(document.querySelector('svg')).toBeInTheDocument();
});
it('applies custom className', () => {
renderWithProviders(
<StatCard label="Styled" value={1} icon={Activity} className="my-stat" />,
);
// The wrapper div uses rounded-xl, find it by that selector
const wrapper = screen.getByText('Styled').closest('.rounded-xl');
expect(wrapper).toHaveClass('my-stat');
});
it('applies default slate accent when accent prop is not provided', () => {
const { container } = renderWithProviders(
<StatCard label="Default Accent" value={1} icon={Activity} />,
);
const iconContainer = container.querySelector('.rounded-lg');
expect(iconContainer).toHaveClass('bg-white/[0.04]');
});
it('applies blue accent', () => {
const { container } = renderWithProviders(
<StatCard label="Blue" value={1} icon={Activity} accent="blue" />,
);
const iconContainer = container.querySelector('.rounded-lg');
expect(iconContainer).toHaveClass('bg-blue-500/8');
});
it('applies green accent', () => {
const { container } = renderWithProviders(
<StatCard label="Green" value={1} icon={Activity} accent="green" />,
);
const iconContainer = container.querySelector('.rounded-lg');
expect(iconContainer).toHaveClass('bg-emerald-500/8');
});
it('applies amber accent', () => {
const { container } = renderWithProviders(
<StatCard label="Amber" value={1} icon={Activity} accent="amber" />,
);
const iconContainer = container.querySelector('.rounded-lg');
expect(iconContainer).toHaveClass('bg-amber-500/8');
});
it('applies purple accent', () => {
const { container } = renderWithProviders(
<StatCard label="Purple" value={1} icon={Activity} accent="purple" />,
);
const iconContainer = container.querySelector('.rounded-lg');
expect(iconContainer).toHaveClass('bg-violet-500/8');
});
it('has uppercase label styling', () => {
renderWithProviders(
<StatCard label="Uppercase Test" value={1} icon={Activity} />,
);
const label = screen.getByText('Uppercase Test');
expect(label).toHaveClass('uppercase');
});
it('has mono font for value', () => {
renderWithProviders(
<StatCard label="Mono" value={999} icon={Activity} />,
);
const value = screen.getByText('999');
expect(value).toHaveClass('font-mono');
});
});