"""E2E: a season of the owner's own, added from the Seasonal row editor (issue #137). Full stack: the built SPA and the real API, the fake PMS (the film search and the library scan a count reads) and the fake TMDB (a tag's list, read to its last page). The editor counts a season on the server before anything is saved, so this is the one place the count, the film search, the save and the row that ticks the season are seen working together. """ from __future__ import annotations import re import pytest from playwright.sync_api import Page, Route, expect from tests.e2e.conftest import FAKE_TMDB_TAGS, THANKSGIVING_DINNER_TAG, THANKSGIVING_TAG, ShortlistApp from tests.fakes.fake_plex import FakePlexState pytestmark = pytest.mark.e2e LOAD = 20_000 #: The first count scans every library before it can answer. COUNT = 60_000 BUILT_INS = ("valentines", "halloween", "christmas") def _films_counted(total: int) -> re.Pattern[str]: """ "7 films in your libraries", and not "17 films …": the count sits flush against the text before it.""" return re.compile(rf"(? None: preset = next(p for p in app.api("GET", "/api/seasons/presets").json() if p["key"] == "thanksgiving_us") rows_before = app.api("GET", "/api/collections").json() page.goto("/rows") page.get_by_role("button", name="Add a row").click() page.get_by_role("group", name="Kinds of row", exact=True).get_by_role( "button", name=re.compile(r"^Seasonal") ).click() page.get_by_role("link", name="Set every option yourself").click() page.get_by_role("searchbox", name="Find a season").fill("Thanksgiving (US)") card = page.get_by_role("list", name="Ready-made seasons").get_by_role("listitem") expect(card).to_contain_text(preset["description"]) pending_creates: list[Route] = [] def hold_create(route: Route) -> None: if route.request.method == "POST": pending_creates.append(route) else: route.continue_() page.route(re.compile(r"/api/seasons$"), hold_create) with page.expect_request(lambda request: request.method == "POST" and request.url.endswith("/api/seasons")): card.get_by_role("button", name="Add Thanksgiving (US)").click() expect(page.get_by_role("button", name="Add row", exact=True)).to_be_disabled() expect(page.get_by_role("button", name="Cancel", exact=True)).to_be_disabled() assert all(season["slug"] != "thanksgiving" for season in app.api("GET", "/api/seasons").json()) assert app.api("GET", "/api/collections").json() == rows_before assert len(pending_creates) == 1 pending_creates[0].continue_() expect(page.get_by_role("dialog")).to_have_count(0) mine = page.locator('li[data-season="thanksgiving"]') expect(mine.get_by_role("checkbox")).to_be_checked(timeout=LOAD) expect(mine.get_by_role("checkbox")).to_be_focused() expect(page.get_by_role("status").filter(has_text=re.compile(r"save (?:this |the )?row", re.I))).to_be_visible() assert app.api("GET", "/api/collections").json() == rows_before season = next(s for s in app.api("GET", "/api/seasons").json() if s["slug"] == "thanksgiving") for field in ( "name", "emoji", "preset", "rule", "lead_days", "after_days", "tags", "genre", "excluded_genres", "collections", "picks", ): assert season[field] == preset[field], field page.get_by_role("button", name="Add row").click() expect(page).to_have_url(re.compile(r"/rows$"), timeout=LOAD) row = next(c for c in app.api("GET", "/api/collections").json() if "thanksgiving" in c["seasons"]) assert set(row["seasons"]) == {*BUILT_INS, "thanksgiving"}