Skip to content

Moderation: hide unreviewable rows, add Reject and diffs; fix scraper discovery - #52

Merged
jjosef merged 4 commits into
mainfrom
fix/moderation-empty-items-reject-and-diff
Sep 21, 2026
Merged

jjosef merged 4 commits into
mainfrom
fix/moderation-empty-items-reject-and-diff

Conversation

@jjosef

@jjosef jjosef commented Sep 21, 2026

Copy link
Copy Markdown
Collaborator

Moderation queue

  • Rows with no name or type no longer show up (they rendered as "(no name)" and could not be approved). approve refuses them.
  • New POST /contributions/:thingId/:sk/reject and a Reject button; rejects the whole card including folded siblings.
  • Each card carries a preview: the field-level diff approval would produce, built by the same applyContributionToThing that approve uses.
  • pnpm --filter @btfp/seed reject:unreviewable (dry run unless --apply) rejects existing nameless rows and rows scraped from Google page chrome.

Scraper

Live logs showed the only "trends" ever researched were terms, privacy, sign in, about, help, send feedback. Rendered Trends rows begin with a blank line, so the parser dropped every row and its <a> fallback scraped the page footer.

  • Parse the first non-blank line; remove the link fallback and throw if no rows load; denylist page chrome.
  • Trending Now is mostly sports/news (the category param is ignored), so its terms pass a per-topic triage. A search-driven source (hazard-news seed queries) finds toxic substances directly. A Trends outage no longer stops the run.
  • Three searches per topic (dogs, cats, symptoms), merged by URL.
  • Classifier moves to Sonnet 4.6 (SCRAPER_BEDROCK_INFERENCE_PROFILE_ID, scraper only; the BFF stays on Haiku) with a system prompt, a per-pet-type severity and a confidence level. Nameless and low-confidence reports are not filed.

Deploy notes

  • Changes the Fargate task role's Bedrock resource and the task's model env var.
  • Web search cost rises to roughly $5-25/mo per env (was $1-2); seen topics are skipped.
  • The end-to-end run needs the deployed AgentCore browser and gateway, so the first dev run after deploy is the real test.

Test plan

  • typecheck, build, tests (16 turbo tasks), oxlint
  • Classifier and triage exercised against live Bedrock (Sonnet 4.6) with synthetic search text
  • Moderation page checked in the browser against a mock API (diffs render, Reject removes the card)
  • First dev scraper run after deploy

The moderation queue now omits rows with no name or type, attaches a
field-level preview (the diff approval would produce, via shared
applyContributionToThing) to each card, and supports
POST /contributions/:thingId/:sk/reject. approve refuses nameless rows.
Also adds reject:unreviewable, a dry-run-by-default script that rejects
such rows already in the pending queue.
Documents the new queue behaviour in architecture.md.
Trending rows render with a leading blank line, so the parser dropped every
row and its link fallback scraped the Google footer ("Terms", "Privacy",
"Sign in") as trends. Parse the first non-blank line, remove the fallback
(fail loudly instead), and denylist page chrome.

Trending Now is mostly sports and news, so its terms pass a per-topic
triage before research, and a search-driven source (hazard-news seed
queries) now finds toxic substances directly. A Trends outage no longer
stops the run.

Research each topic with three searches (dogs, cats, symptoms) merged by
URL. The classifier moves to Sonnet 4.6 with a system prompt (facts from
the sources only, one specific named hazard, severity per pet type,
confidence). Low-confidence and nameless reports are not filed.

reject:unreviewable also catches rows scraped from Trends page chrome.
@jjosef
jjosef merged commit f4d2210 into main Sep 21, 2026
2 checks passed
@jjosef
jjosef deleted the fix/moderation-empty-items-reject-and-diff branch September 21, 2026 00:40
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant