@memtensor/memos-local-openclaw-plugin 0.1.3 → 0.1.5

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 (117) hide show
  1. package/.env.example +13 -5
  2. package/README.md +283 -91
  3. package/dist/capture/index.d.ts +5 -7
  4. package/dist/capture/index.d.ts.map +1 -1
  5. package/dist/capture/index.js +72 -43
  6. package/dist/capture/index.js.map +1 -1
  7. package/dist/ingest/dedup.d.ts +8 -0
  8. package/dist/ingest/dedup.d.ts.map +1 -1
  9. package/dist/ingest/dedup.js +21 -0
  10. package/dist/ingest/dedup.js.map +1 -1
  11. package/dist/ingest/providers/anthropic.d.ts +16 -0
  12. package/dist/ingest/providers/anthropic.d.ts.map +1 -1
  13. package/dist/ingest/providers/anthropic.js +214 -1
  14. package/dist/ingest/providers/anthropic.js.map +1 -1
  15. package/dist/ingest/providers/bedrock.d.ts +16 -5
  16. package/dist/ingest/providers/bedrock.d.ts.map +1 -1
  17. package/dist/ingest/providers/bedrock.js +210 -6
  18. package/dist/ingest/providers/bedrock.js.map +1 -1
  19. package/dist/ingest/providers/gemini.d.ts +16 -0
  20. package/dist/ingest/providers/gemini.d.ts.map +1 -1
  21. package/dist/ingest/providers/gemini.js +202 -1
  22. package/dist/ingest/providers/gemini.js.map +1 -1
  23. package/dist/ingest/providers/index.d.ts +31 -0
  24. package/dist/ingest/providers/index.d.ts.map +1 -1
  25. package/dist/ingest/providers/index.js +134 -4
  26. package/dist/ingest/providers/index.js.map +1 -1
  27. package/dist/ingest/providers/openai.d.ts +24 -0
  28. package/dist/ingest/providers/openai.d.ts.map +1 -1
  29. package/dist/ingest/providers/openai.js +255 -1
  30. package/dist/ingest/providers/openai.js.map +1 -1
  31. package/dist/ingest/task-processor.d.ts +65 -0
  32. package/dist/ingest/task-processor.d.ts.map +1 -0
  33. package/dist/ingest/task-processor.js +354 -0
  34. package/dist/ingest/task-processor.js.map +1 -0
  35. package/dist/ingest/worker.d.ts +3 -1
  36. package/dist/ingest/worker.d.ts.map +1 -1
  37. package/dist/ingest/worker.js +131 -23
  38. package/dist/ingest/worker.js.map +1 -1
  39. package/dist/recall/engine.d.ts +1 -0
  40. package/dist/recall/engine.d.ts.map +1 -1
  41. package/dist/recall/engine.js +22 -11
  42. package/dist/recall/engine.js.map +1 -1
  43. package/dist/recall/mmr.d.ts.map +1 -1
  44. package/dist/recall/mmr.js +3 -1
  45. package/dist/recall/mmr.js.map +1 -1
  46. package/dist/skill/bundled-memory-guide.d.ts +6 -0
  47. package/dist/skill/bundled-memory-guide.d.ts.map +1 -0
  48. package/dist/skill/bundled-memory-guide.js +95 -0
  49. package/dist/skill/bundled-memory-guide.js.map +1 -0
  50. package/dist/skill/evaluator.d.ts +31 -0
  51. package/dist/skill/evaluator.d.ts.map +1 -0
  52. package/dist/skill/evaluator.js +194 -0
  53. package/dist/skill/evaluator.js.map +1 -0
  54. package/dist/skill/evolver.d.ts +22 -0
  55. package/dist/skill/evolver.d.ts.map +1 -0
  56. package/dist/skill/evolver.js +193 -0
  57. package/dist/skill/evolver.js.map +1 -0
  58. package/dist/skill/generator.d.ts +25 -0
  59. package/dist/skill/generator.d.ts.map +1 -0
  60. package/dist/skill/generator.js +477 -0
  61. package/dist/skill/generator.js.map +1 -0
  62. package/dist/skill/installer.d.ts +16 -0
  63. package/dist/skill/installer.d.ts.map +1 -0
  64. package/dist/skill/installer.js +89 -0
  65. package/dist/skill/installer.js.map +1 -0
  66. package/dist/skill/upgrader.d.ts +19 -0
  67. package/dist/skill/upgrader.d.ts.map +1 -0
  68. package/dist/skill/upgrader.js +263 -0
  69. package/dist/skill/upgrader.js.map +1 -0
  70. package/dist/skill/validator.d.ts +29 -0
  71. package/dist/skill/validator.d.ts.map +1 -0
  72. package/dist/skill/validator.js +227 -0
  73. package/dist/skill/validator.js.map +1 -0
  74. package/dist/storage/sqlite.d.ts +141 -1
  75. package/dist/storage/sqlite.d.ts.map +1 -1
  76. package/dist/storage/sqlite.js +664 -7
  77. package/dist/storage/sqlite.js.map +1 -1
  78. package/dist/types.d.ts +93 -0
  79. package/dist/types.d.ts.map +1 -1
  80. package/dist/types.js +8 -0
  81. package/dist/types.js.map +1 -1
  82. package/dist/viewer/html.d.ts +1 -1
  83. package/dist/viewer/html.d.ts.map +1 -1
  84. package/dist/viewer/html.js +2391 -159
  85. package/dist/viewer/html.js.map +1 -1
  86. package/dist/viewer/server.d.ts +16 -0
  87. package/dist/viewer/server.d.ts.map +1 -1
  88. package/dist/viewer/server.js +346 -3
  89. package/dist/viewer/server.js.map +1 -1
  90. package/index.ts +572 -89
  91. package/openclaw.plugin.json +20 -45
  92. package/package.json +3 -4
  93. package/skill/memos-memory-guide/SKILL.md +86 -0
  94. package/src/capture/index.ts +85 -45
  95. package/src/ingest/dedup.ts +29 -0
  96. package/src/ingest/providers/anthropic.ts +258 -1
  97. package/src/ingest/providers/bedrock.ts +256 -6
  98. package/src/ingest/providers/gemini.ts +252 -1
  99. package/src/ingest/providers/index.ts +156 -8
  100. package/src/ingest/providers/openai.ts +304 -1
  101. package/src/ingest/task-processor.ts +396 -0
  102. package/src/ingest/worker.ts +145 -34
  103. package/src/recall/engine.ts +23 -12
  104. package/src/recall/mmr.ts +3 -1
  105. package/src/skill/bundled-memory-guide.ts +91 -0
  106. package/src/skill/evaluator.ts +220 -0
  107. package/src/skill/evolver.ts +169 -0
  108. package/src/skill/generator.ts +506 -0
  109. package/src/skill/installer.ts +59 -0
  110. package/src/skill/upgrader.ts +257 -0
  111. package/src/skill/validator.ts +227 -0
  112. package/src/storage/sqlite.ts +802 -7
  113. package/src/types.ts +96 -0
  114. package/src/viewer/html.ts +2391 -159
  115. package/src/viewer/server.ts +346 -3
  116. package/SKILL.md +0 -43
  117. package/www/index.html +0 -632
package/.env.example CHANGED
@@ -1,11 +1,19 @@
1
- # Embedding API
2
- # Use any OpenAI-compatible embedding service, or leave blank for local offline model
1
+ # ─── Embedding API ───
2
+ # Use any OpenAI-compatible embedding service, or leave blank for local offline model (Xenova/all-MiniLM-L6-v2)
3
+ EMBEDDING_PROVIDER=openai_compatible
3
4
  EMBEDDING_API_KEY=your-embedding-api-key
4
- EMBEDDING_ENDPOINT=https://api.openai.com/v1
5
- EMBEDDING_MODEL=text-embedding-3-small
5
+ EMBEDDING_ENDPOINT=https://your-embedding-api.com/v1
6
+ EMBEDDING_MODEL=bge-m3
6
7
 
7
- # Summarizer API (OpenAI-compatible)
8
+ # ─── Summarizer API ───
9
+ # OpenAI-compatible LLM for one-sentence chunk summaries
8
10
  # Leave blank to use rule-based fallback (no LLM needed)
11
+ SUMMARIZER_PROVIDER=openai_compatible
9
12
  SUMMARIZER_API_KEY=your-summarizer-api-key
10
13
  SUMMARIZER_ENDPOINT=https://api.openai.com/v1
11
14
  SUMMARIZER_MODEL=gpt-4o-mini
15
+ SUMMARIZER_TEMPERATURE=0
16
+
17
+ # ─── Memory Viewer ───
18
+ # Port for the web-based Memory Viewer (default: 18799)
19
+ # VIEWER_PORT=18799
package/README.md CHANGED
@@ -1,18 +1,62 @@
1
- # 🦞 MemOS Local — OpenClaw Memory Plugin
1
+ # 🧠 MemOS Local — OpenClaw Memory Plugin
2
2
 
3
- Persistent local conversation memory for [OpenClaw](https://github.com/nicepkg/openclaw) AI Agents. Every conversation is automatically captured, semantically indexed, and instantly recallable.
3
+ Persistent local conversation memory for [OpenClaw](https://github.com/nicepkg/openclaw) AI Agents. Every conversation is automatically captured, semantically indexed, and instantly recallable — with **smart task summarization** and **automatic skill evolution**.
4
4
 
5
- **Full-write | Hybrid Search (FTS5 + Vector) | RRF Fusion | MMR Diversity | Recency Decay**
5
+ **Full-write | Hybrid Search | Task Summarization | Skill Evolution | Memory Viewer**
6
+
7
+ ## Why MemOS Local
8
+
9
+ | Problem | Solution |
10
+ |---------|----------|
11
+ | Agent forgets everything between sessions | **Persistent memory** — every conversation auto-captured to local SQLite |
12
+ | Fragmented memory chunks lack context | **Smart task summarization** — conversations organized into structured tasks with goals, steps, results |
13
+ | Agent repeats past mistakes on similar tasks | **Skill evolution** — reusable skills auto-generated from real executions, continuously upgraded |
14
+ | No visibility into what the agent remembers | **Memory Viewer** — full visualization of all memories, tasks, and skills |
15
+ | Privacy concerns with cloud storage | **100% local** — zero cloud uploads, zero telemetry, password-protected |
6
16
 
7
17
  ## Features
8
18
 
9
- - **Auto-capture** — Stores user, assistant, and tool messages after each agent turn
10
- - **Semantic chunking** — Preserves complete code blocks, function bodies, and paragraph boundaries
19
+ ### Memory Engine
20
+ - **Auto-capture** — Stores user, assistant, and tool messages after each agent turn via `agent_end` event (consecutive assistant messages merged into one)
21
+ - **Smart deduplication** — Exact content-hash skip; then Top-5 similar chunks (threshold 0.75) with LLM judge: DUPLICATE (skip), UPDATE (merge summary + append content), or NEW (create). Evolved chunks track merge history.
22
+ - **Semantic chunking** — Splits by code blocks, function bodies, paragraphs; never cuts mid-function
11
23
  - **Hybrid retrieval** — FTS5 keyword + vector semantic dual-channel search with RRF fusion
12
- - **LLM summarization** — One-sentence summary per chunk for fast browsing
13
- - **Multi-provider** — OpenAI, Anthropic, Gemini, Cohere, Voyage, Mistral, Bedrock, or local offline
14
- - **Web viewer** — Built-in dashboard at `http://127.0.0.1:18799` with CRUD, search, filters, pagination
15
- - **Privacy first** — All data in local SQLite, no cloud uploads, password-protected viewer
24
+ - **MMR diversity** — Maximal Marginal Relevance reranking prevents near-duplicate results
25
+ - **Recency decay** — Configurable time-based decay (half-life: 14 days) biases recent memories
26
+ - **Multi-provider embedding** — OpenAI-compatible, Gemini, Cohere, Voyage, Mistral, or local offline (Xenova/all-MiniLM-L6-v2)
27
+
28
+ ### Task Summarization
29
+ - **Auto task boundary detection** — LLM topic judgment + 2-hour idle timeout segments conversations into tasks
30
+ - **Structured summaries** — LLM generates Goal, Key Steps, Result, Key Details for each completed task
31
+ - **Key detail preservation** — Code, commands, URLs, file paths, error messages retained in summaries
32
+ - **Quality filtering** — Tasks with too few chunks, too few turns, or trivial content are auto-skipped
33
+ - **Task status** — `active` (in progress), `completed` (with LLM summary), `skipped` (too brief, excluded from search)
34
+
35
+ ### Skill Evolution
36
+ - **Automatic evaluation** — After task completion, rule filter + LLM evaluates if the task is worth distilling into a skill
37
+ - **Skill generation** — Multi-step LLM pipeline creates SKILL.md + scripts + references + evals from real execution records
38
+ - **Skill upgrading** — When similar tasks appear, existing skills are auto-upgraded (refine / extend / fix)
39
+ - **Quality scoring** — 0-10 quality assessment; scores below 6 marked as draft
40
+ - **Version management** — Full version history with changelog, change summary, and upgrade type tracking
41
+ - **Auto-install** — Generated skills can be auto-installed into the workspace for immediate use
42
+ - **Dedicated model** — Optional separate LLM model for skill generation (e.g., Claude 4.6 for higher quality)
43
+
44
+ ### Memory Viewer
45
+ - **6 management pages** — Memories, Tasks, Skills, Analytics, **Logs**, Settings
46
+ - **Full CRUD** — Create, edit, delete, search memories; evolution badges and merge history on memory cards
47
+ - **Task browser** — Status filters, chat-bubble chunk view, structured summaries, skill generation status
48
+ - **Skill browser** — Version history, quality scores, one-click download as ZIP
49
+ - **Analytics dashboard** — Daily read/write activity, memory breakdown charts
50
+ - **Logs** — Tool call log (memory_search, auto_recall, memory_add, etc.) with input/output and duration; filter by tool, auto-refresh
51
+ - **Online configuration** — Modify embedding, summarizer, skill evolution settings via web UI
52
+ - **Security** — Password-protected, localhost-only (127.0.0.1), session cookies
53
+ - **i18n** — Chinese / English toggle
54
+ - **Themes** — Light / Dark mode
55
+
56
+ ### Privacy & Security
57
+ - **100% on-device** — All data in local SQLite, no cloud uploads, no telemetry
58
+ - **Viewer security** — Binds to 127.0.0.1 only, password-protected with session cookies
59
+ - **Auto-recall + Skill** — Each turn, relevant memories are injected via `before_agent_start` hook (invisible to user). When nothing is recalled (e.g. long or unclear query), the agent is prompted to call `memory_search` with a self-generated short query. The bundled skill `memos-memory-guide` documents all tools and when to use them.
16
60
 
17
61
  ## Quick Start
18
62
 
@@ -24,9 +68,9 @@ Persistent local conversation memory for [OpenClaw](https://github.com/nicepkg/o
24
68
  openclaw plugins install @memtensor/memos-local-openclaw-plugin
25
69
  ```
26
70
 
27
- The plugin is installed under `~/.openclaw/extensions/` and registered as `memos-local`. No clone or build required.
71
+ The plugin is installed under `~/.openclaw/extensions/memos-local` and registered as `memos-local`.
28
72
 
29
- > **Important:** Installing the plugin does **not** start the Memory Viewer. The viewer HTTP service is started only when the **OpenClaw gateway** is running. After install, you must **configure** `openclaw.json` (step 2) and **start or restart the gateway** (step 3); then the viewer will be available at `http://127.0.0.1:18799`.
73
+ > **Important:** The Memory Viewer starts only when the **OpenClaw gateway** is running. After install, **configure** `openclaw.json` (step 2) and **start the gateway** (step 3); the viewer will then be available at `http://127.0.0.1:18799`.
30
74
 
31
75
  **From source (development):**
32
76
 
@@ -43,6 +87,14 @@ Add the plugin config to `~/.openclaw/openclaw.json`:
43
87
 
44
88
  ```jsonc
45
89
  {
90
+ "agents": {
91
+ "defaults": {
92
+ // IMPORTANT: Disable OpenClaw's built-in memory to avoid conflicts
93
+ "memorySearch": {
94
+ "enabled": false
95
+ }
96
+ }
97
+ },
46
98
  "plugins": {
47
99
  "slots": {
48
100
  "memory": "memos-local"
@@ -71,6 +123,8 @@ Add the plugin config to `~/.openclaw/openclaw.json`:
71
123
  }
72
124
  ```
73
125
 
126
+ > **Critical:** You must set `agents.defaults.memorySearch.enabled` to `false`. Otherwise OpenClaw's built-in memory search runs alongside this plugin, causing duplicate retrieval and wasted tokens.
127
+
74
128
  #### Embedding Provider Options
75
129
 
76
130
  | Provider | `provider` value | Example `model` | Notes |
@@ -95,6 +149,30 @@ Add the plugin config to `~/.openclaw/openclaw.json`:
95
149
 
96
150
  > **No summarizer config?** A rule-based fallback generates summaries from the first sentence + key entities. Good enough to start.
97
151
 
152
+ #### Skill Evolution Configuration (Optional)
153
+
154
+ You can optionally configure a dedicated model for skill generation (for higher quality skills):
155
+
156
+ ```jsonc
157
+ {
158
+ "config": {
159
+ "skillSummarizer": {
160
+ "provider": "anthropic",
161
+ "apiKey": "sk-ant-xxx",
162
+ "model": "claude-sonnet-4-20250514",
163
+ "temperature": 0
164
+ },
165
+ "skillEvolution": {
166
+ "enabled": true,
167
+ "autoEvaluate": true,
168
+ "autoInstall": false
169
+ }
170
+ }
171
+ }
172
+ ```
173
+
174
+ If `skillSummarizer` is not configured, the plugin uses the regular `summarizer` model for skill generation.
175
+
98
176
  #### Environment Variable Support
99
177
 
100
178
  Use `${ENV_VAR}` placeholders in config to avoid hardcoding keys:
@@ -107,8 +185,6 @@ Use `${ENV_VAR}` placeholders in config to avoid hardcoding keys:
107
185
 
108
186
  ### 3. Start or Restart the Gateway
109
187
 
110
- The Memory Viewer and all plugin features only run when the OpenClaw gateway is running. After installing and configuring the plugin, start (or restart) the gateway:
111
-
112
188
  ```bash
113
189
  openclaw gateway stop # if already running
114
190
  openclaw gateway install # ensure LaunchAgent is installed (macOS)
@@ -120,7 +196,6 @@ Once the gateway is up, the plugin loads and starts the Memory Viewer at `http:/
120
196
  ### 4. Verify Installation
121
197
 
122
198
  ```bash
123
- # Check the gateway log
124
199
  tail -20 ~/.openclaw/logs/gateway.log
125
200
  ```
126
201
 
@@ -145,105 +220,146 @@ memos-local: started (embedding: openai_compatible)
145
220
  **Step C** — In a new conversation, ask the agent to recall what you discussed:
146
221
 
147
222
  ```
148
- You: Do you remember what we talked about?
149
- Agent: (calls memory_search) Yes, we discussed...
223
+ You: 你还记得我之前让你帮我处理过什么事情吗?
224
+ Agent: (calls memory_search) 是的,我们之前讨论过...
150
225
  ```
151
226
 
152
- **Step D** Check the gateway log for ingest activity:
227
+ ## How It Works
153
228
 
154
- ```bash
155
- grep -E "Stored chunk|Chunked turn|Dedup" ~/.openclaw/logs/gateway.log | tail -10
229
+ ### Three Intelligent Pipelines
230
+
231
+ MemOS Local operates through three interconnected pipelines that form a continuous learning loop:
232
+
233
+ ```
234
+ Conversation → Memory Write Pipeline → Task Generation Pipeline → Skill Evolution Pipeline
235
+
236
+ Smart Retrieval Pipeline ← ← ← ← ← ← ← ← ←
156
237
  ```
157
238
 
158
- You should see lines like:
239
+ ### Pipeline 1: Memory Write (auto on every agent turn)
159
240
 
160
241
  ```
161
- Chunked turn=1772459198930-839rr3 into 3 chunks
162
- Stored chunk=667f289e kind=paragraph len=392 hasVec=true
163
- Stored chunk=107d7f32 kind=tool_result role=tool len=210 hasVec=true
242
+ Conversation Capture (filter roles, strip system prompts)
243
+ Semantic chunking (code blocks, paragraphs, error stacks)
244
+ Content hash dedup LLM summarize each chunk
245
+ → Vector embedding → Store (SQLite + FTS5 + Vector)
164
246
  ```
165
247
 
166
- ### 6. Run the Smoke Test (Optional)
248
+ - System messages are skipped; tool results from the plugin's own tools are not re-stored
249
+ - Evidence wrapper blocks (`[STORED_MEMORY]...[/STORED_MEMORY]`) are stripped to prevent feedback loops
250
+ - Content hash (SHA-256, first 16 hex chars) prevents duplicate chunk ingestion within the same session+role
167
251
 
168
- If you have the source (e.g. cloned the repo or develop locally):
252
+ ### Pipeline 2: Task Generation (auto after memory write)
169
253
 
170
- ```bash
171
- cd MemOS/apps/memos-local-openclaw # or the path where the plugin source is
172
- cp .env.example .env
173
- # Edit .env with your actual API keys
174
- npx tsx scripts/smoke-test.ts
254
+ ```
255
+ New chunks Task boundary detection (LLM topic judge / 2h idle / session change)
256
+ Boundary crossed? → Finalize previous task
257
+ Chunks 4 & turns 2? → LLM structured summary → status = "completed"
258
+ Otherwise → status = "skipped" (excluded from search)
175
259
  ```
176
260
 
177
- The smoke test writes test conversations, searches for them, verifies timeline and get operations, and checks anti-writeback protection. If you installed only from npm, you can skip this step.
261
+ **Why Tasks matter:**
262
+ - Raw memory chunks are fragmented — a single conversation about "deploying Nginx" might span 20 chunks
263
+ - Task summarization organizes these fragments into a structured record: Goal → Steps → Result → Key Details
264
+ - When the agent searches memory, it can quickly locate the complete experience via `task_summary`, not just fragments
265
+ - Task summaries preserve code, commands, URLs, configs, and error messages
178
266
 
179
- ### Reinstall (when install fails or you need to upgrade)
267
+ ### Pipeline 3: Skill Evolution (auto after task completion)
180
268
 
181
- If you see **"plugin already exists"** or **"plugin not found"** after deleting the plugin folder:
269
+ ```
270
+ Completed task → Rule filter (min chunks, non-trivial content)
271
+ → Search for related existing skills
272
+ → Related skill found (confidence ≥ 0.7)?
273
+ → Evaluate upgrade (refine/extend/fix) → Merge new experience → Version bump
274
+ → No related skill (or confidence < 0.3)?
275
+ → Evaluate create → Generate SKILL.md + scripts + evals
276
+ → Quality score (0-10) → Install if score ≥ 6
277
+ ```
182
278
 
183
- 1. **Option A — Use OpenClaw install (recommended when config does not reference the plugin yet)**
184
- Delete the extension folder, then run:
185
- ```bash
186
- rm -rf ~/.openclaw/extensions/memos-local
187
- openclaw plugins install @memtensor/memos-local-openclaw-plugin
188
- ```
189
- If your `openclaw.json` already has `plugins.slots.memory: "memos-local"` and `plugins.entries.memos-local`, the config check may fail with "plugin not found" before install runs. In that case use Option B.
279
+ **Why Skills matter:**
280
+ - Without skills, agents rediscover solutions every time they encounter similar problems
281
+ - Skills crystallize successful executions into reusable guides with steps, pitfall warnings, and verification checks
282
+ - Skills auto-upgrade when new tasks bring improved approaches — getting faster, more accurate, and more token-efficient
283
+ - The evolution is automatic: task completes → evaluate → create/upgrade → install
190
284
 
191
- 2. **Option B Manual install (when config already references memos-local)**
192
- Delete the folder, then install from npm and extract:
193
- ```bash
194
- rm -rf ~/.openclaw/extensions/memos-local
195
- cd /tmp
196
- npm pack @memtensor/memos-local-openclaw-plugin
197
- tar -xzf memtensor-memos-local-openclaw-plugin-*.tgz
198
- mv package ~/.openclaw/extensions/memos-local
199
- ```
200
- **No need to run `npm install`** — on first load the plugin will install dependencies automatically. Then restart the gateway: `openclaw gateway stop` then `openclaw gateway start`.
285
+ ### Pipeline 4: Smart Retrieval
201
286
 
202
- **Plugin shows as "error" in `openclaw plugins list`?** (e.g. `Cannot find module '@sinclair/typebox'`)
203
- If auto-install failed (e.g. `npm` not in PATH when the gateway runs), install dependencies manually once:
287
+ **Auto-recall (every turn):** The plugin hooks `before_agent_start`, runs a memory search with the user's message, then uses an LLM to filter which candidates are relevant and whether they are sufficient to answer. The filtered memories are injected into the agent's system context (invisible to the user). If no memories are found or the query is long/unclear, the agent is prompted to call `memory_search` with a self-generated short query.
204
288
 
205
- ```bash
206
- cd ~/.openclaw/extensions/memos-local && npm install --omit=dev
289
+ **On-demand search (`memory_search`):**
290
+ ```
291
+ Query → FTS5 + Vector dual recall → RRF Fusion → MMR Rerank
292
+ → Recency Decay → Score Filter → Top-K (e.g. 20)
293
+ → LLM relevance filter (minimum information) → Dedup by excerpt overlap
294
+ → Return excerpts + chunkId / task_id (no summaries)
295
+ → sufficient=false → suggest task_summary(taskId), skill_get(taskId), memory_timeline(chunkId)
207
296
  ```
208
297
 
209
- Then restart the gateway.
298
+ - **RRF (Reciprocal Rank Fusion):** Merges FTS5 and vector search rankings into a unified score
299
+ - **MMR (Maximal Marginal Relevance):** Re-ranks to balance relevance with diversity
300
+ - **Recency Decay:** Recent memories get a boost (half-life: 14 days by default)
301
+ - **LLM filter:** Only memories that are genuinely useful for the query are returned; sufficiency determines whether follow-up tool tips are appended
302
+
303
+ ## Retrieval Strategy
304
+
305
+ 1. **Auto-recall (hook)** — On every turn, the plugin runs a memory search using the user's message and injects LLM-filtered relevant memories into the agent's context (via `before_agent_start`). The agent sees this as system context; the user does not.
306
+ 2. **When nothing is recalled** — If the user's message is long, vague, or no matches are found, the plugin injects a short hint telling the agent to call **`memory_search`** with a **self-generated short query** (e.g. key topics or a rephrased question).
307
+ 3. **Bundled skill** — The plugin installs `memos-memory-guide` into `~/.openclaw/workspace/skills/memos-memory-guide/` and `~/.openclaw/skills/memos-memory-guide/`. This skill documents all memory tools, when to call them, and how to write good search queries. Add `skills.load.extraDirs: ["~/.openclaw/skills"]` in `openclaw.json` if you want the skill to appear in the OpenClaw skills dashboard.
308
+ 4. **Search results** — `memory_search` returns **excerpts** (original content snippets) and IDs (`chunkId`, `task_id`), not summaries. The agent uses `task_summary(taskId)`, `memory_timeline(chunkId)`, and `skill_get(skillId|taskId)` to drill down when needed. There is no `memory_get`; full context is obtained via `task_summary` or `memory_timeline`.
210
309
 
211
310
  ## Agent Tools
212
311
 
213
- The plugin registers 4 tools that your agent can use:
312
+ The plugin registers **6 tools** and auto-installs the **memos-memory-guide** skill:
214
313
 
215
- | Tool | Purpose |
216
- |---|---|
217
- | `memory_search` | Search memories by natural language query |
218
- | `memory_timeline` | Get surrounding context for a search hit |
219
- | `memory_get` | Get full original text of a memory chunk |
220
- | `memory_viewer` | Get the URL of the web dashboard |
314
+ | Tool | Purpose | When to Use |
315
+ |------|---------|-------------|
316
+ | `memory_search` | Search memories; returns excerpts + `chunkId` / `task_id` | When auto-recall returned nothing or you need a different query; use a short, self-generated query if the user's message was long or unclear |
317
+ | `task_summary` | Full structured summary of a completed task | When a hit has `task_id` and you need the full story (goal, steps, result) |
318
+ | `memory_timeline` | Surrounding conversation around a chunk | When you need the exact dialogue before/after a hit; pass `chunkId` from the hit |
319
+ | `skill_get` | Get skill content by `skillId` or `taskId` | When a hit has a linked task/skill and you want the reusable experience guide |
320
+ | `skill_install` | Install a skill into the agent workspace | When the skill should be permanently available for future turns |
321
+ | `memory_viewer` | Get the URL of the Memory Viewer web UI | When the user asks where to view or manage their memories |
322
+
323
+ There is no `memory_get`; search returns excerpts and IDs; use `task_summary` or `memory_timeline` for deeper context.
221
324
 
222
- The agent uses these automatically via the SKILL.md prompt guide.
325
+ ### Search Parameters
326
+
327
+ | Parameter | Default | Range | Description |
328
+ |-----------|---------|-------|-------------|
329
+ | `query` | — | — | Natural language search query (keep it short and focused) |
330
+ | `maxResults` | 20 | 1–20 | Maximum candidates before LLM filter |
331
+ | `minScore` | 0.45 | 0.35–1.0 | Minimum relevance score |
332
+ | `role` | — | `user` / `assistant` / `tool` | Filter by message role (e.g. `user` to find what the user said) |
223
333
 
224
334
  ## Memory Viewer
225
335
 
226
- Open `http://127.0.0.1:18799` in your browser:
336
+ Open `http://127.0.0.1:18799` in your browser after starting the gateway.
227
337
 
228
- **Viewer won't open or page not loading?**
338
+ **Pages:**
229
339
 
230
- - The viewer is started by the plugin when the **gateway** starts. It does **not** run at install time.
231
- - Ensure the gateway is running: `openclaw gateway start` (or restart with `openclaw gateway stop` then `openclaw gateway start`).
232
- - Ensure the plugin is enabled in `~/.openclaw/openclaw.json`: `plugins.slots.memory` = `"memos-local"` and `plugins.entries.memos-local.enabled` = `true`.
233
- - Check the gateway log: `tail -30 ~/.openclaw/logs/gateway.log` you should see `MemOS Memory Viewer` and `→ http://127.0.0.1:18799`. If the viewer fails to bind (e.g. port in use), the log will show a warning.
340
+ | Page | Features |
341
+ |------|----------|
342
+ | **Memories** | Timeline view, pagination, session/role/kind/date filters, CRUD, semantic search; evolution badges and merge history on cards |
343
+ | **Tasks** | Task list with status filters (active/completed/skipped), chat-bubble chunk view, structured summaries, skill generation status |
344
+ | **Skills** | Skill list with status badges, version history with changelogs, quality scores, related tasks, one-click ZIP download |
345
+ | **Analytics** | Daily write/read activity charts, memory/task/skill totals, role breakdown |
346
+ | **Logs** | Tool call log (memory_search, auto_recall, memory_add, etc.) with input/output, duration, and tool filter; auto-refresh |
347
+ | **Settings** | Online configuration for embedding model, summarizer model, skill evolution settings, viewer port |
234
348
 
235
- - First visit: set a password (min 4 chars)
236
- - Browse, search, create, edit, delete memories
237
- - Filter by role (user/assistant/tool), type, time range (down to seconds)
238
- - Pagination (30 per page)
349
+ **Viewer won't open?**
239
350
 
240
- **Forgot password?** Click "Forgot password?" on the login page and use the reset token from the gateway log:
351
+ - The viewer is started by the plugin when the **gateway** starts. It does **not** run at install time.
352
+ - Ensure the gateway is running: `openclaw gateway start`
353
+ - Ensure the plugin is enabled in `~/.openclaw/openclaw.json`
354
+ - Check the log: `tail -30 ~/.openclaw/logs/gateway.log` — look for `MemOS Memory Viewer`
355
+
356
+ **Forgot password?** Click "Forgot password?" on the login page and use the reset token:
241
357
 
242
358
  ```bash
243
- # 必须用 "password reset token:" 才能匹配到带 token 的那一行(不要用 "reset token")
244
- grep "password reset token:" /tmp/openclaw/openclaw-*.log ~/.openclaw/logs/gateway.log 2>/dev/null | tail -1
359
+ grep "password reset token:" ~/.openclaw/logs/gateway.log 2>/dev/null | tail -1
245
360
  ```
246
- 输出可能是纯文本一行,或一段 JSON;从中复制 `password reset token:` 后面的 32 位 hex 即可。
361
+
362
+ Copy the 32-character hex string after `password reset token:`.
247
363
 
248
364
  ## Advanced Configuration
249
365
 
@@ -262,41 +378,117 @@ All optional — shown with defaults:
262
378
  "recencyHalfLifeDays": 14 // Time decay half-life
263
379
  },
264
380
  "dedup": {
265
- "similarityThreshold": 0.93 // Cosine similarity for dedup
381
+ "similarityThreshold": 0.75, // Cosine similarity for smart-dedup candidates (Top-5)
382
+ "enableSmartMerge": true, // LLM judge: DUPLICATE / UPDATE / NEW
383
+ "maxCandidates": 5 // Max similar chunks to send to LLM
384
+ },
385
+ "skillEvolution": {
386
+ "enabled": true, // Enable skill evolution
387
+ "autoEvaluate": true, // Auto-evaluate tasks for skill generation
388
+ "minChunksForEval": 6, // Min chunks for a task to be evaluated
389
+ "minConfidence": 0.7, // Min LLM confidence to create/upgrade skill
390
+ "autoInstall": false // Auto-install generated skills
266
391
  },
267
392
  "viewerPort": 18799 // Memory Viewer port
268
393
  }
269
394
  }
270
395
  ```
271
396
 
272
- ## How It Works
397
+ ## Reinstall / Upgrade
273
398
 
274
- **Write path** (automatic on every agent turn):
399
+ If you see **"plugin already exists"** or **"plugin not found"**:
275
400
 
401
+ **Option A — Clean reinstall via OpenClaw CLI:**
402
+ ```bash
403
+ rm -rf ~/.openclaw/extensions/memos-local
404
+ openclaw plugins install @memtensor/memos-local-openclaw-plugin
405
+ cd ~/.openclaw/extensions/memos-local && npm install --omit=dev
406
+ openclaw gateway stop && openclaw gateway start
276
407
  ```
277
- Conversation → Capture (filter roles) → Semantic Chunk → LLM Summarize
278
- Embed Dedup Check → Store (SQLite + FTS5 + Vector)
408
+
409
+ **Option B Manual install (when config already references memos-local):**
410
+ ```bash
411
+ rm -rf ~/.openclaw/extensions/memos-local
412
+ cd /tmp
413
+ npm pack @memtensor/memos-local-openclaw-plugin
414
+ tar -xzf memtensor-memos-local-openclaw-plugin-*.tgz
415
+ mv package ~/.openclaw/extensions/memos-local
416
+ cd ~/.openclaw/extensions/memos-local && npm install --omit=dev
417
+ openclaw gateway stop && openclaw gateway start
279
418
  ```
280
419
 
281
- **Read path** (when agent calls `memory_search`):
420
+ **Plugin shows as "error" in `openclaw plugins list`?** (e.g. `Cannot find module '@sinclair/typebox'`)
282
421
 
283
- ```
284
- Query FTS5 + Vector dual recall → RRF Fusion → MMR Rerank
285
- → Recency Decay → Score Filter → Top-K Results
422
+ ```bash
423
+ cd ~/.openclaw/extensions/memos-local && npm install --omit=dev
286
424
  ```
287
425
 
288
- See the [full documentation](www/docs/index.html) in the repo (or open `www/docs/index.html` locally) for detailed architecture and algorithm explanations.
426
+ Then restart the gateway.
289
427
 
290
- ## Data Location
428
+ ## Troubleshooting
429
+
430
+ ### 常见问题排查
291
431
 
292
- Whether you install from npm or from source, the plugin stores data under your OpenClaw state directory:
432
+ 1. **确认报错内容** 记下完整报错,例如:`plugin not found`、`Cannot find module 'xxx'`、`Invalid config` 等。
433
+
434
+ 2. **看插件状态**
435
+ ```bash
436
+ openclaw plugins list
437
+ ```
438
+ - Status 为 **error** → 记下错误信息
439
+ - 列表中没有 MemOS Local → 未安装或未放到 `~/.openclaw/extensions/memos-local`
440
+
441
+ 3. **看网关日志**
442
+ ```bash
443
+ tail -50 ~/.openclaw/logs/gateway.log
444
+ ```
445
+ 搜索 `memos-local`、`failed to load`、`Error`、`Cannot find module`。
446
+
447
+ 4. **检查环境**
448
+ - Node 版本:`node -v`(需要 **>= 18**)
449
+ - 插件目录存在:`ls ~/.openclaw/extensions/memos-local/package.json`
450
+ - 依赖已安装:`ls ~/.openclaw/extensions/memos-local/node_modules/@sinclair/typebox`
451
+ 若不存在:`cd ~/.openclaw/extensions/memos-local && npm install --omit=dev`
452
+
453
+ 5. **检查配置** — 打开 `~/.openclaw/openclaw.json`,确认:
454
+ - `agents.defaults.memorySearch.enabled` = `false`(关闭内置记忆)
455
+ - `plugins.slots.memory` = `"memos-local"`
456
+ - `plugins.entries.memos-local.enabled` = `true`
457
+
458
+ 6. **记忆和 OpenClaw 内置记忆冲突** — 如果看到 agent 同时调用了内置的 memory 搜索和插件的 `memory_search`,说明 `agents.defaults.memorySearch.enabled` 没有设为 `false`。
459
+
460
+ 7. **技能不生成** — 检查:
461
+ - `skillEvolution.enabled` 是否为 `true`
462
+ - 任务是否有足够内容(默认需要 ≥ 6 chunks)
463
+ - 查看日志中 `SkillEvolver` 相关输出
464
+
465
+ ## Data Location
293
466
 
294
467
  | File | Path |
295
468
  |---|---|
296
469
  | Database | `~/.openclaw/memos-local/memos.db` |
297
- | Viewer auth | `~/.openclaw/viewer-auth.json` |
470
+ | Viewer auth | `~/.openclaw/memos-local/viewer-auth.json` |
298
471
  | Gateway log | `~/.openclaw/logs/gateway.log` |
299
- | Plugin code (npm install) | `~/.openclaw/extensions/` (managed by OpenClaw) |
472
+ | Plugin code | `~/.openclaw/extensions/memos-local/` |
473
+ | Memory-guide skill | `~/.openclaw/workspace/skills/memos-memory-guide/SKILL.md` (and `~/.openclaw/skills/memos-memory-guide/`) |
474
+ | Generated skills | `~/.openclaw/memos-local/skills-store/<skill-name>/` |
475
+ | Installed skills | `~/.openclaw/workspace/skills/<skill-name>/` |
476
+
477
+ ## Testing
478
+
479
+ Run the test suite:
480
+
481
+ ```bash
482
+ cd MemOS/apps/memos-local-openclaw
483
+ npm test
484
+ ```
485
+
486
+ Test coverage includes:
487
+ - **Policy tests** — Verifies retrieval strategy, search filtering, evidence extraction, instruction stripping
488
+ - **Recall tests** — RRF fusion, recency decay correctness
489
+ - **Capture tests** — Message filtering, evidence block stripping, self-tool exclusion
490
+ - **Storage tests** — SQLite CRUD, FTS5, vector storage, content hash dedup
491
+ - **Task processor tests** — Task boundary detection, skip logic, summary generation
300
492
 
301
493
  ## License
302
494
 
@@ -1,16 +1,14 @@
1
1
  import type { ConversationMessage, Logger } from "../types";
2
2
  /**
3
- * Filter and extract writable messages from a conversation turn.
3
+ * Extract writable messages from a conversation turn.
4
4
  *
5
- * - Keep user, assistant, and tool messages
6
- * - Skip system prompts
7
- * - Skip tool results from our own memory tools (prevents memory loop)
8
- * - Truncate long tool results to avoid storage bloat
9
- * - Strip injected evidence blocks wrapped in [STORED_MEMORY]...[/STORED_MEMORY]
5
+ * Stores the user's actual text strips only OpenClaw's injected metadata
6
+ * prefixes (Sender info, conversation context, etc.) which are not user content.
7
+ * Only skips: system prompts and our own memory tool results (prevents loop).
10
8
  */
11
9
  export declare function captureMessages(messages: Array<{
12
10
  role: string;
13
11
  content: string;
14
12
  toolName?: string;
15
- }>, sessionKey: string, turnId: string, evidenceTag: string, log: Logger): ConversationMessage[];
13
+ }>, sessionKey: string, turnId: string, _evidenceTag: string, log: Logger): ConversationMessage[];
16
14
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/capture/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,mBAAmB,EAAQ,MAAM,EAAE,MAAM,UAAU,CAAC;AAYlE;;;;;;;;GAQG;AACH,wBAAgB,eAAe,CAC7B,QAAQ,EAAE,KAAK,CAAC;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,EACrE,UAAU,EAAE,MAAM,EAClB,MAAM,EAAE,MAAM,EACd,WAAW,EAAE,MAAM,EACnB,GAAG,EAAE,MAAM,GACV,mBAAmB,EAAE,CA+CvB"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/capture/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,mBAAmB,EAAQ,MAAM,EAAE,MAAM,UAAU,CAAC;AA0BlE;;;;;;GAMG;AACH,wBAAgB,eAAe,CAC7B,QAAQ,EAAE,KAAK,CAAC;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,EAAE,MAAM,CAAA;CAAE,CAAC,EACrE,UAAU,EAAE,MAAM,EAClB,MAAM,EAAE,MAAM,EACd,YAAY,EAAE,MAAM,EACpB,GAAG,EAAE,MAAM,GACV,mBAAmB,EAAE,CAgCvB"}