Files
FabledScribe/docs/changelog.md
T
bvandeusen 47e248d9ac docs: restructure documentation into docs/ directory, slim README, add project .mcp.json
- README.md: reduced to overview + quick start + links to docs/
- docs/architecture.md: stack, design decisions, data models, key services
- docs/configuration.md: all env vars, docker-compose setup, production + security
- docs/development.md: dev workflow, CI/CD, migrations, release process
- docs/features.md: detailed feature breakdown + keyboard shortcuts
- docs/api-keys-and-mcp.md: API key management + Fable MCP install guide
- docs/sso-oauth.md: OAuth/OIDC setup (replaces docs/oauth-setup.md)
- docs/changelog.md: development history from summary.md
- Remove summary.md (content distributed across docs/)
- Remove docs/oauth-setup.md (superseded by docs/sso-oauth.md)
- .gitignore: add .mcp.json

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-03-24 21:03:15 -04:00

151 lines
10 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Changelog
Development history — most recent first.
---
## 2026-03-24 — fable-mcp serve, admin log tool, Settings MCP install UI
- **Dockerfile** — builds `fable-mcp` wheel into `/app/dist/` at image build time
- **`routes/fable_mcp_dist.py`** — `GET /api/fable-mcp/info` (availability check) and `GET /api/fable-mcp/download` (wheel download)
- **`fable_mcp/tools/admin.py`** — `get_app_logs()` calling `/api/admin/logs`
- **`fable_mcp/server.py`** — `fable_get_app_logs` MCP tool
- **SettingsView** — "Fable MCP" section in API Keys tab: wheel download button and install instructions
- **ci.yml** — `fable-mcp/**` added to trigger paths
## 2026-03-23 — fable-mcp scaffold + all tools
- `fable-mcp/` Python package scaffolded (`pyproject.toml`, `hatchling` build)
- `FableClient` — async httpx wrapper with `FABLE_URL` + `FABLE_API_KEY` auth
- Tool modules: `notes`, `tasks`, `projects`, `milestones`, `search`, `chat`, `admin`
- `server.py` — FastMCP stdio transport; all tools registered
- Settings UI — API Keys tab with create/revoke, `.env` download, Claude config download
- `routes/api_keys.py``POST /api/api-keys`, `GET /api/api-keys`, `DELETE /api/api-keys/:id`
## 2026-03-23 — Model management UI, RSS category/refresh, weather city search
- **SettingsView** — Model Management section: list installed models (size, loaded state), pull by name (SSE progress), delete unused
- **`routes/chat.py` `list_models_route`** — also hits `/api/ps` in parallel; returns `loaded: bool` and `modified_at` per model
- **RSS feeds** — category badge, last-fetched age, manual refresh button, category input on add
- **`routes/briefing.py`** — `POST /api/briefing/feeds/refresh` triggers immediate re-fetch
- **`get_weather` tool** — now accepts any city name (geocodes via Nominatim + fetches Open-Meteo); not limited to pre-configured locations
## 2026-03-22 — Briefing scheduler fix, quick capture fix, task back navigation
- **Briefing scheduler** — fixed deadlock: `start_briefing_scheduler` made async; replaced `run_coroutine_threadsafe(...).result()` with `await` (was blocking the event loop thread)
- **Briefing pipeline** — added early return when both LLM synthesis lanes produce empty strings (was always prepending "Good morning" on failure)
- **Quick capture** — fixed: was always creating notes. Two causes fixed: (1) now uses user's `default_model` setting instead of `Config.OLLAMA_MODEL`; (2) removed `create_project` from classifier prompt (tool not offered, causing fallback to note)
- **TaskViewerView** — back button navigates to task's project when `project_id` is set; Esc handler registered in capture phase to prevent conflict with App.vue global handler
## 2026-03-21 — Briefing RSS + project kanban advance buttons
- **ProjectView kanban** — status-advance buttons on task cards (→ todo→in_progress, ✓ in_progress→done), hidden until hover
- **Briefing UI** — RSS feeds section: add URL + category, list feeds with last-fetched age badge, delete, manual refresh
## 2026-03-16 — Fuzzy project resolution, create_project guard, task embedding fix
- `services/tools.py``_resolve_project` rewritten with 4-step lookup: (1) exact DB match, (2) `query in title` substring, (3) `title in query` reverse substring, (4) SequenceMatcher ≥ 0.55. Partial names now reliably resolve without creating duplicates.
- `services/tools.py``create_project` handler: similar-project checks (threshold 0.55) run **before** the `confirmed` gate, so `confirmed=true` cannot bypass them.
- `routes/tasks.py` — fire-and-forget `upsert_note_embedding` added to create and update routes (tasks weren't getting embeddings via REST API).
- `services/briefing_pipeline.py``await is_caldav_configured()` fix (was called without await — latent bug since the function became async).
- `services/notes.py` — removed erroneous duplicate `count_query.where(Note.parent_id == parent_id)` that was applied inside the `no_project` branch.
## 2026-03-12 — CI release process update
- `.forgejo/workflows/ci.yml` — removed `main` from `branches` push trigger. CI fires only on `dev` pushes, `v*` tags. Production release: create release via Forgejo UI on `main` with a `v*` tag → tag push fires CI → build job pushes `:latest` + `:<version>`.
## 2026-03-11 — Daily Briefing (full feature)
Backend:
- Migration `0026_add_briefing_tables.py`: `rss_feeds`, `rss_items`, `weather_cache`; added `conversation_type` and `briefing_date` to `conversations`.
- `services/weather.py`: geocoding via Nominatim, forecast via Open-Meteo, per-user DB cache.
- `services/rss.py`: feedparser-based fetch, per-feed DB cache prune-to-100.
- `services/briefing_pipeline.py`: two-lane parallel gather (weather, RSS, tasks, calendar) → LLM synthesis → GenerationBuffer SSE stream.
- `services/briefing_scheduler.py` (APScheduler): slots morning/midday/evening/night with catch-up logic.
- `routes/briefing.py`: RSS CRUD at `/api/briefing/feeds`, weather config, briefing config, `POST /api/briefing/trigger`.
Frontend:
- `BriefingView.vue`: primary briefing page; digest card + conversation thread + reply bar.
- `BriefingSetupWizard.vue`: 4-step setup wizard shown on first visit.
- SettingsView: Briefing tab (enable toggle, location geocoding, office days, time slot toggles, RSS CRUD).
- AppHeader: "Briefing" nav link added.
## 2026-03-11 — Version footer, task history, note version retention
- CalVer build-time version tracking: `Dockerfile` injects `BUILD_VERSION` ARG; displayed in Settings footer.
- Task history moved to collapsible right sidebar (previously modal overlay).
- Note version retention: configurable max versions per note (default 20) enforced at write time.
- Content deduplication in `build_context()` — same note cannot appear in multiple context blocks.
## 2026-03-11 — Multi-user sharing, notifications, groups, backup rewrite
- Migration `0025_add_sharing_and_notifications.py`: `groups`, `group_memberships`, `project_shares`, `note_shares`, `notifications`.
- `services/access.py`: `PERMISSION_RANK` dict; `get_project_permission` / `get_note_permission` — check ownership, direct share, group-based share, note→project inheritance.
- Share dialog (`ShareDialog.vue`): user tab (search + permission select), group tab, current shares list with inline change/remove.
- `SharedWithMeView.vue`: `/shared` route — shared projects and notes.
- In-app notification bell with 60s polling; push generated on share/group events.
- Backup rewrite (version 2): includes all tables; `restore_full_backup` builds ID maps, two-pass note restore for `parent_id` patching.
## 2026-03-10 — Project Workspace, Graph View, settings tabs, message queue persistence
- `WorkspaceView.vue`: 3-panel layout (tasks/chat/notes), collapse toggles, SSE watcher auto-loads notes and refreshes tasks.
- `WorkspaceTaskPanel.vue`: milestone-grouped task list, detail slide-over with status cycle + log.
- `WorkspaceNoteEditor.vue`: list ↔ TipTap editor, autosave.
- `GraphView.vue`: D3 force-directed graph, tag nodes, project hub nodes, physics panel, peek panel.
- SettingsView fully rewritten with tabbed layout (General, Account, Notifications, Integrations, Data, Admin).
- Message queue: persisted to localStorage; queued bubbles shown in chat with opacity + "QUEUED" label.
- ToolCallCard: confirm/deny inline; "Create anyway" posts directly to API (no LLM round-trip).
- Duplicate detection: scoped to same `is_task` type; semantic threshold raised 0.87 → 0.90.
## 2026-03-10 — "Illuminated Transcript" design language
- Fraunces font for headings; assistant bubbles elevated with left indigo accent + shadow; user bubbles ghosted (transparent bg, muted text).
- Dark palette shifted to slate-indigo (`#111113`). `--radius-lg` 12→18px.
- Cards: shadow depth replaces borders. Send buttons: indigo gradient + glow.
## 2026-03-10 — CI/CD infrastructure
- `infra/Dockerfile.runner-base`: Ubuntu 24.04 + Python 3.12 + Node 22 LTS custom runner image.
- All CI jobs use `py3.12-node22` runner; pip caching added; Node bumped to 22.
## 2026-03-06 — Session invalidation on credential change
- `users.session_version` column; incremented on password change/reset; checked in `_check_auth`; mismatch evicts all other sessions.
## 2026-03-06 — DRY refactoring (backend + frontend)
- `models/base.py`: `TimestampMixin` + `CreatedAtMixin` applied to all models (~60 lines removed).
- `routes/utils.py`: `not_found()` + `parse_iso_date()` helpers.
- Frontend composables: `useAutoSave`, `useEditorGuards`, `useTagSuggestions`, `useFloatingAssist`, `useListKeyboardNavigation`.
- Shared CSS: `editor-shared.css`, `viewer-shared.css`. Net: 634 lines, +237 lines.
## 2026-03-06 — Project-aware writing assist, link suggestions, project-scoped RAG
- Writing assist: `context_notes` param injects project notes; `definition`-tagged notes prioritised.
- Link suggestions: detects note titles as plain text in body; one-click wikilink conversion.
- Project-scoped RAG: `rag_project_id` param restricts semantic + keyword search to a project.
- `search_notes` tool: upgraded to hybrid semantic + keyword; `relevance` field in results.
- SSRF protection: `_is_private_url()` blocks private/loopback addresses; `follow_redirects=False`.
- Config validation: `Config.validate()` at startup.
## 2026-03-05 — Note editor sidebar, full-document writing assist, drafts, version history
- NoteEditorView: two-column layout; writing assistant always visible in sidebar.
- `whole_doc` mode: assistant outputs complete revised document (not just selected section).
- `DiffView.vue`: standalone diff component with equal-line collapsing (git-style context).
- Persistent drafts: `note_drafts` table; draft auto-saved after assist generation; restored on load.
- `note_versions` table: auto-snapshot on body change; version browser with diff + restore.
## 2026-03-05 — Task work log, task editor overhaul
- `task_logs` table; `TaskLogSection.vue` with timestamps, duration badges, inline edit.
- TaskEditorView: two-column layout with collapsible sidebar; sub-tasks section.
- `log_work` LLM tool added to `_CORE_TOOLS`.
## 2026-03-04 — Per-conversation streaming, SSE reconnection, keyboard navigation
- Per-conversation streaming state; auto-new chat on open.
- SSE reconnection: chat `reconnectIfGenerating()` on mount + navigation; assist retry loop with `Last-Event-ID`.
- Model load timeout raised 90s → 180s.
- Writing assist retry loop (3 attempts, exponential backoff).