Mark each item open/mitigated/done, fold completed work into Shipped, and upgrade the clustering bug with the on-device Jackson/airport over-merge proof and a concrete TF-IDF/embeddings fix. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
4.0 KiB
Backlog & status
Source-of-truth tracker. The Gitea issue tracker is currently empty (0 issues) —
run scripts/create-issues.sh with a token to populate it. [client] = iOS,
[backend] = the platform service on the Docker host, [ci] = build/test.
Status: 🔴 open · 🟡 mitigated client-side (real fix still pending) · 🟢 done.
Backend — data quality (highest priority)
- 🟡 [backend] F1 mis-classified into tech/finance/politics. No sport category, so
F1 (100% F1 sources) scatters across topics: "Monaco Grand Prix…" →
tech, "F1 reports 35% CO2…" →finance, "McLaren launch appeal…" →politics. Add asport/f1topic and route motorsport sources there. Client mitigation shipped: F1 pill matches clear F1 headlines + a majority of F1 sources, and F1 is excluded from All/Tech/Finance. Backend still mis-tags. - 🔴 [backend] Catastrophic over-clustering — unrelated articles merged on a single shared word. Newly confirmed on-device: a story merged a Russian-film-director article + "Who's afraid of Michael Jackson?" + "Chelsea Jackson Roberts" (wellness) — grouped on the surname Jackson. Another merged "Gunfire at Niger airport" + "L.A. County Whiteman Airport crash" + "Niger fintech". Result: wrong headline, summary, topic, and inflated signal. Raise the TF-IDF threshold hard (~0.22 → 0.45–0.55) and require multiple shared distinctive terms / named-entity overlap, with a tight time window. If still over-merging, move to sentence embeddings (all-MiniLM-L6-v2, cosine ≥ ~0.6). Make canonical headline + summary come from the same representative article. No client fix is possible — the story object itself is wrong.
- 🔴 [backend] Add accurate per-story tags (topic + region). So the client can read tags (sport, uganda, south-africa, …) instead of keyword-guessing. Unblocks #6.
- 🔴 [backend] Topic-classifier coverage for the 47 feeds. science/world/tech mapping.
Backend — features
- 🔴 [backend] Server-side push for breaking alerts (APNs or ntfy). For breaking-story notifications while the app is closed. Client does local notifications + background refresh only.
Client
- 🔴 [client] Move interest filters server-side once tags (#3) exist. Today's pills are client-side keyword/headline matches on loaded stories. Refined since: regions match headline-only (no polluted summaries/outlets), regions exclusive, F1 by source majority, East Africa removed.
- 🔴 [client] SSID-based trusted networks. Needs Access WiFi Information entitlement (device + paid account). Approximated by LAN reachability today.
- 🔴 [client] Optional in-app WireGuard tunnel. NetworkExtension; entitlement + device. Deferred.
- 🔴 [client] App icon + launch assets.
AppIconis an empty placeholder. - 🔴 [client] Flesh out Latest / Search tabs. Saved is now bookmarks; Latest/Search still minimal.
- 🔴 [client] Verify hero image loading.
AsyncImagevs real feedimageUrls. - 🔴 [client] Offline-first polish. Pre-cache top stories.
CI
- 🔴 [ci] Add unit/UI tests + a test matrix leg. Build matrix compiles, runs no tests.
- 🔴 [ci] Backend CI build matrix. Python 3.11–3.13 + lint + Docker build/health probe.
🟢 Shipped
Signal feed + detail + reader + feed manager · LAN⇄Tailscale connectivity · notifications
(morning/evening briefings + breaking alerts) with Open-Meteo weather · device code signing
· feed resilience (no blank-on-refresh, ignore cancelled, coalesced WS refresh) · clearer
empty states (polling / unreachable+host / offline / caught-up) · deterministic feed order ·
6-line summary preview · pinned filters (F1 split out, regions exclusive & headline-matched,
Finance/Tech by topic) · swipe actions (short→Save / long→Mark read, right→Share) ·
read/seen handling (seen-tracking with per-load snapshot, read stories collapse into a
"Read" shelf with compact rows, "all caught up" state).