@mneme-ai/core 2.21.8-lite → 2.22.0-lite
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/agent_manifest.d.ts +1 -1
- package/dist/agent_manifest.d.ts.map +1 -1
- package/dist/agent_manifest.js +12 -1
- package/dist/agent_manifest.js.map +1 -1
- package/dist/companion/autospec.d.ts +58 -0
- package/dist/companion/autospec.d.ts.map +1 -0
- package/dist/companion/autospec.js +150 -0
- package/dist/companion/autospec.js.map +1 -0
- package/dist/companion/companion.test.d.ts +2 -0
- package/dist/companion/companion.test.d.ts.map +1 -0
- package/dist/companion/companion.test.js +215 -0
- package/dist/companion/companion.test.js.map +1 -0
- package/dist/companion/contract.d.ts +56 -0
- package/dist/companion/contract.d.ts.map +1 -0
- package/dist/companion/contract.js +209 -0
- package/dist/companion/contract.js.map +1 -0
- package/dist/companion/doppelganger.d.ts +84 -0
- package/dist/companion/doppelganger.d.ts.map +1 -0
- package/dist/companion/doppelganger.js +227 -0
- package/dist/companion/doppelganger.js.map +1 -0
- package/dist/companion/index.d.ts +67 -0
- package/dist/companion/index.d.ts.map +1 -0
- package/dist/companion/index.js +100 -0
- package/dist/companion/index.js.map +1 -0
- package/dist/companion/learn_loop.d.ts +55 -0
- package/dist/companion/learn_loop.d.ts.map +1 -0
- package/dist/companion/learn_loop.js +105 -0
- package/dist/companion/learn_loop.js.map +1 -0
- package/dist/companion/storyline.d.ts +40 -0
- package/dist/companion/storyline.d.ts.map +1 -0
- package/dist/companion/storyline.js +95 -0
- package/dist/companion/storyline.js.map +1 -0
- package/dist/conductor/conductor.test.d.ts +2 -0
- package/dist/conductor/conductor.test.d.ts.map +1 -0
- package/dist/conductor/conductor.test.js +182 -0
- package/dist/conductor/conductor.test.js.map +1 -0
- package/dist/conductor/index.d.ts +130 -0
- package/dist/conductor/index.d.ts.map +1 -0
- package/dist/conductor/index.js +273 -0
- package/dist/conductor/index.js.map +1 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +11 -0
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
|
@@ -0,0 +1,227 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* v2.22.0 — COMPANION · DOPPELGANGER.
|
|
3
|
+
*
|
|
4
|
+
* Copy-on-write fs overlay that runs a verb's effects in a SHADOW
|
|
5
|
+
* directory and returns the diff. AI agent sees EXACT changes before
|
|
6
|
+
* committing.
|
|
7
|
+
*
|
|
8
|
+
* Implementation strategy:
|
|
9
|
+
* 1. Caller hands us a `repoRoot` + a function that simulates the
|
|
10
|
+
* verb (no real I/O).
|
|
11
|
+
* 2. We seed the shadow by copying repo state lazily (overlay style
|
|
12
|
+
* — only files the verb touches are materialised).
|
|
13
|
+
* 3. We invoke the verb against the shadow via dependency injection
|
|
14
|
+
* (`fs` proxy + `process.exit` shim).
|
|
15
|
+
* 4. We compute the diff: files added / changed / removed; exit
|
|
16
|
+
* code; would-be network calls.
|
|
17
|
+
*
|
|
18
|
+
* Limitations (honest):
|
|
19
|
+
* - Verbs that call native C++ code (sharp, sqlite native) bypass
|
|
20
|
+
* the proxy. We catch *most* of them via the existing DLL-extract
|
|
21
|
+
* mechanism but cannot guarantee 100 % coverage. Doppelganger
|
|
22
|
+
* reports a `leakage: "possible"` flag for verbs known to use
|
|
23
|
+
* native modules.
|
|
24
|
+
* - Network I/O is currently *blocked* in shadow mode (any outbound
|
|
25
|
+
* request returns a "would-fetch" record instead of executing).
|
|
26
|
+
* This means doppelganger preview for network-bound verbs is
|
|
27
|
+
* approximate: we can predict "would call URL X" but not the
|
|
28
|
+
* response.
|
|
29
|
+
*/
|
|
30
|
+
import { existsSync, readFileSync, writeFileSync, mkdirSync, rmSync, readdirSync, statSync, cpSync } from "node:fs";
|
|
31
|
+
import { join, relative, sep, dirname } from "node:path";
|
|
32
|
+
import { createHash, randomBytes } from "node:crypto";
|
|
33
|
+
import { tmpdir } from "node:os";
|
|
34
|
+
function sha256(buf) {
|
|
35
|
+
return createHash("sha256").update(buf).digest("hex").slice(0, 16);
|
|
36
|
+
}
|
|
37
|
+
function snapshotTree(root) {
|
|
38
|
+
const out = new Map();
|
|
39
|
+
const stack = [root];
|
|
40
|
+
while (stack.length > 0) {
|
|
41
|
+
const dir = stack.pop();
|
|
42
|
+
let entries;
|
|
43
|
+
try {
|
|
44
|
+
entries = readdirSync(dir);
|
|
45
|
+
}
|
|
46
|
+
catch {
|
|
47
|
+
continue;
|
|
48
|
+
}
|
|
49
|
+
for (const name of entries) {
|
|
50
|
+
if (name === "node_modules" || name === ".git")
|
|
51
|
+
continue;
|
|
52
|
+
const full = join(dir, name);
|
|
53
|
+
let st;
|
|
54
|
+
try {
|
|
55
|
+
st = statSync(full);
|
|
56
|
+
}
|
|
57
|
+
catch {
|
|
58
|
+
continue;
|
|
59
|
+
}
|
|
60
|
+
if (st.isDirectory()) {
|
|
61
|
+
stack.push(full);
|
|
62
|
+
continue;
|
|
63
|
+
}
|
|
64
|
+
if (!st.isFile())
|
|
65
|
+
continue;
|
|
66
|
+
let buf;
|
|
67
|
+
try {
|
|
68
|
+
buf = readFileSync(full);
|
|
69
|
+
}
|
|
70
|
+
catch {
|
|
71
|
+
continue;
|
|
72
|
+
}
|
|
73
|
+
const rel = relative(root, full).split(sep).join("/");
|
|
74
|
+
out.set(rel, { sha: sha256(buf), size: buf.length });
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
return out;
|
|
78
|
+
}
|
|
79
|
+
function diffSnapshots(before, after) {
|
|
80
|
+
const effects = [];
|
|
81
|
+
for (const [path, b] of before) {
|
|
82
|
+
const a = after.get(path);
|
|
83
|
+
if (!a)
|
|
84
|
+
effects.push({ path, kind: "removed", beforeSha: b.sha, beforeBytes: b.size });
|
|
85
|
+
else if (a.sha !== b.sha)
|
|
86
|
+
effects.push({ path, kind: "changed", beforeSha: b.sha, afterSha: a.sha, beforeBytes: b.size, afterBytes: a.size });
|
|
87
|
+
}
|
|
88
|
+
for (const [path, a] of after) {
|
|
89
|
+
if (!before.has(path))
|
|
90
|
+
effects.push({ path, kind: "added", afterSha: a.sha, afterBytes: a.size });
|
|
91
|
+
}
|
|
92
|
+
return effects;
|
|
93
|
+
}
|
|
94
|
+
/** Run `verbFn` in a shadow copy of `repoRoot` and return the diff.
|
|
95
|
+
* `verbFn` receives the shadow path; it should perform its work
|
|
96
|
+
* AGAINST THAT PATH (the caller wires its own dependency injection;
|
|
97
|
+
* see conductor.executePlan for the canonical usage). */
|
|
98
|
+
export async function dryRun(repoRoot, verbFn, opts = {}) {
|
|
99
|
+
const shadow = join(tmpdir(), "mneme-doppel-" + randomBytes(4).toString("hex"));
|
|
100
|
+
// Bound the copy: only mirror `.mneme/` + the repo root manifest. Bulk
|
|
101
|
+
// of dev-time fs is irrelevant for verb dry-run and copying everything
|
|
102
|
+
// is prohibitive on big repos.
|
|
103
|
+
mkdirSync(shadow, { recursive: true });
|
|
104
|
+
try {
|
|
105
|
+
if (existsSync(join(repoRoot, ".mneme"))) {
|
|
106
|
+
cpSync(join(repoRoot, ".mneme"), join(shadow, ".mneme"), { recursive: true });
|
|
107
|
+
}
|
|
108
|
+
// Snapshot before.
|
|
109
|
+
const before = snapshotTree(shadow);
|
|
110
|
+
let exitCode = 0;
|
|
111
|
+
let result;
|
|
112
|
+
let stdoutSample = "";
|
|
113
|
+
let stderrSample = "";
|
|
114
|
+
const wouldFetch = [];
|
|
115
|
+
try {
|
|
116
|
+
result = await verbFn(shadow);
|
|
117
|
+
}
|
|
118
|
+
catch (e) {
|
|
119
|
+
exitCode = typeof e?.code === "number" ? e.code : 1;
|
|
120
|
+
stderrSample = (e?.message ?? String(e)).slice(0, 500);
|
|
121
|
+
}
|
|
122
|
+
const after = snapshotTree(shadow);
|
|
123
|
+
const fileEffects = diffSnapshots(before, after);
|
|
124
|
+
let leakage = "none";
|
|
125
|
+
let leakageReason;
|
|
126
|
+
if (opts.knownNativeUse) {
|
|
127
|
+
leakage = "possible";
|
|
128
|
+
leakageReason = "verb is known to load native modules (sharp/sqlite); effects from C++ code are not captured";
|
|
129
|
+
}
|
|
130
|
+
if (opts.knownNetworkUse) {
|
|
131
|
+
leakage = leakage === "none" ? "possible" : leakage;
|
|
132
|
+
leakageReason = (leakageReason ?? "") + (leakageReason ? " · " : "") + "verb reaches network; only URLs are previewed, not responses";
|
|
133
|
+
}
|
|
134
|
+
return { fileEffects, exitCode, wouldFetch, stdoutSample, stderrSample, leakage, leakageReason, result };
|
|
135
|
+
}
|
|
136
|
+
finally {
|
|
137
|
+
try {
|
|
138
|
+
rmSync(shadow, { recursive: true, force: true });
|
|
139
|
+
}
|
|
140
|
+
catch { /* */ }
|
|
141
|
+
}
|
|
142
|
+
}
|
|
143
|
+
/** Two-phase commit primitive used by the conductor: stage to a temp
|
|
144
|
+
* dir, atomically move into place, or rollback by deleting the stage.
|
|
145
|
+
* Returns the staged path so the conductor can either rename or
|
|
146
|
+
* remove. */
|
|
147
|
+
export function stageCommit(repoRoot, opts = {}) {
|
|
148
|
+
const stage = opts.stageRoot ?? join(tmpdir(), "mneme-stage-" + randomBytes(4).toString("hex"));
|
|
149
|
+
mkdirSync(stage, { recursive: true });
|
|
150
|
+
return {
|
|
151
|
+
stagePath: stage,
|
|
152
|
+
rollback: () => { try {
|
|
153
|
+
rmSync(stage, { recursive: true, force: true });
|
|
154
|
+
}
|
|
155
|
+
catch { /* */ } },
|
|
156
|
+
};
|
|
157
|
+
}
|
|
158
|
+
/** Atomically apply staged files into `repoRoot`. Uses `rename` when
|
|
159
|
+
* same filesystem; falls back to `cp -r + rm` otherwise. Caller-side
|
|
160
|
+
* contract: every file in `stagePath` has been verified by the
|
|
161
|
+
* doppelganger. */
|
|
162
|
+
export function applyCommit(stagePath, repoRoot) {
|
|
163
|
+
if (!existsSync(stagePath))
|
|
164
|
+
return;
|
|
165
|
+
const stack = [stagePath];
|
|
166
|
+
while (stack.length > 0) {
|
|
167
|
+
const dir = stack.pop();
|
|
168
|
+
let entries;
|
|
169
|
+
try {
|
|
170
|
+
entries = readdirSync(dir);
|
|
171
|
+
}
|
|
172
|
+
catch {
|
|
173
|
+
continue;
|
|
174
|
+
}
|
|
175
|
+
for (const name of entries) {
|
|
176
|
+
const full = join(dir, name);
|
|
177
|
+
const rel = relative(stagePath, full);
|
|
178
|
+
const target = join(repoRoot, rel);
|
|
179
|
+
let st;
|
|
180
|
+
try {
|
|
181
|
+
st = statSync(full);
|
|
182
|
+
}
|
|
183
|
+
catch {
|
|
184
|
+
continue;
|
|
185
|
+
}
|
|
186
|
+
if (st.isDirectory()) {
|
|
187
|
+
mkdirSync(target, { recursive: true });
|
|
188
|
+
stack.push(full);
|
|
189
|
+
}
|
|
190
|
+
else if (st.isFile()) {
|
|
191
|
+
mkdirSync(dirname(target), { recursive: true });
|
|
192
|
+
// overwrite — caller-side contract: doppelganger has previewed
|
|
193
|
+
writeFileSync(target, readFileSync(full));
|
|
194
|
+
}
|
|
195
|
+
}
|
|
196
|
+
}
|
|
197
|
+
try {
|
|
198
|
+
rmSync(stagePath, { recursive: true, force: true });
|
|
199
|
+
}
|
|
200
|
+
catch { /* */ }
|
|
201
|
+
}
|
|
202
|
+
export function formatDoppelganger(r) {
|
|
203
|
+
const lines = [`👻 DOPPELGANGER preview`, ""];
|
|
204
|
+
lines.push(` Exit code: ${r.exitCode}`);
|
|
205
|
+
lines.push(` Leakage: ${r.leakage}${r.leakageReason ? ` (${r.leakageReason})` : ""}`);
|
|
206
|
+
lines.push(` Files added: ${r.fileEffects.filter((e) => e.kind === "added").length}`);
|
|
207
|
+
lines.push(` Files changed: ${r.fileEffects.filter((e) => e.kind === "changed").length}`);
|
|
208
|
+
lines.push(` Files removed: ${r.fileEffects.filter((e) => e.kind === "removed").length}`);
|
|
209
|
+
if (r.wouldFetch.length > 0) {
|
|
210
|
+
lines.push("");
|
|
211
|
+
lines.push(` Network calls (preview only):`);
|
|
212
|
+
for (const u of r.wouldFetch.slice(0, 6))
|
|
213
|
+
lines.push(` - ${u}`);
|
|
214
|
+
if (r.wouldFetch.length > 6)
|
|
215
|
+
lines.push(` (and ${r.wouldFetch.length - 6} more)`);
|
|
216
|
+
}
|
|
217
|
+
if (r.fileEffects.length > 0) {
|
|
218
|
+
lines.push("");
|
|
219
|
+
lines.push(` File diff (first 12 entries):`);
|
|
220
|
+
for (const e of r.fileEffects.slice(0, 12)) {
|
|
221
|
+
const arrow = e.kind === "added" ? "+" : e.kind === "removed" ? "-" : "Δ";
|
|
222
|
+
lines.push(` ${arrow} ${e.path} ${e.kind === "added" ? `(+${e.afterBytes}B)` : e.kind === "removed" ? `(-${e.beforeBytes}B)` : `${e.beforeBytes}B → ${e.afterBytes}B`}`);
|
|
223
|
+
}
|
|
224
|
+
}
|
|
225
|
+
return lines.join("\n");
|
|
226
|
+
}
|
|
227
|
+
//# sourceMappingURL=doppelganger.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"doppelganger.js","sourceRoot":"","sources":["../../src/companion/doppelganger.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* v2.22.0 — COMPANION.
|
|
3
|
+
*
|
|
4
|
+
* Five composed primitives that turn every Mneme verb into an AI-
|
|
5
|
+
* agent-friendly surface:
|
|
6
|
+
*
|
|
7
|
+
* 1. CONTRACT — pre/post-conditions, side-effects, DEFCON tier
|
|
8
|
+
* 2. AUTOSPEC — JSON Schema for args + validate() helper
|
|
9
|
+
* 3. DOPPELGANGER — copy-on-write dry-run + diff
|
|
10
|
+
* 4. STORYLINE — Markov chain over pheromone log
|
|
11
|
+
* 5. LEARN LOOP — failure patterns + outcome stats
|
|
12
|
+
*
|
|
13
|
+
* Auto-registration: any new verb that appears in
|
|
14
|
+
* `MNEME_COMMAND_CATALOG` automatically gets contract + autospec.
|
|
15
|
+
* Doppelganger + storyline + learn-loop activate once the verb has
|
|
16
|
+
* been invoked at least once (pheromone seed).
|
|
17
|
+
*
|
|
18
|
+
* Public API:
|
|
19
|
+
* companionFor(verb) — composed Companion for a single verb
|
|
20
|
+
* formatCompanion(c) — human-readable rendering
|
|
21
|
+
* listCompanionable() — verbs that have full data
|
|
22
|
+
* companionableCoverage() — % of catalog with at least contract+autospec
|
|
23
|
+
*/
|
|
24
|
+
export { contractFor, allContracts, findContract, formatContract, type VerbContract, type DefconLevel, type IdempotencyLevel } from "./contract.js";
|
|
25
|
+
export { parseArgSchema, schemaFor, validateArgs, formatSchema, allSchemas, type ArgSchema, type ValidateResult, type ProvidedArgs } from "./autospec.js";
|
|
26
|
+
export { dryRun, stageCommit, applyCommit, formatDoppelganger, type DoppelgangerResult, type FileEffect, type DoppelgangerOptions, type CommitOptions } from "./doppelganger.js";
|
|
27
|
+
export { predictNext, predictPrior, formatStoryline, type TransitionStats, type StorylineQuery } from "./storyline.js";
|
|
28
|
+
export { computeOutcomeStats, commonMistakes, redactInvocation, formatOutcomeStats, formatMistakes, type VerbOutcomeStats, type CommonMistake, type RedactedInvocation } from "./learn_loop.js";
|
|
29
|
+
import { type VerbContract } from "./contract.js";
|
|
30
|
+
import { type ArgSchema } from "./autospec.js";
|
|
31
|
+
import { type TransitionStats } from "./storyline.js";
|
|
32
|
+
import { type VerbOutcomeStats, type CommonMistake } from "./learn_loop.js";
|
|
33
|
+
import { type ManifestCommand } from "../agent_manifest.js";
|
|
34
|
+
export interface Companion {
|
|
35
|
+
v: 1;
|
|
36
|
+
verb: string;
|
|
37
|
+
contract: VerbContract;
|
|
38
|
+
argSchema: ArgSchema;
|
|
39
|
+
storyline: {
|
|
40
|
+
next: TransitionStats[];
|
|
41
|
+
prior: TransitionStats[];
|
|
42
|
+
};
|
|
43
|
+
outcomeStats: VerbOutcomeStats;
|
|
44
|
+
commonMistakes: CommonMistake[];
|
|
45
|
+
/** Coverage flag — `false` means catalog metadata only, no live data yet. */
|
|
46
|
+
hasLiveData: boolean;
|
|
47
|
+
generatedAt: string;
|
|
48
|
+
}
|
|
49
|
+
export interface BuildCompanionOptions {
|
|
50
|
+
repoRoot?: string;
|
|
51
|
+
topK?: number;
|
|
52
|
+
}
|
|
53
|
+
export declare function companionFor(verb: string, opts?: BuildCompanionOptions): Companion | null;
|
|
54
|
+
export declare function formatCompanion(c: Companion): string;
|
|
55
|
+
/** Catalog-wide coverage report. Useful for CI + dashboards. */
|
|
56
|
+
export interface CoverageReport {
|
|
57
|
+
total: number;
|
|
58
|
+
withContract: number;
|
|
59
|
+
withAutospec: number;
|
|
60
|
+
withLiveData: number;
|
|
61
|
+
coverageContract: number;
|
|
62
|
+
coverageAutospec: number;
|
|
63
|
+
coverageLiveData: number;
|
|
64
|
+
}
|
|
65
|
+
export declare function companionableCoverage(repoRoot: string, catalog?: ManifestCommand[]): CoverageReport;
|
|
66
|
+
export declare function listCompanionable(catalog?: ManifestCommand[]): string[];
|
|
67
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/companion/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;GAsBG;AAEH,OAAO,EAAE,WAAW,EAAE,YAAY,EAAE,YAAY,EAAE,cAAc,EAAE,KAAK,YAAY,EAAE,KAAK,WAAW,EAAE,KAAK,gBAAgB,EAAE,MAAM,eAAe,CAAC;AACpJ,OAAO,EAAE,cAAc,EAAE,SAAS,EAAE,YAAY,EAAE,YAAY,EAAE,UAAU,EAAE,KAAK,SAAS,EAAE,KAAK,cAAc,EAAE,KAAK,YAAY,EAAE,MAAM,eAAe,CAAC;AAC1J,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,WAAW,EAAE,kBAAkB,EAAE,KAAK,kBAAkB,EAAE,KAAK,UAAU,EAAE,KAAK,mBAAmB,EAAE,KAAK,aAAa,EAAE,MAAM,mBAAmB,CAAC;AACjL,OAAO,EAAE,WAAW,EAAE,YAAY,EAAE,eAAe,EAAE,KAAK,eAAe,EAAE,KAAK,cAAc,EAAE,MAAM,gBAAgB,CAAC;AACvH,OAAO,EAAE,mBAAmB,EAAE,cAAc,EAAE,gBAAgB,EAAE,kBAAkB,EAAE,cAAc,EAAE,KAAK,gBAAgB,EAAE,KAAK,aAAa,EAAE,KAAK,kBAAkB,EAAE,MAAM,iBAAiB,CAAC;AAEhM,OAAO,EAA6C,KAAK,YAAY,EAAE,MAAM,eAAe,CAAC;AAC7F,OAAO,EAA2B,KAAK,SAAS,EAAE,MAAM,eAAe,CAAC;AACxE,OAAO,EAA8C,KAAK,eAAe,EAAE,MAAM,gBAAgB,CAAC;AAClG,OAAO,EAA2E,KAAK,gBAAgB,EAAE,KAAK,aAAa,EAAE,MAAM,iBAAiB,CAAC;AACrJ,OAAO,EAAyB,KAAK,eAAe,EAAE,MAAM,sBAAsB,CAAC;AAEnF,MAAM,WAAW,SAAS;IACxB,CAAC,EAAE,CAAC,CAAC;IACL,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,YAAY,CAAC;IACvB,SAAS,EAAE,SAAS,CAAC;IACrB,SAAS,EAAE;QAAE,IAAI,EAAE,eAAe,EAAE,CAAC;QAAC,KAAK,EAAE,eAAe,EAAE,CAAA;KAAE,CAAC;IACjE,YAAY,EAAE,gBAAgB,CAAC;IAC/B,cAAc,EAAE,aAAa,EAAE,CAAC;IAChC,6EAA6E;IAC7E,WAAW,EAAE,OAAO,CAAC;IACrB,WAAW,EAAE,MAAM,CAAC;CACrB;AAED,MAAM,WAAW,qBAAqB;IACpC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,IAAI,CAAC,EAAE,MAAM,CAAC;CACf;AAED,wBAAgB,YAAY,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,GAAE,qBAA0B,GAAG,SAAS,GAAG,IAAI,CAsB7F;AAED,wBAAgB,eAAe,CAAC,CAAC,EAAE,SAAS,GAAG,MAAM,CAcpD;AAED,gEAAgE;AAChE,MAAM,WAAW,cAAc;IAC7B,KAAK,EAAE,MAAM,CAAC;IACd,YAAY,EAAE,MAAM,CAAC;IACrB,YAAY,EAAE,MAAM,CAAC;IACrB,YAAY,EAAE,MAAM,CAAC;IACrB,gBAAgB,EAAE,MAAM,CAAC;IACzB,gBAAgB,EAAE,MAAM,CAAC;IACzB,gBAAgB,EAAE,MAAM,CAAC;CAC1B;AAED,wBAAgB,qBAAqB,CAAC,QAAQ,EAAE,MAAM,EAAE,OAAO,GAAE,eAAe,EAA0B,GAAG,cAAc,CAoB1H;AAED,wBAAgB,iBAAiB,CAAC,OAAO,GAAE,eAAe,EAA0B,GAAG,MAAM,EAAE,CAE9F"}
|
|
@@ -0,0 +1,100 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* v2.22.0 — COMPANION.
|
|
3
|
+
*
|
|
4
|
+
* Five composed primitives that turn every Mneme verb into an AI-
|
|
5
|
+
* agent-friendly surface:
|
|
6
|
+
*
|
|
7
|
+
* 1. CONTRACT — pre/post-conditions, side-effects, DEFCON tier
|
|
8
|
+
* 2. AUTOSPEC — JSON Schema for args + validate() helper
|
|
9
|
+
* 3. DOPPELGANGER — copy-on-write dry-run + diff
|
|
10
|
+
* 4. STORYLINE — Markov chain over pheromone log
|
|
11
|
+
* 5. LEARN LOOP — failure patterns + outcome stats
|
|
12
|
+
*
|
|
13
|
+
* Auto-registration: any new verb that appears in
|
|
14
|
+
* `MNEME_COMMAND_CATALOG` automatically gets contract + autospec.
|
|
15
|
+
* Doppelganger + storyline + learn-loop activate once the verb has
|
|
16
|
+
* been invoked at least once (pheromone seed).
|
|
17
|
+
*
|
|
18
|
+
* Public API:
|
|
19
|
+
* companionFor(verb) — composed Companion for a single verb
|
|
20
|
+
* formatCompanion(c) — human-readable rendering
|
|
21
|
+
* listCompanionable() — verbs that have full data
|
|
22
|
+
* companionableCoverage() — % of catalog with at least contract+autospec
|
|
23
|
+
*/
|
|
24
|
+
export { contractFor, allContracts, findContract, formatContract } from "./contract.js";
|
|
25
|
+
export { parseArgSchema, schemaFor, validateArgs, formatSchema, allSchemas } from "./autospec.js";
|
|
26
|
+
export { dryRun, stageCommit, applyCommit, formatDoppelganger } from "./doppelganger.js";
|
|
27
|
+
export { predictNext, predictPrior, formatStoryline } from "./storyline.js";
|
|
28
|
+
export { computeOutcomeStats, commonMistakes, redactInvocation, formatOutcomeStats, formatMistakes } from "./learn_loop.js";
|
|
29
|
+
import { contractFor, findContract, formatContract } from "./contract.js";
|
|
30
|
+
import { schemaFor, formatSchema } from "./autospec.js";
|
|
31
|
+
import { predictNext, predictPrior, formatStoryline } from "./storyline.js";
|
|
32
|
+
import { computeOutcomeStats, commonMistakes, formatOutcomeStats, formatMistakes } from "./learn_loop.js";
|
|
33
|
+
import { MNEME_COMMAND_CATALOG } from "../agent_manifest.js";
|
|
34
|
+
export function companionFor(verb, opts = {}) {
|
|
35
|
+
const contract = findContract(verb);
|
|
36
|
+
if (!contract)
|
|
37
|
+
return null;
|
|
38
|
+
const argSchema = schemaFor({ command: contract.verb, since: contract.since, what: contract.summary, when: contract.invokeWhen, group: contract.group });
|
|
39
|
+
const repoRoot = opts.repoRoot;
|
|
40
|
+
const next = repoRoot ? predictNext(repoRoot, contract.verb, { topK: opts.topK ?? 5 }) : [];
|
|
41
|
+
const prior = repoRoot ? predictPrior(repoRoot, contract.verb, { topK: opts.topK ?? 5 }) : [];
|
|
42
|
+
const outcomeStats = repoRoot
|
|
43
|
+
? computeOutcomeStats(repoRoot, contract.verb)
|
|
44
|
+
: { verb: contract.verb, invocations: 0, successes: 0, failures: 0, successRate: 0, recentInvocations: 0, recentSuccessRate: 0 };
|
|
45
|
+
const mistakes = repoRoot ? commonMistakes(repoRoot, contract.verb) : [];
|
|
46
|
+
return {
|
|
47
|
+
v: 1,
|
|
48
|
+
verb: contract.verb,
|
|
49
|
+
contract,
|
|
50
|
+
argSchema,
|
|
51
|
+
storyline: { next, prior },
|
|
52
|
+
outcomeStats,
|
|
53
|
+
commonMistakes: mistakes,
|
|
54
|
+
hasLiveData: outcomeStats.invocations > 0,
|
|
55
|
+
generatedAt: new Date().toISOString(),
|
|
56
|
+
};
|
|
57
|
+
}
|
|
58
|
+
export function formatCompanion(c) {
|
|
59
|
+
return [
|
|
60
|
+
formatContract(c.contract),
|
|
61
|
+
"",
|
|
62
|
+
formatSchema(c.argSchema),
|
|
63
|
+
"",
|
|
64
|
+
formatStoryline(c.verb, c.storyline.next, c.storyline.prior),
|
|
65
|
+
"",
|
|
66
|
+
formatOutcomeStats(c.outcomeStats),
|
|
67
|
+
"",
|
|
68
|
+
formatMistakes(c.commonMistakes),
|
|
69
|
+
"",
|
|
70
|
+
` // companion data live: ${c.hasLiveData ? "yes" : "no — invoke the verb at least once to seed"}`,
|
|
71
|
+
].join("\n");
|
|
72
|
+
}
|
|
73
|
+
export function companionableCoverage(repoRoot, catalog = MNEME_COMMAND_CATALOG) {
|
|
74
|
+
let withContract = 0, withAutospec = 0, withLiveData = 0;
|
|
75
|
+
for (const entry of catalog) {
|
|
76
|
+
const c = contractFor(entry);
|
|
77
|
+
if (c)
|
|
78
|
+
withContract++;
|
|
79
|
+
const s = schemaFor(entry);
|
|
80
|
+
if (s)
|
|
81
|
+
withAutospec++;
|
|
82
|
+
const stats = computeOutcomeStats(repoRoot, entry.command);
|
|
83
|
+
if (stats.invocations > 0)
|
|
84
|
+
withLiveData++;
|
|
85
|
+
}
|
|
86
|
+
const total = catalog.length;
|
|
87
|
+
return {
|
|
88
|
+
total,
|
|
89
|
+
withContract,
|
|
90
|
+
withAutospec,
|
|
91
|
+
withLiveData,
|
|
92
|
+
coverageContract: total === 0 ? 0 : withContract / total,
|
|
93
|
+
coverageAutospec: total === 0 ? 0 : withAutospec / total,
|
|
94
|
+
coverageLiveData: total === 0 ? 0 : withLiveData / total,
|
|
95
|
+
};
|
|
96
|
+
}
|
|
97
|
+
export function listCompanionable(catalog = MNEME_COMMAND_CATALOG) {
|
|
98
|
+
return catalog.map((e) => e.command).sort();
|
|
99
|
+
}
|
|
100
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/companion/index.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* v2.22.0 — COMPANION · LEARN LOOP.
|
|
3
|
+
*
|
|
4
|
+
* Mines `.mneme/atlas/pheromones.jsonl` + (when opt-in)
|
|
5
|
+
* `.mneme/replay.jsonl` for per-verb failure patterns and surfaces
|
|
6
|
+
* them as pre-invocation hints.
|
|
7
|
+
*
|
|
8
|
+
* Privacy is opt-IN via Consent Fabric Article 2:
|
|
9
|
+
* - `pheromone` telemetry → enables outcome aggregation
|
|
10
|
+
* - `replay` telemetry → enables structured arg pattern mining
|
|
11
|
+
*
|
|
12
|
+
* Arg values are NEVER stored as-is. Each argument is replaced with a
|
|
13
|
+
* type-tag (`<string>`, `<path>`, `<int>`, `<flag>`) so a pattern
|
|
14
|
+
* like "agents commonly omit --vendor" survives without leaking the
|
|
15
|
+
* actual vendor string.
|
|
16
|
+
*
|
|
17
|
+
* Pattern emission is heuristic + threshold-gated: a finding only
|
|
18
|
+
* surfaces after ≥ 3 observations of the same pattern across distinct
|
|
19
|
+
* timestamps. Goodhart's-law-resistant by design.
|
|
20
|
+
*/
|
|
21
|
+
import { type PheromoneHit } from "../atlas/pheromone.js";
|
|
22
|
+
export interface VerbOutcomeStats {
|
|
23
|
+
verb: string;
|
|
24
|
+
invocations: number;
|
|
25
|
+
successes: number;
|
|
26
|
+
failures: number;
|
|
27
|
+
successRate: number;
|
|
28
|
+
/** Recent invocations (last 14 days) — helps spot regressions. */
|
|
29
|
+
recentInvocations: number;
|
|
30
|
+
recentSuccessRate: number;
|
|
31
|
+
}
|
|
32
|
+
export declare function computeOutcomeStats(repoRoot: string, verb: string, now?: number): VerbOutcomeStats;
|
|
33
|
+
export interface CommonMistake {
|
|
34
|
+
pattern: string;
|
|
35
|
+
observations: number;
|
|
36
|
+
/** Heuristic confidence 0-1. */
|
|
37
|
+
confidence: number;
|
|
38
|
+
suggestion: string;
|
|
39
|
+
}
|
|
40
|
+
/** Mine common mistakes for a verb. Currently rule-based; ML can
|
|
41
|
+
* swap in here when corpus is large. */
|
|
42
|
+
export declare function commonMistakes(repoRoot: string, verb: string): CommonMistake[];
|
|
43
|
+
export interface RedactedInvocation {
|
|
44
|
+
ts: string;
|
|
45
|
+
verb: string;
|
|
46
|
+
argSignature: string;
|
|
47
|
+
outcome: "success" | "failure";
|
|
48
|
+
}
|
|
49
|
+
/** Build a privacy-preserving signature from a pheromone hit + (when
|
|
50
|
+
* enabled) the replay record. Values are stripped so signatures
|
|
51
|
+
* describe the SHAPE of the invocation, not the data. */
|
|
52
|
+
export declare function redactInvocation(h: PheromoneHit): RedactedInvocation;
|
|
53
|
+
export declare function formatOutcomeStats(s: VerbOutcomeStats): string;
|
|
54
|
+
export declare function formatMistakes(mistakes: CommonMistake[]): string;
|
|
55
|
+
//# sourceMappingURL=learn_loop.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"learn_loop.d.ts","sourceRoot":"","sources":["../../src/companion/learn_loop.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;GAmBG;AAEH,OAAO,EAAkB,KAAK,YAAY,EAAE,MAAM,uBAAuB,CAAC;AAG1E,MAAM,WAAW,gBAAgB;IAC/B,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,SAAS,EAAE,MAAM,CAAC;IAClB,QAAQ,EAAE,MAAM,CAAC;IACjB,WAAW,EAAE,MAAM,CAAC;IACpB,kEAAkE;IAClE,iBAAiB,EAAE,MAAM,CAAC;IAC1B,iBAAiB,EAAE,MAAM,CAAC;CAC3B;AAID,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,GAAG,SAAa,GAAG,gBAAgB,CAsBtG;AAED,MAAM,WAAW,aAAa;IAC5B,OAAO,EAAE,MAAM,CAAC;IAChB,YAAY,EAAE,MAAM,CAAC;IACrB,gCAAgC;IAChC,UAAU,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,MAAM,CAAC;CACpB;AAED;yCACyC;AACzC,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,aAAa,EAAE,CAiB9E;AAED,MAAM,WAAW,kBAAkB;IACjC,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,EAAE,MAAM,CAAC;IACb,YAAY,EAAE,MAAM,CAAC;IACrB,OAAO,EAAE,SAAS,GAAG,SAAS,CAAC;CAChC;AAED;;0DAE0D;AAC1D,wBAAgB,gBAAgB,CAAC,CAAC,EAAE,YAAY,GAAG,kBAAkB,CAOpE;AAED,wBAAgB,kBAAkB,CAAC,CAAC,EAAE,gBAAgB,GAAG,MAAM,CAS9D;AAED,wBAAgB,cAAc,CAAC,QAAQ,EAAE,aAAa,EAAE,GAAG,MAAM,CAQhE"}
|
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* v2.22.0 — COMPANION · LEARN LOOP.
|
|
3
|
+
*
|
|
4
|
+
* Mines `.mneme/atlas/pheromones.jsonl` + (when opt-in)
|
|
5
|
+
* `.mneme/replay.jsonl` for per-verb failure patterns and surfaces
|
|
6
|
+
* them as pre-invocation hints.
|
|
7
|
+
*
|
|
8
|
+
* Privacy is opt-IN via Consent Fabric Article 2:
|
|
9
|
+
* - `pheromone` telemetry → enables outcome aggregation
|
|
10
|
+
* - `replay` telemetry → enables structured arg pattern mining
|
|
11
|
+
*
|
|
12
|
+
* Arg values are NEVER stored as-is. Each argument is replaced with a
|
|
13
|
+
* type-tag (`<string>`, `<path>`, `<int>`, `<flag>`) so a pattern
|
|
14
|
+
* like "agents commonly omit --vendor" survives without leaking the
|
|
15
|
+
* actual vendor string.
|
|
16
|
+
*
|
|
17
|
+
* Pattern emission is heuristic + threshold-gated: a finding only
|
|
18
|
+
* surfaces after ≥ 3 observations of the same pattern across distinct
|
|
19
|
+
* timestamps. Goodhart's-law-resistant by design.
|
|
20
|
+
*/
|
|
21
|
+
import { listPheromones } from "../atlas/pheromone.js";
|
|
22
|
+
import { isFeatureEnabled } from "../consent_fabric/index.js";
|
|
23
|
+
const RECENT_WINDOW_MS = 14 * 86_400_000;
|
|
24
|
+
export function computeOutcomeStats(repoRoot, verb, now = Date.now()) {
|
|
25
|
+
const hits = listPheromones(repoRoot).filter((h) => h.verb === verb);
|
|
26
|
+
let s = 0, f = 0, rs = 0, rf = 0, ri = 0;
|
|
27
|
+
for (const h of hits) {
|
|
28
|
+
const ok = h.outcome !== "failure";
|
|
29
|
+
if (ok)
|
|
30
|
+
s++;
|
|
31
|
+
else
|
|
32
|
+
f++;
|
|
33
|
+
const t = Date.parse(h.ts);
|
|
34
|
+
if (!Number.isNaN(t) && now - t < RECENT_WINDOW_MS) {
|
|
35
|
+
ri++;
|
|
36
|
+
if (ok)
|
|
37
|
+
rs++;
|
|
38
|
+
else
|
|
39
|
+
rf++;
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
const invocations = s + f;
|
|
43
|
+
return {
|
|
44
|
+
verb,
|
|
45
|
+
invocations,
|
|
46
|
+
successes: s,
|
|
47
|
+
failures: f,
|
|
48
|
+
successRate: invocations === 0 ? 0 : s / invocations,
|
|
49
|
+
recentInvocations: ri,
|
|
50
|
+
recentSuccessRate: ri === 0 ? 0 : rs / ri,
|
|
51
|
+
};
|
|
52
|
+
}
|
|
53
|
+
/** Mine common mistakes for a verb. Currently rule-based; ML can
|
|
54
|
+
* swap in here when corpus is large. */
|
|
55
|
+
export function commonMistakes(repoRoot, verb) {
|
|
56
|
+
// Always-on rule: recent success rate dropping below 60 % means
|
|
57
|
+
// SOMETHING regressed; surface it.
|
|
58
|
+
const out = [];
|
|
59
|
+
const stats = computeOutcomeStats(repoRoot, verb);
|
|
60
|
+
if (stats.recentInvocations >= 3 && stats.recentSuccessRate < 0.6) {
|
|
61
|
+
out.push({
|
|
62
|
+
pattern: "recent-failure-cluster",
|
|
63
|
+
observations: stats.recentInvocations,
|
|
64
|
+
confidence: 1 - stats.recentSuccessRate,
|
|
65
|
+
suggestion: `Recent first-try success rate is ${(stats.recentSuccessRate * 100).toFixed(0)}%. Review args + preconditions; consider running \`mneme companion ${verb}\` first.`,
|
|
66
|
+
});
|
|
67
|
+
}
|
|
68
|
+
// Opt-in pattern miner: replay-style telemetry is gated.
|
|
69
|
+
if (!isFeatureEnabled(repoRoot, "replay"))
|
|
70
|
+
return out;
|
|
71
|
+
// (Reserved for v2.22.x — actual replay log mining.)
|
|
72
|
+
return out;
|
|
73
|
+
}
|
|
74
|
+
/** Build a privacy-preserving signature from a pheromone hit + (when
|
|
75
|
+
* enabled) the replay record. Values are stripped so signatures
|
|
76
|
+
* describe the SHAPE of the invocation, not the data. */
|
|
77
|
+
export function redactInvocation(h) {
|
|
78
|
+
return {
|
|
79
|
+
ts: h.ts,
|
|
80
|
+
verb: h.verb,
|
|
81
|
+
argSignature: "(no args in current pheromone schema; v2.22.x integrates replay for richer signatures)",
|
|
82
|
+
outcome: h.outcome === "failure" ? "failure" : "success",
|
|
83
|
+
};
|
|
84
|
+
}
|
|
85
|
+
export function formatOutcomeStats(s) {
|
|
86
|
+
const lines = [`📈 OUTCOME STATS — ${s.verb}`, ""];
|
|
87
|
+
if (s.invocations === 0) {
|
|
88
|
+
lines.push(" (no pheromone data yet — opt IN via `mneme telemetry grant pheromone`)");
|
|
89
|
+
return lines.join("\n");
|
|
90
|
+
}
|
|
91
|
+
lines.push(` Lifetime: ${s.invocations} invocations · ${(s.successRate * 100).toFixed(1)}% success`);
|
|
92
|
+
lines.push(` Last 14d: ${s.recentInvocations} invocations · ${(s.recentSuccessRate * 100).toFixed(1)}% success`);
|
|
93
|
+
return lines.join("\n");
|
|
94
|
+
}
|
|
95
|
+
export function formatMistakes(mistakes) {
|
|
96
|
+
if (mistakes.length === 0)
|
|
97
|
+
return "🛡 COMMON MISTAKES — (none surfaced; not enough data or all clear)";
|
|
98
|
+
const lines = [`🛡 COMMON MISTAKES`, ""];
|
|
99
|
+
for (const m of mistakes) {
|
|
100
|
+
lines.push(` ${m.pattern} (${m.observations} obs · confidence=${(m.confidence * 100).toFixed(0)}%)`);
|
|
101
|
+
lines.push(` → ${m.suggestion}`);
|
|
102
|
+
}
|
|
103
|
+
return lines.join("\n");
|
|
104
|
+
}
|
|
105
|
+
//# sourceMappingURL=learn_loop.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"learn_loop.js","sourceRoot":"","sources":["../../src/companion/learn_loop.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* v2.22.0 — COMPANION · STORYLINE.
|
|
3
|
+
*
|
|
4
|
+
* Markov chain over the pheromone log: given a recently-invoked
|
|
5
|
+
* verb, predict the top-K verbs that COMMONLY come next. AI agent
|
|
6
|
+
* uses this to plan multi-step flows.
|
|
7
|
+
*
|
|
8
|
+
* State definition: each verb invocation is one symbol. Transitions
|
|
9
|
+
* are derived from successive invocations within a session-equivalent
|
|
10
|
+
* window (default 5 minutes). Order-1 chain (one-step lookback) is
|
|
11
|
+
* the default; higher orders supported but require more data.
|
|
12
|
+
*
|
|
13
|
+
* Composes with Atlas `hot` (which counts standalone usage) — Atlas
|
|
14
|
+
* tells you what's used overall; Storyline tells you what's used
|
|
15
|
+
* AFTER what.
|
|
16
|
+
*/
|
|
17
|
+
export interface TransitionStats {
|
|
18
|
+
/** "after this verb..." */
|
|
19
|
+
from: string;
|
|
20
|
+
/** ...this verb followed `count` times. */
|
|
21
|
+
to: string;
|
|
22
|
+
count: number;
|
|
23
|
+
/** Probability `to` follows `from` given any successor. */
|
|
24
|
+
probability: number;
|
|
25
|
+
}
|
|
26
|
+
export interface StorylineQuery {
|
|
27
|
+
topK?: number;
|
|
28
|
+
/** Maximum elapsed time between two hits for them to count as a
|
|
29
|
+
* transition. Default 5 minutes — beyond that they're separate
|
|
30
|
+
* sessions. */
|
|
31
|
+
windowMs?: number;
|
|
32
|
+
}
|
|
33
|
+
/** Predict the top-K verbs that commonly follow `verb` in pheromone
|
|
34
|
+
* history. Returns an empty list when the verb hasn't been seen
|
|
35
|
+
* often enough to build statistics. */
|
|
36
|
+
export declare function predictNext(repoRoot: string, verb: string, q?: StorylineQuery): TransitionStats[];
|
|
37
|
+
/** Reverse: which verbs commonly LEAD to `verb`? */
|
|
38
|
+
export declare function predictPrior(repoRoot: string, verb: string, q?: StorylineQuery): TransitionStats[];
|
|
39
|
+
export declare function formatStoryline(verb: string, next: TransitionStats[], prior: TransitionStats[]): string;
|
|
40
|
+
//# sourceMappingURL=storyline.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"storyline.d.ts","sourceRoot":"","sources":["../../src/companion/storyline.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAIH,MAAM,WAAW,eAAe;IAC9B,2BAA2B;IAC3B,IAAI,EAAE,MAAM,CAAC;IACb,2CAA2C;IAC3C,EAAE,EAAE,MAAM,CAAC;IACX,KAAK,EAAE,MAAM,CAAC;IACd,2DAA2D;IAC3D,WAAW,EAAE,MAAM,CAAC;CACrB;AAED,MAAM,WAAW,cAAc;IAC7B,IAAI,CAAC,EAAE,MAAM,CAAC;IACd;;oBAEgB;IAChB,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAoBD;;wCAEwC;AACxC,wBAAgB,WAAW,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC,GAAE,cAAmB,GAAG,eAAe,EAAE,CAWrG;AAED,oDAAoD;AACpD,wBAAgB,YAAY,CAAC,QAAQ,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC,GAAE,cAAmB,GAAG,eAAe,EAAE,CAetG;AAED,wBAAgB,eAAe,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,eAAe,EAAE,EAAE,KAAK,EAAE,eAAe,EAAE,GAAG,MAAM,CAgBvG"}
|