technicalpickles / technicalpickles/cq

Explore semantic/similarity search via DuckDB vss extension

Open
#39 4 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Dominant language
Rust
Stars
11
Forks
1
Avg merge
4h 43m
Merged PRs (30d)
22

Description

Right now cq search is keyword-only: `--grep` does substring/ILIKE matching, and `cq sql` is raw SQL over the DuckDB views. That covers "I remember roughly what I typed" but not "find sessions where I was doing something like X" when the wording doesn't match.

DuckDB has a first-party answer for this: the vss extension. It adds FIXED_SIZE_ARRAY(FLOAT, N) columns, HNSW indexing, and distance functions (array_distance, array_cosine_similarity) for ANN queries. Since cq is already DuckDB under the hood, this is schema and pipeline work, not a new storage engine.

Filing this to explore, not as a committed plan. There's real work and some open questions before this is worth building.

What it would take

  • Embeddings, not just storage. vss handles the vector index, but something still has to turn message/tool-result text into vectors in the first place. Nothing in cq's sync pipeline does that today. Needs a model choice (local, e.g. something on Ollama, vs. an API call) and a call on cost/latency per row.
  • Fits the incremental sync model. cq's whole design is incremental caching of JSONL into DuckDB. Embedding would need to slot into that the same way: only new/changed rows get embedded, not a full rebuild every sync.
  • HNSW persistence is still a little sketchy. Durable HNSW indexes to disk went through an experimental flag (SET hnsw_enable_experimental_persistence = true) for a while. Worth checking current DuckDB's status on that before leaning on it, since cq's cache DB is expected to survive across runs. If it's not solid, that's an index rebuild on every sync, which changes the sync-time budget.
  • What actually gets embedded. Full message text? Chunked? Do tool results get embedded too, or just messages? Answering this affects both index size and what "similar" ends up meaning.
  • Query surface. New subcommand, or a --semantic flag on an existing one? However it lands, it needs to compose with the existing scope flags (--project, --session, --since) the same way keyword search does.
  • Model churn. If the embedding model changes later, old vectors are stale. Need a plan for detecting that and re-embedding, even if it's just "bump a schema version and rebuild."

Why explore this now

qmd already does semantic search well, but only over markdown docs, not session transcripts. cq is the tool that actually has the transcripts. If semantic search on sessions is worth having, this is the natural place for it.

Contributor guide

No contributing guide indexed for this repository

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start with the existing cq search, --grep, cq sql, and incremental sync pipeline, then verify DuckDB vss persistence and embedding options. Decide what text is embedded, how model version changes are handled, and how semantic queries compose with --project, --session, and --since; done means a documented implementation direction with its storage, cost, and rebuild implications.

Written by the indexing model from the issue text.

Assessment

Tech stack
rust, sql
Domain
backend, databases, search
Issue type
Feature
Difficulty
5/5
Estimated time
Over a week
Activity status
Active
Clarity
Needs clarification
Newbie friendliness
25/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.