Triage cards expand to show every report behind a story
Cards showed a hard-capped 5 members with no way to see the rest. They now render every report, with the first three inline and the remainder behind a native <details> disclosure -- so it works without JavaScript and stays keyboard accessible. Each entry carries its publication time and outlet, and the summary names how many reports across how many outlets. `e` expands the selected card. Loaded inline rather than through a lazy endpoint because the data is small: measured on this corpus the largest cluster is 23 members and multi-item clusters hold 249 between them. Also fixes a bug this introduced. The sources-list comprehension was byte identical in triage() and digest_page(), so a str.replace() intended for one hit both, and digest_page started reading a published_at column its query does not select -- four tests went red. The assert only checked that the anchor EXISTS, not that it is UNIQUE. Edits now assert the occurrence count. The digest query gained the column properly, since a timestamp is useful there too.
This commit is contained in:
1 parent
8ed007a75f
commit
90077aa3bd
3 files changed
+83
-10
No files matched your search
@@ -267,3 +267,38 @@ def test_palette_is_defined_once_from_the_shared_partial(client, path):
|
||||
html = c.get(path).text
|
||||
assert html.count(".sitenav {") == 1
|
||||
assert html.count("--accent:#7c3aed") == 1, "light palette declared more than once"
|
||||
|
||||
|
||||
def test_triage_cards_expand_to_every_report(tmp_path, monkeypatch):
|
||||
"""A card must show all the reports behind a story, not a truncated slice."""
|
||||
import numpy as np
|
||||
from datetime import UTC, datetime
|
||||
|
||||
monkeypatch.setenv("NEWS_DB", str(tmp_path / "e.db"))
|
||||
monkeypatch.setenv("NEWS_FEEDBACK_SECRET", SECRET)
|
||||
con = store.connect(tmp_path / "e.db")
|
||||
now = datetime.now(UTC)
|
||||
for n in range(7):
|
||||
store.upsert_source(con, id=f"s{n}", name=f"Outlet{n}", url=f"http://s{n}",
|
||||
kind="rss", bucket=f"b{n}", weight=1.0, prominence=0,
|
||||
enabled=1, poll_interval_secs=900)
|
||||
con.execute("""INSERT INTO items (id,source_id,title,summary,url,canonical_url,
|
||||
published_at,first_seen_at,content_hash)
|
||||
VALUES (?,?,?,'',?,?,?,?,?)""",
|
||||
(f"i{n}", f"s{n}", f"Report number {n}", f"http://x/{n}",
|
||||
f"http://x/{n}", now.isoformat(), now.isoformat(), f"h{n}"))
|
||||
con.execute("""INSERT INTO clusters (id,centroid,size,first_seen_at,last_seen_at,lead_item_id)
|
||||
VALUES ('big',?,7,?,?,'i0')""",
|
||||
(store.to_blob(np.zeros(384, dtype="float32")),
|
||||
now.isoformat(), now.isoformat()))
|
||||
for n in range(7):
|
||||
con.execute("INSERT INTO cluster_members VALUES ('big',?,?)", (f"i{n}", now.isoformat()))
|
||||
|
||||
from news import web
|
||||
web._VECTORS = None
|
||||
html = TestClient(web.app).get("/").text
|
||||
|
||||
for n in range(7):
|
||||
assert f"Report number {n}" in html, f"report {n} missing from the card"
|
||||
assert "<details" in html and "4 more reports" in html
|
||||
assert "across 7 outlets" in html
|
||||
Reference in new issue
Block a user