@blulotus/trellis-core 0.7.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/LICENSE +235 -0
- package/dist/channel/api/assert.d.ts +3 -0
- package/dist/channel/api/assert.d.ts.map +1 -0
- package/dist/channel/api/assert.js +11 -0
- package/dist/channel/api/assert.js.map +1 -0
- package/dist/channel/api/context.d.ts +21 -0
- package/dist/channel/api/context.d.ts.map +1 -0
- package/dist/channel/api/context.js +99 -0
- package/dist/channel/api/context.js.map +1 -0
- package/dist/channel/api/create.d.ts +9 -0
- package/dist/channel/api/create.d.ts.map +1 -0
- package/dist/channel/api/create.js +104 -0
- package/dist/channel/api/create.js.map +1 -0
- package/dist/channel/api/inbox.d.ts +51 -0
- package/dist/channel/api/inbox.d.ts.map +1 -0
- package/dist/channel/api/inbox.js +176 -0
- package/dist/channel/api/inbox.js.map +1 -0
- package/dist/channel/api/interrupt.d.ts +31 -0
- package/dist/channel/api/interrupt.d.ts.map +1 -0
- package/dist/channel/api/interrupt.js +102 -0
- package/dist/channel/api/interrupt.js.map +1 -0
- package/dist/channel/api/post-thread.d.ts +14 -0
- package/dist/channel/api/post-thread.d.ts.map +1 -0
- package/dist/channel/api/post-thread.js +109 -0
- package/dist/channel/api/post-thread.js.map +1 -0
- package/dist/channel/api/read.d.ts +17 -0
- package/dist/channel/api/read.d.ts.map +1 -0
- package/dist/channel/api/read.js +44 -0
- package/dist/channel/api/read.js.map +1 -0
- package/dist/channel/api/resolve.d.ts +21 -0
- package/dist/channel/api/resolve.d.ts.map +1 -0
- package/dist/channel/api/resolve.js +28 -0
- package/dist/channel/api/resolve.js.map +1 -0
- package/dist/channel/api/runtime.d.ts +70 -0
- package/dist/channel/api/runtime.d.ts.map +1 -0
- package/dist/channel/api/runtime.js +11 -0
- package/dist/channel/api/runtime.js.map +1 -0
- package/dist/channel/api/send.d.ts +4 -0
- package/dist/channel/api/send.d.ts.map +1 -0
- package/dist/channel/api/send.js +52 -0
- package/dist/channel/api/send.js.map +1 -0
- package/dist/channel/api/spawn.d.ts +13 -0
- package/dist/channel/api/spawn.d.ts.map +1 -0
- package/dist/channel/api/spawn.js +54 -0
- package/dist/channel/api/spawn.js.map +1 -0
- package/dist/channel/api/title.d.ts +5 -0
- package/dist/channel/api/title.d.ts.map +1 -0
- package/dist/channel/api/title.js +40 -0
- package/dist/channel/api/title.js.map +1 -0
- package/dist/channel/api/types.d.ts +65 -0
- package/dist/channel/api/types.d.ts.map +1 -0
- package/dist/channel/api/types.js +2 -0
- package/dist/channel/api/types.js.map +1 -0
- package/dist/channel/api/watch-channels.d.ts +40 -0
- package/dist/channel/api/watch-channels.d.ts.map +1 -0
- package/dist/channel/api/watch-channels.js +143 -0
- package/dist/channel/api/watch-channels.js.map +1 -0
- package/dist/channel/api/watch.d.ts +11 -0
- package/dist/channel/api/watch.d.ts.map +1 -0
- package/dist/channel/api/watch.js +17 -0
- package/dist/channel/api/watch.js.map +1 -0
- package/dist/channel/api/workers.d.ts +69 -0
- package/dist/channel/api/workers.d.ts.map +1 -0
- package/dist/channel/api/workers.js +145 -0
- package/dist/channel/api/workers.js.map +1 -0
- package/dist/channel/index.d.ts +38 -0
- package/dist/channel/index.d.ts.map +1 -0
- package/dist/channel/index.js +23 -0
- package/dist/channel/index.js.map +1 -0
- package/dist/channel/internal/store/channel-metadata.d.ts +23 -0
- package/dist/channel/internal/store/channel-metadata.d.ts.map +1 -0
- package/dist/channel/internal/store/channel-metadata.js +94 -0
- package/dist/channel/internal/store/channel-metadata.js.map +1 -0
- package/dist/channel/internal/store/delivery.d.ts +27 -0
- package/dist/channel/internal/store/delivery.d.ts.map +1 -0
- package/dist/channel/internal/store/delivery.js +37 -0
- package/dist/channel/internal/store/delivery.js.map +1 -0
- package/dist/channel/internal/store/events.d.ts +215 -0
- package/dist/channel/internal/store/events.d.ts.map +1 -0
- package/dist/channel/internal/store/events.js +206 -0
- package/dist/channel/internal/store/events.js.map +1 -0
- package/dist/channel/internal/store/filter.d.ts +21 -0
- package/dist/channel/internal/store/filter.d.ts.map +1 -0
- package/dist/channel/internal/store/filter.js +75 -0
- package/dist/channel/internal/store/filter.js.map +1 -0
- package/dist/channel/internal/store/inbox.d.ts +17 -0
- package/dist/channel/internal/store/inbox.d.ts.map +1 -0
- package/dist/channel/internal/store/inbox.js +30 -0
- package/dist/channel/internal/store/inbox.js.map +1 -0
- package/dist/channel/internal/store/lock.d.ts +17 -0
- package/dist/channel/internal/store/lock.d.ts.map +1 -0
- package/dist/channel/internal/store/lock.js +88 -0
- package/dist/channel/internal/store/lock.js.map +1 -0
- package/dist/channel/internal/store/paths.d.ts +57 -0
- package/dist/channel/internal/store/paths.d.ts.map +1 -0
- package/dist/channel/internal/store/paths.js +264 -0
- package/dist/channel/internal/store/paths.js.map +1 -0
- package/dist/channel/internal/store/schema.d.ts +77 -0
- package/dist/channel/internal/store/schema.d.ts.map +1 -0
- package/dist/channel/internal/store/schema.js +127 -0
- package/dist/channel/internal/store/schema.js.map +1 -0
- package/dist/channel/internal/store/seq.d.ts +12 -0
- package/dist/channel/internal/store/seq.d.ts.map +1 -0
- package/dist/channel/internal/store/seq.js +133 -0
- package/dist/channel/internal/store/seq.js.map +1 -0
- package/dist/channel/internal/store/thread-state.d.ts +37 -0
- package/dist/channel/internal/store/thread-state.d.ts.map +1 -0
- package/dist/channel/internal/store/thread-state.js +206 -0
- package/dist/channel/internal/store/thread-state.js.map +1 -0
- package/dist/channel/internal/store/watch.d.ts +10 -0
- package/dist/channel/internal/store/watch.d.ts.map +1 -0
- package/dist/channel/internal/store/watch.js +122 -0
- package/dist/channel/internal/store/watch.js.map +1 -0
- package/dist/channel/internal/store/worker-state.d.ts +56 -0
- package/dist/channel/internal/store/worker-state.d.ts.map +1 -0
- package/dist/channel/internal/store/worker-state.js +220 -0
- package/dist/channel/internal/store/worker-state.js.map +1 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +7 -0
- package/dist/index.js.map +1 -0
- package/dist/mem/adapters/claude.d.ts +22 -0
- package/dist/mem/adapters/claude.d.ts.map +1 -0
- package/dist/mem/adapters/claude.js +209 -0
- package/dist/mem/adapters/claude.js.map +1 -0
- package/dist/mem/adapters/codex.d.ts +55 -0
- package/dist/mem/adapters/codex.d.ts.map +1 -0
- package/dist/mem/adapters/codex.js +344 -0
- package/dist/mem/adapters/codex.js.map +1 -0
- package/dist/mem/adapters/grok.d.ts +41 -0
- package/dist/mem/adapters/grok.d.ts.map +1 -0
- package/dist/mem/adapters/grok.js +202 -0
- package/dist/mem/adapters/grok.js.map +1 -0
- package/dist/mem/adapters/opencode.d.ts +19 -0
- package/dist/mem/adapters/opencode.d.ts.map +1 -0
- package/dist/mem/adapters/opencode.js +25 -0
- package/dist/mem/adapters/opencode.js.map +1 -0
- package/dist/mem/adapters/pi.d.ts +24 -0
- package/dist/mem/adapters/pi.d.ts.map +1 -0
- package/dist/mem/adapters/pi.js +290 -0
- package/dist/mem/adapters/pi.js.map +1 -0
- package/dist/mem/adapters/zcode.d.ts +76 -0
- package/dist/mem/adapters/zcode.d.ts.map +1 -0
- package/dist/mem/adapters/zcode.js +434 -0
- package/dist/mem/adapters/zcode.js.map +1 -0
- package/dist/mem/context.d.ts +23 -0
- package/dist/mem/context.d.ts.map +1 -0
- package/dist/mem/context.js +120 -0
- package/dist/mem/context.js.map +1 -0
- package/dist/mem/dialogue.d.ts +32 -0
- package/dist/mem/dialogue.d.ts.map +1 -0
- package/dist/mem/dialogue.js +0 -0
- package/dist/mem/dialogue.js.map +1 -0
- package/dist/mem/filter.d.ts +31 -0
- package/dist/mem/filter.d.ts.map +1 -0
- package/dist/mem/filter.js +66 -0
- package/dist/mem/filter.js.map +1 -0
- package/dist/mem/index.d.ts +18 -0
- package/dist/mem/index.d.ts.map +1 -0
- package/dist/mem/index.js +17 -0
- package/dist/mem/index.js.map +1 -0
- package/dist/mem/internal/jsonl.d.ts +35 -0
- package/dist/mem/internal/jsonl.d.ts.map +1 -0
- package/dist/mem/internal/jsonl.js +125 -0
- package/dist/mem/internal/jsonl.js.map +1 -0
- package/dist/mem/internal/paths.d.ts +38 -0
- package/dist/mem/internal/paths.d.ts.map +1 -0
- package/dist/mem/internal/paths.js +126 -0
- package/dist/mem/internal/paths.js.map +1 -0
- package/dist/mem/internal/sqlite-readonly.d.ts +77 -0
- package/dist/mem/internal/sqlite-readonly.d.ts.map +1 -0
- package/dist/mem/internal/sqlite-readonly.js +797 -0
- package/dist/mem/internal/sqlite-readonly.js.map +1 -0
- package/dist/mem/phase.d.ts +45 -0
- package/dist/mem/phase.d.ts.map +1 -0
- package/dist/mem/phase.js +220 -0
- package/dist/mem/phase.js.map +1 -0
- package/dist/mem/projects.d.ts +13 -0
- package/dist/mem/projects.d.ts.map +1 -0
- package/dist/mem/projects.js +47 -0
- package/dist/mem/projects.js.map +1 -0
- package/dist/mem/search.d.ts +39 -0
- package/dist/mem/search.d.ts.map +1 -0
- package/dist/mem/search.js +133 -0
- package/dist/mem/search.js.map +1 -0
- package/dist/mem/sessions.d.ts +38 -0
- package/dist/mem/sessions.d.ts.map +1 -0
- package/dist/mem/sessions.js +313 -0
- package/dist/mem/sessions.js.map +1 -0
- package/dist/mem/types.d.ts +188 -0
- package/dist/mem/types.d.ts.map +1 -0
- package/dist/mem/types.js +10 -0
- package/dist/mem/types.js.map +1 -0
- package/dist/task/index.d.ts +9 -0
- package/dist/task/index.d.ts.map +1 -0
- package/dist/task/index.js +9 -0
- package/dist/task/index.js.map +1 -0
- package/dist/task/paths.d.ts +37 -0
- package/dist/task/paths.d.ts.map +1 -0
- package/dist/task/paths.js +49 -0
- package/dist/task/paths.js.map +1 -0
- package/dist/task/phase.d.ts +27 -0
- package/dist/task/phase.d.ts.map +1 -0
- package/dist/task/phase.js +24 -0
- package/dist/task/phase.js.map +1 -0
- package/dist/task/records.d.ts +39 -0
- package/dist/task/records.d.ts.map +1 -0
- package/dist/task/records.js +89 -0
- package/dist/task/records.js.map +1 -0
- package/dist/task/schema.d.ts +77 -0
- package/dist/task/schema.d.ts.map +1 -0
- package/dist/task/schema.js +220 -0
- package/dist/task/schema.js.map +1 -0
- package/dist/testing/index.d.ts +2 -0
- package/dist/testing/index.d.ts.map +1 -0
- package/dist/testing/index.js +4 -0
- package/dist/testing/index.js.map +1 -0
- package/package.json +77 -0
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Project / time-range / source filters for mem session selection.
|
|
3
|
+
*
|
|
4
|
+
* These primitives belong to mem session filtering only — they are not
|
|
5
|
+
* promoted into a cross-domain `core/internal` until another core subdomain
|
|
6
|
+
* needs exactly the same semantics.
|
|
7
|
+
*/
|
|
8
|
+
import type { MemFilter } from "./types.js";
|
|
9
|
+
/** Single-point range check: `since ≤ t ≤ until`. Pass-through when `iso` is
|
|
10
|
+
* undefined or unparseable. Internal-only — session list filtering uses
|
|
11
|
+
* {@link inRangeOverlap}. */
|
|
12
|
+
export declare function inRange(iso: string | undefined, f: MemFilter): boolean;
|
|
13
|
+
/**
|
|
14
|
+
* Interval-overlap range check for sessions with both a start and an end
|
|
15
|
+
* timestamp. A session is kept iff its lifetime `[start, end]` overlaps the
|
|
16
|
+
* query window `[since, until]`.
|
|
17
|
+
*
|
|
18
|
+
* Long / cross-day sessions (created before `--since` but still active inside
|
|
19
|
+
* the window) must survive — single-point `inRange(created, f)` dropped them.
|
|
20
|
+
*
|
|
21
|
+
* Degenerate inputs:
|
|
22
|
+
* - both undefined → pass through (no timestamp = don't filter)
|
|
23
|
+
* - one undefined → fall back to single-point semantics on the other end
|
|
24
|
+
* - unparseable iso → defer to the parsable end (or pass through if both bad)
|
|
25
|
+
*/
|
|
26
|
+
export declare function inRangeOverlap(start: string | undefined, end: string | undefined, f: MemFilter): boolean;
|
|
27
|
+
/** True iff `sessionCwd` is within `target` (exact match or descendant
|
|
28
|
+
* directory). When `target` is undefined there is no scoping and everything
|
|
29
|
+
* matches; sessions with an unknown cwd are dropped under scoping. */
|
|
30
|
+
export declare function sameProject(sessionCwd: string | undefined, target: string | undefined): boolean;
|
|
31
|
+
//# sourceMappingURL=filter.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"filter.d.ts","sourceRoot":"","sources":["../../src/mem/filter.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAIH,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAE5C;;6BAE6B;AAC7B,wBAAgB,OAAO,CAAC,GAAG,EAAE,MAAM,GAAG,SAAS,EAAE,CAAC,EAAE,SAAS,GAAG,OAAO,CAOtE;AAED;;;;;;;;;;;;GAYG;AACH,wBAAgB,cAAc,CAC5B,KAAK,EAAE,MAAM,GAAG,SAAS,EACzB,GAAG,EAAE,MAAM,GAAG,SAAS,EACvB,CAAC,EAAE,SAAS,GACX,OAAO,CAaT;AAED;;sEAEsE;AACtE,wBAAgB,WAAW,CACzB,UAAU,EAAE,MAAM,GAAG,SAAS,EAC9B,MAAM,EAAE,MAAM,GAAG,SAAS,GACzB,OAAO,CAMT"}
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Project / time-range / source filters for mem session selection.
|
|
3
|
+
*
|
|
4
|
+
* These primitives belong to mem session filtering only — they are not
|
|
5
|
+
* promoted into a cross-domain `core/internal` until another core subdomain
|
|
6
|
+
* needs exactly the same semantics.
|
|
7
|
+
*/
|
|
8
|
+
import * as path from "node:path";
|
|
9
|
+
/** Single-point range check: `since ≤ t ≤ until`. Pass-through when `iso` is
|
|
10
|
+
* undefined or unparseable. Internal-only — session list filtering uses
|
|
11
|
+
* {@link inRangeOverlap}. */
|
|
12
|
+
export function inRange(iso, f) {
|
|
13
|
+
if (!iso)
|
|
14
|
+
return true;
|
|
15
|
+
const t = new Date(iso);
|
|
16
|
+
if (Number.isNaN(+t))
|
|
17
|
+
return true;
|
|
18
|
+
if (f.since && t < f.since)
|
|
19
|
+
return false;
|
|
20
|
+
if (f.until && t > f.until)
|
|
21
|
+
return false;
|
|
22
|
+
return true;
|
|
23
|
+
}
|
|
24
|
+
/**
|
|
25
|
+
* Interval-overlap range check for sessions with both a start and an end
|
|
26
|
+
* timestamp. A session is kept iff its lifetime `[start, end]` overlaps the
|
|
27
|
+
* query window `[since, until]`.
|
|
28
|
+
*
|
|
29
|
+
* Long / cross-day sessions (created before `--since` but still active inside
|
|
30
|
+
* the window) must survive — single-point `inRange(created, f)` dropped them.
|
|
31
|
+
*
|
|
32
|
+
* Degenerate inputs:
|
|
33
|
+
* - both undefined → pass through (no timestamp = don't filter)
|
|
34
|
+
* - one undefined → fall back to single-point semantics on the other end
|
|
35
|
+
* - unparseable iso → defer to the parsable end (or pass through if both bad)
|
|
36
|
+
*/
|
|
37
|
+
export function inRangeOverlap(start, end, f) {
|
|
38
|
+
const s = start ?? end;
|
|
39
|
+
const e = end ?? start;
|
|
40
|
+
if (!s && !e)
|
|
41
|
+
return true;
|
|
42
|
+
if (f.since && e) {
|
|
43
|
+
const eT = new Date(e);
|
|
44
|
+
if (!Number.isNaN(+eT) && eT < f.since)
|
|
45
|
+
return false;
|
|
46
|
+
}
|
|
47
|
+
if (f.until && s) {
|
|
48
|
+
const sT = new Date(s);
|
|
49
|
+
if (!Number.isNaN(+sT) && sT > f.until)
|
|
50
|
+
return false;
|
|
51
|
+
}
|
|
52
|
+
return true;
|
|
53
|
+
}
|
|
54
|
+
/** True iff `sessionCwd` is within `target` (exact match or descendant
|
|
55
|
+
* directory). When `target` is undefined there is no scoping and everything
|
|
56
|
+
* matches; sessions with an unknown cwd are dropped under scoping. */
|
|
57
|
+
export function sameProject(sessionCwd, target) {
|
|
58
|
+
if (!target)
|
|
59
|
+
return true;
|
|
60
|
+
if (!sessionCwd)
|
|
61
|
+
return false;
|
|
62
|
+
const a = path.resolve(sessionCwd);
|
|
63
|
+
const b = path.resolve(target);
|
|
64
|
+
return a === b || a.startsWith(b + path.sep);
|
|
65
|
+
}
|
|
66
|
+
//# sourceMappingURL=filter.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"filter.js","sourceRoot":"","sources":["../../src/mem/filter.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,KAAK,IAAI,MAAM,WAAW,CAAC;AAIlC;;6BAE6B;AAC7B,MAAM,UAAU,OAAO,CAAC,GAAuB,EAAE,CAAY;IAC3D,IAAI,CAAC,GAAG;QAAE,OAAO,IAAI,CAAC;IACtB,MAAM,CAAC,GAAG,IAAI,IAAI,CAAC,GAAG,CAAC,CAAC;IACxB,IAAI,MAAM,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;QAAE,OAAO,IAAI,CAAC;IAClC,IAAI,CAAC,CAAC,KAAK,IAAI,CAAC,GAAG,CAAC,CAAC,KAAK;QAAE,OAAO,KAAK,CAAC;IACzC,IAAI,CAAC,CAAC,KAAK,IAAI,CAAC,GAAG,CAAC,CAAC,KAAK;QAAE,OAAO,KAAK,CAAC;IACzC,OAAO,IAAI,CAAC;AACd,CAAC;AAED;;;;;;;;;;;;GAYG;AACH,MAAM,UAAU,cAAc,CAC5B,KAAyB,EACzB,GAAuB,EACvB,CAAY;IAEZ,MAAM,CAAC,GAAG,KAAK,IAAI,GAAG,CAAC;IACvB,MAAM,CAAC,GAAG,GAAG,IAAI,KAAK,CAAC;IACvB,IAAI,CAAC,CAAC,IAAI,CAAC,CAAC;QAAE,OAAO,IAAI,CAAC;IAC1B,IAAI,CAAC,CAAC,KAAK,IAAI,CAAC,EAAE,CAAC;QACjB,MAAM,EAAE,GAAG,IAAI,IAAI,CAAC,CAAC,CAAC,CAAC;QACvB,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC,KAAK;YAAE,OAAO,KAAK,CAAC;IACvD,CAAC;IACD,IAAI,CAAC,CAAC,KAAK,IAAI,CAAC,EAAE,CAAC;QACjB,MAAM,EAAE,GAAG,IAAI,IAAI,CAAC,CAAC,CAAC,CAAC;QACvB,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC,KAAK;YAAE,OAAO,KAAK,CAAC;IACvD,CAAC;IACD,OAAO,IAAI,CAAC;AACd,CAAC;AAED;;sEAEsE;AACtE,MAAM,UAAU,WAAW,CACzB,UAA8B,EAC9B,MAA0B;IAE1B,IAAI,CAAC,MAAM;QAAE,OAAO,IAAI,CAAC;IACzB,IAAI,CAAC,UAAU;QAAE,OAAO,KAAK,CAAC;IAC9B,MAAM,CAAC,GAAG,IAAI,CAAC,OAAO,CAAC,UAAU,CAAC,CAAC;IACnC,MAAM,CAAC,GAAG,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC;IAC/B,OAAO,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,UAAU,CAAC,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC;AAC/C,CAAC"}
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Public surface for `@blulotus/trellis-core/mem` — reusable retrieval and
|
|
3
|
+
* dialogue-context extraction over persisted Claude Code / Codex / OpenCode
|
|
4
|
+
* sessions.
|
|
5
|
+
*
|
|
6
|
+
* This subpackage is intentionally NOT re-exported from the root
|
|
7
|
+
* `@blulotus/trellis-core` barrel. Import it explicitly:
|
|
8
|
+
*
|
|
9
|
+
* import { searchMemSessions } from "@blulotus/trellis-core/mem";
|
|
10
|
+
*
|
|
11
|
+
* v1 scope: persisted-session search and context extraction only. It does not
|
|
12
|
+
* read channel / forum / thread event logs and has no cursor / pagination.
|
|
13
|
+
*/
|
|
14
|
+
export { listMemSessions, searchMemSessions, extractMemDialogue, MemSessionNotFoundError, } from "./sessions.js";
|
|
15
|
+
export { readMemContext } from "./context.js";
|
|
16
|
+
export { listMemProjects } from "./projects.js";
|
|
17
|
+
export type { MemSourceKind, MemSourceFilter, MemPhase, DialogueRole, DialogueTurn, MemFilter, MemSessionInfo, SearchExcerpt, SearchHit, MemWarning, MemSearchMatch, MemSearchResult, MemContextTurn, MemContextResult, BrainstormWindow, MemDialogueGroup, MemExtractResult, MemProjectSummary, ListMemSessionsOptions, SearchMemSessionsOptions, ReadMemContextOptions, ExtractMemDialogueOptions, ListMemProjectsOptions, } from "./types.js";
|
|
18
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/mem/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,EACL,eAAe,EACf,iBAAiB,EACjB,kBAAkB,EAClB,uBAAuB,GACxB,MAAM,eAAe,CAAC;AAEvB,OAAO,EAAE,cAAc,EAAE,MAAM,cAAc,CAAC;AAE9C,OAAO,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC;AAEhD,YAAY,EACV,aAAa,EACb,eAAe,EACf,QAAQ,EACR,YAAY,EACZ,YAAY,EACZ,SAAS,EACT,cAAc,EACd,aAAa,EACb,SAAS,EACT,UAAU,EACV,cAAc,EACd,eAAe,EACf,cAAc,EACd,gBAAgB,EAChB,gBAAgB,EAChB,gBAAgB,EAChB,gBAAgB,EAChB,iBAAiB,EACjB,sBAAsB,EACtB,wBAAwB,EACxB,qBAAqB,EACrB,yBAAyB,EACzB,sBAAsB,GACvB,MAAM,YAAY,CAAC"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Public surface for `@blulotus/trellis-core/mem` — reusable retrieval and
|
|
3
|
+
* dialogue-context extraction over persisted Claude Code / Codex / OpenCode
|
|
4
|
+
* sessions.
|
|
5
|
+
*
|
|
6
|
+
* This subpackage is intentionally NOT re-exported from the root
|
|
7
|
+
* `@blulotus/trellis-core` barrel. Import it explicitly:
|
|
8
|
+
*
|
|
9
|
+
* import { searchMemSessions } from "@blulotus/trellis-core/mem";
|
|
10
|
+
*
|
|
11
|
+
* v1 scope: persisted-session search and context extraction only. It does not
|
|
12
|
+
* read channel / forum / thread event logs and has no cursor / pagination.
|
|
13
|
+
*/
|
|
14
|
+
export { listMemSessions, searchMemSessions, extractMemDialogue, MemSessionNotFoundError, } from "./sessions.js";
|
|
15
|
+
export { readMemContext } from "./context.js";
|
|
16
|
+
export { listMemProjects } from "./projects.js";
|
|
17
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/mem/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,EACL,eAAe,EACf,iBAAiB,EACjB,kBAAkB,EAClB,uBAAuB,GACxB,MAAM,eAAe,CAAC;AAEvB,OAAO,EAAE,cAAc,EAAE,MAAM,cAAc,CAAC;AAE9C,OAAO,EAAE,eAAe,EAAE,MAAM,eAAe,CAAC"}
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Streaming JSONL / JSON readers for the persisted-session adapters.
|
|
3
|
+
*
|
|
4
|
+
* Zero-dependency on purpose — `@blulotus/trellis-core` does not depend on
|
|
5
|
+
* `zod`. The original CLI implementation validated every line against a Zod
|
|
6
|
+
* schema; the external session formats were all declared `.loose()` with every
|
|
7
|
+
* field `.optional()`, so the only thing the schema actually rejected was a
|
|
8
|
+
* top-level non-object line — which the `0x7b` byte-prefix fast-reject already
|
|
9
|
+
* filters. Adapters therefore receive each parsed line cast to a hand-written
|
|
10
|
+
* loose interface and read fields defensively.
|
|
11
|
+
*/
|
|
12
|
+
/**
|
|
13
|
+
* Walk a JSONL file line-by-line, invoking `onLine` with each parsed object.
|
|
14
|
+
* Bad JSON lines are skipped. Returning the literal `"stop"` from `onLine`
|
|
15
|
+
* halts iteration.
|
|
16
|
+
*
|
|
17
|
+
* Chunked sync streaming: 256 KB read window, leftover preserved across chunks
|
|
18
|
+
* for split-line reassembly — bounded heap on multi-MB session files and a
|
|
19
|
+
* `"stop"` short-circuit that avoids reading the whole file when only the head
|
|
20
|
+
* is needed.
|
|
21
|
+
*
|
|
22
|
+
* Byte-prefix fast-reject: a JSONL event line virtually always begins with `{`.
|
|
23
|
+
* Lines whose first byte is not `{` are blanks / log preambles / partial writes
|
|
24
|
+
* and are skipped before paying the `JSON.parse` cost.
|
|
25
|
+
*/
|
|
26
|
+
export declare function readJsonl<T>(file: string, onLine: (obj: T) => unknown): void;
|
|
27
|
+
/** Read just the first parseable JSONL object (stops after one line). */
|
|
28
|
+
export declare function readJsonlFirst<T>(file: string): T | undefined;
|
|
29
|
+
/** Find the first JSONL object satisfying `predicate`, scanning at most
|
|
30
|
+
* `maxLines` lines. */
|
|
31
|
+
export declare function findInJsonl<T>(file: string, predicate: (obj: T) => boolean, maxLines?: number): T | undefined;
|
|
32
|
+
/** Read and JSON-parse a whole file; returns `undefined` on read / parse
|
|
33
|
+
* failure. The caller is responsible for shape-checking the result. */
|
|
34
|
+
export declare function readJsonFile<T>(file: string): T | undefined;
|
|
35
|
+
//# sourceMappingURL=jsonl.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"jsonl.d.ts","sourceRoot":"","sources":["../../../src/mem/internal/jsonl.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAOH;;;;;;;;;;;;;GAaG;AACH,wBAAgB,SAAS,CAAC,CAAC,EAAE,IAAI,EAAE,MAAM,EAAE,MAAM,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,OAAO,GAAG,IAAI,CAqD5E;AAED,yEAAyE;AACzE,wBAAgB,cAAc,CAAC,CAAC,EAAE,IAAI,EAAE,MAAM,GAAG,CAAC,GAAG,SAAS,CAO7D;AAED;uBACuB;AACvB,wBAAgB,WAAW,CAAC,CAAC,EAC3B,IAAI,EAAE,MAAM,EACZ,SAAS,EAAE,CAAC,GAAG,EAAE,CAAC,KAAK,OAAO,EAC9B,QAAQ,SAAM,GACb,CAAC,GAAG,SAAS,CAYf;AAED;uEACuE;AACvE,wBAAgB,YAAY,CAAC,CAAC,EAAE,IAAI,EAAE,MAAM,GAAG,CAAC,GAAG,SAAS,CAM3D"}
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Streaming JSONL / JSON readers for the persisted-session adapters.
|
|
3
|
+
*
|
|
4
|
+
* Zero-dependency on purpose — `@blulotus/trellis-core` does not depend on
|
|
5
|
+
* `zod`. The original CLI implementation validated every line against a Zod
|
|
6
|
+
* schema; the external session formats were all declared `.loose()` with every
|
|
7
|
+
* field `.optional()`, so the only thing the schema actually rejected was a
|
|
8
|
+
* top-level non-object line — which the `0x7b` byte-prefix fast-reject already
|
|
9
|
+
* filters. Adapters therefore receive each parsed line cast to a hand-written
|
|
10
|
+
* loose interface and read fields defensively.
|
|
11
|
+
*/
|
|
12
|
+
import * as fs from "node:fs";
|
|
13
|
+
const CHUNK = 256 * 1024;
|
|
14
|
+
const OPEN_BRACE = 0x7b; // '{'
|
|
15
|
+
/**
|
|
16
|
+
* Walk a JSONL file line-by-line, invoking `onLine` with each parsed object.
|
|
17
|
+
* Bad JSON lines are skipped. Returning the literal `"stop"` from `onLine`
|
|
18
|
+
* halts iteration.
|
|
19
|
+
*
|
|
20
|
+
* Chunked sync streaming: 256 KB read window, leftover preserved across chunks
|
|
21
|
+
* for split-line reassembly — bounded heap on multi-MB session files and a
|
|
22
|
+
* `"stop"` short-circuit that avoids reading the whole file when only the head
|
|
23
|
+
* is needed.
|
|
24
|
+
*
|
|
25
|
+
* Byte-prefix fast-reject: a JSONL event line virtually always begins with `{`.
|
|
26
|
+
* Lines whose first byte is not `{` are blanks / log preambles / partial writes
|
|
27
|
+
* and are skipped before paying the `JSON.parse` cost.
|
|
28
|
+
*/
|
|
29
|
+
export function readJsonl(file, onLine) {
|
|
30
|
+
let fd;
|
|
31
|
+
try {
|
|
32
|
+
fd = fs.openSync(file, "r");
|
|
33
|
+
}
|
|
34
|
+
catch {
|
|
35
|
+
return;
|
|
36
|
+
}
|
|
37
|
+
const buf = Buffer.alloc(CHUNK);
|
|
38
|
+
let leftover = "";
|
|
39
|
+
try {
|
|
40
|
+
let stop = false;
|
|
41
|
+
while (!stop) {
|
|
42
|
+
const n = fs.readSync(fd, buf, 0, CHUNK, null);
|
|
43
|
+
if (n === 0)
|
|
44
|
+
break;
|
|
45
|
+
const chunk = leftover + buf.toString("utf8", 0, n);
|
|
46
|
+
let from = 0;
|
|
47
|
+
while (true) {
|
|
48
|
+
const nl = chunk.indexOf("\n", from);
|
|
49
|
+
if (nl === -1) {
|
|
50
|
+
leftover = chunk.slice(from);
|
|
51
|
+
break;
|
|
52
|
+
}
|
|
53
|
+
const line = chunk.slice(from, nl);
|
|
54
|
+
from = nl + 1;
|
|
55
|
+
if (!line)
|
|
56
|
+
continue;
|
|
57
|
+
if (line.charCodeAt(0) !== OPEN_BRACE)
|
|
58
|
+
continue;
|
|
59
|
+
let raw;
|
|
60
|
+
try {
|
|
61
|
+
raw = JSON.parse(line);
|
|
62
|
+
}
|
|
63
|
+
catch {
|
|
64
|
+
continue;
|
|
65
|
+
}
|
|
66
|
+
if (onLine(raw) === "stop") {
|
|
67
|
+
stop = true;
|
|
68
|
+
break;
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
if (!stop && leftover) {
|
|
73
|
+
// File ended without a trailing newline — process the last partial line.
|
|
74
|
+
const line = leftover;
|
|
75
|
+
if (line.charCodeAt(0) === OPEN_BRACE) {
|
|
76
|
+
try {
|
|
77
|
+
const raw = JSON.parse(line);
|
|
78
|
+
onLine(raw);
|
|
79
|
+
}
|
|
80
|
+
catch {
|
|
81
|
+
/* skip */
|
|
82
|
+
}
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
finally {
|
|
87
|
+
fs.closeSync(fd);
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
/** Read just the first parseable JSONL object (stops after one line). */
|
|
91
|
+
export function readJsonlFirst(file) {
|
|
92
|
+
let result;
|
|
93
|
+
readJsonl(file, (obj) => {
|
|
94
|
+
result = obj;
|
|
95
|
+
return "stop";
|
|
96
|
+
});
|
|
97
|
+
return result;
|
|
98
|
+
}
|
|
99
|
+
/** Find the first JSONL object satisfying `predicate`, scanning at most
|
|
100
|
+
* `maxLines` lines. */
|
|
101
|
+
export function findInJsonl(file, predicate, maxLines = 200) {
|
|
102
|
+
let count = 0;
|
|
103
|
+
let hit;
|
|
104
|
+
readJsonl(file, (obj) => {
|
|
105
|
+
count++;
|
|
106
|
+
if (predicate(obj)) {
|
|
107
|
+
hit = obj;
|
|
108
|
+
return "stop";
|
|
109
|
+
}
|
|
110
|
+
if (count >= maxLines)
|
|
111
|
+
return "stop";
|
|
112
|
+
});
|
|
113
|
+
return hit;
|
|
114
|
+
}
|
|
115
|
+
/** Read and JSON-parse a whole file; returns `undefined` on read / parse
|
|
116
|
+
* failure. The caller is responsible for shape-checking the result. */
|
|
117
|
+
export function readJsonFile(file) {
|
|
118
|
+
try {
|
|
119
|
+
return JSON.parse(fs.readFileSync(file, "utf8"));
|
|
120
|
+
}
|
|
121
|
+
catch {
|
|
122
|
+
return undefined;
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
//# sourceMappingURL=jsonl.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"jsonl.js","sourceRoot":"","sources":["../../../src/mem/internal/jsonl.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Default home-based session roots for the persisted-session adapters.
|
|
3
|
+
*
|
|
4
|
+
* `HOME` is captured once at module load — consumers that need to point the
|
|
5
|
+
* adapters at a fake home (tests) must mock `node:os` before importing any
|
|
6
|
+
* mem module.
|
|
7
|
+
*/
|
|
8
|
+
export declare const HOME: string;
|
|
9
|
+
export declare const CLAUDE_PROJECTS: string;
|
|
10
|
+
export declare const CODEX_SESSIONS: string;
|
|
11
|
+
/** ZCode (Zhipu) persisted-session SQLite store. The companion `-wal` file is
|
|
12
|
+
* auto-detected by the readonly parser. */
|
|
13
|
+
export declare const ZCODE_DB: string;
|
|
14
|
+
/** Grok CLI session root: `<cwd url-encoded>/<session-id>/chat_history.jsonl`.
|
|
15
|
+
* The sibling `session_search.sqlite` is a search index only and is not read —
|
|
16
|
+
* this adapter needs no database and adds no dependency. */
|
|
17
|
+
export declare const GROK_SESSIONS: string;
|
|
18
|
+
export declare const PI_AGENT_DIR: string;
|
|
19
|
+
export declare const PI_SESSIONS: string;
|
|
20
|
+
/** Claude sanitizes a cwd into its on-disk project dir name by replacing
|
|
21
|
+
* every path separator (`/` and Windows `\`), drive colon (`:`), `_`, and `.`
|
|
22
|
+
* with `-`. Confirmed empirically against `~/.claude/projects/`:
|
|
23
|
+
* `/Users/x/.codex/...` → `-Users-x--codex-...`, `snap_note` → `snap-note`. */
|
|
24
|
+
export declare function claudeProjectDirFromCwd(cwd: string): string;
|
|
25
|
+
/** Grok names each project dir with the URL-encoded absolute cwd, e.g.
|
|
26
|
+
* `/Users/x/proj` → `%2FUsers%2Fx%2Fproj`. */
|
|
27
|
+
export declare function grokProjectDirFromCwd(cwd: string): string;
|
|
28
|
+
/** Inverse of {@link grokProjectDirFromCwd}. Returns `undefined` when the name
|
|
29
|
+
* is not valid percent-encoding rather than throwing on a stray `%`. */
|
|
30
|
+
export declare function grokCwdFromProjectDir(dirName: string): string | undefined;
|
|
31
|
+
/** Pi encodes a cwd as `--<resolved-cwd-with-separators-as-dashes>--`. */
|
|
32
|
+
export declare function piProjectDirFromCwd(cwd: string): string;
|
|
33
|
+
/** Discover Pi session roots visible from the current process and project. */
|
|
34
|
+
export declare function piSessionRoots(cwd?: string): string[];
|
|
35
|
+
/** Lazy stack-based recursive file walk — yields every file path under
|
|
36
|
+
* `root`. Missing roots and unreadable directories are skipped silently. */
|
|
37
|
+
export declare function walkDir(root: string): Generator<string>;
|
|
38
|
+
//# sourceMappingURL=paths.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"paths.d.ts","sourceRoot":"","sources":["../../../src/mem/internal/paths.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAMH,eAAO,MAAM,IAAI,QAAe,CAAC;AACjC,eAAO,MAAM,eAAe,QAAyC,CAAC;AACtE,eAAO,MAAM,cAAc,QAAwC,CAAC;AACpE;2CAC2C;AAC3C,eAAO,MAAM,QAAQ,QAAsD,CAAC;AAC5E;;4DAE4D;AAC5D,eAAO,MAAM,aAAa,QAAuC,CAAC;AASlE,eAAO,MAAM,YAAY,QAExB,CAAC;AACF,eAAO,MAAM,WAAW,QAGvB,CAAC;AAiBF;;;+EAG+E;AAC/E,wBAAgB,uBAAuB,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAE3D;AAED;8CAC8C;AAC9C,wBAAgB,qBAAqB,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAEzD;AAED;wEACwE;AACxE,wBAAgB,qBAAqB,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAMzE;AAED,0EAA0E;AAC1E,wBAAgB,mBAAmB,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAIvD;AAED,8EAA8E;AAC9E,wBAAgB,cAAc,CAAC,GAAG,CAAC,EAAE,MAAM,GAAG,MAAM,EAAE,CAsBrD;AAED;4EAC4E;AAC5E,wBAAiB,OAAO,CAAC,IAAI,EAAE,MAAM,GAAG,SAAS,CAAC,MAAM,CAAC,CAkBxD"}
|
|
@@ -0,0 +1,126 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Default home-based session roots for the persisted-session adapters.
|
|
3
|
+
*
|
|
4
|
+
* `HOME` is captured once at module load — consumers that need to point the
|
|
5
|
+
* adapters at a fake home (tests) must mock `node:os` before importing any
|
|
6
|
+
* mem module.
|
|
7
|
+
*/
|
|
8
|
+
import * as fs from "node:fs";
|
|
9
|
+
import * as os from "node:os";
|
|
10
|
+
import * as path from "node:path";
|
|
11
|
+
export const HOME = os.homedir();
|
|
12
|
+
export const CLAUDE_PROJECTS = path.join(HOME, ".claude", "projects");
|
|
13
|
+
export const CODEX_SESSIONS = path.join(HOME, ".codex", "sessions");
|
|
14
|
+
/** ZCode (Zhipu) persisted-session SQLite store. The companion `-wal` file is
|
|
15
|
+
* auto-detected by the readonly parser. */
|
|
16
|
+
export const ZCODE_DB = path.join(HOME, ".zcode", "cli", "db", "db.sqlite");
|
|
17
|
+
/** Grok CLI session root: `<cwd url-encoded>/<session-id>/chat_history.jsonl`.
|
|
18
|
+
* The sibling `session_search.sqlite` is a search index only and is not read —
|
|
19
|
+
* this adapter needs no database and adds no dependency. */
|
|
20
|
+
export const GROK_SESSIONS = path.join(HOME, ".grok", "sessions");
|
|
21
|
+
function expandHome(p) {
|
|
22
|
+
if (p === "~")
|
|
23
|
+
return HOME;
|
|
24
|
+
if (p.startsWith(`~${path.sep}`))
|
|
25
|
+
return path.join(HOME, p.slice(2));
|
|
26
|
+
if (p.startsWith("~/"))
|
|
27
|
+
return path.join(HOME, p.slice(2));
|
|
28
|
+
return p;
|
|
29
|
+
}
|
|
30
|
+
export const PI_AGENT_DIR = expandHome(process.env.PI_CODING_AGENT_DIR ?? path.join(HOME, ".pi", "agent"));
|
|
31
|
+
export const PI_SESSIONS = expandHome(process.env.PI_CODING_AGENT_SESSION_DIR ??
|
|
32
|
+
path.join(PI_AGENT_DIR, "sessions"));
|
|
33
|
+
function readPiSettingsSessionDir(settingsFile) {
|
|
34
|
+
try {
|
|
35
|
+
const raw = JSON.parse(fs.readFileSync(settingsFile, "utf8"));
|
|
36
|
+
if (!raw || typeof raw !== "object" || Array.isArray(raw))
|
|
37
|
+
return undefined;
|
|
38
|
+
const sessionDir = raw.sessionDir;
|
|
39
|
+
if (typeof sessionDir !== "string" || !sessionDir.trim())
|
|
40
|
+
return undefined;
|
|
41
|
+
const expanded = expandHome(sessionDir);
|
|
42
|
+
return path.isAbsolute(expanded)
|
|
43
|
+
? expanded
|
|
44
|
+
: path.resolve(path.dirname(settingsFile), expanded);
|
|
45
|
+
}
|
|
46
|
+
catch {
|
|
47
|
+
return undefined;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
/** Claude sanitizes a cwd into its on-disk project dir name by replacing
|
|
51
|
+
* every path separator (`/` and Windows `\`), drive colon (`:`), `_`, and `.`
|
|
52
|
+
* with `-`. Confirmed empirically against `~/.claude/projects/`:
|
|
53
|
+
* `/Users/x/.codex/...` → `-Users-x--codex-...`, `snap_note` → `snap-note`. */
|
|
54
|
+
export function claudeProjectDirFromCwd(cwd) {
|
|
55
|
+
return path.join(CLAUDE_PROJECTS, cwd.replace(/[/\\:_.]/g, "-"));
|
|
56
|
+
}
|
|
57
|
+
/** Grok names each project dir with the URL-encoded absolute cwd, e.g.
|
|
58
|
+
* `/Users/x/proj` → `%2FUsers%2Fx%2Fproj`. */
|
|
59
|
+
export function grokProjectDirFromCwd(cwd) {
|
|
60
|
+
return path.join(GROK_SESSIONS, encodeURIComponent(path.resolve(cwd)));
|
|
61
|
+
}
|
|
62
|
+
/** Inverse of {@link grokProjectDirFromCwd}. Returns `undefined` when the name
|
|
63
|
+
* is not valid percent-encoding rather than throwing on a stray `%`. */
|
|
64
|
+
export function grokCwdFromProjectDir(dirName) {
|
|
65
|
+
try {
|
|
66
|
+
return decodeURIComponent(dirName);
|
|
67
|
+
}
|
|
68
|
+
catch {
|
|
69
|
+
return undefined;
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
/** Pi encodes a cwd as `--<resolved-cwd-with-separators-as-dashes>--`. */
|
|
73
|
+
export function piProjectDirFromCwd(cwd) {
|
|
74
|
+
const resolvedCwd = path.resolve(cwd);
|
|
75
|
+
const safePath = `--${resolvedCwd.replace(/^[/\\]/, "").replace(/[/\\:]/g, "-")}--`;
|
|
76
|
+
return path.join(path.join(PI_AGENT_DIR, "sessions"), safePath);
|
|
77
|
+
}
|
|
78
|
+
/** Discover Pi session roots visible from the current process and project. */
|
|
79
|
+
export function piSessionRoots(cwd) {
|
|
80
|
+
const roots = [path.join(PI_AGENT_DIR, "sessions"), PI_SESSIONS];
|
|
81
|
+
const globalSettingsDir = readPiSettingsSessionDir(path.join(PI_AGENT_DIR, "settings.json"));
|
|
82
|
+
if (globalSettingsDir)
|
|
83
|
+
roots.push(globalSettingsDir);
|
|
84
|
+
if (cwd) {
|
|
85
|
+
const projectSettingsDir = readPiSettingsSessionDir(path.join(path.resolve(cwd), ".pi", "settings.json"));
|
|
86
|
+
if (projectSettingsDir)
|
|
87
|
+
roots.push(projectSettingsDir);
|
|
88
|
+
}
|
|
89
|
+
const seen = new Set();
|
|
90
|
+
const out = [];
|
|
91
|
+
for (const root of roots) {
|
|
92
|
+
const normalized = path.resolve(root);
|
|
93
|
+
if (seen.has(normalized))
|
|
94
|
+
continue;
|
|
95
|
+
seen.add(normalized);
|
|
96
|
+
out.push(root);
|
|
97
|
+
}
|
|
98
|
+
return out;
|
|
99
|
+
}
|
|
100
|
+
/** Lazy stack-based recursive file walk — yields every file path under
|
|
101
|
+
* `root`. Missing roots and unreadable directories are skipped silently. */
|
|
102
|
+
export function* walkDir(root) {
|
|
103
|
+
if (!fs.existsSync(root))
|
|
104
|
+
return;
|
|
105
|
+
const stack = [root];
|
|
106
|
+
while (stack.length) {
|
|
107
|
+
const cur = stack.pop();
|
|
108
|
+
if (cur === undefined)
|
|
109
|
+
break;
|
|
110
|
+
let entries;
|
|
111
|
+
try {
|
|
112
|
+
entries = fs.readdirSync(cur, { withFileTypes: true });
|
|
113
|
+
}
|
|
114
|
+
catch {
|
|
115
|
+
continue;
|
|
116
|
+
}
|
|
117
|
+
for (const e of entries) {
|
|
118
|
+
const p = path.join(cur, e.name);
|
|
119
|
+
if (e.isDirectory())
|
|
120
|
+
stack.push(p);
|
|
121
|
+
else if (e.isFile())
|
|
122
|
+
yield p;
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
//# sourceMappingURL=paths.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"paths.js","sourceRoot":"","sources":["../../../src/mem/internal/paths.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Zero-dependency read-only SQLite file parser.
|
|
3
|
+
*
|
|
4
|
+
* `@blulotus/trellis-core` is intentionally free of runtime dependencies —
|
|
5
|
+
* `better-sqlite3` was tried for the OpenCode adapter and reverted because its
|
|
6
|
+
* native build chain broke `npm install` on Windows + restricted networks. This
|
|
7
|
+
* parser is the minimum viable reader needed by the ZCode `mem` adapter: list
|
|
8
|
+
* tables, full-scan one table, return rows as `{ [columnName]: value }`. It is
|
|
9
|
+
* NOT a SQL engine: no WHERE pushdown, no index lookup, no writes.
|
|
10
|
+
*
|
|
11
|
+
* Scope:
|
|
12
|
+
* - Database header (page size, db size, text encoding, WAL flag)
|
|
13
|
+
* - Table b-tree leaf (0x0d) + interior (0x05) traversal
|
|
14
|
+
* - Record decode for TEXT / INTEGER / NULL / float64 / BLOB(serial only)
|
|
15
|
+
* - Overflow page chains (long TEXT rows like ZCode `message.data`)
|
|
16
|
+
* - WAL replay: stable main/WAL snapshot, WAL-index `mxFrame` end mark, and
|
|
17
|
+
* cumulative header/frame checksum verification.
|
|
18
|
+
*
|
|
19
|
+
* Out of scope:
|
|
20
|
+
* - WITHOUT ROWID tables (return [] — their rows live in index b-trees,
|
|
21
|
+
* which this parser doesn't walk). ZCode's tables are normal rowid tables.
|
|
22
|
+
*
|
|
23
|
+
* Format references:
|
|
24
|
+
* - https://www.sqlite.org/fileformat2.html
|
|
25
|
+
* - https://www.sqlite.org/walformat.html
|
|
26
|
+
*
|
|
27
|
+
* All multi-byte integers are big-endian (SQLite's native byte order).
|
|
28
|
+
*/
|
|
29
|
+
/** One row from `scanTable`, keyed by column name. Values are decoded JS
|
|
30
|
+
* primitives. NULL → null, INTEGER → number, TEXT → string, BLOB →
|
|
31
|
+
* Uint8Array, float → number. Columns are keyed by the CREATE TABLE column
|
|
32
|
+
* order; if the column-name parse failed, keys fall back to `col0`, `col1`... */
|
|
33
|
+
export type SqliteRow = Record<string, unknown>;
|
|
34
|
+
export interface SqliteTableInfo {
|
|
35
|
+
name: string;
|
|
36
|
+
rootPgno: number;
|
|
37
|
+
/** The raw `CREATE TABLE` SQL (used to recover column names). */
|
|
38
|
+
sql: string;
|
|
39
|
+
}
|
|
40
|
+
export interface SqliteReadOnly {
|
|
41
|
+
/** List user tables (type='table') from sqlite_master. */
|
|
42
|
+
listTables(): SqliteTableInfo[];
|
|
43
|
+
/** Full-scan a table by name, yielding rows. Returns [] when the table is
|
|
44
|
+
* missing. Throws `SqliteParseError` on structural corruption. */
|
|
45
|
+
scanTable(tableName: string, predicate?: (row: SqliteRow) => boolean): SqliteRow[];
|
|
46
|
+
/** The db file path this reader was opened against. */
|
|
47
|
+
readonly dbPath: string;
|
|
48
|
+
close(): void;
|
|
49
|
+
}
|
|
50
|
+
/** Thrown when the SQLite file is structurally invalid. Adapters are expected
|
|
51
|
+
* to catch this and degrade to an empty result rather than crash the CLI. */
|
|
52
|
+
export declare class SqliteParseError extends Error {
|
|
53
|
+
readonly cause?: unknown | undefined;
|
|
54
|
+
constructor(message: string, cause?: unknown | undefined);
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* Thrown when the database files do not remain stable across all snapshot
|
|
58
|
+
* capture attempts. This is deliberately distinct from a malformed database:
|
|
59
|
+
* callers must not parse a snapshot whose consistency they could not verify.
|
|
60
|
+
*/
|
|
61
|
+
export declare class SqliteSnapshotUnstableError extends SqliteParseError {
|
|
62
|
+
constructor(mainPath: string);
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* Open a SQLite database file for read-only access. Automatically loads the
|
|
66
|
+
* sibling `<db>-wal` file when present so active WAL-mode databases (e.g.
|
|
67
|
+
* ZCode's running store) return their latest committed data.
|
|
68
|
+
*
|
|
69
|
+
* Throws `SqliteParseError` if `mainPath` is not a SQLite file or is too
|
|
70
|
+
* corrupted to read the header. Adapters should catch and degrade.
|
|
71
|
+
*/
|
|
72
|
+
export declare function openSqliteReadOnly(mainPath: string): SqliteReadOnly;
|
|
73
|
+
/** Convenience: open + scan + close in one call. Returns [] on any parse error
|
|
74
|
+
* or missing table, never throws. Useful for adapters that already decided to
|
|
75
|
+
* degrade silently. */
|
|
76
|
+
export declare function scanTableSafe(mainPath: string, tableName: string): SqliteRow[];
|
|
77
|
+
//# sourceMappingURL=sqlite-readonly.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sqlite-readonly.d.ts","sourceRoot":"","sources":["../../../src/mem/internal/sqlite-readonly.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AAMH;;;iFAGiF;AACjF,MAAM,MAAM,SAAS,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;AAEhD,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,MAAM,CAAC;IACjB,iEAAiE;IACjE,GAAG,EAAE,MAAM,CAAC;CACb;AAED,MAAM,WAAW,cAAc;IAC7B,0DAA0D;IAC1D,UAAU,IAAI,eAAe,EAAE,CAAC;IAChC;sEACkE;IAClE,SAAS,CACP,SAAS,EAAE,MAAM,EACjB,SAAS,CAAC,EAAE,CAAC,GAAG,EAAE,SAAS,KAAK,OAAO,GACtC,SAAS,EAAE,CAAC;IACf,uDAAuD;IACvD,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,KAAK,IAAI,IAAI,CAAC;CACf;AAID;6EAC6E;AAC7E,qBAAa,gBAAiB,SAAQ,KAAK;IAGvC,QAAQ,CAAC,KAAK,CAAC,EAAE,OAAO;gBADxB,OAAO,EAAE,MAAM,EACN,KAAK,CAAC,EAAE,OAAO,YAAA;CAK3B;AAED;;;;GAIG;AACH,qBAAa,2BAA4B,SAAQ,gBAAgB;gBACnD,QAAQ,EAAE,MAAM;CAM7B;AAyxBD;;;;;;;GAOG;AACH,wBAAgB,kBAAkB,CAAC,QAAQ,EAAE,MAAM,GAAG,cAAc,CA2HnE;AAED;;uBAEuB;AACvB,wBAAgB,aAAa,CAC3B,QAAQ,EAAE,MAAM,EAChB,SAAS,EAAE,MAAM,GAChB,SAAS,EAAE,CAWb"}
|