hippo-memory 1.52.5 → 1.52.7

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.
@@ -224,35 +224,56 @@ const HOME_SPELLINGS = [
224
224
  fileUrlPath,
225
225
  (p) => p.replace(/[^A-Za-z0-9]/g, '-'),
226
226
  ];
227
- // A Windows separator can be written \, / or JSON-escaped (\\ in a log line quoting JSON), so any of them matches.
228
- function spellingPattern(spelling) {
227
+ // Git Bash, Cygwin and WSL mount a drive at /c, /cygdrive/c and /mnt/c; a Claude Code folder name writes each / and : as -.
228
+ function mountedDrive(letter) {
229
+ return `(?:${letter}[:-]|(?:[-/](?:cygdrive|mnt))?[-/]${letter})`;
230
+ }
231
+ /** Regex source for one spelling of the home, or null when too little of it is left to swap safely. */
232
+ function spellingPattern(spelling, deep) {
229
233
  if (process.platform !== 'win32')
230
- return escapeRegExp(spelling);
231
- return spelling.split(/[\\/]+/).map(escapeRegExp).join('(?:\\\\+|/)');
234
+ return spelling.length >= 3 ? escapeRegExp(spelling) : null;
235
+ // Each tool that mounts a drive writes it its own way, so a home two or more folders below its drive (\Users\<name>)
236
+ // matches after any prefix, with \, / or JSON's \\ between folders. A drive written a known way goes into the swap with it.
237
+ const drive = /^([A-Za-z])[:-]/.exec(spelling);
238
+ const below = drive === null ? spelling : spelling.slice(2);
239
+ const body = below.split(/[\\/]+/).map(escapeRegExp).join('[\\\\/]+');
240
+ if (drive === null) {
241
+ if (spelling.length < 3)
242
+ return null;
243
+ return deep ? body : `(?<![\\p{L}\\p{N}_])${body}`;
244
+ }
245
+ if (deep)
246
+ return `${mountedDrive(drive[1])}?${body}`;
247
+ // One folder (C:\x, D:\home) is a name any path may hold, so it swaps only after its drive and as a whole name; a drive
248
+ // root swaps nothing.
249
+ return /[^\\/-]/.test(below) ? `(?<![\\p{L}\\p{N}_])${mountedDrive(drive[1])}${body}` : null;
232
250
  }
233
251
  /** One pattern for every alias of the home in every spelling, or null when none is long enough to swap safely. */
234
252
  function buildHomePattern(home, probes) {
235
- const spellings = new Set();
253
+ const spellings = [];
236
254
  for (const alias of collectHomeAliases(home, probes)) {
237
- for (const spell of HOME_SPELLINGS) {
238
- const s = spell(alias);
239
- if (s.length >= 3)
240
- spellings.add(s);
241
- }
255
+ // Counted on the path, since its folder-name spelling cannot tell C:\a-b from C:\a\b.
256
+ const deep = alias.replace(/^[A-Za-z]:/, '').split(/[\\/]+/).filter(Boolean).length >= 2;
257
+ for (const spell of HOME_SPELLINGS)
258
+ spellings.push([spell(alias), deep]);
242
259
  }
243
260
  // Longest first: where one home nests in another (a test home under the real one), swap the longer.
244
261
  const patterns = new Map();
245
- for (const s of [...spellings].sort((a, b) => b.length - a.length)) {
246
- const pattern = spellingPattern(s);
262
+ for (const [s, deep] of spellings.sort(([a], [b]) => b.length - a.length)) {
263
+ const pattern = spellingPattern(s, deep);
264
+ if (pattern === null)
265
+ continue;
247
266
  const key = process.platform === 'win32' ? pattern.toLowerCase() : pattern;
248
267
  if (!patterns.has(key))
249
268
  patterns.set(key, pattern);
250
269
  }
251
270
  if (patterns.size === 0)
252
271
  return null;
253
- // Whole names only: "<home> now" and "<home>." swap; "<home>ty", or "web-app" for a home of /app, do not.
272
+ // Whole names only: "<home> now" and "<home>." swap; "<home>ty", or "web-app" for a home of /app, do not. On Windows
273
+ // the start is spellingPattern's call, because the path below the drive may follow anything.
274
+ const before = process.platform === 'win32' ? '' : '(?<![\\p{L}\\p{N}_])';
254
275
  const alternatives = [...patterns.values()].join('|');
255
- return new RegExp(`(?<![\\p{L}\\p{N}_])(?:${alternatives})(?![\\p{L}\\p{N}_])`, process.platform === 'win32' ? 'giu' : 'gu');
276
+ return new RegExp(`${before}(?:${alternatives})(?![\\p{L}\\p{N}_])`, process.platform === 'win32' ? 'giu' : 'gu');
256
277
  }
257
278
  const URL_RE = /\b[a-z][a-z0-9+.-]*:\/\/[^\s"'<>]+/gi;
258
279
  function redactUrlsInString(text) {
package/dist/version.d.ts CHANGED
@@ -16,7 +16,7 @@
16
16
  * an ESM `import` can resolve cleanly, and a hardcoded constant survives
17
17
  * any packager that drops .json files.
18
18
  */
19
- export declare const PACKAGE_VERSION = "1.52.5";
19
+ export declare const PACKAGE_VERSION = "1.52.7";
20
20
  /** Compares plain x.y.z versions, positive if a > b; tags throw so the rollback guard never misfires silently. */
21
21
  export declare function compareSemver(a: string, b: string): number;
22
22
  //# sourceMappingURL=version.d.ts.map
package/dist/version.js CHANGED
@@ -16,7 +16,7 @@
16
16
  * an ESM `import` can resolve cleanly, and a hardcoded constant survives
17
17
  * any packager that drops .json files.
18
18
  */
19
- export const PACKAGE_VERSION = '1.52.5';
19
+ export const PACKAGE_VERSION = '1.52.7';
20
20
  /** Compares plain x.y.z versions, positive if a > b; tags throw so the rollback guard never misfires silently. */
21
21
  export function compareSemver(a, b) {
22
22
  const parse = (v) => {
@@ -2,7 +2,7 @@
2
2
  "id": "hippo-memory",
3
3
  "name": "Hippo Memory",
4
4
  "description": "Memory for AI agents that learns what is wrong and stops repeating it. Injects context at session start and captures errors.",
5
- "version": "1.52.5",
5
+ "version": "1.52.7",
6
6
 
7
7
  "configSchema": {
8
8
  "type": "object",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "hippo-memory",
3
- "version": "1.52.5",
3
+ "version": "1.52.7",
4
4
  "type": "module",
5
5
  "description": "Hippo Memory plugin for OpenClaw - biologically-inspired agent memory",
6
6
  "main": "index.ts",
@@ -2,7 +2,7 @@
2
2
  "id": "hippo-memory",
3
3
  "name": "Hippo Memory",
4
4
  "description": "Memory for AI agents that learns what is wrong and stops repeating it. Injects context at session start and captures errors.",
5
- "version": "1.52.5",
5
+ "version": "1.52.7",
6
6
  "configSchema": {
7
7
  "type": "object",
8
8
  "additionalProperties": false,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "hippo-memory",
3
- "version": "1.52.5",
3
+ "version": "1.52.7",
4
4
  "description": "Memory for AI agents that learns what is wrong and stops repeating it. MCP server and hooks for Claude Code, Codex and Cursor. SQLite, zero runtime deps.",
5
5
  "mcpName": "io.github.kitfunso/hippo-memory",
6
6
  "type": "module",