@yottameta/yotta-memory 0.17.1 → 0.17.3
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/CHANGELOG.md +16 -3
- package/README.md +2 -1
- package/README.zh-CN.md +2 -1
- package/SKILL.md +1 -1
- package/bin/yotta-memory.js +32 -6
- package/install.sh +23 -4
- package/package.json +1 -1
- package/skill-manifest.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -1,10 +1,25 @@
|
|
|
1
|
-
## v0.17.
|
|
1
|
+
## v0.17.3 (2026-09-26)
|
|
2
|
+
|
|
3
|
+
帮助可读性微调:顶层 `--help` 的每个选项去掉逐项重复的「做什么:」前缀,直接写说明正文;
|
|
4
|
+
「什么时候用:」与「注意:」保留不变。仅影响帮助文案输出,命令行为、参数与退出码零变化。
|
|
5
|
+
|
|
6
|
+
## v0.17.2 (2026-09-25)
|
|
7
|
+
|
|
8
|
+
安全修复:私密维护的 owner 门(explain fail-closed / archive / maintain 跨 owner 跳过)。
|
|
9
|
+
|
|
10
|
+
- 背景:`explain` 对其它 owner 的私密条目照样输出 subject + statement(只加一句「仅元数据」注释);`archive` / `maintain` 遍历全部 owner,任何身份都能归档 / 遗忘别人的私密记忆(ClawHub T05 High)。
|
|
11
|
+
- 修复:`explain` 命中跨 owner 时直接拒绝(不回显正文);`archive` / `maintain` 逐条走 `checkOwnerWritable`,跨 owner(含未声明身份)私密条目一律跳过并在输出里说明数量与补救方式;CLI 与 MCP 两条路径都传入调用方身份。
|
|
12
|
+
- 边界:公共明文 FACT 不受影响;加密库里无对应密钥的条目本就不可解,本次把明文库与写路径补齐。
|
|
13
|
+
- 安装器加固:拒绝对符号链接目标写入、不做整目录删除。
|
|
14
|
+
- 回归:新增 `test/owner-gate.test.js` 5 项,`npm test` 232/232 通过。
|
|
2
15
|
|
|
3
16
|
**view 删除身份的错误提示修复**
|
|
4
17
|
|
|
5
18
|
- `view` 的 AI 列表点击「删除」后,如果确认 ID 输入错误,前端现在会立即提示「ID 不匹配,请输入完整 agent ID:<id>」;用户取消仍保持静默,不会误触删除。
|
|
6
19
|
- 回归:`test/identity-remove.test.js` 新增 1 项,确认错误 ID 有可见提示;后端 400 校验与破坏性闸门保持不变。
|
|
7
20
|
|
|
21
|
+
## v0.17.1 (2026-09-25)
|
|
22
|
+
|
|
8
23
|
## v0.17.0 (2026-09-25)
|
|
9
24
|
|
|
10
25
|
**帮助改造(A)**
|
|
@@ -302,8 +317,6 @@
|
|
|
302
317
|
- SKILL.md:新增「常见问题 FAQ(速查)」小节,指向 references/faq.md。
|
|
303
318
|
- 版本四件对齐 0.8.7(package.json / SKILL.md / CHANGELOG / 引擎 VERSION)。
|
|
304
319
|
|
|
305
|
-
# 更新日志
|
|
306
|
-
|
|
307
320
|
## v0.8.5 (2026-08-29)
|
|
308
321
|
|
|
309
322
|
安全修复(安全扫描发现高危,修复后三源同步升版):
|
package/README.md
CHANGED
|
@@ -23,7 +23,8 @@
|
|
|
23
23
|
|
|
24
24
|
> 📖 The user-facing operations manual lives in [USER_GUIDE.md](USER_GUIDE.md).
|
|
25
25
|
|
|
26
|
-
> 🆕 **v0.17.
|
|
26
|
+
> 🆕 **v0.17.3 (help readability)**: the top-level `--help` no longer repeats a "做什么:" label on every command and option — each entry starts straight with its description, while "什么时候用:" and "注意:" stay as-is. Help text only: commands, arguments and exit codes are unchanged.
|
|
27
|
+
> 🆕 **v0.17.2 (owner gate for private maintenance)**: `explain` now refuses entries owned by another agent instead of printing their subject/statement, and `archive` / `maintain` skip private entries the caller does not own (declare your identity with `--agent <id>`; only an explicit user `--unsafe` overrides). Installer hardening: symlinked targets are refused and no whole-directory delete is performed. Previous v0.17.1: a mismatched identity-confirmation ID in `view` now shows an immediate error instead of returning silently; cancel stays silent and the server-side confirmation and destructive-operation gates are unchanged.
|
|
27
28
|
> 🆕 **v0.17.0 (scale: year/month layout + doctor scale check + lazy index + bench)**: new entries are written into year/month folders — public `facts/<yyyy>/<mm>/`, private `private/<owner>/<type>/<yyyy>/<mm>/`. Flat files from v0.16 and earlier stay in place and remain readable; nothing is migrated automatically. Archiving keeps the year/month path, so same-named files from different months no longer overwrite each other. `doctor` gained a scale section (entry count / largest directory / index size / index cold start) with thresholds set through `config set scale_warn_entries` / `scale_warn_files_per_dir` / `scale_warn_index_bytes` / `scale_warn_cold_start_ms`; exceeding a threshold warns only and never locks destructive writes. Large stores can read only the shards of a given year: `recall --year <yyyy>` / `context --year <yyyy>` (repeatable; omitting it loads everything exactly as before). New `bench` command: deterministic auto sampling or `--evalset <file>` (evalset v1), reporting Recall@k / MRR / nDCG@k / HitRate with bootstrap 95% CI plus store and evalset fingerprints; `--gate <metric>=<value>` fits CI, and the same store + evalset + parameters always produce the same output. `bench` is read-only: it never rebuilds the index, never touches access counters and never calls an external embedding plugin. Previous v0.16.7: interactive `yotta-memory migrate --recovery-key-out` prompt, `YOTTA_MEMORY_PASS` for automation, and a `view` memory-home fingerprint before reusing a running server.
|
|
28
29
|
> 🆕 **v0.17.0 (recovery probe + memory-store scan)**: `doctor --baseline [--against <store>] [--template <file>]` and `backup drill --probe` run six read-only baseline probes (identity / recent / source-only diff / CJK / operation rules / owner scope) against the target store or restored copy. Entry identity keys are layout-independent, so an old flat store migrating into the year/month layout never reports false gaps; missing items are listed and exit non-zero (`doctor` exit 2 / `drill` fails). Probes never hard-code any memory and `--template` only tightens the verdict. New `scan` command: seven classes (malicious instruction / prompt injection / credential leak / data exfiltration / guardrail bypass / behaviour manipulation / privilege escalation), five severities and `file:line` evidence; report-only by default, zero network and zero dependencies. `--gate` exits 1 at or above the given severity; `--quarantine` needs `--yes` or interactive confirmation and backs up each original file byte-for-byte into `.memory-scan/quarantine/` before redacting hit lines, with `--restore` to roll back; credential snippets are always masked.
|
|
29
30
|
> 🆕 **v0.16.5 (doctor JSON contract)**: `doctor --json` now exposes stable top-level `schemaVersion`, `encryption`, and `migration_required` fields while preserving the existing `checks` / `warnings` / `identity` structure.
|
package/README.zh-CN.md
CHANGED
|
@@ -23,7 +23,8 @@
|
|
|
23
23
|
|
|
24
24
|
> 📖 面向用户的操作手册见 [USER_GUIDE.md](USER_GUIDE.md)。
|
|
25
25
|
|
|
26
|
-
> 🆕 **v0.17.
|
|
26
|
+
> 🆕 **v0.17.3(帮助可读性)**:顶层 `--help` 不再逐项重复「做什么:」前缀——每条命令与选项直接写说明正文,「什么时候用:」与「注意:」保留不变。仅帮助文案变化,命令、参数与退出码零改动。
|
|
27
|
+
> 🆕 **v0.17.2(私密维护的 owner 门)**:`explain` 对其它 owner 的私密条目改为直接拒绝,不再打印 subject / statement;`archive` / `maintain` 跳过不属于当前身份的私密条目(用 `--agent <id>` 声明身份,只有用户显式 `--unsafe` 才越界)。安装器加固:拒绝对符号链接目标写入,不做整目录删除。上一版 v0.17.1:`view` 删除 AI 身份时确认 ID 输入错误会立即提示「ID 不匹配,请输入完整 agent ID」,不再静默返回;用户取消仍保持静默,后端确认校验与破坏性操作闸门不变。
|
|
27
28
|
> 🆕 **v0.17.0(规模:文件分层 + doctor 规模体检 + 索引按需加载 + bench 基准评测)**:新写入按年/月分层——公共 `facts/<年>/<月>/`、私密 `private/<owner>/<type>/<年>/<月>/`;v0.16 及更早的平铺文件留在原位继续可读,不做自动迁移。归档保留分层,不同月份的同名文件不会互相覆盖。`doctor` 新增规模段(记忆条数 / 单目录最大文件数 / 索引总体积 / 索引冷启动耗时),阈值用 `config set scale_warn_entries` / `scale_warn_files_per_dir` / `scale_warn_index_bytes` / `scale_warn_cold_start_ms` 调整,超阈值只告警,不锁定破坏性写入。大库检索可以按年份只读对应分片:`recall --year <yyyy>` / `context --year <yyyy>`(可重复传多次,不传即全量、行为与旧版一致)。新增 `bench` 可复算基准评测:默认按库内条目确定性抽样,`--evalset <文件>` 也可指定评测集;输出 Recall@k / MRR / nDCG@k / HitRate + 95% 置信区间、库指纹与评测集指纹,`--gate <指标>=<数值>` 可接 CI,同库同评测集同参数必得同结果;全程只读,不重建索引、不写访问计数、不调用外部 embedding。上一版 v0.16.7:明文库转加密推荐交互式 `yotta-memory migrate --recovery-key-out "$env:USERPROFILE\yotta-memory-recovery.key"`,自动化使用 `YOTTA_MEMORY_PASS`;`view` 复用端口前校验 memory_home 指纹。
|
|
28
29
|
> 🆕 **v0.17.0(恢复探针 + 记忆库安全扫描)**:`doctor --baseline [--against <库路径>] [--template <文件>]` 与 `backup drill --probe` 在目标库 / 恢复副本上跑六类只读基线探针(身份 / 近期 / 仅源库独有 / CJK / 操作规则 / owner 范围);条目身份键与布局无关,旧平铺 → 新年/月分层的迁移不会误报「缺失」;缺失项列出清单并非零退出(`doctor` exit 2 / `drill` 判失败),探针不硬编码任何记忆,`--template` 只加严判定。新增 `scan` 记忆库安全扫描:七类(恶意指令 / Prompt 注入 / 凭证泄漏 / 数据外泄 / 护栏绕过 / 行为操纵 / 权限提升)+ 五级分级 + `file:line` 证据,默认只报告、零网络零依赖;`--gate` 命中该级别及以上 exit 1;`--quarantine` 需 `--yes` 或交互确认,先把原文件逐字节备份到 `.memory-scan/quarantine/` 再替换命中行,`--restore` 还原;凭证片段一律打码不回显。
|
|
29
30
|
> 🆕 **v0.16.5(doctor JSON 契约)**:`doctor --json` 顶层新增稳定字段 `schemaVersion` / `encryption` / `migration_required`,同时保留原有 `checks` / `warnings` / `identity` 结构。
|
package/SKILL.md
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: yotta-memory
|
|
3
3
|
description: 元忆 —— 有权限边界的文件式智能体记忆。文件式、零依赖、可 diff/可回滚:让任何 AI 智能体活过会话,开工 recall 恢复上下文、重要信息 remember 落盘、收工归档。类型体系 FACT(公共共享)/ PREF / BOUND / COMMIT(私密隔离)。触发:记住、别忘了、记一笔、记忆、remember、recall、跨会话、上次说到、续测、交接、归档、记忆盘、共享记忆、局域网记忆、画像、开工上下文、长期理解摘要、近期走廊、会话闭环、记忆守则、profile、context、越用越懂、语义检索、反馈、维护、蒸馏、feedback、maintain、distill、explain、自我学习、自我进化、自我提升、查看平台分页、recall 候选预过滤、任务相关记忆、--focus、--embedding、压缩遗忘、consolidate、周期摘要、自动合并、分类型衰减、回滚、备份、backup、防误删、doctor、事务快照、基线探针、恢复演练、记忆库安全扫描、scan
|
|
4
|
-
version: 0.17.
|
|
4
|
+
version: 0.17.3
|
|
5
5
|
license: MIT
|
|
6
6
|
---
|
|
7
7
|
|
package/bin/yotta-memory.js
CHANGED
|
@@ -25,7 +25,7 @@ const net = require('net');
|
|
|
25
25
|
const child_process = require('child_process');
|
|
26
26
|
const { AsyncLocalStorage } = require('async_hooks');
|
|
27
27
|
|
|
28
|
-
const VERSION = '0.17.
|
|
28
|
+
const VERSION = '0.17.3';
|
|
29
29
|
const CLI_VALUE_OPTS = new Set(['--type', '--limit', '--days', '--out', '--owner', '--agent', '--agent-id', '--agent-key', '--agent-key-file', '--plugin-data', '--threshold', '--scope', '--host', '--port', '--dir', '--name', '--user', '--relationship', '--source', '--weight', '--budget', '--password', '--new-password', '--recovery-key', '--recovery-key-out', '--reason', '--merge', '--model', '--subject', '--embedding', '--focus', '--embedding-timeout', '--min-age', '--min-idle', '--max-utility', '--min-group', '--period', '--to', '--id', '--time', '--tools', '--mcp-config', '--skill-dir', '--year', '--evalset', '--k', '--seed', '--bootstrap', '--gate', '--against', '--template', '--path']);
|
|
30
30
|
const CLI_FLAG_OPTS = new Set(['--project', '--all', '--unsafe', '--no-auth', '--stdio', '--onstart', '--from-current', '--restart', '--force', '--attach', '--allow-same-volume', '--verify', '--no-hint', '--encrypt', '--no-encrypt', '--password-stdin', '--json', '--manual', '--skip-schedule', '--useful', '--useless', '--undo', '--dry-run', '--apply', '--purge', '--dedup', '--batches', '--explain', '--semantic', '--runtime', '--ablate', '--timing', '--baseline', '--probe', '--quarantine', '--restore', '--yes', '--keep-memories', '--keep-identity']);
|
|
31
31
|
|
|
@@ -4518,9 +4518,17 @@ function archiveCore(opts) {
|
|
|
4518
4518
|
if (guard.error) return { error: true, text: guard.text };
|
|
4519
4519
|
const cutoff = Date.now() - days * 24 * 60 * 60 * 1000;
|
|
4520
4520
|
let moved = 0;
|
|
4521
|
+
let deniedCrossOwner = 0;
|
|
4521
4522
|
const movedFiles = [];
|
|
4523
|
+
const selfAgent = resolveIdentity(opts).id;
|
|
4522
4524
|
for (const fp of collectEntryFiles(root)) {
|
|
4523
4525
|
const owner = ownerFromPrivatePath(root, fp);
|
|
4526
|
+
// v0.17.2:只归档自己有权写的条目 —— 旧行为遍历全部 owner,
|
|
4527
|
+
// 任何身份都能把别的智能体的私密记忆移进归档区。
|
|
4528
|
+
if (checkOwnerWritable(root, relOf(root, fp), selfAgent, opts.unsafe)) {
|
|
4529
|
+
deniedCrossOwner++;
|
|
4530
|
+
continue;
|
|
4531
|
+
}
|
|
4524
4532
|
let meta;
|
|
4525
4533
|
try { meta = parseFrontmatter(readMemoryText(root, fp, owner)).meta; } catch (e) { continue; }
|
|
4526
4534
|
if (meta.immutable === 'true') continue;
|
|
@@ -4541,7 +4549,11 @@ function archiveCore(opts) {
|
|
|
4541
4549
|
}
|
|
4542
4550
|
}
|
|
4543
4551
|
if (movedFiles.length) removeIndexEntries(root, movedFiles);
|
|
4544
|
-
|
|
4552
|
+
let text = '已归档 ' + moved + ' 条旧记忆到 ' + path.join(root, ARCHIVE_DIR) + '\n事务快照: ' + guard.snapshot.id;
|
|
4553
|
+
if (deniedCrossOwner) {
|
|
4554
|
+
text += '\n跨 owner 私密条目已跳过(' + deniedCrossOwner + ' 条):请用 --agent <id> 声明自己的身份;只有用户显式授权(--unsafe)才能越界维护。';
|
|
4555
|
+
}
|
|
4556
|
+
return { error: false, text: text };
|
|
4545
4557
|
}
|
|
4546
4558
|
|
|
4547
4559
|
// ---- v0.8.0 自我学习/自我进化/自我提升:feedback / explain / maintain / distill ----
|
|
@@ -4643,7 +4655,9 @@ function explainCore(ref, opts) {
|
|
|
4643
4655
|
let entry;
|
|
4644
4656
|
try { entry = readEntry(target.fp, target.root); } catch (e) { return { error: true, text: '读取失败: ' + e.message }; }
|
|
4645
4657
|
const deny = checkOwnerWritable(target.root, target.rel, selfAgent, opts.unsafe);
|
|
4646
|
-
|
|
4658
|
+
// v0.17.2:跨 owner 私密条目 fail-closed —— 旧行为只是加一句「仅元数据」,
|
|
4659
|
+
// 正文(subject / statement)照样输出,等于把别人的私密记忆读给调用方。
|
|
4660
|
+
if (deny) return { error: true, text: deny };
|
|
4647
4661
|
const ub = utilityBreakdown(entry);
|
|
4648
4662
|
const ageDays = entry.created ? daysBetween(entry.created, today()) : 0;
|
|
4649
4663
|
const cfg = loadConfig();
|
|
@@ -4653,7 +4667,7 @@ function explainCore(ref, opts) {
|
|
|
4653
4667
|
const forgetU = parseFloat(cfg.maintain_forget_utility || 0.12);
|
|
4654
4668
|
const forgetAge = parseInt(cfg.maintain_forget_age || '365', 10) || 365;
|
|
4655
4669
|
const lines = ['[' + entry.type + '] ' + entry.subject + ': ' + entry.statement];
|
|
4656
|
-
lines.push(' 文件: ' + target.rel
|
|
4670
|
+
lines.push(' 文件: ' + target.rel);
|
|
4657
4671
|
lines.push(' 效用分: ' + ub.total + ' = confidence ' + ub.confidence + ' + 使用 ' + ub.usage + ' + 时效 ' + ub.recency + '(半衰 ' + hlText + ') + 类型 ' + ub.type + ' + 结构 ' + ub.structure + ')×weight ' + ub.weight);
|
|
4658
4672
|
lines.push(' 年龄: ' + ageDays + ' 天 / access_count ' + (entry.access_count || 0) + ' / feedback_net ' + entry.feedback_net + ' / immutable ' + (entry.immutable ? '是' : '否'));
|
|
4659
4673
|
const importScore = round3(importanceScore(entry));
|
|
@@ -4713,8 +4727,15 @@ function maintainCore(opts) {
|
|
|
4713
4727
|
if (guard) lines.push('- 事务快照: ' + guard.snapshot.id);
|
|
4714
4728
|
lines.push('');
|
|
4715
4729
|
const toArchive = [], toForget = [], skipped = [];
|
|
4730
|
+
const selfAgent = resolveIdentity(opts).id;
|
|
4731
|
+
let deniedCrossOwner = 0;
|
|
4716
4732
|
for (const fp of collectEntryFiles(root)) {
|
|
4717
4733
|
const owner = ownerFromPrivatePath(root, fp);
|
|
4734
|
+
// v0.17.2:跨 owner 私密条目默认跳过(旧行为会遍历全部 owner 做归档 / 遗忘)。
|
|
4735
|
+
if (checkOwnerWritable(root, relOf(root, fp), selfAgent, opts.unsafe)) {
|
|
4736
|
+
deniedCrossOwner++;
|
|
4737
|
+
continue;
|
|
4738
|
+
}
|
|
4718
4739
|
let meta;
|
|
4719
4740
|
try { meta = parseFrontmatter(readMemoryText(root, fp, owner)).meta; } catch (e) { continue; }
|
|
4720
4741
|
if (meta.immutable === 'true') { skipped.push({ fp: fp, reason: 'immutable 豁免' }); continue; }
|
|
@@ -4785,6 +4806,10 @@ function maintainCore(opts) {
|
|
|
4785
4806
|
for (const s of skipped) { grouped[s.reason] = (grouped[s.reason] || 0) + 1; }
|
|
4786
4807
|
for (const k of Object.keys(grouped)) lines.push('- ' + k + ': ' + grouped[k] + ' 条');
|
|
4787
4808
|
}
|
|
4809
|
+
if (deniedCrossOwner) {
|
|
4810
|
+
lines.push('');
|
|
4811
|
+
lines.push('- 跨 owner 私密条目已跳过(' + deniedCrossOwner + ' 条):请用 --agent <id> 声明自己的身份;只有用户显式授权(--unsafe)才能越界维护。');
|
|
4812
|
+
}
|
|
4788
4813
|
// 去重(v0.10.0:置信度分档 + --apply 自动合并;--dedup 与归档/遗忘互斥)
|
|
4789
4814
|
if (opts.dedup) appendDedupBlock(lines, root, opts);
|
|
4790
4815
|
return { error: false, text: lines.join('\n') };
|
|
@@ -8034,7 +8059,7 @@ function callToolInner(name, args, ctx) {
|
|
|
8034
8059
|
return { text: r.text, error: r.error };
|
|
8035
8060
|
}
|
|
8036
8061
|
if (name === 'archive') {
|
|
8037
|
-
const r = archiveCore({ days: args.days, threshold: args.threshold });
|
|
8062
|
+
const r = archiveCore({ selfAgent: agent, days: args.days, threshold: args.threshold });
|
|
8038
8063
|
return { text: r.text, error: r.error };
|
|
8039
8064
|
}
|
|
8040
8065
|
if (name === 'reindex') {
|
|
@@ -9316,7 +9341,8 @@ function helpPad(text, width) {
|
|
|
9316
9341
|
}
|
|
9317
9342
|
function helpText(item) {
|
|
9318
9343
|
const parts = [];
|
|
9319
|
-
|
|
9344
|
+
// v0.17.3:去掉逐项重复的「做什么:」前缀,直接写说明;「什么时候用 / 注意」保留。
|
|
9345
|
+
if (item.what) parts.push(item.what);
|
|
9320
9346
|
if (item.when) parts.push('什么时候用:' + item.when);
|
|
9321
9347
|
if (item.caution) parts.push('注意:' + item.caution);
|
|
9322
9348
|
return parts.join(';');
|
package/install.sh
CHANGED
|
@@ -61,10 +61,29 @@ resolve_user() {
|
|
|
61
61
|
}
|
|
62
62
|
|
|
63
63
|
install_to() {
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
64
|
+
local base="$1"
|
|
65
|
+
local dest
|
|
66
|
+
case "$base" in
|
|
67
|
+
""|"/") echo "安装失败:拒绝不安全的目标目录:'$base'" >&2; return 1 ;;
|
|
68
|
+
esac
|
|
69
|
+
if [ -L "$base" ]; then
|
|
70
|
+
echo "安装失败:目标目录是符号链接,拒绝跟随:$base" >&2; return 1
|
|
71
|
+
fi
|
|
72
|
+
mkdir -p "$base"
|
|
73
|
+
dest="$base/$SKILL_NAME"
|
|
74
|
+
if [ -L "$dest" ]; then
|
|
75
|
+
echo "安装失败:技能目录是符号链接,拒绝跟随:$dest" >&2; return 1
|
|
76
|
+
fi
|
|
77
|
+
if [ -e "$dest" ] && [ ! -d "$dest" ]; then
|
|
78
|
+
echo "安装失败:技能路径已存在且不是目录:$dest" >&2; return 1
|
|
79
|
+
fi
|
|
80
|
+
mkdir -p "$dest"
|
|
81
|
+
cp -RP "$SOURCE_DIR/." "$dest/"
|
|
82
|
+
# 只清理副本内部的开发残留(固定子路径),不做整目录删除、不跟随符号链接
|
|
83
|
+
if [ -d "$dest/.git" ] && [ ! -L "$dest/.git" ]; then rm -rf "$dest/.git"; fi
|
|
84
|
+
find "$dest" -type d -name '__pycache__' -prune -exec rm -rf {} + 2>/dev/null || true
|
|
85
|
+
find "$dest" -type f -name '*.pyc' -delete 2>/dev/null || true
|
|
86
|
+
echo "installed -> $dest"
|
|
68
87
|
}
|
|
69
88
|
|
|
70
89
|
list() {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@yottameta/yotta-memory",
|
|
3
|
-
"version": "0.17.
|
|
3
|
+
"version": "0.17.3",
|
|
4
4
|
"description": "Yuanyi (元忆) — boundary-aware, file-based memory for AI agents. File-based, zero-dependency, diff/rollback-able; FACT/PREF/BOUND/COMMIT types (public shared / private isolated), user-level + project-level storage; v0.12 reliability baseline (init guard, trash-based deletion, independent-volume backup/list/doctor/restore, start-of-work doctor, transactional snapshots before destructive writes), v0.10 consolidation (periodic summaries with provenance, near-duplicate auto-merge, per-type decay, batch audit + rollback), v0.9 recall quality + context focus + optional local embedding plugin, plus v0.8 semantic search, feedback loop, self-organization and distillation.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"keywords": [
|