import json def test_hard_refresh_preserves_triage_state(base_url, page, seed_state, flask_app): """State is server-side — hard refresh must not reset it.""" album_id = seed_state("phase2_state") page.goto(f"{base_url}/triage?album_id={album_id}") page.locator(".photo-card").first.click() page.keyboard.press("j") page.wait_for_timeout(400) page.reload() first_card = page.locator(".photo-card").first assert "border-success" in first_card.get_attribute("class") def test_back_nav_from_group_to_triage_marks_curate_group_stale(base_url, page, seed_state): album_id = seed_state("phase4_state") # completed=[triage, curate], phase=group page.request.post( f"{base_url}/nav/phase", data=json.dumps({"album_id": album_id, "target_phase": "triage"}), headers={"Content-Type": "application/json"}, ) resp = page.request.get(f"{base_url}/state/{album_id}") state = resp.json() assert "curate" in state["phase_stale"] assert "group" in state["phase_stale"] def test_stale_banner_visible_on_stale_phase(base_url, page, seed_state): album_id = seed_state("phase4_state") page.request.post( f"{base_url}/nav/phase", data=json.dumps({"album_id": album_id, "target_phase": "triage"}), headers={"Content-Type": "application/json"}, ) # Now visit curate (which is stale) page.goto(f"{base_url}/curate?album_id={album_id}") assert page.locator("#stale-banner").is_visible() def test_dismiss_stale_clears_flag(base_url, page, seed_state, flask_app): album_id = seed_state("phase4_state") page.request.post( f"{base_url}/nav/phase", data=json.dumps({"album_id": album_id, "target_phase": "triage"}), headers={"Content-Type": "application/json"}, ) page.goto(f"{base_url}/curate?album_id={album_id}") page.locator("#stale-banner button").click() page.wait_for_url("**/curate**") with flask_app.app_context(): from app.state import load_state state = load_state(album_id, flask_app) assert "curate" not in state.phase_stale def test_exported_group_not_affected_by_back_nav(base_url, page, seed_state, flask_app): """Exporting then going back to triage must not touch the exported group.""" album_id = seed_state("phase6_state") # Manually set one group to exported with flask_app.app_context(): from app.state import load_state, save_state state = load_state(album_id, flask_app) state.groups[0].status = "exported" save_state(state, flask_app) # Navigate back page.request.post( f"{base_url}/nav/phase", data=json.dumps({"album_id": album_id, "target_phase": "triage"}), headers={"Content-Type": "application/json"}, ) with flask_app.app_context(): from app.state import load_state state = load_state(album_id, flask_app) assert state.groups[0].status == "exported" def test_notes_autosave_survives_phase_navigation(base_url, page, seed_state, flask_app): album_id = seed_state("phase2_state") page.request.post( f"{base_url}/notes/save", data=json.dumps({"album_id": album_id, "notes": "survives navigation"}), headers={"Content-Type": "application/json"}, ) page.goto(f"{base_url}/curate?album_id={album_id}") resp = page.request.get(f"{base_url}/notes/{album_id}") assert resp.json()["notes"] == "survives navigation"