memory-agent-mcp 1.2.2 → 1.3.1

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.
package/README.md CHANGED
@@ -12,6 +12,22 @@ MCP wrapper for [Memory01](https://memory.node01.org) — agentic memory for AI
12
12
  - **Subscribe**: Subscription plans (Starter $2/500, Pro $9/mo, Enterprise $20/mo)
13
13
  - **Health / Stats / Sample**: Free utilities
14
14
 
15
+ ## Auto-update
16
+
17
+ MCP clients do not auto-update servers. To always use the latest version:
18
+
19
+ - **Recommended config**: use `npx -y memory-agent-mcp@latest` in your MCP config. npx checks the registry on each launch (cached, fast).
20
+ - **Global install**: run `npm install -g memory-agent-mcp@latest` periodically, or `npm update -g memory-agent-mcp`.
21
+ - The server prints a note on startup if a newer version is available.
22
+
23
+ ## One-command setup
24
+
25
+ After installing, tell your agent:
26
+
27
+ > Install `memory-agent-mcp` and call the `init` tool with your agentId. It will set everything up and explain the rest.
28
+
29
+ The `init` tool creates the token, saves credentials to `~/.memory01_token` / `~/.memory01_recovery` (chmod 600), bootstraps base memories, and returns a full guide.
30
+
15
31
  ## Installation
16
32
 
17
33
  ```bash
@@ -87,6 +103,9 @@ Add to your `opencode.json`:
87
103
 
88
104
  ## Tools
89
105
 
106
+ ### init
107
+ Initialize Memory01 in one call: creates token, saves credentials to standard files (chmod 600), bootstraps base memories, stores credentials-location pointer. Returns full guide. Call once per agent.
108
+
90
109
  ### store
91
110
  Store a memory (free). First call returns a write_token and recovery_code — save both! All future operations require the write_token. Re-storing with the same key updates in place (upsert). Supports `base: true` for small (2KB) contextual memories.
92
111
 
package/glama.json ADDED
@@ -0,0 +1,4 @@
1
+ {
2
+ "$schema": "https://glama.ai/mcp/schemas/server.json",
3
+ "maintainers": ["geco"]
4
+ }
package/index.js CHANGED
@@ -39,6 +39,9 @@ import {
39
39
  import { createWalletClient, http, parseEther } from "viem";
40
40
  import { privateKeyToAccount } from "viem/accounts";
41
41
  import { base } from "viem/chains";
42
+ import os from "node:os";
43
+ import path from "node:path";
44
+ import fs from "node:fs";
42
45
 
43
46
  // ============================= Config =============================
44
47
  const MEMORY_BASE_URL = process.env.MEMORY_BASE_URL || "https://memory.node01.org";
@@ -274,6 +277,20 @@ server.setRequestHandler(ListToolsRequestSchema, async () => {
274
277
  required: ["agentId", "writeToken", "key"],
275
278
  },
276
279
  },
280
+ {
281
+ name: "init",
282
+ description: "Initialize Memory01 for this agent in one call: creates a write_token (first store), saves token+recovery_code to standard files (~/.memory01_token, ~/.memory01_recovery, chmod 600), bootstraps conventional base memories, and stores a credentials-location pointer. Returns full guide. Call once per agent; idempotent-ish (if token exists, pass writeToken).",
283
+ inputSchema: {
284
+ type: "object",
285
+ properties: {
286
+ agentId: { type: "string", description: "Your agent identifier (required)" },
287
+ writeToken: { type: "string", description: "Existing write token (omit on first run)" },
288
+ key: { type: "string", description: "Optional first memory key (default: 'init')" },
289
+ value: { type: "string", description: "Optional first memory value" },
290
+ },
291
+ required: ["agentId"],
292
+ },
293
+ },
277
294
  {
278
295
  name: "guide",
279
296
  description: "Get a concise guide on how to use Memory01: init flow, base memories, recovery, upsert, limits. Call this first if unsure. Full guide: https://memory.node01.org/agents.md",
@@ -494,6 +511,88 @@ server.setRequestHandler(CallToolRequestSchema, async (request) => {
494
511
  return { content: [{ type: "text", text: JSON.stringify(result.data, null, 2) }] };
495
512
  }
496
513
 
514
+ case "init": {
515
+ const { agentId, writeToken: providedToken, key = "init", value = "Memory01 initialized." } = args;
516
+ if (!agentId) {
517
+ throw new McpError(ErrorCode.InvalidParams, "agentId is required");
518
+ }
519
+
520
+ const home = os.homedir();
521
+ const tokenFile = path.join(home, ".memory01_token");
522
+ const recoveryFile = path.join(home, ".memory01_recovery");
523
+
524
+ // Step 1: get or create token
525
+ let token = providedToken;
526
+ let recoveryCode = null;
527
+ let isNew = false;
528
+ let storeResult = null;
529
+
530
+ if (!token) {
531
+ const r = await callFree("/api/memory/store", "POST", { agent_id: agentId, key, value });
532
+ if (r.status === 403 && r.data && r.data.error === "token_required") {
533
+ throw new McpError(ErrorCode.InvalidParams, "A token already exists for this (IP, agent_id). Pass writeToken to init, or use recover if your IP changed.");
534
+ }
535
+ if (r.status >= 400) {
536
+ throw new McpError(ErrorCode.InternalError, `API error: ${JSON.stringify(r.data)}`);
537
+ }
538
+ token = r.data.write_token;
539
+ recoveryCode = r.data.recovery_code;
540
+ isNew = true;
541
+ storeResult = r.data;
542
+ }
543
+
544
+ // Step 2: write credential files (chmod 600)
545
+ const savedFiles = [];
546
+ if (isNew && token) {
547
+ try {
548
+ fs.writeFileSync(tokenFile, token + "\n", { mode: 0o600 });
549
+ savedFiles.push(tokenFile);
550
+ } catch (e) {
551
+ console.error("Could not write token file:", e);
552
+ }
553
+ }
554
+ if (isNew && recoveryCode) {
555
+ try {
556
+ fs.writeFileSync(recoveryFile, recoveryCode + "\n", { mode: 0o600 });
557
+ savedFiles.push(recoveryFile);
558
+ } catch (e) {
559
+ console.error("Could not write recovery file:", e);
560
+ }
561
+ }
562
+
563
+ // Step 3: bootstrap base memories (idempotent)
564
+ const bootstrapResult = await callFree("/api/memory/bootstrap", "POST", { agent_id: agentId, write_token: token });
565
+
566
+ // Step 4: upsert credentials-location base memory pointing to the files
567
+ const credValue = `Token at ${tokenFile}, recovery at ${recoveryFile} (chmod 600). Do not store secrets in memory.`;
568
+ await callFree("/api/memory/store", "POST", { agent_id: agentId, write_token: token, key: "credentials-location", value: credValue, base: true });
569
+
570
+ return {
571
+ content: [{
572
+ type: "text",
573
+ text: JSON.stringify({
574
+ ok: true,
575
+ new_token: isNew,
576
+ write_token: token,
577
+ recovery_code: recoveryCode,
578
+ credential_files: savedFiles,
579
+ bootstrap: bootstrapResult.data,
580
+ guide: {
581
+ init_done: "Memory01 initialized. Token and recovery code saved to standard files (chmod 600). Base memories bootstrapped. credentials-location base memory stored.",
582
+ next_steps: [
583
+ "Use store(key, value) to save memories. Re-store with same key to update (upsert).",
584
+ "Use search(query) for semantic search (free: 30/day). Use includeBase:true to load context at session start.",
585
+ "Recovery: if your IP changes, call recover(agentId, recoveryCode) from the new host.",
586
+ "Regenerate recovery code from original IP with regenerate_recovery(writeToken) if lost.",
587
+ "Full guide: https://memory.node01.org/agents.md",
588
+ ],
589
+ standard_paths: { token: tokenFile, recovery: recoveryFile },
590
+ },
591
+ }, null, 2),
592
+ }],
593
+ };
594
+ }
595
+
497
596
  case "guide": {
498
597
  return {
499
598
  content: [{
@@ -545,7 +644,27 @@ server.setRequestHandler(CallToolRequestSchema, async (request) => {
545
644
  }
546
645
  });
547
646
 
647
+ // ============================= Version Check =============================
648
+ async function checkLatestVersion() {
649
+ try {
650
+ const controller = new AbortController();
651
+ const timer = setTimeout(() => controller.abort(), 3000);
652
+ const res = await fetch("https://registry.npmjs.org/memory-agent-mcp/latest", { signal: controller.signal });
653
+ clearTimeout(timer);
654
+ if (!res.ok) return;
655
+ const data = await res.json();
656
+ const latest = data.version;
657
+ const current = "1.3.1";
658
+ if (latest && latest !== current) {
659
+ console.error(`NOTE: memory-agent-mcp ${current} is installed; latest is ${latest}. Run 'npm install -g memory-agent-mcp@latest' to update.`);
660
+ }
661
+ } catch (e) {
662
+ // best-effort, ignore
663
+ }
664
+ }
665
+
548
666
  async function main() {
667
+ checkLatestVersion(); // best-effort, non-blocking
549
668
  const transport = new StdioServerTransport();
550
669
  await server.connect(transport);
551
670
  console.error("memory-agent-mcp running on stdio");
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "memory-agent-mcp",
3
- "version": "1.2.2",
3
+ "version": "1.3.1",
4
4
  "description": "MCP wrapper for Memory01 agentic memory service - persistent memory for AI agents, free to store and search. Base memories, recovery codes, upsert, 50+ languages.",
5
5
  "type": "module",
6
6
  "main": "index.js",
@@ -31,5 +31,13 @@
31
31
  },
32
32
  "engines": {
33
33
  "node": ">=20.0.0"
34
+ },
35
+ "repository": {
36
+ "type": "git",
37
+ "url": "https://github.com/geco/memory-agent-mcp.git"
38
+ },
39
+ "homepage": "https://github.com/geco/memory-agent-mcp#readme",
40
+ "bugs": {
41
+ "url": "https://github.com/geco/memory-agent-mcp/issues"
34
42
  }
35
43
  }