# SPEC-013 — News digest Replaces the broken pre-1.0-openai `news_feed.py`. A CLI (`python -m fjerkroa_bot.news --config `) fetches the `news-feeds` and writes a compact digest to the `news` file that `AIResponder.message` injects into the `{news}` slot. Feeds are external input and operator-configured. ### NEWS-01 — RSS and Atom parse to items (coverage: test) `parse_feed(bytes, label)` extracts `{title, link, source}` from both RSS (``) and Atom (``) documents, tolerates malformed XML (returns an empty list, logs), and never raises. ### NEWS-02 — Digest is sanitized and bounded (coverage: test) `render_digest` caps at `news-max-items`, and every headline passes `sanitize_external_text` (SAF-03) — a feed cannot inject `@everyone` or control characters into the prompt via a headline. ### NEWS-03 — Feeds are SSRF-guarded and deduped (coverage: test) `NewsFetcher.collect` skips any feed URL the SSRF guard rejects, skips feeds that fail to fetch (one bad feed never sinks the run), and drops duplicate headlines across feeds.