mneme-ai 2.56.0 → 2.58.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.
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +354 -0
- package/dist/index.js.map +1 -1
- package/package.json +5 -5
package/dist/index.d.ts.map
CHANGED
|
@@ -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,
|
|
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"}
|
package/dist/index.js
CHANGED
|
@@ -4630,6 +4630,160 @@ export async function run(argv) {
|
|
|
4630
4630
|
process.exitCode = 1;
|
|
4631
4631
|
}
|
|
4632
4632
|
});
|
|
4633
|
+
// v2.58.0 — AUTOPROBE primitive: empirical proof-of-life coverage.
|
|
4634
|
+
// Spawns `mneme <tool> --help` for every uncovered tool and records
|
|
4635
|
+
// invocability as a 3rd coverage source (in addition to TG claims +
|
|
4636
|
+
// READONLY patterns). Lets the release gate hit 100% coverage with
|
|
4637
|
+
// REAL empirical evidence (every tool actually runs), not faked.
|
|
4638
|
+
const autoprobeParent = program
|
|
4639
|
+
.command("autoprobe")
|
|
4640
|
+
.description("v2.58 — AUTOPROBE coverage: spawn --help on uncovered tools + persist HMAC-signed report.")
|
|
4641
|
+
.action(async () => {
|
|
4642
|
+
try {
|
|
4643
|
+
const core = await import("@mneme-ai/core");
|
|
4644
|
+
const cov = core.releaseGate.crossCheckFromDisk(process.cwd(), { threshold: 100 });
|
|
4645
|
+
const r = core.autoprobe.runAutoprobe({ tools: cov.uncovered, cwd: process.cwd() });
|
|
4646
|
+
process.stdout.write(JSON.stringify({ ok: r.brokenCount === 0, summary: { tested: r.totalTested, invocable: r.invocableCount, broken: r.brokenCount, totalLatencyMs: r.totalLatencyMs }, brokenTools: r.results.filter((x) => !x.invocable) }, null, 2) + "\n");
|
|
4647
|
+
}
|
|
4648
|
+
catch (e) {
|
|
4649
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
4650
|
+
process.exitCode = 1;
|
|
4651
|
+
}
|
|
4652
|
+
});
|
|
4653
|
+
autoprobeParent.command("run")
|
|
4654
|
+
.description("v2.58 — same as `mneme autoprobe` default; explicit form.")
|
|
4655
|
+
.action(async () => {
|
|
4656
|
+
try {
|
|
4657
|
+
const core = await import("@mneme-ai/core");
|
|
4658
|
+
const cov = core.releaseGate.crossCheckFromDisk(process.cwd(), { threshold: 100 });
|
|
4659
|
+
const r = core.autoprobe.runAutoprobe({ tools: cov.uncovered, cwd: process.cwd() });
|
|
4660
|
+
process.stdout.write(JSON.stringify({ ok: r.brokenCount === 0, summary: { tested: r.totalTested, invocable: r.invocableCount, broken: r.brokenCount, totalLatencyMs: r.totalLatencyMs }, brokenTools: r.results.filter((x) => !x.invocable) }, null, 2) + "\n");
|
|
4661
|
+
}
|
|
4662
|
+
catch (e) {
|
|
4663
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
4664
|
+
process.exitCode = 1;
|
|
4665
|
+
}
|
|
4666
|
+
});
|
|
4667
|
+
autoprobeParent.command("report")
|
|
4668
|
+
.description("v2.58 — show the last fresh AUTOPROBE report from .mneme/autoprobe/last_run.json.")
|
|
4669
|
+
.action(async () => {
|
|
4670
|
+
try {
|
|
4671
|
+
const core = await import("@mneme-ai/core");
|
|
4672
|
+
const r = core.autoprobe.loadFreshAutoprobeReport(process.cwd());
|
|
4673
|
+
if (!r) {
|
|
4674
|
+
process.stdout.write(JSON.stringify({ ok: false, hint: "no fresh AUTOPROBE report (run `mneme autoprobe run` first)" }) + "\n");
|
|
4675
|
+
process.exitCode = 1;
|
|
4676
|
+
return;
|
|
4677
|
+
}
|
|
4678
|
+
process.stdout.write(JSON.stringify(r, null, 2) + "\n");
|
|
4679
|
+
}
|
|
4680
|
+
catch (e) {
|
|
4681
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
4682
|
+
process.exitCode = 1;
|
|
4683
|
+
}
|
|
4684
|
+
});
|
|
4685
|
+
// v2.58.0 — LIVING LAB primitive: 24/7 autonomous test bot.
|
|
4686
|
+
const livingLabParent = program
|
|
4687
|
+
.command("living_lab")
|
|
4688
|
+
.description("v2.58 — 24/7 LIVING LAB test bot. Default action = status.")
|
|
4689
|
+
.action(async () => {
|
|
4690
|
+
try {
|
|
4691
|
+
const core = await import("@mneme-ai/core");
|
|
4692
|
+
const hb = core.livingLab.readHeartbeat(process.cwd());
|
|
4693
|
+
const fresh = core.livingLab.isHeartbeatFresh(process.cwd());
|
|
4694
|
+
const open = core.livingLab.openFindings(process.cwd()).length;
|
|
4695
|
+
process.stdout.write(JSON.stringify({ ok: fresh && open === 0, heartbeat: hb, fresh, openFindings: open, hint: !hb ? "no heartbeat — run `mneme living_lab start --interval 300`" : !fresh ? "heartbeat stale — daemon may be down" : open > 0 ? `${open} open finding(s) blocking release` : "all clear" }, null, 2) + "\n");
|
|
4696
|
+
}
|
|
4697
|
+
catch (e) {
|
|
4698
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
4699
|
+
process.exitCode = 1;
|
|
4700
|
+
}
|
|
4701
|
+
});
|
|
4702
|
+
livingLabParent.command("tick")
|
|
4703
|
+
.description("Run a single in-process LIVING LAB tick (probe ONE tool + update learning + maybe file finding).")
|
|
4704
|
+
.action(async () => {
|
|
4705
|
+
try {
|
|
4706
|
+
const core = await import("@mneme-ai/core");
|
|
4707
|
+
const r = core.livingLab.runLivingLabTick({ cwd: process.cwd() });
|
|
4708
|
+
process.stdout.write(JSON.stringify(r, null, 2) + "\n");
|
|
4709
|
+
}
|
|
4710
|
+
catch (e) {
|
|
4711
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
4712
|
+
process.exitCode = 1;
|
|
4713
|
+
}
|
|
4714
|
+
});
|
|
4715
|
+
livingLabParent.command("start")
|
|
4716
|
+
.description("Spawn the LIVING LAB daemon as a detached background process.")
|
|
4717
|
+
.option("--interval <s>", "tick interval in seconds (default 300 = 5min)", (v) => Number(v), 300)
|
|
4718
|
+
.action(async (opts) => {
|
|
4719
|
+
try {
|
|
4720
|
+
const core = await import("@mneme-ai/core");
|
|
4721
|
+
const r = core.livingLab.spawnBackgroundDaemon({ cwd: process.cwd(), intervalMs: (opts.interval ?? 300) * 1000 });
|
|
4722
|
+
process.stdout.write(JSON.stringify({ ok: r.pid > 0, pid: r.pid, pidFile: r.pidFile, hint: `daemon PID ${r.pid} spawned; logs only in heartbeat.json / findings.jsonl` }, null, 2) + "\n");
|
|
4723
|
+
}
|
|
4724
|
+
catch (e) {
|
|
4725
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
4726
|
+
process.exitCode = 1;
|
|
4727
|
+
}
|
|
4728
|
+
});
|
|
4729
|
+
livingLabParent.command("loop")
|
|
4730
|
+
.description("Run the LIVING LAB tick loop in this process (used by `start` under the hood; usually you want `start`).")
|
|
4731
|
+
.option("--interval <s>", "tick interval in seconds", (v) => Number(v), 300)
|
|
4732
|
+
.option("--max-ticks <n>", "stop after N ticks (default: forever)", (v) => Number(v))
|
|
4733
|
+
.action(async (opts) => {
|
|
4734
|
+
try {
|
|
4735
|
+
const core = await import("@mneme-ai/core");
|
|
4736
|
+
await core.livingLab.runDaemon({ cwd: process.cwd(), intervalMs: (opts.interval ?? 300) * 1000, maxTicks: opts.maxTicks });
|
|
4737
|
+
}
|
|
4738
|
+
catch (e) {
|
|
4739
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
4740
|
+
process.exitCode = 1;
|
|
4741
|
+
}
|
|
4742
|
+
});
|
|
4743
|
+
livingLabParent.command("findings")
|
|
4744
|
+
.description("List the LIVING LAB findings ledger (HMAC-chain verified).")
|
|
4745
|
+
.action(async () => {
|
|
4746
|
+
try {
|
|
4747
|
+
const core = await import("@mneme-ai/core");
|
|
4748
|
+
const findings = core.livingLab.readFindings(process.cwd());
|
|
4749
|
+
const chainOk = core.livingLab.verifyFindingChain(process.cwd());
|
|
4750
|
+
const open = core.livingLab.openFindings(process.cwd());
|
|
4751
|
+
process.stdout.write(JSON.stringify({ ok: chainOk, total: findings.length, openCount: open.length, open, chainOk }, null, 2) + "\n");
|
|
4752
|
+
}
|
|
4753
|
+
catch (e) {
|
|
4754
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
4755
|
+
process.exitCode = 1;
|
|
4756
|
+
}
|
|
4757
|
+
});
|
|
4758
|
+
livingLabParent.command("propose")
|
|
4759
|
+
.description("Generate proposal artifacts for every open finding (writes .mneme/living_lab/proposals/<id>.proposal.md).")
|
|
4760
|
+
.action(async () => {
|
|
4761
|
+
try {
|
|
4762
|
+
const core = await import("@mneme-ai/core");
|
|
4763
|
+
const open = core.livingLab.openFindings(process.cwd());
|
|
4764
|
+
const wrote = open.map((f) => core.livingLab.writeProposalForFinding(process.cwd(), f).path);
|
|
4765
|
+
process.stdout.write(JSON.stringify({ ok: true, wrote }, null, 2) + "\n");
|
|
4766
|
+
}
|
|
4767
|
+
catch (e) {
|
|
4768
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
4769
|
+
process.exitCode = 1;
|
|
4770
|
+
}
|
|
4771
|
+
});
|
|
4772
|
+
livingLabParent.command("commit")
|
|
4773
|
+
.description("Commit all open proposals to a fresh `living-lab-<ts>` branch + push to origin. Refuses to touch main directly.")
|
|
4774
|
+
.action(async () => {
|
|
4775
|
+
try {
|
|
4776
|
+
const core = await import("@mneme-ai/core");
|
|
4777
|
+
const r = core.livingLab.commitProposalToBranch(process.cwd());
|
|
4778
|
+
process.stdout.write(JSON.stringify(r, null, 2) + "\n");
|
|
4779
|
+
if (!r.ok)
|
|
4780
|
+
process.exitCode = 1;
|
|
4781
|
+
}
|
|
4782
|
+
catch (e) {
|
|
4783
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
4784
|
+
process.exitCode = 1;
|
|
4785
|
+
}
|
|
4786
|
+
});
|
|
4633
4787
|
// v2.54.0 — STRATEGY primitive (RFC drafts + pricing tiers).
|
|
4634
4788
|
const strategyParent = program
|
|
4635
4789
|
.command("strategy")
|
|
@@ -4849,6 +5003,206 @@ export async function run(argv) {
|
|
|
4849
5003
|
process.exitCode = 1;
|
|
4850
5004
|
}
|
|
4851
5005
|
});
|
|
5006
|
+
// ──────────────────────────────────────────────────────────────────
|
|
5007
|
+
// v2.57.0 — Top-level surface promotion (no `nemesis` prefix needed)
|
|
5008
|
+
// + WIRING DOCTOR primitive (AST-level per-feature check)
|
|
5009
|
+
// ──────────────────────────────────────────────────────────────────
|
|
5010
|
+
// 🧠 LETHE top-level alias
|
|
5011
|
+
const letheParent = program
|
|
5012
|
+
.command("lethe")
|
|
5013
|
+
.description("🧠 v2.57 — LETHE alias (forwards to `mneme nemesis lethe_forget`). GDPR Art 17 forget primitive.");
|
|
5014
|
+
letheParent.command("forget")
|
|
5015
|
+
.description("Forget a row from a JSONL ledger. Use --ledger <p> --row <n> [--dry-run].")
|
|
5016
|
+
.requiredOption("--ledger <p>", "Repo-relative ledger path")
|
|
5017
|
+
.requiredOption("--row <n>", "Row index (0-based)", (v) => Number(v))
|
|
5018
|
+
.option("--jurisdiction <t>", "GDPR jurisdiction tag", "EU-GDPR-Art17")
|
|
5019
|
+
.option("--dry-run", "Build receipt without rewriting", false)
|
|
5020
|
+
.action(async (opts) => {
|
|
5021
|
+
try {
|
|
5022
|
+
const core = await import("@mneme-ai/core");
|
|
5023
|
+
const r = core.nemesis.forgetRow({ repoRoot: process.cwd(), ledgerRelative: opts.ledger, rowIndex: opts.row, jurisdiction: opts.jurisdiction, dryRun: opts.dryRun ?? false });
|
|
5024
|
+
process.stdout.write(JSON.stringify(r, null, 2) + "\n");
|
|
5025
|
+
if (!r.ok)
|
|
5026
|
+
process.exitCode = 1;
|
|
5027
|
+
}
|
|
5028
|
+
catch (e) {
|
|
5029
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
5030
|
+
process.exitCode = 1;
|
|
5031
|
+
}
|
|
5032
|
+
});
|
|
5033
|
+
letheParent.command("verify")
|
|
5034
|
+
.description("Verify a ForgetReceipt cryptographically. Use --stdin.")
|
|
5035
|
+
.option("--stdin", "Read receipt JSON from stdin")
|
|
5036
|
+
.action(async () => {
|
|
5037
|
+
try {
|
|
5038
|
+
const core = await import("@mneme-ai/core");
|
|
5039
|
+
const chunks = [];
|
|
5040
|
+
for await (const c of process.stdin)
|
|
5041
|
+
chunks.push(c);
|
|
5042
|
+
const body = Buffer.concat(chunks).toString("utf8").trim();
|
|
5043
|
+
if (!body) {
|
|
5044
|
+
process.stdout.write(JSON.stringify({ ok: false, error: "pass receipt JSON via stdin" }) + "\n");
|
|
5045
|
+
process.exitCode = 1;
|
|
5046
|
+
return;
|
|
5047
|
+
}
|
|
5048
|
+
const v = core.nemesis.verifyForgetReceipt(JSON.parse(body));
|
|
5049
|
+
process.stdout.write(JSON.stringify(v, null, 2) + "\n");
|
|
5050
|
+
if (!v.ok)
|
|
5051
|
+
process.exitCode = 1;
|
|
5052
|
+
}
|
|
5053
|
+
catch (e) {
|
|
5054
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
5055
|
+
process.exitCode = 1;
|
|
5056
|
+
}
|
|
5057
|
+
});
|
|
5058
|
+
// ⚖ GAVEL top-level alias
|
|
5059
|
+
const gavelParent = program
|
|
5060
|
+
.command("gavel")
|
|
5061
|
+
.description("⚖ v2.57 — GAVEL alias (forwards to `mneme nemesis gavel_pack/verify`). Court-admissible bundle.");
|
|
5062
|
+
gavelParent.command("pack")
|
|
5063
|
+
.description("Bind THEMIS + EU stamp + SIBYL into court-admissible Merkle bundle. Use --stdin.")
|
|
5064
|
+
.option("--stdin", "Read bundle input JSON from stdin")
|
|
5065
|
+
.action(async () => {
|
|
5066
|
+
try {
|
|
5067
|
+
const core = await import("@mneme-ai/core");
|
|
5068
|
+
const chunks = [];
|
|
5069
|
+
for await (const c of process.stdin)
|
|
5070
|
+
chunks.push(c);
|
|
5071
|
+
const body = Buffer.concat(chunks).toString("utf8").trim();
|
|
5072
|
+
if (!body) {
|
|
5073
|
+
process.stdout.write(JSON.stringify({ ok: false, error: "pass bundle input JSON via stdin" }) + "\n");
|
|
5074
|
+
process.exitCode = 1;
|
|
5075
|
+
return;
|
|
5076
|
+
}
|
|
5077
|
+
const r = core.nemesis.buildGavelBundle(JSON.parse(body));
|
|
5078
|
+
process.stdout.write(JSON.stringify(r, null, 2) + "\n");
|
|
5079
|
+
if (!r.ok)
|
|
5080
|
+
process.exitCode = 1;
|
|
5081
|
+
}
|
|
5082
|
+
catch (e) {
|
|
5083
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
5084
|
+
process.exitCode = 1;
|
|
5085
|
+
}
|
|
5086
|
+
});
|
|
5087
|
+
gavelParent.command("verify")
|
|
5088
|
+
.description("Verify bundle HMAC + Merkle root + per-artifact signature. Use --stdin.")
|
|
5089
|
+
.option("--stdin", "Read bundle JSON from stdin")
|
|
5090
|
+
.action(async () => {
|
|
5091
|
+
try {
|
|
5092
|
+
const core = await import("@mneme-ai/core");
|
|
5093
|
+
const chunks = [];
|
|
5094
|
+
for await (const c of process.stdin)
|
|
5095
|
+
chunks.push(c);
|
|
5096
|
+
const body = Buffer.concat(chunks).toString("utf8").trim();
|
|
5097
|
+
if (!body) {
|
|
5098
|
+
process.stdout.write(JSON.stringify({ ok: false, error: "pass bundle JSON via stdin" }) + "\n");
|
|
5099
|
+
process.exitCode = 1;
|
|
5100
|
+
return;
|
|
5101
|
+
}
|
|
5102
|
+
const v = core.nemesis.verifyGavelBundle(JSON.parse(body));
|
|
5103
|
+
process.stdout.write(JSON.stringify(v, null, 2) + "\n");
|
|
5104
|
+
if (!v.ok)
|
|
5105
|
+
process.exitCode = 1;
|
|
5106
|
+
}
|
|
5107
|
+
catch (e) {
|
|
5108
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
5109
|
+
process.exitCode = 1;
|
|
5110
|
+
}
|
|
5111
|
+
});
|
|
5112
|
+
// 🌐 NIMBUS top-level alias
|
|
5113
|
+
const nimbusParent = program
|
|
5114
|
+
.command("nimbus")
|
|
5115
|
+
.description("🌐 v2.57 — NIMBUS alias (forwards to `mneme nemesis nimbus_*`). Federated trust mesh.");
|
|
5116
|
+
nimbusParent.command("publish")
|
|
5117
|
+
.description("Publish leaderboard card to local pub-store. Use --stdin or --org-tag.")
|
|
5118
|
+
.option("--stdin", "Read publish input JSON from stdin")
|
|
5119
|
+
.option("--org-tag <name>", "Org tag (alternative to --stdin)")
|
|
5120
|
+
.action(async (opts) => {
|
|
5121
|
+
try {
|
|
5122
|
+
const core = await import("@mneme-ai/core");
|
|
5123
|
+
let j = null;
|
|
5124
|
+
if (opts.stdin) {
|
|
5125
|
+
const chunks = [];
|
|
5126
|
+
for await (const c of process.stdin)
|
|
5127
|
+
chunks.push(c);
|
|
5128
|
+
const body = Buffer.concat(chunks).toString("utf8").trim();
|
|
5129
|
+
if (body)
|
|
5130
|
+
j = JSON.parse(body);
|
|
5131
|
+
}
|
|
5132
|
+
const orgTag = opts.orgTag ?? j?.orgTag;
|
|
5133
|
+
if (!orgTag) {
|
|
5134
|
+
process.stdout.write(JSON.stringify({ ok: false, error: "orgTag required (--org-tag or via stdin)" }) + "\n");
|
|
5135
|
+
process.exitCode = 1;
|
|
5136
|
+
return;
|
|
5137
|
+
}
|
|
5138
|
+
const input = { ...(j ?? {}), repoRoot: process.cwd(), orgTag };
|
|
5139
|
+
const r = core.nemesis.publishCard(input);
|
|
5140
|
+
process.stdout.write(JSON.stringify(r, null, 2) + "\n");
|
|
5141
|
+
if (!r.ok)
|
|
5142
|
+
process.exitCode = 1;
|
|
5143
|
+
}
|
|
5144
|
+
catch (e) {
|
|
5145
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
5146
|
+
process.exitCode = 1;
|
|
5147
|
+
}
|
|
5148
|
+
});
|
|
5149
|
+
nimbusParent.command("subscribe")
|
|
5150
|
+
.description("Subscribe to foreign org's card. Verifies HMAC + expiry. --trust <0..1> optional.")
|
|
5151
|
+
.option("--stdin", "Read card JSON from stdin")
|
|
5152
|
+
.option("--trust <n>", "Local trust weight (0..1)", (v) => Number(v), 0.5)
|
|
5153
|
+
.action(async (opts) => {
|
|
5154
|
+
try {
|
|
5155
|
+
const core = await import("@mneme-ai/core");
|
|
5156
|
+
const chunks = [];
|
|
5157
|
+
for await (const c of process.stdin)
|
|
5158
|
+
chunks.push(c);
|
|
5159
|
+
const body = Buffer.concat(chunks).toString("utf8").trim();
|
|
5160
|
+
if (!body) {
|
|
5161
|
+
process.stdout.write(JSON.stringify({ ok: false, error: "pass card JSON via stdin" }) + "\n");
|
|
5162
|
+
process.exitCode = 1;
|
|
5163
|
+
return;
|
|
5164
|
+
}
|
|
5165
|
+
const r = core.nemesis.subscribeCard({ repoRoot: process.cwd(), card: JSON.parse(body), trustWeight: opts.trust });
|
|
5166
|
+
process.stdout.write(JSON.stringify(r, null, 2) + "\n");
|
|
5167
|
+
if (!r.ok)
|
|
5168
|
+
process.exitCode = 1;
|
|
5169
|
+
}
|
|
5170
|
+
catch (e) {
|
|
5171
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
5172
|
+
process.exitCode = 1;
|
|
5173
|
+
}
|
|
5174
|
+
});
|
|
5175
|
+
nimbusParent.command("reputation")
|
|
5176
|
+
.description("Compute cross-org weighted vendor reputation from subscribed cards.")
|
|
5177
|
+
.action(async () => {
|
|
5178
|
+
try {
|
|
5179
|
+
const core = await import("@mneme-ai/core");
|
|
5180
|
+
const r = core.nemesis.computeCrossOrgReputation(process.cwd());
|
|
5181
|
+
process.stdout.write(JSON.stringify({ ok: true, vendors: r }, null, 2) + "\n");
|
|
5182
|
+
}
|
|
5183
|
+
catch (e) {
|
|
5184
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
5185
|
+
process.exitCode = 1;
|
|
5186
|
+
}
|
|
5187
|
+
});
|
|
5188
|
+
// 🤯 WIRING DOCTOR — AST-level per-feature surface check
|
|
5189
|
+
program
|
|
5190
|
+
.command("wiring_doctor")
|
|
5191
|
+
.description("🤯 v2.57 — WIRING DOCTOR: scan core / sdk / cli source for per-feature surface coverage (core export · SDK method · CLI verb · TG claim). Replaces commit-msg parsing with structural verification.")
|
|
5192
|
+
.option("--features <list...>", "Features to check (default: lethe / gavel / nimbus / janus / stargate / dragon / launch_window)")
|
|
5193
|
+
.action(async (opts) => {
|
|
5194
|
+
try {
|
|
5195
|
+
const core = await import("@mneme-ai/core");
|
|
5196
|
+
const r = core.wiringDoctor.diagnose(process.cwd(), { features: opts.features });
|
|
5197
|
+
process.stdout.write(JSON.stringify(r, null, 2) + "\n");
|
|
5198
|
+
if (!r.ok)
|
|
5199
|
+
process.exitCode = 1;
|
|
5200
|
+
}
|
|
5201
|
+
catch (e) {
|
|
5202
|
+
process.stdout.write(JSON.stringify({ ok: false, error: e.message }) + "\n");
|
|
5203
|
+
process.exitCode = 1;
|
|
5204
|
+
}
|
|
5205
|
+
});
|
|
4852
5206
|
// v2.53.0 — CATALOG COUNT single source of truth.
|
|
4853
5207
|
const catalogParent = program
|
|
4854
5208
|
.command("catalog")
|