68 lines
3.1 KiB
Plaintext
68 lines
3.1 KiB
Plaintext
Todo 19 — news-web UI (CSR) with Leptos 0.8
|
|
|
|
Completed: 2026-09-01
|
|
|
|
Scope
|
|
- Scaffolded `crates/news-web` as a Leptos 0.8 client-side-rendered (CSR)
|
|
web app, mirroring `runway-web`'s Trunk + Tailwind v4 toolchain.
|
|
- Implemented three API client routes against the same-origin `/api/*` proxy:
|
|
- GET /api/stories
|
|
- POST /api/feedback
|
|
- GET /api/config
|
|
- Built three UI views:
|
|
- Story list: table of clusters with title, source count, importance,
|
|
relevance, percentile badges, server decision, and per-row feedback
|
|
buttons (Interested / Not interested).
|
|
- Config view: read-only summary of topics, notification settings, and
|
|
sources.
|
|
- Error / loading states for both data fetches and feedback actions.
|
|
- Kept the WASM bundle lean by avoiding `news-core` and any markdown/chart
|
|
libraries.
|
|
|
|
Verification
|
|
- `cargo check -p news-web --target wasm32-unknown-unknown` passes.
|
|
- `trunk build --release` succeeds; generated WASM is
|
|
`news-web-263e7ab3a1a1c8aa_bg.wasm` at 525 KiB (well under the 1.8 MiB
|
|
budget enforced by todo 20).
|
|
- `cargo fmt --all --check`, `cargo clippy --workspace --all-targets -- -D warnings`,
|
|
and `cargo test --workspace` all pass (87 tests total).
|
|
|
|
Playwright QA — happy path
|
|
- Seeded a temporary SQLite database with one source and one story cluster
|
|
("Mars Rover Finds Water").
|
|
- Started `target/debug/news-server` on port 3000 and `trunk serve` on
|
|
port 8080 with Trunk proxying `/api` to the backend.
|
|
- Navigated to http://127.0.0.1:8080/ in Playwright.
|
|
- Asserted the story title "Mars Rover Finds Water" rendered in the table.
|
|
- Clicked the "Interested" feedback button.
|
|
- Asserted the per-row "Saved" success indicator appeared.
|
|
- Verified the network request log contained:
|
|
POST http://127.0.0.1:8080/api/feedback => 200 OK
|
|
- Captured screenshot: `.omo/evidence/task-19-news-triage.png`
|
|
|
|
Playwright QA — failure path
|
|
- Stopped the backend server (port 3000).
|
|
- Reloaded http://127.0.0.1:8080/ in Playwright.
|
|
- Asserted the visible error state text "Could not load stories" appeared.
|
|
- Verified the network request log contained:
|
|
GET http://127.0.0.1:8080/api/stories => 500 Internal Server Error
|
|
- Captured screenshot: `.omo/evidence/task-19-news-triage-failure.png`
|
|
|
|
Evidence files
|
|
- `.omo/evidence/task-19-news-triage.png` — happy-path story list with
|
|
feedback success state.
|
|
- `.omo/evidence/task-19-news-triage-failure.png` — failure-path error state.
|
|
- `.omo/evidence/task-19-news-triage.txt` — this file.
|
|
|
|
Notes / gotchas
|
|
- Leptos 0.8's `Action::new` requires `Send` futures, which are not available
|
|
on `wasm32-unknown-unknown`. On WASM, use `Action::new_local` for actions
|
|
backed by `gloo_net` (or any non-Send JS future).
|
|
- `news-server` stores `source.kind` and `raw_items.kind` as snake_case strings
|
|
(`rss_atom`, `news`). Seeding with `rss` or any other string causes a startup
|
|
parse error (`InvalidStoredValue`).
|
|
- The Playwright MCP was configured to launch Google Chrome at
|
|
`/opt/google/chrome/chrome`; on this Arch box that required installing the
|
|
system `chromium` package and symlinking `/opt/google/chrome/chrome ->
|
|
/usr/bin/chromium` so the MCP could launch the browser.
|