import { describe, expect, it } from 'vitest'; import { render, screen } from '@testing-library/react'; import { Breadcrumb, BreadcrumbItem, BreadcrumbLink, BreadcrumbList, BreadcrumbPage, BreadcrumbSeparator, } from './breadcrumb'; const Example = ({ size }: { size?: 'xs' | 'md' } = {}) => ( Home Reports Q3 ); describe('Breadcrumb', () => { it('names the landmark so it is distinguishable from other navs', () => { render(); expect(screen.getByRole('navigation', { name: 'breadcrumb' })).toBeInTheDocument(); }); it('marks the last crumb as the current page', () => { render(); const current = screen.getByText('Q3'); expect(current).toHaveAttribute('aria-current', 'page'); expect(current).toHaveAttribute('aria-disabled', 'true'); }); it('leaves the ancestors as real links', () => { render(); expect(screen.getByRole('link', { name: 'Home' })).toHaveAttribute('href', '/'); }); /* Separators are decoration; announcing "chevron right" between every crumb is noise, so they must stay out of the accessibility tree. */ it('hides the separators from assistive technology', () => { const { container } = render(); const separators = container.querySelectorAll('[data-slot="breadcrumb-separator"]'); expect(separators).toHaveLength(2); separators.forEach((separator) => expect(separator).toHaveAttribute('aria-hidden', 'true')); }); /* The crumbs read their height and padding off the list through `group-data-*`, so this attribute is the contract between them. */ it('publishes the size the crumbs style themselves from', () => { const { container, rerender } = render(); expect(container.querySelector('[data-slot="breadcrumb-list"]')).toHaveAttribute( 'data-size', 'md' ); rerender(); expect(container.querySelector('[data-slot="breadcrumb-list"]')).toHaveAttribute( 'data-size', 'xs' ); }); });