meal filtering feature
ci/woodpecker/push/fmt Pipeline was successful
ci/woodpecker/push/test Pipeline failed

This commit is contained in:
2026-08-08 16:19:49 -04:00
parent 975cf38170
commit 35de0e1990
7 changed files with 274 additions and 56 deletions
+57
View File
@@ -0,0 +1,57 @@
import { expect } from "@playwright/test";
import { test } from "../fixtures";
import { registerAndLogin, createList, createMeal } from "../helpers";
test("the meals page filters by name as you type", async ({ page }) => {
await registerAndLogin(page, "alice@example.com");
await createMeal(page, "Spaghetti Bolognese", "");
await createMeal(page, "Chicken Curry", "");
await createMeal(page, "Pancakes", "");
await page.goto("/meals");
await expect(page.locator(".list-card").filter({ hasText: "Spaghetti Bolognese" })).toBeVisible();
await expect(page.locator(".list-card").filter({ hasText: "Chicken Curry" })).toBeVisible();
await expect(page.locator(".list-card").filter({ hasText: "Pancakes" })).toBeVisible();
// Type a query; only matching meals remain.
await page.fill("#meal-search", "chicken");
await expect(page.locator(".list-card").filter({ hasText: "Chicken Curry" })).toBeVisible();
await expect(page.locator(".list-card").filter({ hasText: "Spaghetti Bolognese" })).toHaveCount(0);
await expect(page.locator(".list-card").filter({ hasText: "Pancakes" })).toHaveCount(0);
// Clearing the search restores all meals.
await page.fill("#meal-search", "");
await expect(page.locator(".list-card").filter({ hasText: "Spaghetti Bolognese" })).toBeVisible();
await expect(page.locator(".list-card").filter({ hasText: "Pancakes" })).toBeVisible();
});
test("the meals page shows an empty state when nothing matches", async ({ page }) => {
await registerAndLogin(page, "alice@example.com");
await createMeal(page, "Spaghetti Bolognese", "");
await page.goto("/meals");
await page.fill("#meal-search", "zzzz");
await expect(page.locator(".meal-filter-empty")).toBeVisible();
await expect(page.locator(".list-card")).toHaveCount(0);
});
test("the add-meal picker filters meals as you type", async ({ page }) => {
await registerAndLogin(page, "alice@example.com");
await createMeal(page, "Spaghetti Bolognese", "");
await createMeal(page, "Chicken Curry", "");
await createList(page, "Weekly shop");
await page.click(".add-meal-button");
const picker = page.locator(".meal-picker-backdrop");
await expect(picker).toBeVisible();
await expect(picker.locator(".meal-picker-button").filter({ hasText: "Spaghetti Bolognese" })).toBeVisible();
await expect(picker.locator(".meal-picker-button").filter({ hasText: "Chicken Curry" })).toBeVisible();
await picker.locator(".meal-filter").fill("curry");
await expect(picker.locator(".meal-picker-button").filter({ hasText: "Chicken Curry" })).toBeVisible();
await expect(picker.locator(".meal-picker-button").filter({ hasText: "Spaghetti Bolognese" })).toHaveCount(0);
// The search box keeps focus and the modal stays open.
await expect(picker.locator(".meal-filter")).toBeFocused();
await expect(picker).toBeVisible();
});