@matrixorigin/thememoria 0.4.0 → 0.4.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.
@@ -1,13 +1,13 @@
1
1
  {
2
- "id": "memory-memoria",
3
- "name": "Memory (Memoria)",
2
+ "id": "thememoria",
3
+ "name": "Memoria",
4
4
  "description": "Memoria-backed long-term memory plugin for OpenClaw powered by the Rust memoria CLI and API.",
5
- "version": "0.3.0",
5
+ "version": "0.4.1",
6
6
  "kind": "memory",
7
7
  "uiHints": {
8
8
  "backend": {
9
9
  "label": "Backend Mode",
10
- "help": "embedded runs the Rust memoria CLI locally against MatrixOne; http connects to an existing Memoria API.",
10
+ "help": "embedded runs the Rust memoria CLI locally against MatrixOne; api connects directly to the Memoria REST API over HTTP.",
11
11
  "placeholder": "embedded"
12
12
  },
13
13
  "dbUrl": {
@@ -17,14 +17,14 @@
17
17
  },
18
18
  "apiUrl": {
19
19
  "label": "Memoria API URL",
20
- "help": "Only used when backend=http.",
20
+ "help": "Only used when backend=api.",
21
21
  "placeholder": "http://127.0.0.1:8100"
22
22
  },
23
23
  "apiKey": {
24
24
  "label": "Memoria API Token",
25
- "help": "Bearer token for backend=http.",
25
+ "help": "Bearer token for backend=api.",
26
26
  "sensitive": true,
27
- "placeholder": "mem-..."
27
+ "placeholder": "sk-..."
28
28
  },
29
29
  "memoriaExecutable": {
30
30
  "label": "Memoria Executable",
@@ -151,7 +151,7 @@
151
151
  "properties": {
152
152
  "backend": {
153
153
  "type": "string",
154
- "enum": ["embedded", "http"]
154
+ "enum": ["embedded", "api"]
155
155
  },
156
156
  "dbUrl": {
157
157
  "type": "string"
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@matrixorigin/thememoria",
3
- "version": "0.4.0",
3
+ "version": "0.4.1",
4
4
  "description": "OpenClaw memory plugin that uses the Rust Memoria CLI/API for embedded and remote backends.",
5
5
  "repository": {
6
6
  "type": "git",
@@ -33,6 +33,10 @@
33
33
  "engines": {
34
34
  "node": ">=22"
35
35
  },
36
+ "scripts": {
37
+ "test": "vitest --run",
38
+ "test:watch": "vitest"
39
+ },
36
40
  "peerDependencies": {
37
41
  "openclaw": ">=2026.3.0"
38
42
  },
@@ -41,6 +45,11 @@
41
45
  "optional": true
42
46
  }
43
47
  },
48
+ "devDependencies": {
49
+ "@types/node": "^25.5.0",
50
+ "typescript": "^5.9.3",
51
+ "vitest": "^4.1.0"
52
+ },
44
53
  "openclaw": {
45
54
  "extensions": [
46
55
  "./openclaw/index.ts"
@@ -1,9 +1,10 @@
1
1
  #!/usr/bin/env node
2
+ import { spawnSync } from "node:child_process";
2
3
  import fs from "node:fs";
3
4
  import path from "node:path";
4
5
 
5
6
  function fail(message) {
6
- console.error(`[memory-memoria] ${message}`);
7
+ console.error(`[thememoria] ${message}`);
7
8
  process.exit(1);
8
9
  }
9
10
 
@@ -23,13 +24,40 @@ function normalizeUrl(value) {
23
24
  return value.trim().replace(/\/+$/, "");
24
25
  }
25
26
 
27
+ function resolveExecutable(command) {
28
+ if (!command) {
29
+ return null;
30
+ }
31
+ if (command.includes("/") || command.includes("\\")) {
32
+ return fs.existsSync(command) ? path.resolve(command) : null;
33
+ }
34
+ const result = spawnSync("/usr/bin/env", ["which", command], {
35
+ encoding: "utf8",
36
+ stdio: ["ignore", "pipe", "ignore"],
37
+ });
38
+ if (result.status !== 0 || typeof result.stdout !== "string") {
39
+ return null;
40
+ }
41
+ const resolved = result.stdout.trim().split(/\r?\n/).find(Boolean);
42
+ return resolved ? path.resolve(resolved) : null;
43
+ }
44
+
45
+ function binaryLacksLocalEmbeddingSupport(executablePath) {
46
+ try {
47
+ const content = fs.readFileSync(executablePath);
48
+ return content.includes(Buffer.from("compiled without local-embedding feature", "utf8"));
49
+ } catch {
50
+ return false;
51
+ }
52
+ }
53
+
26
54
  const modeRaw = readArg("--mode", "cloud").trim().toLowerCase();
27
55
  if (modeRaw !== "cloud" && modeRaw !== "local") {
28
56
  fail("mode must be one of: cloud, local");
29
57
  }
30
58
  const mode = modeRaw;
31
59
 
32
- const pluginId = readArg("--plugin-id", "memory-memoria").trim() || "memory-memoria";
60
+ const pluginId = readArg("--plugin-id", "thememoria").trim() || "thememoria";
33
61
  const configFile = path.resolve(
34
62
  readArg(
35
63
  "--config-file",
@@ -82,7 +110,7 @@ if (mode === "cloud") {
82
110
  if (!apiKey) {
83
111
  fail("--api-key required when mode=cloud");
84
112
  }
85
- pluginConfig.backend = "http";
113
+ pluginConfig.backend = "api";
86
114
  pluginConfig.apiUrl = normalizeUrl(apiUrl);
87
115
  pluginConfig.apiKey = apiKey;
88
116
  delete pluginConfig.dbUrl;
@@ -106,6 +134,24 @@ if (mode === "cloud") {
106
134
  fail("--embedding-api-key required for mode=local when embedding-provider is not 'local'");
107
135
  }
108
136
 
137
+ const effectiveMemoriaExecutable =
138
+ memoriaExecutable ||
139
+ (typeof pluginConfig.memoriaExecutable === "string" ? pluginConfig.memoriaExecutable.trim() : "") ||
140
+ "memoria";
141
+ if (embeddingProvider === "local") {
142
+ const resolvedExecutable = resolveExecutable(effectiveMemoriaExecutable);
143
+ if (!resolvedExecutable) {
144
+ fail(
145
+ `embedding-provider=local requires a usable memoria executable, but '${effectiveMemoriaExecutable}' could not be resolved. Pass --memoria-executable <path> or install memoria first.`,
146
+ );
147
+ }
148
+ if (binaryLacksLocalEmbeddingSupport(resolvedExecutable)) {
149
+ fail(
150
+ `embedding-provider=local requires a memoria binary built with local-embedding support. Resolved '${resolvedExecutable}', but this binary was built without that feature. Use a remote embedding provider or install/rebuild a local-embedding-enabled memoria binary.`,
151
+ );
152
+ }
153
+ }
154
+
109
155
  pluginConfig.backend = "embedded";
110
156
  pluginConfig.dbUrl = dbUrl;
111
157
  pluginConfig.embeddingProvider = embeddingProvider;
@@ -153,11 +199,11 @@ console.log(
153
199
  pluginId,
154
200
  backend: pluginConfig.backend,
155
201
  apiUrl:
156
- pluginConfig.backend === "http" && typeof pluginConfig.apiUrl === "string"
202
+ pluginConfig.backend === "api" && typeof pluginConfig.apiUrl === "string"
157
203
  ? pluginConfig.apiUrl
158
204
  : undefined,
159
205
  apiKeySet:
160
- pluginConfig.backend === "http" &&
206
+ pluginConfig.backend === "api" &&
161
207
  typeof pluginConfig.apiKey === "string" &&
162
208
  pluginConfig.apiKey.length > 0,
163
209
  dbUrl: typeof pluginConfig.dbUrl === "string" ? pluginConfig.dbUrl : undefined,
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env bash
2
2
  set -euo pipefail
3
3
 
4
- PLUGIN_ID="memory-memoria"
4
+ PLUGIN_ID="thememoria"
5
5
  DEFAULT_REPO_URL="https://github.com/matrixorigin/Memoria.git"
6
6
  DEFAULT_REPO_REF="main"
7
7
  DEFAULT_MEMORIA_VERSION="v0.1.0"
@@ -39,14 +39,20 @@ MEMORIA_TOOL_NAMES=(
39
39
  )
40
40
 
41
41
  log() {
42
- printf '[memory-memoria] %s\n' "$*"
42
+ printf '[thememoria] %s\n' "$*"
43
43
  }
44
44
 
45
45
  fail() {
46
- printf '[memory-memoria] error: %s\n' "$*" >&2
46
+ printf '[thememoria] error: %s\n' "$*" >&2
47
47
  exit 1
48
48
  }
49
49
 
50
+ binary_lacks_local_embedding_support() {
51
+ local bin_path="$1"
52
+ [[ -f "${bin_path}" ]] || return 1
53
+ LC_ALL=C grep -a -q 'compiled without local-embedding feature' "${bin_path}"
54
+ }
55
+
50
56
  need_cmd() {
51
57
  command -v "$1" >/dev/null 2>&1 || fail "Missing required command: $1"
52
58
  }
@@ -508,7 +514,10 @@ if [[ "${MEMORIA_EMBEDDING_PROVIDER}" != "local" && -z "${MEMORIA_EMBEDDING_DIM}
508
514
  log "Auto-selected embedding dimension ${MEMORIA_EMBEDDING_DIM} for ${MEMORIA_EMBEDDING_MODEL}"
509
515
  fi
510
516
  if [[ "${MEMORIA_EMBEDDING_PROVIDER}" == "local" ]]; then
511
- log "Embedding provider is local. Make sure your memoria binary was built with local-embedding support."
517
+ if binary_lacks_local_embedding_support "${MEMORIA_EXECUTABLE_VALUE}"; then
518
+ fail "MEMORIA_EMBEDDING_PROVIDER=local requires a memoria binary built with local-embedding support. Resolved ${MEMORIA_EXECUTABLE_VALUE}, but that binary was built without the feature. Use a remote embedding provider or install/rebuild a local-embedding-enabled memoria binary."
519
+ fi
520
+ log "Embedding provider is local and the selected memoria binary passed the local-embedding capability check."
512
521
  fi
513
522
  if [[ "${MEMORIA_AUTO_OBSERVE}" == "true" ]]; then
514
523
  [[ -n "${MEMORIA_LLM_API_KEY}" ]] || fail "MEMORIA_AUTO_OBSERVE=true requires MEMORIA_LLM_API_KEY"
@@ -1,7 +1,7 @@
1
1
  #!/usr/bin/env bash
2
2
  set -euo pipefail
3
3
 
4
- PLUGIN_ID="memory-memoria"
4
+ PLUGIN_ID="thememoria"
5
5
  DEFAULT_INSTALL_DIR="${HOME}/.local/share/openclaw-plugins/openclaw-memoria"
6
6
 
7
7
  MEMORIA_TOOL_NAMES=(
@@ -37,11 +37,11 @@ MEMORIA_TOOL_NAMES=(
37
37
  )
38
38
 
39
39
  log() {
40
- printf '[memory-memoria] %s\n' "$*"
40
+ printf '[thememoria] %s\n' "$*"
41
41
  }
42
42
 
43
43
  fail() {
44
- printf '[memory-memoria] error: %s\n' "$*" >&2
44
+ printf '[thememoria] error: %s\n' "$*" >&2
45
45
  exit 1
46
46
  }
47
47
 
@@ -66,9 +66,9 @@ Environment overrides:
66
66
  OPENCLAW_HOME Optional target OpenClaw home.
67
67
 
68
68
  What gets removed by default:
69
- - plugins.entries["memory-memoria"]
70
- - plugins.installs["memory-memoria"]
71
- - plugins.allow entry for memory-memoria
69
+ - plugins.entries["thememoria"]
70
+ - plugins.installs["thememoria"]
71
+ - plugins.allow entry for thememoria
72
72
  - plugins.load.paths entries that point at this plugin
73
73
  - tool policy entries for the Memoria tool surface
74
74
  - managed companion skills in ~/.openclaw/skills: memoria-memory, memoria-recovery
@@ -357,6 +357,6 @@ Config file: ${CONFIG_FILE}
357
357
 
358
358
  Recommended follow-up checks:
359
359
  cd ~
360
- openclaw plugins list --json | rg 'memory-memoria|openclaw-memoria' || true
360
+ openclaw plugins list --json | rg 'thememoria|openclaw-memoria' || true
361
361
  openclaw config get 'plugins.slots.memory'
362
362
  EOF
@@ -78,14 +78,14 @@ if (!fs.existsSync(configFile)) {
78
78
  }
79
79
 
80
80
  const config = JSON.parse(fs.readFileSync(configFile, "utf8"));
81
- const pluginEntry = config?.plugins?.entries?.["memory-memoria"];
81
+ const pluginEntry = config?.plugins?.entries?.["thememoria"];
82
82
  if (!pluginEntry || pluginEntry.enabled !== true) {
83
- throw new Error("plugins.entries.memory-memoria is not enabled");
83
+ throw new Error("plugins.entries.thememoria is not enabled");
84
84
  }
85
85
 
86
86
  const pluginConfig = pluginEntry.config ?? {};
87
87
  if (pluginConfig.memoriaExecutable == null) {
88
- throw new Error("plugins.entries.memory-memoria.config.memoriaExecutable is missing");
88
+ throw new Error("plugins.entries.thememoria.config.memoriaExecutable is missing");
89
89
  }
90
90
 
91
91
  const resolvedMemoriaBin = pluginConfig.memoriaExecutable || memoriaBin;