nano-brain 2026.1.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 (79) hide show
  1. package/AGENTS_SNIPPET.md +36 -0
  2. package/CHANGELOG.md +68 -0
  3. package/README.md +281 -0
  4. package/SKILL.md +153 -0
  5. package/bin/cli.js +18 -0
  6. package/index.html +929 -0
  7. package/nano-brain +4 -0
  8. package/opencode-mcp.json +9 -0
  9. package/openspec/changes/archive/2026-02-16-fix-mcp-server-bugs/.openspec.yaml +2 -0
  10. package/openspec/changes/archive/2026-02-16-fix-mcp-server-bugs/design.md +68 -0
  11. package/openspec/changes/archive/2026-02-16-fix-mcp-server-bugs/proposal.md +27 -0
  12. package/openspec/changes/archive/2026-02-16-fix-mcp-server-bugs/specs/mcp-integration-testing/spec.md +50 -0
  13. package/openspec/changes/archive/2026-02-16-fix-mcp-server-bugs/specs/mcp-server/spec.md +40 -0
  14. package/openspec/changes/archive/2026-02-16-fix-mcp-server-bugs/specs/search-pipeline/spec.md +29 -0
  15. package/openspec/changes/archive/2026-02-16-fix-mcp-server-bugs/tasks.md +37 -0
  16. package/openspec/changes/archive/2026-02-23-workspace-scoped-memory-and-storage-limits/.openspec.yaml +2 -0
  17. package/openspec/changes/archive/2026-02-23-workspace-scoped-memory-and-storage-limits/design.md +111 -0
  18. package/openspec/changes/archive/2026-02-23-workspace-scoped-memory-and-storage-limits/proposal.md +30 -0
  19. package/openspec/changes/archive/2026-02-23-workspace-scoped-memory-and-storage-limits/specs/mcp-server/spec.md +33 -0
  20. package/openspec/changes/archive/2026-02-23-workspace-scoped-memory-and-storage-limits/specs/storage-limits/spec.md +90 -0
  21. package/openspec/changes/archive/2026-02-23-workspace-scoped-memory-and-storage-limits/specs/workspace-scoping/spec.md +66 -0
  22. package/openspec/changes/archive/2026-02-23-workspace-scoped-memory-and-storage-limits/tasks.md +199 -0
  23. package/openspec/changes/codebase-indexing/.openspec.yaml +2 -0
  24. package/openspec/changes/codebase-indexing/design.md +169 -0
  25. package/openspec/changes/codebase-indexing/proposal.md +30 -0
  26. package/openspec/changes/codebase-indexing/specs/codebase-collection/spec.md +187 -0
  27. package/openspec/changes/codebase-indexing/specs/mcp-server/spec.md +36 -0
  28. package/openspec/changes/codebase-indexing/tasks.md +56 -0
  29. package/openspec/specs/mcp-integration-testing/spec.md +50 -0
  30. package/openspec/specs/mcp-server/spec.md +75 -0
  31. package/openspec/specs/search-pipeline/spec.md +29 -0
  32. package/openspec/specs/storage-limits/spec.md +94 -0
  33. package/openspec/specs/workspace-scoping/spec.md +70 -0
  34. package/package.json +34 -0
  35. package/site/build.js +66 -0
  36. package/site/partials/_api.html +83 -0
  37. package/site/partials/_compare.html +100 -0
  38. package/site/partials/_config.html +23 -0
  39. package/site/partials/_features.html +43 -0
  40. package/site/partials/_footer.html +6 -0
  41. package/site/partials/_hero.html +9 -0
  42. package/site/partials/_how-it-works.html +26 -0
  43. package/site/partials/_models.html +18 -0
  44. package/site/partials/_quick-start.html +15 -0
  45. package/site/partials/_stats.html +1 -0
  46. package/site/partials/_tech-stack.html +13 -0
  47. package/site/script.js +12 -0
  48. package/site/shell.html +44 -0
  49. package/site/styles.css +548 -0
  50. package/src/chunker.ts +427 -0
  51. package/src/codebase.ts +331 -0
  52. package/src/collections.ts +192 -0
  53. package/src/embeddings.ts +293 -0
  54. package/src/expansion.ts +79 -0
  55. package/src/harvester.ts +306 -0
  56. package/src/index.ts +503 -0
  57. package/src/reranker.ts +103 -0
  58. package/src/search.ts +294 -0
  59. package/src/server.ts +664 -0
  60. package/src/storage.ts +221 -0
  61. package/src/store.ts +623 -0
  62. package/src/types.ts +202 -0
  63. package/src/watcher.ts +384 -0
  64. package/test/chunker.test.ts +479 -0
  65. package/test/cli.test.ts +309 -0
  66. package/test/codebase-chunker.test.ts +446 -0
  67. package/test/codebase.test.ts +678 -0
  68. package/test/collections.test.ts +571 -0
  69. package/test/harvester.test.ts +636 -0
  70. package/test/integration.test.ts +150 -0
  71. package/test/llm.test.ts +322 -0
  72. package/test/search.test.ts +572 -0
  73. package/test/server.test.ts +541 -0
  74. package/test/storage.test.ts +302 -0
  75. package/test/store.test.ts +465 -0
  76. package/test/watcher.test.ts +656 -0
  77. package/test/workspace.test.ts +239 -0
  78. package/tsconfig.json +19 -0
  79. package/vitest.config.ts +16 -0
@@ -0,0 +1,36 @@
1
+ <!-- OPENCODE-MEMORY:START -->
2
+ <!-- Managed block - do not edit manually. Updated by: npx nano-brain init -->
3
+
4
+ ## Memory System (nano-brain)
5
+
6
+ This project uses **nano-brain** for persistent context across sessions.
7
+
8
+ ### Quick Reference
9
+
10
+ | I want to... | Command |
11
+ |--------------|---------|
12
+ | Recall past work on a topic | `memory_query("topic")` |
13
+ | Find exact error/function name | `memory_search("exact term")` |
14
+ | Explore a concept semantically | `memory_vsearch("concept")` |
15
+ | Save a decision for future sessions | `memory_write("decision context")` |
16
+ | Check index health | `memory_status` |
17
+
18
+ ### Session Workflow
19
+
20
+ **Start of session:** Check memory for relevant past context before exploring the codebase.
21
+ ```
22
+ memory_query("what have we done regarding {current task topic}")
23
+ ```
24
+
25
+ **End of session:** Save key decisions, patterns discovered, and debugging insights.
26
+ ```
27
+ memory_write("## Summary\n- Decision: ...\n- Why: ...\n- Files: ...")
28
+ ```
29
+
30
+ ### When to Search Memory vs Codebase
31
+
32
+ - **"Have we done this before?"** → `memory_query` (searches past sessions)
33
+ - **"Where is this in the code?"** → grep / ast-grep (searches current files)
34
+ - **"How does this concept work here?"** → Both (memory for past context + grep for current code)
35
+
36
+ <!-- OPENCODE-MEMORY:END -->
package/CHANGELOG.md ADDED
@@ -0,0 +1,68 @@
1
+ # Changelog
2
+
3
+ ## [2026.1.0] - 2026-02-23
4
+
5
+ ### Added
6
+
7
+ - **AI agent routing instructions (SKILL.md)**: Enhanced SKILL.md with trigger phrases, when-to-use rules, tool selection guide, collection filtering, and integration patterns for orchestrator and subagent workflows. Agents now auto-route to memory for recall, past decisions, cross-session context, and repeated patterns.
8
+ - **AGENTS_SNIPPET.md**: Optional managed block for project-level AGENTS.md installation. Provides quick reference table, session workflow (start/end), and memory vs codebase search guidance. Designed for `npx nano-brain init` injection.
9
+ - **`memory_index_codebase` documented**: Added to SKILL.md, README, and site API reference.
10
+ - **`workspace` parameter documented**: Added to search tool docs showing workspace scoping.
11
+
12
+ ## [0.3.0] - 2026-02-23
13
+
14
+ ### Added
15
+
16
+ - **Codebase indexing**: Opt-in source code indexing via `codebase: { enabled: true }` in config.yml. Indexes source files from the current workspace into the search pipeline for semantic code search.
17
+ - **Source code chunker**: Line-based chunking with structural boundary detection (function/class/type definitions, import blocks). Same 900-token target and 15% overlap as markdown chunker. Metadata headers (`File:`, `Language:`, `Lines:`) prepended to each chunk.
18
+ - **Project type auto-detection**: Detects project type from marker files (package.json, pyproject.toml, go.mod, Cargo.toml, etc.) and selects appropriate file extensions to index. Falls back to all common extensions.
19
+ - **Exclude pattern merging**: Combines exclude patterns from three sources: config `codebase.exclude`, `.gitignore`, and built-in defaults (node_modules, .git, dist, build, etc.).
20
+ - **Codebase storage budget**: Independent `codebase.maxSize` (default 2GB) limits codebase storage separately from session storage. Indexing stops when budget is exceeded. Storage usage reported in `memory_status`.
21
+ - **Max file size guard**: Skips files larger than `codebase.maxFileSize` (default 5MB) to avoid indexing generated/minified files.
22
+ - **`memory_index_codebase` MCP tool**: On-demand full codebase scan and index with summary stats (files scanned, indexed, skipped, storage usage).
23
+ - **Codebase stats in `memory_status`**: Shows enabled state, document count, storage used/limit, resolved extensions, and exclude pattern count.
24
+ - **Watcher integration**: File watcher monitors workspace directory for source code changes with exclude patterns, triggering incremental reindex.
25
+ - **`getCollectionStorageSize()`**: New Store method to query per-collection storage usage.
26
+ - **118 new tests**: `codebase.test.ts` (68 tests), `codebase-chunker.test.ts` (50 tests). Total: 428 tests.
27
+
28
+ ### Changed
29
+
30
+ - Increased vitest worker heap size to 8GB to prevent OOM during test runs with large test suites.
31
+
32
+ ## [0.2.0] - 2026-02-23
33
+
34
+ ### Added
35
+
36
+ - **Workspace scoping**: Search results are now scoped to the current workspace by default. Each workspace is identified by a SHA-256 hash of its directory path, matching the harvester convention. Cross-workspace search is available via `workspace: "all"` parameter.
37
+ - **Storage limits**: Configurable `maxSize` (default 2GB), `retention` (default 90d), and `minFreeDisk` (default 100MB) in `config.yml` under a `storage` section. Human-readable values like `500MB`, `30d`, `1y` are supported.
38
+ - **Disk safety guard**: Checks available disk space via `fs.statfsSync()` before writes. Skips harvest/reindex/embed when disk is critically low.
39
+ - **Retention-based eviction**: Automatically deletes harvested session markdown older than the retention period during each harvest cycle.
40
+ - **Size-based eviction**: If total storage exceeds `maxSize` after retention eviction, deletes oldest sessions until under limit. Original OpenCode session JSON is never touched.
41
+ - **Orphan embedding cleanup**: Removes embedding vectors for deleted documents every 10 harvest cycles.
42
+ - **Incremental harvesting**: Tracks session file mtimes in `.harvest-state.json` to skip unchanged files, reducing harvest time from O(all) to O(changed).
43
+ - **`workspace` parameter** on `memory_search`, `memory_vsearch`, and `memory_query` MCP tools. Omit for current workspace, `"all"` for cross-workspace.
44
+ - **Per-workspace stats** in `memory_status` output showing document counts per workspace hash.
45
+ - **45 new tests**: `workspace.test.ts` (18), `storage.test.ts` (27), plus integration tests in `server.test.ts` and `watcher.test.ts`. Total: 310 tests.
46
+
47
+ ### Changed
48
+
49
+ - Switched embedding model from EmbeddingGemma-300M (384d) to **nomic-embed-text-v1.5** (768d) for better search quality.
50
+ - Switched reranker from Qwen3-Reranker-0.6B to **bge-reranker-v2-m3** (8192 context) for improved reranking.
51
+ - Updated prompt format to nomic `search_query:`/`search_document:` convention.
52
+ - `documents` table now has a `project_hash` column with automatic migration and backfill on first startup.
53
+
54
+ ### Fixed
55
+
56
+ - Crash when session JSON has undefined `slug` field (now falls back to session id).
57
+
58
+ ## [0.1.0] - 2026-02-16
59
+
60
+ ### Added
61
+
62
+ - Initial release with hybrid search (BM25 + vector + LLM reranking).
63
+ - 8 MCP tools: `memory_search`, `memory_vsearch`, `memory_query`, `memory_get`, `memory_multi_get`, `memory_write`, `memory_status`, `memory_update`.
64
+ - SQLite storage with FTS5 and sqlite-vec.
65
+ - Heading-aware markdown chunking.
66
+ - YAML-configured collections with auto-indexing via chokidar.
67
+ - OpenCode session harvesting (JSON to markdown).
68
+ - GGUF model inference via node-llama-cpp.
package/README.md ADDED
@@ -0,0 +1,281 @@
1
+ # nano-brain
2
+
3
+ Persistent memory system for AI coding agents. Hybrid search (BM25 + vector + LLM reranking) across past sessions, codebase, curated notes, and daily logs.
4
+
5
+ ## What It Does
6
+
7
+ An MCP server that gives AI coding agents persistent memory across sessions. Indexes markdown documents, past sessions, and daily logs into a searchable SQLite database with FTS5 and vector embeddings. Provides 10 MCP tools for search, retrieval, and memory management using a sophisticated hybrid search pipeline with query expansion, RRF fusion, and neural reranking.
8
+
9
+ Inspired by [QMD](https://github.com/tobi/qmd) and [OpenClaw](https://github.com/openclaw/openclaw).
10
+
11
+ ## Architecture
12
+
13
+ ```
14
+ User Query
15
+
16
+
17
+ ┌─────────────────┐
18
+ │ Query Expansion │ ← qmd-query-expansion-1.7B (GGUF)
19
+ │ (optional) │ generates 2-3 query variants
20
+ └────────┬────────┘
21
+
22
+ ┌────┴────┐
23
+ ▼ ▼
24
+ ┌────────┐ ┌──────────┐
25
+ │ BM25 │ │ Vector │
26
+ │ (FTS5) │ │(sqlite- │
27
+ │ │ │ vec) │
28
+ └───┬────┘ └────┬─────┘
29
+ │ │
30
+ ▼ ▼
31
+ ┌─────────────────┐
32
+ │ RRF Fusion │ ← k=60, original query 2× weight
33
+ │ │
34
+ └────────┬────────┘
35
+
36
+
37
+ ┌─────────────────┐
38
+ │ LLM Reranking │ ← bge-reranker-v2-m3 (GGUF)
39
+ │ (optional) │
40
+ └────────┬────────┘
41
+
42
+
43
+ ┌─────────────────┐
44
+ │ Position-Aware │ ← top 3: 75/25, 4-10: 60/40, 11+: 40/60
45
+ │ Blending │ (RRF weight / rerank weight)
46
+ └────────┬────────┘
47
+
48
+
49
+ Final Results
50
+ ```
51
+
52
+ ## How It Works
53
+
54
+ ### Storage Layer
55
+
56
+ - **SQLite** via better-sqlite3 for document metadata and content
57
+ - **FTS5** virtual table with porter stemming for BM25 full-text search
58
+ - **sqlite-vec** extension for vector similarity search (cosine distance)
59
+ - **Content-addressed storage** using SHA-256 hash deduplication
60
+
61
+ ### Chunking
62
+
63
+ Heading-aware markdown chunking that respects document structure:
64
+
65
+ - **Target size:** 900 tokens (~3600 characters)
66
+ - **Overlap:** 15% between chunks (~540 characters)
67
+ - **Respects boundaries:** Code fences, headings, paragraphs
68
+ - **Break point scoring:** h1=100, h2=90, h3=80, code-fence=80, hr=60, blank-line=40
69
+
70
+ ### Search Pipeline (3 Tiers)
71
+
72
+ **`memory_search`** — BM25 only (fast, exact keyword matching)
73
+
74
+ **`memory_vsearch`** — Vector only (semantic similarity via embeddings)
75
+
76
+ **`memory_query`** — Full hybrid pipeline:
77
+ 1. Query expansion generates 2-3 variants (optional)
78
+ 2. Parallel BM25 + vector search
79
+ 3. RRF fusion (k=60, original query weighted 2×)
80
+ 4. LLM reranking with bge-reranker-v2-m3 (optional)
81
+ 5. Position-aware blending:
82
+ - Top 3 results: 75% RRF / 25% rerank
83
+ - Ranks 4-10: 60% RRF / 40% rerank
84
+ - Ranks 11+: 40% RRF / 60% rerank
85
+
86
+ ### Collections
87
+
88
+ - **YAML-configured** directories of markdown files
89
+ - **Auto-indexing** via chokidar file watcher
90
+ - **Incremental updates** using dirty-flag tracking
91
+ - **Session harvesting** converts OpenCode JSON sessions into searchable markdown
92
+
93
+ ## MCP Tools
94
+
95
+ | Tool | Description |
96
+ |------|-------------|
97
+ | `memory_search` | BM25 keyword search (fast) |
98
+ | `memory_vsearch` | Semantic vector search |
99
+ | `memory_query` | Full hybrid search with expansion + reranking |
100
+ | `memory_get` | Retrieve document by path or docid (#abc123) |
101
+ | `memory_multi_get` | Batch retrieve by glob pattern |
102
+ | `memory_write` | Write to daily log or MEMORY.md |
103
+ | `memory_status` | Index health, collections, model status |
104
+ | `memory_index_codebase` | Index codebase files in current workspace |
105
+ | `memory_update` | Trigger reindex of all collections |
106
+
107
+ ## Installation
108
+
109
+ ```bash
110
+ # Clone and install
111
+ git clone <repo-url>
112
+ cd nano-brain
113
+ npm install
114
+ ```
115
+
116
+ Add to OpenCode config (`~/.config/opencode/opencode.json`):
117
+
118
+ ```json
119
+ {
120
+ "mcp": {
121
+ "nano-brain": {
122
+ "type": "local",
123
+ "command": ["node", "/path/to/nano-brain/bin/cli.js", "mcp"],
124
+ "enabled": true
125
+ }
126
+ }
127
+ }
128
+ ```
129
+
130
+ ## Configuration
131
+
132
+ Create `~/.config/nano-brain/config.yml`:
133
+
134
+ ```yaml
135
+ collections:
136
+ memory:
137
+ path: ~/.nano-brain
138
+ pattern: "**/*.md"
139
+ update: auto
140
+
141
+ project-docs:
142
+ path: /path/to/project/docs
143
+ pattern: "**/*.md"
144
+ update: auto
145
+
146
+ sessions:
147
+ path: ~/.local/share/opencode/sessions
148
+ pattern: "**/*.json"
149
+ update: auto
150
+ ```
151
+
152
+ **Collection options:**
153
+ - `path` — Directory to index
154
+ - `pattern` — Glob pattern for files
155
+ - `update` — `auto` (watch for changes) or `manual`
156
+
157
+ ## CLI Usage
158
+
159
+ ```bash
160
+ # MCP server
161
+ nano-brain mcp # Start MCP server (stdio)
162
+ nano-brain mcp --http # Start MCP server (HTTP, port 8282)
163
+
164
+ # Index management
165
+ nano-brain status # Show index health
166
+ nano-brain update # Reindex all collections
167
+
168
+ # Search
169
+ nano-brain search "query" # BM25 search
170
+ nano-brain vsearch "query" # Vector search
171
+ nano-brain query "query" # Hybrid search
172
+
173
+ # Collections
174
+ nano-brain collection add <name> <path> # Add collection
175
+ nano-brain collection remove <name> # Remove collection
176
+ nano-brain collection list # List collections
177
+ ```
178
+
179
+ ## Project Structure
180
+
181
+ ```
182
+ src/
183
+ ├── index.ts # CLI entry point
184
+ ├── server.ts # MCP server (10 tools, stdio/HTTP)
185
+ ├── store.ts # SQLite storage (FTS5 + sqlite-vec)
186
+ ├── search.ts # Hybrid search pipeline (RRF, reranking, blending)
187
+ ├── chunker.ts # Heading-aware markdown chunking
188
+ ├── collections.ts # YAML config, collection scanning
189
+ ├── embeddings.ts # GGUF embedding model (nomic-embed-text-v1.5)
190
+ ├── reranker.ts # GGUF reranker model (bge-reranker-v2-m3)
191
+ ├── expansion.ts # GGUF query expansion (qmd-query-expansion-1.7B)
192
+ ├── harvester.ts # OpenCode session → markdown converter
193
+ ├── watcher.ts # File watcher (chokidar, dirty flags)
194
+ └── types.ts # TypeScript interfaces
195
+ bin/
196
+ └── cli.js # CLI wrapper
197
+
198
+ test/
199
+ └── *.test.ts # 428 tests (vitest)
200
+ SKILL.md # AI agent routing instructions (auto-loaded by OpenCode)
201
+ AGENTS_SNIPPET.md # Optional project-level AGENTS.md managed block
202
+ ```
203
+
204
+ ## Tech Stack
205
+
206
+ - **TypeScript + Node.js** (via tsx)
207
+ - **better-sqlite3** + **sqlite-vec** for storage
208
+ - **@modelcontextprotocol/sdk** for MCP server
209
+ - **node-llama-cpp** for GGUF model inference
210
+ - **chokidar** for file watching
211
+ - **vitest** for testing (428 tests)
212
+
213
+ ## Models
214
+
215
+ All models are GGUF format, loaded on-demand:
216
+
217
+ - **Embeddings:** nomic-embed-text-v1.5 (~270MB)
218
+ - **Reranker:** bge-reranker-v2-m3 (~1.1GB)
219
+ - **Query Expansion:** qmd-query-expansion-1.7B (~1GB)
220
+
221
+ Models are downloaded automatically on first use to `~/.cache/nano-brain/models/`.
222
+
223
+ ## How nano-brain Compares
224
+
225
+ | | nano-brain | Mem0 / OpenMemory | Zep / Graphiti | OMEGA | Letta (MemGPT) | Claude Native |
226
+ |---|---|---|---|---|---|---|
227
+ | **Search** | Hybrid (BM25 + vector + LLM reranking) | Vector only | Graph traversal + vector | Semantic + BM25 | Agent-managed | Text file read |
228
+ | **Storage** | SQLite (single file) | PostgreSQL + Qdrant | Neo4j | SQLite | PostgreSQL / SQLite | Flat text files |
229
+ | **MCP Tools** | 10 | 4-9 | 9-10 | 12 | 7 | 0 |
230
+ | **Local-First** | Yes (zero cloud) | Requires OpenAI API key | Requires Docker + Neo4j | Yes | Yes | Yes |
231
+ | **AI Models** | Local GGUF (nomic-embed, bge-reranker) | Cloud API (OpenAI) | Cloud API | Local ONNX | Cloud API | None |
232
+ | **Codebase Indexing** | Yes (structural boundary detection) | No | No | No | No | No |
233
+ | **Session Recall** | Yes (auto-harvests past sessions) | No | No | No | No | Limited (CLAUDE.md) |
234
+ | **Query Expansion** | Yes (local LLM) | No | No | No | No | No |
235
+ | **LLM Reranking** | Yes (bge-reranker-v2-m3) | No | No | No | No | No |
236
+ | **Privacy** | 100% local, no data leaves machine | Cloud API calls | Cloud or self-host | 100% local | Self-host or cloud | Local files |
237
+ | **Dependencies** | SQLite + GGUF models (~1.5GB) | Docker + PostgreSQL + Qdrant + OpenAI key | Docker + Neo4j | SQLite + ONNX | PostgreSQL | None |
238
+ | **Pricing** | Free (open source, MIT) | Free tier / Pro $249/mo | Free self-host / Cloud $25-475/mo | Free (Apache-2.0) | Free (Apache-2.0) | Free (with Claude) |
239
+ | **GitHub Stars** | New | ~47K | ~23K | ~25 | ~21K | N/A |
240
+
241
+ ### Where nano-brain shines
242
+
243
+ - **Hybrid search pipeline** — the only MCP memory server with BM25 + vector + query expansion + LLM reranking in a single pipeline
244
+ - **Codebase indexing** — index your source files with structural boundary detection, not just conversations
245
+ - **Session recall** — automatically harvests and indexes past AI coding sessions
246
+ - **Zero dependencies** — single SQLite file, local GGUF models, no Docker/PostgreSQL/Neo4j/API keys
247
+ - **Privacy** — 100% local processing, your code and conversations never leave your machine
248
+
249
+ ### Consider alternatives if
250
+
251
+ - You need a knowledge graph with temporal reasoning (Zep/Graphiti)
252
+ - You want a full agent framework, not just memory (Letta)
253
+ - You need cloud-hosted memory shared across teams (Mem0 Cloud)
254
+ - You only need basic session notes (Claude native memory)
255
+
256
+ ## AI Agent Integration
257
+
258
+ nano-brain ships with a SKILL.md that teaches AI agents when and how to use memory tools. When loaded as an OpenCode skill, agents automatically:
259
+
260
+ - **Check memory before starting work** — recall past decisions, patterns, and context
261
+ - **Save context after completing work** — persist key decisions and debugging insights
262
+ - **Route queries to the right search tool** — BM25 for exact terms, vector for concepts, hybrid for best quality
263
+
264
+ ### SKILL.md (Auto-loaded)
265
+
266
+ The skill file at `SKILL.md` provides routing rules, trigger phrases, tool selection guides, and integration patterns. It's automatically loaded when any agent references the `nano-brain` skill.
267
+
268
+ ### AGENTS_SNIPPET.md (Optional, project-level)
269
+
270
+ For project-level integration, `AGENTS_SNIPPET.md` provides a managed block that can be injected into a project's `AGENTS.md`:
271
+
272
+ ```bash
273
+ # Future: npx nano-brain init
274
+ # For now: copy the managed block from AGENTS_SNIPPET.md into your project's AGENTS.md
275
+ ```
276
+
277
+ See [SKILL.md](./SKILL.md) for full routing rules and [AGENTS_SNIPPET.md](./AGENTS_SNIPPET.md) for the project-level snippet.
278
+
279
+ ## License
280
+
281
+ MIT
package/SKILL.md ADDED
@@ -0,0 +1,153 @@
1
+ # nano-brain
2
+
3
+ Persistent memory system for OpenCode. Hybrid search across past sessions, codebase, curated notes, and daily logs.
4
+
5
+ ## When to Use (Routing Rules)
6
+
7
+ ### ALWAYS use memory BEFORE starting work when:
8
+
9
+ - **Resuming or continuing work** — "continue", "pick up where we left off", "what were we doing"
10
+ - **Referencing past decisions** — "we decided", "last time", "previously", "remember when"
11
+ - **Cross-session context** — "what did we do about X", "how did we solve Y before"
12
+ - **Unfamiliar codebase area** — search memory for past exploration sessions before re-exploring
13
+ - **Repeated patterns** — "same as before", "like we did for X", "follow the same approach"
14
+
15
+ ### ALWAYS use memory AFTER completing work:
16
+
17
+ - **Save key decisions** — architecture choices, tradeoffs, rejected alternatives
18
+ - **Save implementation patterns** — reusable approaches discovered during work
19
+ - **Save debugging insights** — root causes, non-obvious fixes, gotchas
20
+ - **Save project context** — domain knowledge, business rules, conventions learned
21
+
22
+ ### Trigger Phrases (auto-route to memory)
23
+
24
+ | Phrase | Action |
25
+ |--------|--------|
26
+ | "what did we...", "have we ever...", "did we already..." | `memory_query` → recall past work |
27
+ | "remember", "last time", "before", "previously" | `memory_query` → find past context |
28
+ | "save this", "remember this", "note that" | `memory_write` → persist to memory |
29
+ | "what's the status of memory", "is memory indexed" | `memory_status` → check health |
30
+ | Starting a new feature in a known area | `memory_query` → find past sessions in that area |
31
+ | Debugging a recurring issue | `memory_search` → find past fixes |
32
+
33
+ ## Tool Selection Guide
34
+
35
+ ### Which search tool to use:
36
+
37
+ | Scenario | Tool | Why |
38
+ |----------|------|-----|
39
+ | Exact function/variable name, error message | `memory_search` (BM25) | Fast exact keyword matching |
40
+ | Conceptual question ("how does X work") | `memory_vsearch` (semantic) | Understands meaning, not just keywords |
41
+ | Complex question, best quality needed | `memory_query` (hybrid) | BM25 + vector + LLM reranking |
42
+ | Retrieve a specific known document | `memory_get` | Direct fetch by path or docid |
43
+ | Save a decision or insight | `memory_write` | Persist to daily log or MEMORY.md |
44
+
45
+ ### Search strategy for best results:
46
+
47
+ 1. **Start with `memory_query`** for complex/conceptual questions (best quality)
48
+ 2. **Use `memory_search`** for exact terms — function names, error codes, specific strings
49
+ 3. **Use `memory_vsearch`** when you want semantic similarity without reranking overhead
50
+ 4. **Combine with native tools** — memory excels at recall and semantic search; grep/ast-grep excel at precise code pattern matching
51
+
52
+ ### Collection filtering:
53
+
54
+ - `collection: "codebase"` — search only indexed source files
55
+ - `collection: "sessions-{project}"` — search only past sessions for a specific project
56
+ - `collection: "curated"` — search only manually saved notes
57
+ - Omit `collection` — search everything (recommended default)
58
+
59
+ ## Available Tools
60
+
61
+ ### memory_search
62
+ BM25 keyword search. Fast, exact matching.
63
+ - query: Search query (required)
64
+ - limit: Max results (default: 10)
65
+ - collection: Filter by collection
66
+
67
+ ### memory_vsearch
68
+ Semantic vector search using embeddings.
69
+ - query: Search query (required)
70
+ - limit: Max results (default: 10)
71
+ - collection: Filter by collection
72
+
73
+ ### memory_query
74
+ Full hybrid search with query expansion, RRF fusion, and LLM reranking. Best quality.
75
+ - query: Search query (required)
76
+ - limit: Max results (default: 10)
77
+ - collection: Filter by collection
78
+ - minScore: Minimum score threshold
79
+
80
+ ### memory_get
81
+ Retrieve a document by path or docid.
82
+ - id: Document path or #docid (required)
83
+ - fromLine: Start line number
84
+ - maxLines: Number of lines to return
85
+
86
+ ### memory_multi_get
87
+ Batch retrieve documents by glob pattern or comma-separated list.
88
+ - pattern: Glob pattern or comma-separated docids/paths (required)
89
+ - maxBytes: Maximum total bytes to return (default: 50000)
90
+
91
+ ### memory_write
92
+ Write content to daily log or MEMORY.md.
93
+ - content: Content to write (required)
94
+ - target: "daily" for daily log, "memory" for MEMORY.md (default: "daily")
95
+
96
+ ### memory_status
97
+ Show index health, collection info, and model status.
98
+
99
+ ### memory_index_codebase
100
+ Index codebase files in the current workspace.
101
+ - root: Workspace root path (optional, defaults to current workspace)
102
+
103
+ ### memory_update
104
+ Trigger immediate reindex of all collections.
105
+
106
+ ## Integration with Agent Workflow
107
+
108
+ ### As an orchestrator (Sisyphus):
109
+
110
+ ```
111
+ # Before starting any non-trivial task, check memory:
112
+ memory_query("what have we done regarding {topic}")
113
+
114
+ # After completing significant work, save context:
115
+ memory_write("## {date} - {topic}\n- Decision: ...\n- Reason: ...\n- Files changed: ...")
116
+
117
+ # When delegating to subagents, include memory context:
118
+ task(category="...", load_skills=["nano-brain"], prompt="... CONTEXT from memory: ...")
119
+ ```
120
+
121
+ ### As a subagent:
122
+
123
+ ```
124
+ # If the task involves an area you're unfamiliar with:
125
+ memory_query("{area} implementation patterns")
126
+
127
+ # If debugging and the fix isn't obvious:
128
+ memory_search("{error message or symptom}")
129
+ ```
130
+
131
+ ## Memory vs Native Tools
132
+
133
+ | Capability | nano-brain | Native (grep/glob/ast-grep) |
134
+ |-----------|----------------|---------------------------|
135
+ | Past session recall | ✅ Searches all past sessions | ❌ session_search is basic text match |
136
+ | Semantic understanding | ✅ "notification workflow" finds related concepts | ❌ Literal pattern matching only |
137
+ | Cross-project knowledge | ✅ Searches across all indexed workspaces | ❌ Scoped to current directory |
138
+ | Exact code patterns | ⚠️ BM25 works, but less precise | ✅ ast-grep, grep are superior |
139
+ | Structural code search | ❌ Not AST-aware | ✅ ast-grep matches code structure |
140
+ | Curated knowledge | ✅ MEMORY.md + daily logs | ❌ No equivalent |
141
+
142
+ **They are complementary.** Use memory for recall + semantics, native tools for precise code matching.
143
+
144
+ ## First-Time Setup
145
+
146
+ If memory is not yet indexed for a workspace:
147
+
148
+ ```
149
+ memory_status # Check current state
150
+ memory_index_codebase root="/path/to/ws" # Index codebase files
151
+ memory_update # Trigger reindex of sessions + curated
152
+ memory_status # Verify completion
153
+ ```
package/bin/cli.js ADDED
@@ -0,0 +1,18 @@
1
+ #!/usr/bin/env node
2
+
3
+ import { execFileSync } from 'node:child_process';
4
+ import { fileURLToPath } from 'node:url';
5
+ import { dirname, join } from 'node:path';
6
+
7
+ const __filename = fileURLToPath(import.meta.url);
8
+ const __dirname = dirname(__filename);
9
+
10
+ const entry = join(__dirname, '..', 'src', 'index.ts');
11
+ const tsxBin = join(__dirname, '..', 'node_modules', '.bin', 'tsx');
12
+ const args = process.argv.slice(2);
13
+
14
+ try {
15
+ execFileSync(tsxBin, [entry, ...args], { stdio: 'inherit' });
16
+ } catch (err) {
17
+ process.exit(err.status || 1);
18
+ }