Full-text chat search: a ⌘K palette over every visible conversation (#509)
Adds search across the content of every conversation the viewer can see — not just titles — from a ⌘K/Ctrl+K palette; Enter opens the matched conversation, and ⌘/Ctrl+Enter starts a new chat with the query as the prompt, so a fruitless search becomes a question. The session store gains searchEntries backed by Postgres full-text search: an immutable text-extraction helper with a partial GIN expression index over user/assistant/text entries, and prefix-match tsquery so results feel type-ahead; the memory store mirrors the semantics for tests and dev. The SQL joins participants and enforces the same visibility-window predicate the transcript uses, with viewer-level filtering applied again at the app layer, and the route is exposed user-scoped as GET /v1/sessions/search. The palette is debounced, aborts stale fetches, groups hits by session, highlights terms, and is keyboard-first. **Deployment notes** MIGRATION Release-note the one-time index build on session_entries; large deployments may want to pre-create the index CONCURRENTLY before upgrading Confirm the safe_json boot DDL is already present upstream (it predates this change in the fork) New GIN full-text index on session_entries created at boot via plain CREATE INDEX IF NOT EXISTS (not CONCURRENTLY) in the pg store's boot DDL — idempotent, but on a deployment with a large session_entries table the build blocks writes to that table and delays the new instance's boot for the build duration; blue-green reads keep working on the old instance, writes stall New plpgsql function entry_search_text created with CREATE OR REPLACE (idempotent); the search SQL also calls the pre-existing safe_json() boot function — verify upstream already carries that DDL before this lands New endpoint GET /v1/sessions/search + web-ui /api/search: during the mixed window a new web-ui against an old core gets 404 (palette shows no results; no data risk) Rollback safe: old code ignores the index and function; no data rewrite, old entries are searchable as-is <!-- codesmith:footer --> --- <a href="https://app.blacksmith.sh/yc-software/codesmith/qm/pr/455"><picture><source media="(prefers-color-scheme: dark)" srcset="https://pr-comments-assets.blacksmith.sh/codesmith/view-with-codesmith-dark-v2.svg"><source media="(prefers-color-scheme: light)" srcset="https://pr-comments-assets.blacksmith.sh/codesmith/view-with-codesmith-light-v2.svg"><img alt="View with [code]smith" src="https://pr-comments-assets.blacksmith.sh/codesmith/view-with-codesmith-dark-v2.svg"></picture></a> <a href="https://backend.blacksmith.sh/track/enable-autofix?expires=1789245864&installation_model_id=19911&pr_number=455&repository=yc-software%2Fqm&return_to=https%3A%2F%2Fgithub.com%2Fyc-software%2Fqm%2Fpull%2F455&signature=499014bb040755d6b4ce9b5756fea5a1f8d3b6a228ff317c6df4b492df63bdf0"><picture><source media="(prefers-color-scheme: dark)" srcset="https://pr-comments-assets.blacksmith.sh/codesmith/autofix-with-codesmith-dark.svg"><source media="(prefers-color-scheme: light)" srcset="https://pr-comments-assets.blacksmith.sh/codesmith/autofix-with-codesmith-light.svg"><img alt="Autofix with [code]smith" src="https://pr-comments-assets.blacksmith.sh/codesmith/autofix-with-codesmith-dark.svg"></picture></a> <sup>Need help on this PR? Tag <code>@codesmith-bot</code> with what you need. Autofix is disabled.</sup> <!-- codesmith:autofix:disabled --> <!-- /codesmith:footer -->
R
Regan Bell committed
db3ee653d053ea7c9c0254f15a0647f909fef38a
Parent: 73f7c00
Committed by GitHub <noreply@github.com>
on 8/13/2026, 11:20:44 PM