Replace "Lire la suite" and "Reduire" with t('synthesis.readMore')
and t('synthesis.collapse'). Adds both keys to fr.ts.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
normalizeUrl and isValidUrl are now in ~/utils/url. ThemeManager
and sources-utils tests import from the new location. The /sources
route redirect to /themes is preserved in App.tsx.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Settings tests now reference fields that exist in the current UI
(max articles per source instead of removed theme field). Generate
tests now mock the themes API and use current pipeline step names.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Users can mark sources as preferred via star buttons on the theme page.
Preferred sources are processed first in the pipeline (ordered before
non-preferred in waves, shuffled separately then merged).
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Adds Arc<AtomicBool> cancellation flag to JobStore/JobEntry. The pipeline
checks the flag before each wave and after each batch, then saves whatever
articles have been collected. A new POST /syntheses/generate/:job_id/stop
endpoint sets the flag. The frontend shows a red stop button during generation
and POSTs to the stop endpoint on click.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Remove content settings from settings table (moved to themes).
Add theme_id to sources and syntheses. Pipeline loads content
settings from the selected theme. Generate endpoint requires theme_id.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
When the slider is not at full (level < 4), each truncated article
shows a "Lire la suite" button to expand its summary inline.
A "Reduire" button collapses it back. Expansion is per-card and
independent of the global slider.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Add generation time below date in synthesis cards
- Show all categories with article count in parentheses
- Use flex-col layout for uniform card height
- Add sections_summary to SynthesisListItem API response
- Add formatTime utility
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
5 sections organized by purpose:
1. Contenu — theme, categories, summary length
2. Sources — per-source limits, Brave Search
3. Intelligence Artificielle — provider + API keys merged in one visual card
4. Performance — batch size, history, rate limits
5. Import/Export — collapsed by default
Sticky save button, smaller number inputs, integrated API key status
badge in the AI provider card.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Reorganize settings into 5 logical sections (Content, Sources, AI,
Performance, Import/Export) with visual cards. Merge AI provider
selection with API key management into one cohesive section.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
The LLM now determines if scraped content is a real article during
classify (zero extra cost). The separate LLM link extraction option
is removed — heuristic extraction is sufficient.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Add published_date column to article_history table
- Add date field to NewsItem (serialized in synthesis JSONB)
- Pass LLM-extracted date through ArticleTrace to article history
- Display date below article title in SynthesisDetail page
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Convert LlmLogs from onMount+signals to createResource for idiomatic
reactive data fetching. Replace duplicated inline save/add button markup
in Settings and Sources with the shared Button component.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Prevents timers from firing after component unmount in Home (delete
confirmation timers), ArticleHistory (clear confirmation timer), and
SynthesisDetail (email success banner timer).
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Adds a dedicated Brave Search section after the Advanced Extraction section,
including inline API key management (save/test/delete) and a use_brave_search
toggle that auto-disables when the key is removed.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Add use_brave_search boolean field to all settings structs, DB layer,
SQL queries, frontend types, i18n labels, and test fixtures following
the same pattern as use_llm_for_source_links.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Adds an optional article_url column to llm_call_log so classify_summarize
entries are traceable back to their source article in the LLM Logs UI.
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Add a user-configurable batch_size setting (default 5, range 1-20)
that controls how many articles are processed in parallel during
Phase 1 scrape+classify. Previously hardcoded to 5.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Update algorithm.md to reflect the rewritten per-article classify/summarize
pipeline (no batch classification, no rewrite pass). Update generation time
estimate from 1 minute to 10 minutes in frontend i18n and docs.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Replace the single `models` array in `ProviderConfig` and `AdminProvider`
with separate `models_scraping` / `models_websearch` lists. Rename
`ai_model_writing` → `ai_model_websearch` in `UserSettings` and all
references (Settings page, admin Providers page, E2E test, fixtures,
and unit tests). Update i18n label for the second dropdown to
"Modele d'IA (Recherche Web)".
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Add LlmLogs page with collapsible prompts/response sections, call-type
colored badges, and duration display
- Wire /llm-logs/:jobId route in App.tsx (lazy-loaded)
- Expose job_id in backend SynthesisListItem and frontend SynthesisListItem
type; update test fixture accordingly
- Add log-icon link next to delete button on each Home synthesis card
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Add ArticleHistoryEntry/ArticleHistoryResponse types
- Add articleHistoryApi client (list + getProvenance endpoints)
- Add ArticleHistory page with status/source_type filters and pagination
- Add collapsible provenance section to SynthesisDetail
- Register /article-history route in App.tsx
- Add viewHistory link in Settings near articleHistoryDays input
- Add all French i18n strings for article history feature
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Add article_history_days (defaulting to 90) to UserSettings interface and DEFAULT_SETTINGS, French translation, and Settings page number input.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Add max_articles_per_source field to UserSettings interface and DEFAULT_SETTINGS,
expose it as a number input on the Settings page, and add the French i18n label.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
normalizeUrl now strips smart quotes, zero-width spaces, and other invisible
formatting characters that browsers inject when copy-pasting URLs from rich
text sources. Prevents false "URL invalid" errors for valid URLs.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- updateRole return type matches backend's {id, role} instead of full AdminUser
- fetchFile error priority aligned with central client (message before error)
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Wire hardened scraper client into runtime (SSRF redirect validation was defined but unused)
- Stream scraper body with per-chunk size limit instead of post-download check (DoS/OOM)
- Persist user rate-limit overrides across generation jobs via AppState DashMap
- Roll back magic-link token on email send failure to prevent quota exhaustion
- Fix API error UX: prefer human message over machine error code in frontend
- Unwrap GET /syntheses { items } wrapper in frontend API layer (contract mismatch)
- Bind Postgres to localhost in docker-compose (was exposed on all interfaces)
- Fix CLAUDE.md: runtime queries not compile-time, 10 migrations not 9
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>