- Create BeneficiaryDetailPage with Overview, Sensors, and Activity tabs - Add StatusBadge and SensorStatusBadge UI components - Add Tabs component (Tabs, TabsList, TabsTrigger, TabsContent) - Add getBeneficiary API method - Include comprehensive tests for all new components - Update ESLint config with root:true to prevent config inheritance 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude <noreply@anthropic.com>
95 lines
3.4 KiB
TypeScript
95 lines
3.4 KiB
TypeScript
import React from 'react';
|
|
import { render, screen, fireEvent } from '@testing-library/react';
|
|
import { Tabs, TabsList, TabsTrigger, TabsContent } from '../Tabs';
|
|
|
|
describe('Tabs', () => {
|
|
const TestTabs = () => (
|
|
<Tabs defaultValue="tab1">
|
|
<TabsList>
|
|
<TabsTrigger value="tab1">Tab 1</TabsTrigger>
|
|
<TabsTrigger value="tab2">Tab 2</TabsTrigger>
|
|
<TabsTrigger value="tab3">Tab 3</TabsTrigger>
|
|
</TabsList>
|
|
<TabsContent value="tab1">Content 1</TabsContent>
|
|
<TabsContent value="tab2">Content 2</TabsContent>
|
|
<TabsContent value="tab3">Content 3</TabsContent>
|
|
</Tabs>
|
|
);
|
|
|
|
it('renders with default tab selected', () => {
|
|
render(<TestTabs />);
|
|
|
|
expect(screen.getByText('Tab 1')).toBeInTheDocument();
|
|
expect(screen.getByText('Tab 2')).toBeInTheDocument();
|
|
expect(screen.getByText('Tab 3')).toBeInTheDocument();
|
|
expect(screen.getByText('Content 1')).toBeInTheDocument();
|
|
expect(screen.queryByText('Content 2')).not.toBeInTheDocument();
|
|
expect(screen.queryByText('Content 3')).not.toBeInTheDocument();
|
|
});
|
|
|
|
it('switches tab content when clicking triggers', () => {
|
|
render(<TestTabs />);
|
|
|
|
// Click Tab 2
|
|
fireEvent.click(screen.getByText('Tab 2'));
|
|
expect(screen.queryByText('Content 1')).not.toBeInTheDocument();
|
|
expect(screen.getByText('Content 2')).toBeInTheDocument();
|
|
expect(screen.queryByText('Content 3')).not.toBeInTheDocument();
|
|
|
|
// Click Tab 3
|
|
fireEvent.click(screen.getByText('Tab 3'));
|
|
expect(screen.queryByText('Content 1')).not.toBeInTheDocument();
|
|
expect(screen.queryByText('Content 2')).not.toBeInTheDocument();
|
|
expect(screen.getByText('Content 3')).toBeInTheDocument();
|
|
|
|
// Click back to Tab 1
|
|
fireEvent.click(screen.getByText('Tab 1'));
|
|
expect(screen.getByText('Content 1')).toBeInTheDocument();
|
|
expect(screen.queryByText('Content 2')).not.toBeInTheDocument();
|
|
expect(screen.queryByText('Content 3')).not.toBeInTheDocument();
|
|
});
|
|
|
|
it('applies correct aria attributes', () => {
|
|
render(<TestTabs />);
|
|
|
|
const tab1 = screen.getByText('Tab 1');
|
|
const tab2 = screen.getByText('Tab 2');
|
|
|
|
expect(tab1).toHaveAttribute('role', 'tab');
|
|
expect(tab1).toHaveAttribute('aria-selected', 'true');
|
|
expect(tab2).toHaveAttribute('role', 'tab');
|
|
expect(tab2).toHaveAttribute('aria-selected', 'false');
|
|
|
|
fireEvent.click(tab2);
|
|
expect(tab1).toHaveAttribute('aria-selected', 'false');
|
|
expect(tab2).toHaveAttribute('aria-selected', 'true');
|
|
});
|
|
|
|
it('renders content with tabpanel role', () => {
|
|
render(<TestTabs />);
|
|
|
|
const content = screen.getByRole('tabpanel');
|
|
expect(content).toHaveTextContent('Content 1');
|
|
});
|
|
|
|
it('applies custom className to components', () => {
|
|
render(
|
|
<Tabs defaultValue="test" className="custom-tabs">
|
|
<TabsList className="custom-list">
|
|
<TabsTrigger value="test" className="custom-trigger">
|
|
Test
|
|
</TabsTrigger>
|
|
</TabsList>
|
|
<TabsContent value="test" className="custom-content">
|
|
Test Content
|
|
</TabsContent>
|
|
</Tabs>
|
|
);
|
|
|
|
expect(document.querySelector('.custom-tabs')).toBeInTheDocument();
|
|
expect(document.querySelector('.custom-list')).toBeInTheDocument();
|
|
expect(document.querySelector('.custom-trigger')).toBeInTheDocument();
|
|
expect(document.querySelector('.custom-content')).toBeInTheDocument();
|
|
});
|
|
});
|