sverklo 0.12.4 → 0.16.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (187) hide show
  1. package/README.md +79 -9
  2. package/dist/bin/sverklo.js +483 -22
  3. package/dist/bin/sverklo.js.map +1 -1
  4. package/dist/src/digest.d.ts +8 -0
  5. package/dist/src/digest.js +59 -0
  6. package/dist/src/digest.js.map +1 -0
  7. package/dist/src/doctor.js +23 -6
  8. package/dist/src/doctor.js.map +1 -1
  9. package/dist/src/indexer/concept-labeler.d.ts +25 -0
  10. package/dist/src/indexer/concept-labeler.js +117 -0
  11. package/dist/src/indexer/concept-labeler.js.map +1 -0
  12. package/dist/src/indexer/doc-linker.d.ts +21 -0
  13. package/dist/src/indexer/doc-linker.js +201 -0
  14. package/dist/src/indexer/doc-linker.js.map +1 -0
  15. package/dist/src/indexer/graph-builder.js +33 -3
  16. package/dist/src/indexer/graph-builder.js.map +1 -1
  17. package/dist/src/indexer/indexer.d.ts +12 -0
  18. package/dist/src/indexer/indexer.js +71 -2
  19. package/dist/src/indexer/indexer.js.map +1 -1
  20. package/dist/src/indexer/parser-ipynb.d.ts +2 -0
  21. package/dist/src/indexer/parser-ipynb.js +92 -0
  22. package/dist/src/indexer/parser-ipynb.js.map +1 -0
  23. package/dist/src/indexer/parser-md.d.ts +2 -0
  24. package/dist/src/indexer/parser-md.js +123 -0
  25. package/dist/src/indexer/parser-md.js.map +1 -0
  26. package/dist/src/indexer/parser.js +172 -0
  27. package/dist/src/indexer/parser.js.map +1 -1
  28. package/dist/src/indexer/pattern-labeler.d.ts +20 -0
  29. package/dist/src/indexer/pattern-labeler.js +101 -0
  30. package/dist/src/indexer/pattern-labeler.js.map +1 -0
  31. package/dist/src/indexer/symbol-purpose.d.ts +21 -0
  32. package/dist/src/indexer/symbol-purpose.js +88 -0
  33. package/dist/src/indexer/symbol-purpose.js.map +1 -0
  34. package/dist/src/init.js +45 -14
  35. package/dist/src/init.js.map +1 -1
  36. package/dist/src/memory/evidence-emit.d.ts +13 -0
  37. package/dist/src/memory/evidence-emit.js +24 -0
  38. package/dist/src/memory/evidence-emit.js.map +1 -0
  39. package/dist/src/memory/evidence.d.ts +28 -0
  40. package/dist/src/memory/evidence.js +147 -0
  41. package/dist/src/memory/evidence.js.map +1 -0
  42. package/dist/src/memory/import.d.ts +1 -0
  43. package/dist/src/memory/import.js +7 -0
  44. package/dist/src/memory/import.js.map +1 -1
  45. package/dist/src/memory/prune.d.ts +25 -0
  46. package/dist/src/memory/prune.js +195 -0
  47. package/dist/src/memory/prune.js.map +1 -0
  48. package/dist/src/search/bundle.d.ts +35 -0
  49. package/dist/src/search/bundle.js +120 -0
  50. package/dist/src/search/bundle.js.map +1 -0
  51. package/dist/src/search/compact.d.ts +17 -0
  52. package/dist/src/search/compact.js +103 -0
  53. package/dist/src/search/compact.js.map +1 -0
  54. package/dist/src/search/hybrid-search.d.ts +2 -0
  55. package/dist/src/search/hybrid-search.js +41 -15
  56. package/dist/src/search/hybrid-search.js.map +1 -1
  57. package/dist/src/search/investigate.d.ts +48 -0
  58. package/dist/src/search/investigate.js +509 -0
  59. package/dist/src/search/investigate.js.map +1 -0
  60. package/dist/src/search/partition.d.ts +33 -0
  61. package/dist/src/search/partition.js +133 -0
  62. package/dist/src/search/partition.js.map +1 -0
  63. package/dist/src/search/post-filter.d.ts +36 -0
  64. package/dist/src/search/post-filter.js +124 -0
  65. package/dist/src/search/post-filter.js.map +1 -0
  66. package/dist/src/search/synonyms.d.ts +18 -0
  67. package/dist/src/search/synonyms.js +113 -0
  68. package/dist/src/search/synonyms.js.map +1 -0
  69. package/dist/src/search/token-budget.d.ts +1 -1
  70. package/dist/src/search/token-budget.js +36 -9
  71. package/dist/src/search/token-budget.js.map +1 -1
  72. package/dist/src/server/audit-html.js +6 -5
  73. package/dist/src/server/audit-html.js.map +1 -1
  74. package/dist/src/server/dashboard-html.js +63 -9
  75. package/dist/src/server/dashboard-html.js.map +1 -1
  76. package/dist/src/server/http-server.js +5 -1
  77. package/dist/src/server/http-server.js.map +1 -1
  78. package/dist/src/server/mcp-server.js +171 -2
  79. package/dist/src/server/mcp-server.js.map +1 -1
  80. package/dist/src/server/prompts.js +75 -0
  81. package/dist/src/server/prompts.js.map +1 -1
  82. package/dist/src/server/response-store.d.ts +16 -0
  83. package/dist/src/server/response-store.js +57 -0
  84. package/dist/src/server/response-store.js.map +1 -0
  85. package/dist/src/server/tool-overrides.d.ts +4 -2
  86. package/dist/src/server/tool-overrides.js +107 -6
  87. package/dist/src/server/tool-overrides.js.map +1 -1
  88. package/dist/src/server/tools/_validation.d.ts +15 -0
  89. package/dist/src/server/tools/_validation.js +31 -0
  90. package/dist/src/server/tools/_validation.js.map +1 -0
  91. package/dist/src/server/tools/ask.d.ts +25 -0
  92. package/dist/src/server/tools/ask.js +115 -0
  93. package/dist/src/server/tools/ask.js.map +1 -0
  94. package/dist/src/server/tools/ast-grep.js +29 -2
  95. package/dist/src/server/tools/ast-grep.js.map +1 -1
  96. package/dist/src/server/tools/audit.js +5 -1
  97. package/dist/src/server/tools/audit.js.map +1 -1
  98. package/dist/src/server/tools/clusters.js +6 -2
  99. package/dist/src/server/tools/clusters.js.map +1 -1
  100. package/dist/src/server/tools/concepts.d.ts +20 -0
  101. package/dist/src/server/tools/concepts.js +75 -0
  102. package/dist/src/server/tools/concepts.js.map +1 -0
  103. package/dist/src/server/tools/context.js +7 -7
  104. package/dist/src/server/tools/context.js.map +1 -1
  105. package/dist/src/server/tools/critique.d.ts +30 -0
  106. package/dist/src/server/tools/critique.js +175 -0
  107. package/dist/src/server/tools/critique.js.map +1 -0
  108. package/dist/src/server/tools/ctx-handles.d.ts +60 -0
  109. package/dist/src/server/tools/ctx-handles.js +130 -0
  110. package/dist/src/server/tools/ctx-handles.js.map +1 -0
  111. package/dist/src/server/tools/find-references.js +45 -0
  112. package/dist/src/server/tools/find-references.js.map +1 -1
  113. package/dist/src/server/tools/forget.js +5 -1
  114. package/dist/src/server/tools/forget.js.map +1 -1
  115. package/dist/src/server/tools/impact.d.ts +4 -0
  116. package/dist/src/server/tools/impact.js +19 -0
  117. package/dist/src/server/tools/impact.js.map +1 -1
  118. package/dist/src/server/tools/investigate.d.ts +32 -0
  119. package/dist/src/server/tools/investigate.js +58 -0
  120. package/dist/src/server/tools/investigate.js.map +1 -0
  121. package/dist/src/server/tools/overview.d.ts +4 -0
  122. package/dist/src/server/tools/overview.js +19 -1
  123. package/dist/src/server/tools/overview.js.map +1 -1
  124. package/dist/src/server/tools/patterns.d.ts +20 -0
  125. package/dist/src/server/tools/patterns.js +74 -0
  126. package/dist/src/server/tools/patterns.js.map +1 -0
  127. package/dist/src/server/tools/post-filter.d.ts +63 -0
  128. package/dist/src/server/tools/post-filter.js +72 -0
  129. package/dist/src/server/tools/post-filter.js.map +1 -0
  130. package/dist/src/server/tools/recall.d.ts +5 -0
  131. package/dist/src/server/tools/recall.js +29 -12
  132. package/dist/src/server/tools/recall.js.map +1 -1
  133. package/dist/src/server/tools/remember.d.ts +5 -0
  134. package/dist/src/server/tools/remember.js +55 -25
  135. package/dist/src/server/tools/remember.js.map +1 -1
  136. package/dist/src/server/tools/search-iterative.d.ts +23 -0
  137. package/dist/src/server/tools/search-iterative.js +136 -0
  138. package/dist/src/server/tools/search-iterative.js.map +1 -0
  139. package/dist/src/server/tools/search.d.ts +14 -0
  140. package/dist/src/server/tools/search.js +78 -5
  141. package/dist/src/server/tools/search.js.map +1 -1
  142. package/dist/src/server/tools/verify.d.ts +23 -0
  143. package/dist/src/server/tools/verify.js +78 -0
  144. package/dist/src/server/tools/verify.js.map +1 -0
  145. package/dist/src/server/tools/wakeup.js +5 -1
  146. package/dist/src/server/tools/wakeup.js.map +1 -1
  147. package/dist/src/server/trajectory.d.ts +18 -0
  148. package/dist/src/server/trajectory.js +70 -0
  149. package/dist/src/server/trajectory.js.map +1 -0
  150. package/dist/src/storage/chunk-store.d.ts +5 -0
  151. package/dist/src/storage/chunk-store.js +12 -0
  152. package/dist/src/storage/chunk-store.js.map +1 -1
  153. package/dist/src/storage/concept-store.d.ts +46 -0
  154. package/dist/src/storage/concept-store.js +79 -0
  155. package/dist/src/storage/concept-store.js.map +1 -0
  156. package/dist/src/storage/database.d.ts +1 -1
  157. package/dist/src/storage/database.js +142 -2
  158. package/dist/src/storage/database.js.map +1 -1
  159. package/dist/src/storage/doc-edge-store.d.ts +55 -0
  160. package/dist/src/storage/doc-edge-store.js +115 -0
  161. package/dist/src/storage/doc-edge-store.js.map +1 -0
  162. package/dist/src/storage/evidence-store.d.ts +55 -0
  163. package/dist/src/storage/evidence-store.js +126 -0
  164. package/dist/src/storage/evidence-store.js.map +1 -0
  165. package/dist/src/storage/handle-store.d.ts +32 -0
  166. package/dist/src/storage/handle-store.js +77 -0
  167. package/dist/src/storage/handle-store.js.map +1 -0
  168. package/dist/src/storage/memory-embedding-store.d.ts +23 -0
  169. package/dist/src/storage/memory-embedding-store.js +92 -4
  170. package/dist/src/storage/memory-embedding-store.js.map +1 -1
  171. package/dist/src/storage/memory-store.d.ts +17 -2
  172. package/dist/src/storage/memory-store.js +50 -4
  173. package/dist/src/storage/memory-store.js.map +1 -1
  174. package/dist/src/storage/pattern-store.d.ts +42 -0
  175. package/dist/src/storage/pattern-store.js +106 -0
  176. package/dist/src/storage/pattern-store.js.map +1 -0
  177. package/dist/src/telemetry/index.d.ts +3 -0
  178. package/dist/src/telemetry/index.js.map +1 -1
  179. package/dist/src/types/index.d.ts +26 -1
  180. package/dist/src/types/index.js +2 -0
  181. package/dist/src/types/index.js.map +1 -1
  182. package/dist/src/utils/ollama.d.ts +41 -0
  183. package/dist/src/utils/ollama.js +100 -0
  184. package/dist/src/utils/ollama.js.map +1 -0
  185. package/package.json +5 -3
  186. package/src/skills/sverklo-onboard.md +2 -0
  187. package/src/skills/sverklo-refactor.md +2 -0
package/README.md CHANGED
@@ -1,7 +1,9 @@
1
- # Sverklo
1
+ <p align="left">
2
+ <img src="./docs/logo.svg" alt="sverklo" width="280" height="79"/>
3
+ </p>
2
4
 
3
- > **Hallucination-resistant code intelligence for Claude Code, Cursor, Windsurf, and Zed.**
4
- > Semantic search, impact analysis, persistent memory — pick 3. Local, MIT, zero config.
5
+ > **Stop your AI from making things up about your codebase.**
6
+ > Local-first MCP server that gives Claude Code, Cursor, Windsurf, and Zed a real symbol graph, a blast-radius lens, and a git-pinned memory — so the agent stops guessing. MIT. Zero config. Your code never leaves the machine.
5
7
 
6
8
  [![npm version](https://img.shields.io/npm/v/sverklo.svg?color=E85A2A)](https://www.npmjs.com/package/sverklo)
7
9
  [![npm downloads](https://img.shields.io/npm/dw/sverklo.svg?color=E85A2A)](https://www.npmjs.com/package/sverklo)
@@ -12,13 +14,13 @@
12
14
 
13
15
  ## Why
14
16
 
15
- Your AI agent edits `UserService.validate()`. It doesn't know 47 other functions call it. It hallucinates an import. It forgets the design decision you made yesterday because context was compacted. Tests pass because they mock the dependency. Breaking changes ship.
17
+ Your AI agent edits `UserService.validate()`. It doesn't know 47 other functions call it. It hallucinates `getUserByEmail()` because that's how its training data spelled it — your code uses `findByEmail()`. It forgets the design decision you made yesterday because context was compacted. Tests pass because they mock the dependency. Breaking changes ship.
16
18
 
17
- Sverklo (Russian: *сверкло*, "drill") gives your agent a structural understanding of your codebase — symbol graph, blast radius, semantic recall, and git-pinned memory — so it stops guessing.
19
+ Sverklo drills into your repo before the agent does — symbol graph, blast radius, semantic recall, and git-pinned memory — so the agent reasons about *your* code instead of pattern-matching from training data.
18
20
 
19
21
  <table>
20
22
  <tr>
21
- <td align="center"><b>20</b><br/>MCP tools your agent uses</td>
23
+ <td align="center"><b>37</b><br/>MCP tools your agent uses</td>
22
24
  <td align="center"><b>&lt; 2 s</b><br/>to index a 1,700-file monorepo</td>
23
25
  <td align="center"><b>0 bytes</b><br/>of your code leave the machine</td>
24
26
  </tr>
@@ -31,7 +33,7 @@ cd your-project && sverklo init
31
33
 
32
34
  That's it. `sverklo init` auto-detects your installed AI coding agent (Claude Code, Cursor, Windsurf, Zed), writes the right MCP config, appends instructions to your `CLAUDE.md`, and runs `sverklo doctor` to verify the setup. **No API keys. No cloud. Telemetry off by default.**
33
35
 
34
- > **First-run note.** Sverklo's embedding model (`all-MiniLM-L6-v2` ONNX, ~86 MB) is downloaded from HuggingFace on first use into `~/.sverklo/models/` and cached forever — every subsequent run is fully offline. Bundling the model into the npm tarball is on the v0.13 roadmap.
36
+ > The embedding model (`all-MiniLM-L6-v2` ONNX, ~86 MB) is downloaded from HuggingFace on first use into `~/.sverklo/models/` and cached forever — every subsequent run is fully offline.
35
37
 
36
38
  **Want proof before installing?** Browse the [/report leaderboard](https://sverklo.com/report) — Sverklo audits of 47 popular OSS repos (express, react-hook-form, vite, lodash, prisma, …) with grade cards for dead code, circular deps, coupling, and security.
37
39
 
@@ -77,7 +79,7 @@ If the answer to your question is "exact string X exists somewhere," grep wins.
77
79
  | `sverklo_impact` | Walk the symbol graph, return ranked transitive callers — the real blast radius. |
78
80
  | `sverklo_review_diff` | Risk-scored review of `git diff`: touched-symbol importance x coverage x churn. |
79
81
 
80
- [See all 23 tools below.](#full-tool-reference)
82
+ [See all 37 tools below.](#full-tool-reference)
81
83
 
82
84
  <details>
83
85
  <summary><h2>Full tool reference</h2></summary>
@@ -145,6 +147,48 @@ If a launch post tells you a tool is great for everything, close the tab.
145
147
 
146
148
  ---
147
149
 
150
+ ## Common questions
151
+
152
+ ### How do I stop Claude Code from hallucinating about my codebase?
153
+
154
+ Claude generates code from training-data patterns, not your repo. Without a symbol graph, it invents `getUserByEmail()` when your code uses `findByEmail()`. Sverklo grounds the agent in your actual symbol graph — `sverklo_lookup` and `sverklo_refs` resolve names to `file:line` and prove existence before the agent writes the call. Verifiable retrieval (`sverklo_verify`) lets the agent re-check that a quoted span is still present at the cited SHA, so a stale citation gets caught instead of confabulated.
155
+
156
+ ### Is there a local-first MCP server for codebase memory?
157
+
158
+ Yes — sverklo. `sverklo_remember` and `sverklo_recall` ship a bi-temporal memory layer: every memory is pinned to the git SHA it was authored on, and `valid_until_sha` + `superseded_by` preserve a timeline of supersessions instead of overwriting. Recall is hybrid (FTS5 + cosine over an ONNX embedding) and runs entirely in embedded SQLite. No cloud, no API keys, no external vector database — unlike most "memory MCP" projects which require Zilliz, Milvus, or a managed Postgres+pgvector.
159
+
160
+ ### Is there an open-source alternative to Sourcegraph Cody I can run locally?
161
+
162
+ Sverklo is the open-source local alternative to Sourcegraph Cody for codebase Q&A: hybrid BM25 + vector + PageRank retrieval, symbol-graph navigation, MIT-licensed instead of source-available, single-machine instead of Cody's enterprise deployment, and free instead of $9–19 per developer per month. Sverklo doesn't try to ship the same feature set — it's a primitives layer for AI coding agents (37 MCP tools), not a hosted IDE plug-in — but for the "give the agent semantic understanding of my codebase" job, it covers the same surface.
163
+
164
+ ### Where does my code go when I use sverklo?
165
+
166
+ Nowhere. Sverklo runs entirely on your machine. Indexing, search, embeddings, audits, and PR review all execute locally with embedded SQLite plus a local ONNX embedding model. The model itself is downloaded from HuggingFace on first run (~86 MB), cached in `~/.sverklo/models/`, and never touched again. Telemetry is opt-in and off by default — sverklo makes zero network calls unless you explicitly run `sverklo telemetry enable`.
167
+
168
+ ### Does sverklo work with Cursor's @codebase or Cursor Tab?
169
+
170
+ Sverklo runs alongside Cursor's built-in indexing rather than replacing it. Cursor's @codebase ships embedding-based search inside the IDE; sverklo adds the symbol graph, blast radius, diff-aware risk-scored review, and bi-temporal memory that Cursor doesn't expose. Wire sverklo as an MCP server in Cursor and both layers are available to the agent simultaneously. The same setup works for Claude Code, Windsurf, Zed, Antigravity, and anything else that speaks MCP.
171
+
172
+ ---
173
+
174
+ ## Three retrieval techniques you'll only find here
175
+
176
+ Most code-search MCPs are a single BM25 + vector RRF on top of Milvus or pgvector. Sverklo's recall is built on three named moves that work because they exploit *codebase structure*, not just text similarity. Each one was added to close a real recall failure on real questions; together they're the reason sverklo's research benchmark hits 99% recall (31 of 32) without a managed vector database.
177
+
178
+ ### 1. Filename-as-signal retrieval
179
+
180
+ When a query token matches a *filename* — even when the body of that file doesn't FTS-match — sverklo pulls every named definition in that file into the candidate set. Conversely, when FTS surfaces a file at all (because of a comment hit, an import line, anything), every definition in that file becomes a plausible answer. This is the single move that closes the "private helper function" gap: the function is too short for embeddings to disambiguate and uses a name no one would `grep` for, but it lives next to the code that *does* match. Implemented in `src/search/investigate.ts` (`runDefinitionsByPathTokens`, `runDefinitionsInFtsFiles`).
181
+
182
+ ### 2. Channelized RRF fusion
183
+
184
+ Most hybrid retrievers run *one* Reciprocal Rank Fusion over `fts ∪ vector` and call it a day. Sverklo runs RRF *per channel* — FTS, vector, doc-section, path, symbol-name — then fuses the per-channel ranks with channel-specific weights. The path channel is weighted **1.5×** because filename matches are precision-skewed; doc chunks score in their own channel so a 200-line markdown section can't drown a 4-line function body. This is structural retrieval, not just lexical-vs-semantic. Implemented in `src/search/investigate.ts` (per-channel RRF + weighted fusion).
185
+
186
+ ### 3. Bi-temporal memory with `superseded_by` lineage
187
+
188
+ Every memory carries `valid_from_sha` and `valid_until_sha`. Updating a memory doesn't overwrite — it inserts a new row, sets `valid_until_sha` on the old one, and links them via `superseded_by`. Recall queries naturally exclude invalidated rows, but the timeline view keeps everything, so you can ask "what did this team believe about the auth flow at commit `abc123`?" and get the answer that was true *then*. `sverklo prune` consolidates clusters of similar episodic memories into one semantic note while preserving the lineage. Implemented across `src/storage/memory-store.ts` and `src/memory/prune.ts`.
189
+
190
+ ---
191
+
148
192
  ## How It Works
149
193
 
150
194
  ```mermaid
@@ -256,6 +300,32 @@ Sverklo ships a CLI for CI and local use: `sverklo review --ci --fail-on high` f
256
300
 
257
301
  ---
258
302
 
303
+ ## Claude Code hooks recipe
304
+
305
+ Sverklo plays well with [Claude Code hooks](https://docs.claude.com/claude-code/hooks). The simplest hook to wire is a post-tool-use review: after Claude makes file edits, run `sverklo review` against the working tree and surface any high-risk findings in the agent transcript. Add this to `~/.claude/settings.json`:
306
+
307
+ ```json
308
+ {
309
+ "hooks": {
310
+ "PostToolUse": [
311
+ {
312
+ "matcher": "Edit|Write",
313
+ "hooks": [
314
+ {
315
+ "type": "command",
316
+ "command": "sverklo review --ref HEAD --format json --fail-on high || true"
317
+ }
318
+ ]
319
+ }
320
+ ]
321
+ }
322
+ }
323
+ ```
324
+
325
+ The trailing `|| true` keeps the hook from blocking edits when sverklo isn't installed or the working tree has no diff yet. For project-scoped hooks, put the same block in `.claude/settings.json` at the repo root instead.
326
+
327
+ ---
328
+
259
329
  ## Telemetry
260
330
 
261
331
  **Off by default.** Sverklo makes zero network calls unless you explicitly run `sverklo telemetry enable`. If you opt in, we collect only anonymous usage metrics (no code, no queries, no file paths). Full schema and implementation details in [`TELEMETRY.md`](./TELEMETRY.md).
@@ -264,7 +334,7 @@ Sverklo ships a CLI for CI and local use: `sverklo review --ci --fail-on high` f
264
334
 
265
335
  ## Open Source, Open Core
266
336
 
267
- The full MCP server is **free and open source** (MIT). All 23 tools, no limits, no telemetry, no "free tier" — that's not where the line is.
337
+ The full MCP server is **free and open source** (MIT). All 37 tools, no limits, no telemetry, no "free tier" — that's not where the line is.
268
338
 
269
339
  **Sverklo Pro** (later this year) adds smart auto-capture of decisions, cross-project pattern learning, and larger embedding models. **Sverklo Team** adds shared team memory and on-prem deployment.
270
340