import React from 'react';
import { render, screen, fireEvent } from '@testing-library/react';
import {
Card,
CardHeader,
CardTitle,
CardDescription,
CardContent,
CardFooter,
} from '../Card';
describe('Card', () => {
it('renders children correctly', () => {
render(Card content);
expect(screen.getByText('Card content')).toBeInTheDocument();
});
it('renders with base card styling', () => {
const { container } = render(Content);
const card = container.firstChild as HTMLElement;
expect(card.className).toContain('bg-white');
expect(card.className).toContain('rounded-lg');
});
it('applies padding classes based on padding prop', () => {
const { container: container1 } = render(Content);
expect((container1.firstChild as HTMLElement).className).toContain('p-3');
const { container: container2 } = render(Content);
expect((container2.firstChild as HTMLElement).className).toContain('p-4');
const { container: container3 } = render(Content);
expect((container3.firstChild as HTMLElement).className).toContain('p-6');
});
it('applies hover class when hover prop is true', () => {
const { container } = render(Hoverable card);
const card = container.firstChild as HTMLElement;
expect(card.className).toContain('hover:shadow-md');
});
it('renders as button role when onClick is provided', () => {
const handleClick = jest.fn();
render(Clickable card);
expect(screen.getByRole('button')).toBeInTheDocument();
});
it('calls onClick when clicked', () => {
const handleClick = jest.fn();
render(Clickable card);
const card = screen.getByRole('button');
fireEvent.click(card);
expect(handleClick).toHaveBeenCalledTimes(1);
});
it('applies custom className', () => {
const { container } = render(Content);
const card = container.firstChild as HTMLElement;
expect(card.className).toContain('custom-class');
});
});
describe('CardHeader', () => {
it('renders children correctly', () => {
render(Header content);
expect(screen.getByText('Header content')).toBeInTheDocument();
});
it('applies border bottom styling', () => {
const { container } = render(Header);
const header = container.firstChild as HTMLElement;
expect(header.className).toContain('border-b');
});
});
describe('CardTitle', () => {
it('renders title correctly', () => {
render(Card Title);
expect(screen.getByText('Card Title')).toBeInTheDocument();
});
it('renders as h3 element', () => {
render(Title);
const title = screen.getByText('Title');
expect(title.tagName).toBe('H3');
});
});
describe('CardDescription', () => {
it('renders description correctly', () => {
render(Card description);
expect(screen.getByText('Card description')).toBeInTheDocument();
});
it('applies text styling', () => {
render(Description);
const description = screen.getByText('Description');
expect(description).toHaveClass('text-sm');
expect(description).toHaveClass('text-textSecondary');
});
});
describe('CardContent', () => {
it('renders content correctly', () => {
render(Content area);
expect(screen.getByText('Content area')).toBeInTheDocument();
});
});
describe('CardFooter', () => {
it('renders footer correctly', () => {
render(Footer content);
expect(screen.getByText('Footer content')).toBeInTheDocument();
});
it('applies border top styling', () => {
const { container } = render(Footer);
const footer = container.firstChild as HTMLElement;
expect(footer.className).toContain('border-t');
});
});
describe('Card composition', () => {
it('renders complete card with all components', () => {
render(
Test Card
This is a test card
Main content
Footer actions
);
expect(screen.getByText('Test Card')).toBeInTheDocument();
expect(screen.getByText('This is a test card')).toBeInTheDocument();
expect(screen.getByText('Main content')).toBeInTheDocument();
expect(screen.getByText('Footer actions')).toBeInTheDocument();
});
});