import { describe, it, expect } from 'vitest'; import { render, screen } from '@testing-library/svelte'; import { userEvent } from '@testing-library/user-event'; import Page from './+page.svelte'; const mockData = { recipes: [ { id: 'r1', name: 'Spaghetti Bolognese', cookTimeMin: 30, effort: 'Easy' }, { id: 'r2', name: 'Chicken Curry', cookTimeMin: 45, effort: 'Medium' }, { id: 'r3', name: 'Gemüsesuppe', cookTimeMin: 20, effort: 'Easy' } ] }; describe('recipe library page', () => { it('renders all recipe cards initially', () => { render(Page, { props: { data: mockData } }); expect(screen.getByText('Spaghetti Bolognese')).toBeInTheDocument(); expect(screen.getByText('Chicken Curry')).toBeInTheDocument(); expect(screen.getByText('Gemüsesuppe')).toBeInTheDocument(); }); it('renders the page title', () => { render(Page, { props: { data: mockData } }); expect(document.title).toBe('Rezepte — Mealplan'); }); it('renders a link to add a new recipe', () => { render(Page, { props: { data: mockData } }); const addLink = screen.getByRole('link', { name: /rezept hinzufügen/i }); expect(addLink).toHaveAttribute('href', '/recipes/new'); }); it('filters recipes by search term', async () => { const user = userEvent.setup(); render(Page, { props: { data: mockData } }); const searchInput = screen.getByPlaceholderText(/suchen/i); await user.type(searchInput, 'Curry'); expect(screen.getByText('Chicken Curry')).toBeInTheDocument(); expect(screen.queryByText('Spaghetti Bolognese')).not.toBeInTheDocument(); }); it('filters recipes by effort chip', async () => { const user = userEvent.setup(); render(Page, { props: { data: mockData } }); await user.click(screen.getByRole('button', { name: 'Mittel' })); expect(screen.getByText('Chicken Curry')).toBeInTheDocument(); expect(screen.queryByText('Spaghetti Bolognese')).not.toBeInTheDocument(); }); it('shows empty state when no recipes match search', async () => { const user = userEvent.setup(); render(Page, { props: { data: mockData } }); const searchInput = screen.getByPlaceholderText(/suchen/i); await user.type(searchInput, 'xyznotexist'); expect(screen.getByText(/keine rezepte/i)).toBeInTheDocument(); }); it('renders filter chips', () => { render(Page, { props: { data: mockData } }); expect(screen.getByRole('button', { name: 'Alle' })).toBeInTheDocument(); expect(screen.getByRole('button', { name: 'Leicht' })).toBeInTheDocument(); }); it('renders empty state page when no recipes at all', () => { render(Page, { props: { data: { recipes: [] } } }); expect(screen.getByText(/keine rezepte/i)).toBeInTheDocument(); }); it('applies search and effort filter together', async () => { const user = userEvent.setup(); render(Page, { props: { data: mockData } }); await user.click(screen.getByRole('button', { name: 'Leicht' })); const searchInput = screen.getByPlaceholderText(/suchen/i); await user.type(searchInput, 'Gemüse'); expect(screen.getByText('Gemüsesuppe')).toBeInTheDocument(); expect(screen.queryByText('Spaghetti Bolognese')).not.toBeInTheDocument(); expect(screen.queryByText('Chicken Curry')).not.toBeInTheDocument(); }); it('resets to all recipes when Alle chip is clicked', async () => { const user = userEvent.setup(); render(Page, { props: { data: mockData } }); await user.click(screen.getByRole('button', { name: 'Mittel' })); expect(screen.queryByText('Spaghetti Bolognese')).not.toBeInTheDocument(); await user.click(screen.getByRole('button', { name: 'Alle' })); expect(screen.getByText('Spaghetti Bolognese')).toBeInTheDocument(); expect(screen.getByText('Chicken Curry')).toBeInTheDocument(); }); });