5.7 KiB
Design: Multi-Theme Synthesis Support
Date: 2026-03-26 Scope: Allow users to create multiple themes, each with its own content settings and sources, generating syntheses per theme.
Context
Currently each user has a single theme with one set of categories. Users who follow multiple topics (e.g. AI + Cybersecurity) must choose one or regenerate with different settings. This feature adds support for multiple themes per user.
1. Data Model
New table: themes
CREATE TABLE themes (
id UUID PRIMARY KEY DEFAULT gen_random_uuid(),
user_id UUID NOT NULL REFERENCES users(id) ON DELETE CASCADE,
name TEXT NOT NULL,
theme TEXT NOT NULL,
categories JSONB NOT NULL DEFAULT '[]',
max_items_per_category INTEGER NOT NULL DEFAULT 4,
max_age_days INTEGER NOT NULL DEFAULT 7,
summary_length INTEGER NOT NULL DEFAULT 3,
created_at TIMESTAMPTZ NOT NULL DEFAULT now(),
updated_at TIMESTAMPTZ NOT NULL DEFAULT now()
);
CREATE INDEX idx_themes_user_id ON themes(user_id);
Modified table: sources
Add theme_id UUID REFERENCES themes(id) ON DELETE CASCADE. Sources become per-theme.
Modified table: syntheses
Add theme_id UUID REFERENCES themes(id) ON DELETE SET NULL. Links each synthesis to its theme. SET NULL preserves syntheses when a theme is deleted.
Modified table: settings
Remove columns that move to themes: theme, categories, max_items_per_category, max_age_days, summary_length.
Migration strategy
- Create
themestable - For each user with settings, create a default theme from their current content settings
- Add
theme_idtosources, populate with the user's default theme - Add
theme_idtosyntheses, populate with the user's default theme - Drop moved columns from
settings
2. Backend API
New endpoints — Themes CRUD
GET /api/v1/themes— list user's themesPOST /api/v1/themes— create a new themePUT /api/v1/themes/:id— update a themeDELETE /api/v1/themes/:id— delete a theme (syntheses kept withtheme_id = NULL)
Modified endpoints
GET /api/v1/sources— add optional?theme_id=filterPOST /api/v1/sources— requiretheme_idin request bodyPOST /api/v1/syntheses/generate— requiretheme_idin request bodyGET /api/v1/syntheses— response includestheme_name. Add optional?sort=date|themeparam.
Pipeline change
run_generation_inner receives theme_id and loads content settings (theme, categories, max_items, max_age, summary_length) from the themes table instead of settings. Global settings (provider, models, batch_size, rate limits, etc.) still come from settings.
3. Frontend — "Personnaliser les syntheses" page
Navigation rename
"Sources personnalisees" → "Personnaliser les syntheses"
Page layout
- Theme selector — dropdown listing all user themes + "Creer un nouveau theme" button
- Content settings — theme name, search topic, categories (add/remove), max age, max items, summary length slider. Moved from Settings page.
- Sources — existing sources list, filtered by selected theme. Add/delete/bulk import scoped to current theme.
- Delete theme — danger button with confirmation.
Settings page changes
Remove the "Contenu" section. Keep: Sources (pipeline tuning), Intelligence Artificielle, Performance, Import/Export.
4. Frontend — Home page enhancements
- Theme badge on synthesis cards (below week label). "Theme supprime" for null theme_id.
- Sort toggle: "Trier par: Date | Theme". Default: Date. Theme sort groups by theme name.
- Generate page: theme dropdown before "Generate" button. Pre-selects last used theme.
5. Implementation phases
| Phase | Scope | Dependencies |
|---|---|---|
| 1 | Data model + backend API (migrations, themes CRUD, pipeline) | None |
| 2 | Theme management page (new page, move content settings) | Phase 1 |
| 3 | Generation with theme (generate page dropdown) | Phase 1 |
| 4 | Home page enhancements (theme badge, sort) | Phase 1 |
Each phase produces working software. Phases 2-4 can be done in any order after Phase 1.
Files overview
Phase 1 (Backend)
- Create:
backend/migrations/20260326000028_create_themes.sql - Create:
backend/src/db/themes.rs - Create:
backend/src/models/theme.rs - Create:
backend/src/handlers/themes.rs - Modify:
backend/src/db/mod.rs,backend/src/models/mod.rs,backend/src/handlers/mod.rs - Modify:
backend/src/router.rs— add theme routes - Modify:
backend/src/db/sources.rs— addtheme_idfilter - Modify:
backend/src/db/syntheses.rs— addtheme_id,theme_nameto queries - Modify:
backend/src/models/settings.rs— remove moved fields - Modify:
backend/src/db/settings.rs— remove moved columns from queries - Modify:
backend/src/services/synthesis.rs— load content settings from theme - Modify:
backend/src/handlers/generation.rs— accepttheme_id
Phase 2 (Theme page)
- Create:
frontend/src/pages/ThemeManager.tsx - Create:
frontend/src/api/themes.ts - Modify:
frontend/src/App.tsx— routes - Modify:
frontend/src/components/Navbar.tsx— rename nav item - Modify:
frontend/src/pages/Settings.tsx— remove Contenu section - Modify:
frontend/src/i18n/fr.ts— labels
Phase 3 (Generate)
- Modify:
frontend/src/pages/GenerateSynthesis.tsx— theme dropdown - Modify:
frontend/src/api/syntheses.ts— pass theme_id
Phase 4 (Home)
- Modify:
frontend/src/pages/Home.tsx— theme badge, sort - Modify:
frontend/src/types.ts— add theme fields to types