mneme-ai 2.58.0 → 2.60.0

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 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAuIA,wBAAsB,GAAG,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC,CAy6KvD"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAuIA,wBAAsB,GAAG,CAAC,IAAI,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,IAAI,CAAC,CA6jLvD"}
package/dist/index.js CHANGED
@@ -4682,6 +4682,169 @@ export async function run(argv) {
4682
4682
  process.exitCode = 1;
4683
4683
  }
4684
4684
  });
4685
+ // v2.60.0 — SKELETON KEY: MCP server security auditor.
4686
+ // First MCP security audit tool in the ecosystem. Discovers MCP
4687
+ // servers in Claude Desktop / Cursor / Continue / Cline configs +
4688
+ // risk-scores them + computes transitive bypass graph + pins HMAC
4689
+ // snapshot for drift detection.
4690
+ const skeletonKeyParent = program
4691
+ .command("skeleton_key")
4692
+ .description("v2.60 — MCP server security auditor. Default action = audit.")
4693
+ .option("--budget <n>", "risk budget cap (default 5.0)", (v) => Number(v), 5.0)
4694
+ .option("--empirical", "spawn each MCP server + read tools/list (slow, accurate)", false)
4695
+ .action(async (opts) => {
4696
+ try {
4697
+ const core = await import("@mneme-ai/core");
4698
+ const r = await core.skeletonKey.auditMcpConfigs({ budgetCap: opts.budget, empiricalProbe: opts.empirical });
4699
+ process.stdout.write(JSON.stringify(r, null, 2) + "\n");
4700
+ if (!r.ok)
4701
+ process.exitCode = 1;
4702
+ }
4703
+ catch (e) {
4704
+ process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
4705
+ process.exitCode = 1;
4706
+ }
4707
+ });
4708
+ skeletonKeyParent.command("audit")
4709
+ .description("Full MCP audit: discover servers, score risk, compute bypass graph, render banner.")
4710
+ .option("--budget <n>", "risk budget cap (default 5.0)", (v) => Number(v), 5.0)
4711
+ .option("--empirical", "spawn each MCP server + read tools/list (slow, accurate)", false)
4712
+ .option("--banner", "render ASCII banner instead of JSON", false)
4713
+ .action(async (opts) => {
4714
+ try {
4715
+ const core = await import("@mneme-ai/core");
4716
+ const r = await core.skeletonKey.auditMcpConfigs({ budgetCap: opts.budget, empiricalProbe: opts.empirical });
4717
+ if (opts.banner)
4718
+ process.stdout.write(core.skeletonKey.renderAuditBanner(r) + "\n");
4719
+ else
4720
+ process.stdout.write(JSON.stringify(r, null, 2) + "\n");
4721
+ if (!r.ok)
4722
+ process.exitCode = 1;
4723
+ }
4724
+ catch (e) {
4725
+ process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
4726
+ process.exitCode = 1;
4727
+ }
4728
+ });
4729
+ skeletonKeyParent.command("recommend")
4730
+ .description("Concrete config changes to reduce risk surface.")
4731
+ .option("--budget <n>", "risk budget cap (default 5.0)", (v) => Number(v), 5.0)
4732
+ .action(async (opts) => {
4733
+ try {
4734
+ const core = await import("@mneme-ai/core");
4735
+ const a = await core.skeletonKey.auditMcpConfigs({ budgetCap: opts.budget });
4736
+ const recs = core.skeletonKey.buildRecommendations(a);
4737
+ process.stdout.write(JSON.stringify({ ok: recs.length === 0, count: recs.length, recommendations: recs }, null, 2) + "\n");
4738
+ }
4739
+ catch (e) {
4740
+ process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
4741
+ process.exitCode = 1;
4742
+ }
4743
+ });
4744
+ skeletonKeyParent.command("pin")
4745
+ .description("Snapshot the current MCP config (HMAC-signed). Future drift checks compare against this.")
4746
+ .action(async () => {
4747
+ try {
4748
+ const core = await import("@mneme-ai/core");
4749
+ const snap = core.skeletonKey.pinConfigSnapshot(process.cwd());
4750
+ process.stdout.write(JSON.stringify({ ok: true, snapshot: snap }, null, 2) + "\n");
4751
+ }
4752
+ catch (e) {
4753
+ process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
4754
+ process.exitCode = 1;
4755
+ }
4756
+ });
4757
+ skeletonKeyParent.command("drift")
4758
+ .description("Compare current MCP config vs pinned snapshot. Detects silent tampering.")
4759
+ .action(async () => {
4760
+ try {
4761
+ const core = await import("@mneme-ai/core");
4762
+ const r = core.skeletonKey.detectConfigDrift(process.cwd());
4763
+ process.stdout.write(JSON.stringify(r, null, 2) + "\n");
4764
+ if (!r.ok)
4765
+ process.exitCode = 1;
4766
+ }
4767
+ catch (e) {
4768
+ process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
4769
+ process.exitCode = 1;
4770
+ }
4771
+ });
4772
+ skeletonKeyParent.command("probe")
4773
+ .description("Empirically spawn ONE MCP server + read its tools/list. Reveals real capabilities (not name-heuristic).")
4774
+ .requiredOption("--server <name>", "MCP server name to probe (must match a discovered config entry)")
4775
+ .action(async (opts) => {
4776
+ try {
4777
+ const core = await import("@mneme-ai/core");
4778
+ const all = core.skeletonKey.discoverServers(core.skeletonKey.defaultConfigPaths());
4779
+ const found = all.find((s) => s.name === opts.server);
4780
+ if (!found || !found.command) {
4781
+ process.stdout.write(JSON.stringify({ ok: false, hint: `server '${opts.server}' not found in any discovered config (or has no command)` }) + "\n");
4782
+ process.exitCode = 1;
4783
+ return;
4784
+ }
4785
+ const r = await core.skeletonKey.probeServer({ name: found.name, command: found.command, args: found.args, env: found.env });
4786
+ process.stdout.write(JSON.stringify(r, null, 2) + "\n");
4787
+ }
4788
+ catch (e) {
4789
+ process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
4790
+ process.exitCode = 1;
4791
+ }
4792
+ });
4793
+ // v2.59.0 — SDK SURFACE AUDITOR: gate-self-verification.
4794
+ // Empirically imports @mneme-ai/sdk + checks the external public
4795
+ // surface matches WIRING DOCTOR's claims. Closes the v2.58 blind-spot
4796
+ // bug class (WIRING DOCTOR said wired but external `import { ... }
4797
+ // from "@mneme-ai/sdk"` returned undefined).
4798
+ const sdkAuditorParent = program
4799
+ .command("sdk_auditor")
4800
+ .description("v2.59 — empirically audit @mneme-ai/sdk external public surface; default = run + persist + report.")
4801
+ .action(async () => {
4802
+ try {
4803
+ const core = await import("@mneme-ai/core");
4804
+ const r = await core.sdkAuditor.auditSdkSurface({ cwd: process.cwd() });
4805
+ core.sdkAuditor.persistAuditorReport(process.cwd(), r);
4806
+ process.stdout.write(JSON.stringify({ ok: r.ok, totalExports: r.totalExports, okCount: r.okCount, brokenCount: r.brokenCount, broken: r.findings.filter((f) => !f.present) }, null, 2) + "\n");
4807
+ if (!r.ok)
4808
+ process.exitCode = 1;
4809
+ }
4810
+ catch (e) {
4811
+ process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
4812
+ process.exitCode = 1;
4813
+ }
4814
+ });
4815
+ sdkAuditorParent.command("run")
4816
+ .description("v2.59 — same as `mneme sdk_auditor` default.")
4817
+ .action(async () => {
4818
+ try {
4819
+ const core = await import("@mneme-ai/core");
4820
+ const r = await core.sdkAuditor.auditSdkSurface({ cwd: process.cwd() });
4821
+ core.sdkAuditor.persistAuditorReport(process.cwd(), r);
4822
+ process.stdout.write(JSON.stringify({ ok: r.ok, totalExports: r.totalExports, okCount: r.okCount, brokenCount: r.brokenCount, broken: r.findings.filter((f) => !f.present) }, null, 2) + "\n");
4823
+ if (!r.ok)
4824
+ process.exitCode = 1;
4825
+ }
4826
+ catch (e) {
4827
+ process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
4828
+ process.exitCode = 1;
4829
+ }
4830
+ });
4831
+ sdkAuditorParent.command("consistency")
4832
+ .description("v2.59 — cross-check SDK_AUDITOR vs WIRING DOCTOR for gate-agreement (contradictions = release block).")
4833
+ .action(async () => {
4834
+ try {
4835
+ const core = await import("@mneme-ai/core");
4836
+ const wd = core.wiringDoctor.diagnose(process.cwd());
4837
+ const auditor = await core.sdkAuditor.auditSdkSurface({ cwd: process.cwd() });
4838
+ const r = core.sdkAuditor.crossCheckGates(wd, auditor);
4839
+ process.stdout.write(JSON.stringify(r, null, 2) + "\n");
4840
+ if (!r.ok)
4841
+ process.exitCode = 1;
4842
+ }
4843
+ catch (e) {
4844
+ process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
4845
+ process.exitCode = 1;
4846
+ }
4847
+ });
4685
4848
  // v2.58.0 — LIVING LAB primitive: 24/7 autonomous test bot.
4686
4849
  const livingLabParent = program
4687
4850
  .command("living_lab")