@zenera/cli 1.1.23 → 1.1.25

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.
Files changed (184) hide show
  1. package/README.md +88 -2
  2. package/dist/ask.d.ts +51 -0
  3. package/dist/ask.js +166 -0
  4. package/dist/banner.js +2 -2
  5. package/dist/batch.d.ts +83 -0
  6. package/dist/batch.js +413 -0
  7. package/dist/catalog.d.ts +11 -1
  8. package/dist/catalog.js +80 -7
  9. package/dist/command.d.ts +6 -0
  10. package/dist/commands/inspect.d.ts +57 -0
  11. package/dist/commands/inspect.js +539 -91
  12. package/dist/commands/list.js +128 -19
  13. package/dist/commands/memory.js +461 -32
  14. package/dist/commands/meta.js +311 -21
  15. package/dist/commands/models.js +110 -14
  16. package/dist/commands/open.js +4 -4
  17. package/dist/commands/run.js +175 -36
  18. package/dist/commands/sandbox.js +148 -15
  19. package/dist/engine.d.ts +24 -0
  20. package/dist/engine.js +61 -8
  21. package/dist/eventlog.d.ts +59 -0
  22. package/dist/eventlog.js +146 -0
  23. package/dist/liveness.d.ts +7 -0
  24. package/dist/liveness.js +20 -3
  25. package/dist/main.js +5 -2
  26. package/dist/meta/editor.d.ts +9 -0
  27. package/dist/meta/editor.js +60 -0
  28. package/dist/meta/finetune/children.d.ts +8 -0
  29. package/dist/meta/finetune/children.js +76 -0
  30. package/dist/meta/finetune/command.d.ts +30 -0
  31. package/dist/meta/finetune/command.js +338 -0
  32. package/dist/meta/finetune/dataset/anchors.d.ts +41 -0
  33. package/dist/meta/finetune/dataset/anchors.js +239 -0
  34. package/dist/meta/finetune/dataset/changes.d.ts +36 -0
  35. package/dist/meta/finetune/dataset/changes.js +319 -0
  36. package/dist/meta/finetune/dataset/command.d.ts +17 -0
  37. package/dist/meta/finetune/dataset/command.js +1011 -0
  38. package/dist/meta/finetune/dataset/drift.d.ts +33 -0
  39. package/dist/meta/finetune/dataset/drift.js +71 -0
  40. package/dist/meta/finetune/dataset/export.d.ts +26 -0
  41. package/dist/meta/finetune/dataset/export.js +51 -0
  42. package/dist/meta/finetune/dataset/index.d.ts +2 -0
  43. package/dist/meta/finetune/dataset/index.js +2 -0
  44. package/dist/meta/finetune/dataset/sample.d.ts +50 -0
  45. package/dist/meta/finetune/dataset/sample.js +197 -0
  46. package/dist/meta/finetune/dataset/schema.d.ts +33 -0
  47. package/dist/meta/finetune/dataset/schema.js +216 -0
  48. package/dist/meta/finetune/dataset/store.d.ts +35 -0
  49. package/dist/meta/finetune/dataset/store.js +177 -0
  50. package/dist/meta/finetune/dataset/types.d.ts +125 -0
  51. package/dist/meta/finetune/dataset/types.js +39 -0
  52. package/dist/meta/finetune/failure.d.ts +15 -0
  53. package/dist/meta/finetune/failure.js +26 -0
  54. package/dist/meta/finetune/feedback.d.ts +45 -0
  55. package/dist/meta/finetune/feedback.js +85 -0
  56. package/dist/meta/finetune/improvements.d.ts +51 -0
  57. package/dist/meta/finetune/improvements.js +244 -0
  58. package/dist/meta/finetune/index.d.ts +2 -0
  59. package/dist/meta/finetune/index.js +2 -0
  60. package/dist/meta/finetune/journal.d.ts +35 -0
  61. package/dist/meta/finetune/journal.js +135 -0
  62. package/dist/meta/finetune/live.d.ts +74 -0
  63. package/dist/meta/finetune/live.js +226 -0
  64. package/dist/meta/finetune/loop.d.ts +3 -0
  65. package/dist/meta/finetune/loop.js +114 -0
  66. package/dist/meta/finetune/memories.d.ts +47 -0
  67. package/dist/meta/finetune/memories.js +154 -0
  68. package/dist/meta/finetune/report.d.ts +33 -0
  69. package/dist/meta/finetune/report.js +1284 -0
  70. package/dist/meta/finetune/retry.d.ts +24 -0
  71. package/dist/meta/finetune/retry.js +96 -0
  72. package/dist/meta/finetune/sampler.d.ts +18 -0
  73. package/dist/meta/finetune/sampler.js +41 -0
  74. package/dist/meta/finetune/system.d.ts +27 -0
  75. package/dist/meta/finetune/system.js +132 -0
  76. package/dist/meta/finetune/train.d.ts +39 -0
  77. package/dist/meta/finetune/train.js +391 -0
  78. package/dist/meta/finetune/tui.d.ts +16 -0
  79. package/dist/meta/finetune/tui.js +291 -0
  80. package/dist/meta/finetune/tuning.d.ts +167 -0
  81. package/dist/meta/finetune/tuning.js +289 -0
  82. package/dist/meta/finetune/usage.d.ts +62 -0
  83. package/dist/meta/finetune/usage.js +225 -0
  84. package/dist/meta/host.d.ts +14 -0
  85. package/dist/meta/host.js +20 -0
  86. package/dist/meta/index.d.ts +11 -0
  87. package/dist/meta/index.js +11 -0
  88. package/dist/meta/launch.d.ts +81 -0
  89. package/dist/meta/launch.js +286 -0
  90. package/dist/meta/model.d.ts +44 -0
  91. package/dist/meta/model.js +119 -0
  92. package/dist/meta/prompts.d.ts +18 -0
  93. package/dist/meta/prompts.js +61 -0
  94. package/dist/meta/relay.d.ts +20 -0
  95. package/dist/meta/relay.js +123 -0
  96. package/dist/meta/tokens.d.ts +52 -0
  97. package/dist/meta/tokens.js +226 -0
  98. package/dist/meta/window.d.ts +61 -0
  99. package/dist/meta/window.js +198 -0
  100. package/dist/meta/wire.d.ts +42 -0
  101. package/dist/meta/wire.js +129 -0
  102. package/dist/modelref.d.ts +16 -0
  103. package/dist/modelref.js +41 -0
  104. package/dist/narrate.js +5 -2
  105. package/dist/podman.d.ts +42 -0
  106. package/dist/podman.js +198 -5
  107. package/dist/progress.d.ts +33 -0
  108. package/dist/progress.js +402 -0
  109. package/dist/projects.d.ts +0 -5
  110. package/dist/projects.js +2 -15
  111. package/dist/request.d.ts +45 -0
  112. package/dist/request.js +300 -0
  113. package/dist/sandbox.d.ts +2 -0
  114. package/dist/sandbox.js +20 -3
  115. package/dist/scaffold.d.ts +15 -6
  116. package/dist/scaffold.js +5 -60
  117. package/dist/session.d.ts +26 -1
  118. package/dist/session.js +46 -32
  119. package/dist/term.d.ts +5 -0
  120. package/dist/term.js +28 -3
  121. package/dist/trace.d.ts +84 -0
  122. package/dist/trace.js +737 -0
  123. package/dist/tui/models.d.ts +33 -0
  124. package/dist/tui/models.js +389 -0
  125. package/dist/tui/wrap.d.ts +5 -0
  126. package/dist/tui/wrap.js +12 -0
  127. package/dist/usage.d.ts +78 -0
  128. package/dist/usage.js +51 -0
  129. package/dist/validate.js +25 -3
  130. package/package.json +3 -2
  131. package/templates/editor/.github/copilot-instructions.md +41 -107
  132. package/templates/editor/.github/prompts/analyze.prompt.md +31 -0
  133. package/templates/editor/.github/prompts/dataset.prompt.md +108 -0
  134. package/templates/editor/.github/prompts/finetune-apply.prompt.md +91 -0
  135. package/templates/editor/.github/prompts/finetune.prompt.md +744 -0
  136. package/templates/editor/.github/prompts/new-agent.prompt.md +3 -1
  137. package/templates/editor/.github/prompts/new-skill.prompt.md +2 -0
  138. package/templates/editor/.github/prompts/project-review.prompt.md +4 -3
  139. package/templates/editor/.github/skills/zen-analyze-run/SKILL.md +483 -0
  140. package/templates/editor/.github/skills/zen-cli/SKILL.md +18 -4
  141. package/templates/editor/.github/skills/zen-cli/references/check.md +7 -5
  142. package/templates/editor/.github/skills/zen-cli/references/dataset.md +34 -0
  143. package/templates/editor/.github/skills/zen-cli/references/finetune.md +77 -0
  144. package/templates/editor/.github/skills/zen-cli/references/inspect.md +300 -21
  145. package/templates/editor/.github/skills/zen-cli/references/memory.md +121 -28
  146. package/templates/editor/.github/skills/zen-cli/references/meta.md +61 -0
  147. package/templates/editor/.github/skills/zen-cli/references/models.md +6 -2
  148. package/templates/editor/.github/skills/zen-cli/references/projects.md +12 -5
  149. package/templates/editor/.github/skills/zen-cli/references/rag.md +24 -6
  150. package/templates/editor/.github/skills/zen-cli/references/run.md +201 -4
  151. package/templates/editor/.github/skills/zen-cli/references/sandbox.md +10 -1
  152. package/templates/editor/.github/skills/zen-code-python/SKILL.md +123 -0
  153. package/templates/editor/.github/skills/zen-code-python/references/code_python.md +48 -0
  154. package/templates/editor/.github/skills/zen-dataset/SKILL.md +253 -0
  155. package/templates/editor/.github/skills/zen-finetune/SKILL.md +1791 -0
  156. package/templates/editor/.github/skills/zen-finetune/references/readme-template.md +268 -0
  157. package/templates/editor/.github/skills/zen-finetune/scripts/batch.mjs +390 -0
  158. package/templates/editor/.github/skills/zen-finetune/scripts/difficult.mjs +243 -0
  159. package/templates/editor/.github/skills/zen-finetune/scripts/memory.mjs +280 -0
  160. package/templates/editor/.github/skills/zen-finetune/scripts/next.mjs +398 -0
  161. package/templates/editor/.github/skills/zen-finetune/scripts/report.mjs +797 -0
  162. package/templates/editor/.github/skills/zen-finetune/scripts/select.mjs +354 -0
  163. package/templates/editor/.github/skills/zen-finetune/scripts/usage.mjs +722 -0
  164. package/templates/editor/.github/skills/zen-inspect/SKILL.md +431 -0
  165. package/templates/editor/.github/skills/zen-inspect-ask/SKILL.md +270 -0
  166. package/templates/editor/.github/skills/zen-memory/SKILL.md +78 -29
  167. package/templates/editor/.github/skills/zen-memory-warmup/SKILL.md +363 -531
  168. package/templates/editor/.github/skills/zen-rag-docs/SKILL.md +20 -8
  169. package/templates/editor/.github/skills/zen-review/SKILL.md +5 -3
  170. package/templates/editor/.github/skills/zen-review/scripts/check-paths.sh +5 -4
  171. package/templates/editor/.github/skills/zen-sandbox/SKILL.md +25 -2
  172. package/templates/editor/.github/skills/zen-sandbox-capacity/SKILL.md +334 -0
  173. package/templates/editor/.github/skills/zen-sandbox-capacity/references/loadtest.md +181 -0
  174. package/templates/editor/.github/skills/zen-sandbox-capacity/scripts/preflight_sandbox.sh +457 -0
  175. package/templates/editor/.github/skills/zen-topology/SKILL.md +283 -0
  176. package/templates/editor/.vscode/agents.schema.json +1 -1
  177. package/templates/editor/.vscode/settings.json +2 -0
  178. package/templates/project/agents/files-instructions.md +35 -13
  179. package/templates/project/agents/fork-instructions.md +27 -0
  180. package/templates/project/agents/memory-instructions.md +106 -34
  181. package/templates/project/agents/tools-instructions.md +7 -4
  182. package/templates/project/gitignore +5 -0
  183. package/dist/meta.d.ts +0 -221
  184. package/dist/meta.js +0 -684
package/dist/session.d.ts CHANGED
@@ -6,7 +6,6 @@ export interface SessionPaths {
6
6
  data: string;
7
7
  /** the live, resumable state — rewritten after every run */
8
8
  state: string;
9
- memory: string;
10
9
  blobs: string;
11
10
  runs: string;
12
11
  lock: string;
@@ -52,10 +51,30 @@ export interface RunPaths {
52
51
  output: string;
53
52
  state: string;
54
53
  report: string;
54
+ /** the same run as one Mermaid flowchart, for a model to read */
55
+ graph: string;
55
56
  meta: string;
56
57
  }
57
58
  export declare function runPaths(session: SessionPaths, id: string): RunPaths;
58
59
  export declare function createRun(session: SessionPaths): RunPaths;
60
+ /**
61
+ * The same paths, reached from a directory instead of from a pair of ids.
62
+ *
63
+ * `zen run --json` hands back a run directory, and a caller holding one has no
64
+ * reason to take it apart again to ask a second question about the same run.
65
+ * The layout is fixed, so the ids can be read back out of the path — and both
66
+ * still go through `isStamp`, so a path from anywhere cannot name a directory
67
+ * this layout would never have produced.
68
+ *
69
+ * The session comes back too, not only the run: blobs are stored per session,
70
+ * so anything that resolves a payload needs both halves — and the project, so
71
+ * a command reached this way can still read the project's config.
72
+ */
73
+ export declare function runPathsAt(dir: string): {
74
+ project: string;
75
+ session: SessionPaths;
76
+ run: RunPaths;
77
+ };
59
78
  export interface RunMeta {
60
79
  version: 1;
61
80
  id: string;
@@ -68,9 +87,15 @@ export interface RunMeta {
68
87
  turns: number;
69
88
  usage: unknown;
70
89
  workspace: string;
90
+ memory?: string;
71
91
  error?: string;
72
92
  }
73
93
  export declare function writeRunMeta(p: RunPaths, meta: RunMeta): void;
94
+ /**
95
+ * Partial, because a run killed before it recorded anything still has a
96
+ * directory, and every field here is worth having on its own.
97
+ */
98
+ export declare function readRunMeta(p: RunPaths): Promise<Partial<RunMeta>>;
74
99
  export interface RunSummary {
75
100
  id: string;
76
101
  startedAt?: string;
package/dist/session.js CHANGED
@@ -1,9 +1,9 @@
1
- import { existsSync, mkdirSync, readFileSync, rmSync, writeFileSync } from 'node:fs';
2
- import { hostname } from 'node:os';
3
- import { join, relative, resolve } from 'node:path';
1
+ import { claimLock, ownLock } from '@zenera/neo';
2
+ import { existsSync, mkdirSync, rmSync } from 'node:fs';
3
+ import { basename, dirname, join, relative, resolve } from 'node:path';
4
4
  import { readJson, writeJson } from "./home.js";
5
5
  import { isStamp, stamp, stampInstant } from "./ids.js";
6
- import { alive, isBusy, runIds, sessionIds, sessionsDir } from "./projects.js";
6
+ import { isBusy, runIds, sessionIds, sessionsDir } from "./projects.js";
7
7
  import { CliError, EXIT, invalidError, usageError } from "./term.js";
8
8
  export function sessionPaths(projectDir, id) {
9
9
  if (!isStamp(id)) {
@@ -17,7 +17,6 @@ export function sessionPaths(projectDir, id) {
17
17
  workspace: join(dir, 'workspace'),
18
18
  data,
19
19
  state: join(data, 'state.json'),
20
- memory: join(data, 'memory'),
21
20
  blobs: join(data, 'blobs'),
22
21
  runs: join(dir, 'runs'),
23
22
  lock: join(dir, '.lock'),
@@ -86,24 +85,7 @@ export function requireSession(projectDir, id) {
86
85
  return p;
87
86
  }
88
87
  export function acquire(p) {
89
- const lock = { pid: process.pid, host: hostname(), startedAt: new Date().toISOString() };
90
- const body = `${JSON.stringify(lock, null, 2)}\n`;
91
- try {
92
- // 'wx' fails when the file exists — the create and the check are one
93
- // operation, so two `zen run`s racing cannot both win.
94
- writeFileSync(p.lock, body, { flag: 'wx' });
95
- }
96
- catch (err) {
97
- if (err.code !== 'EEXIST') {
98
- throw err;
99
- }
100
- const held = current(p);
101
- if (held && alive(held.pid) && held.host === hostname()) {
102
- throw new CliError(`session ${p.id} is already running (pid ${held.pid})`, EXIT.failed, 'wait for it, or start another with --new');
103
- }
104
- // Stale, or from another machine's run that cannot be verified here.
105
- writeFileSync(p.lock, body);
106
- }
88
+ claimLock(p.lock, ownLock(), (held) => new CliError(`session ${p.id} is already running (pid ${held.pid})`, EXIT.failed, 'wait for it, or start another with --new'), 2);
107
89
  let released = false;
108
90
  const release = () => {
109
91
  if (released) {
@@ -114,14 +96,6 @@ export function acquire(p) {
114
96
  };
115
97
  return { release };
116
98
  }
117
- function current(p) {
118
- try {
119
- return JSON.parse(readFileSync(p.lock, 'utf8'));
120
- }
121
- catch {
122
- return undefined;
123
- }
124
- }
125
99
  export function runPaths(session, id) {
126
100
  if (!isStamp(id)) {
127
101
  throw usageError(`"${id}" is not a run id`);
@@ -134,6 +108,7 @@ export function runPaths(session, id) {
134
108
  output: join(dir, 'output.md'),
135
109
  state: join(dir, 'state.json'),
136
110
  report: join(dir, 'report.html'),
111
+ graph: join(dir, 'graph.mmd'),
137
112
  meta: join(dir, 'meta.json'),
138
113
  };
139
114
  }
@@ -142,16 +117,55 @@ export function createRun(session) {
142
117
  mkdirSync(p.dir, { recursive: true });
143
118
  return p;
144
119
  }
120
+ /**
121
+ * The same paths, reached from a directory instead of from a pair of ids.
122
+ *
123
+ * `zen run --json` hands back a run directory, and a caller holding one has no
124
+ * reason to take it apart again to ask a second question about the same run.
125
+ * The layout is fixed, so the ids can be read back out of the path — and both
126
+ * still go through `isStamp`, so a path from anywhere cannot name a directory
127
+ * this layout would never have produced.
128
+ *
129
+ * The session comes back too, not only the run: blobs are stored per session,
130
+ * so anything that resolves a payload needs both halves — and the project, so
131
+ * a command reached this way can still read the project's config.
132
+ */
133
+ export function runPathsAt(dir) {
134
+ const full = resolve(dir);
135
+ const runId = basename(full);
136
+ const sessionDir = dirname(dirname(full));
137
+ const wrong = () => usageError(`${display(full)} is not a run directory`, 'runs live at <project>/sessions/<session>/runs/<run>');
138
+ if (!isStamp(runId) || !isStamp(basename(sessionDir)) || basename(dirname(full)) !== 'runs') {
139
+ throw wrong();
140
+ }
141
+ const project = dirname(dirname(sessionDir));
142
+ const session = sessionPaths(project, basename(sessionDir));
143
+ const run = runPaths(session, runId);
144
+ if (resolve(run.dir) !== full) {
145
+ throw wrong();
146
+ }
147
+ if (!existsSync(run.state)) {
148
+ throw invalidError(`run ${runId} has no state.json`, 'only a run that got far enough to save state can be inspected');
149
+ }
150
+ return { project, session, run };
151
+ }
145
152
  export function writeRunMeta(p, meta) {
146
153
  writeJson(p.meta, meta, 0o644);
147
154
  }
155
+ /**
156
+ * Partial, because a run killed before it recorded anything still has a
157
+ * directory, and every field here is worth having on its own.
158
+ */
159
+ export async function readRunMeta(p) {
160
+ return await readJson(p.meta, {});
161
+ }
148
162
  /** Newest first — the order a picker wants. */
149
163
  export async function listRuns(session) {
150
164
  const out = [];
151
165
  for (const id of runIds(session.dir).reverse()) {
152
166
  // A run killed before it recorded anything still has an id, and the id
153
167
  // says when it started, so it is listable without its meta.
154
- const meta = await readJson(runPaths(session, id).meta, {});
168
+ const meta = await readRunMeta(runPaths(session, id));
155
169
  out.push({
156
170
  id,
157
171
  startedAt: meta.startedAt ?? stampInstant(id),
package/dist/term.d.ts CHANGED
@@ -56,6 +56,8 @@ export declare function write(line?: string): void;
56
56
  export declare function writeAll(lines: readonly string[]): void;
57
57
  /** Machine-readable output. Pretty-printed: it is read by people too. */
58
58
  export declare function json(value: unknown): void;
59
+ /** The same bytes, for a caller sending them somewhere other than stdout. */
60
+ export declare function jsonText(value: unknown): string;
59
61
  export declare function note(line?: string): void;
60
62
  /**
61
63
  * One line of narration that rewrites itself while work is in flight, so a
@@ -71,7 +73,10 @@ export declare function warn(message: string): void;
71
73
  /** What this run calls itself, in the process table and on the terminal's tab. */
72
74
  export declare function title(text: string): void;
73
75
  export declare function fail(message: string, hint?: string): void;
76
+ /** An agent's terminal can be a real pty (VS Code Copilot's is), so TTY checks alone miss it. */
77
+ export declare function drivenByAgent(): boolean;
74
78
  export declare function isInteractive(): boolean;
79
+ export declare function deferBanner(print: () => void): void;
75
80
  export declare function ask(question: string, fallback?: string): Promise<string>;
76
81
  /**
77
82
  * Reads without echoing. `readline` writes what you type through its `output`
package/dist/term.js CHANGED
@@ -154,7 +154,11 @@ export function writeAll(lines) {
154
154
  }
155
155
  /** Machine-readable output. Pretty-printed: it is read by people too. */
156
156
  export function json(value) {
157
- process.stdout.write(`${JSON.stringify(value, null, 2)}\n`);
157
+ process.stdout.write(jsonText(value));
158
+ }
159
+ /** The same bytes, for a caller sending them somewhere other than stdout. */
160
+ export function jsonText(value) {
161
+ return `${JSON.stringify(value, null, 2)}\n`;
158
162
  }
159
163
  export function note(line = '') {
160
164
  process.stderr.write(`${line}\n`);
@@ -226,13 +230,34 @@ export function fail(message, hint) {
226
230
  // a stdin that will never answer. A CLI that hangs in CI is worse than one that
227
231
  // fails in CI, because only one of the two tells you which flag you forgot.
228
232
  // ---------------------------------------------------------------------------
233
+ /** An agent's terminal can be a real pty (VS Code Copilot's is), so TTY checks alone miss it. */
234
+ export function drivenByAgent() {
235
+ const own = process.env['ZENERA_AGENT'];
236
+ if (own !== undefined) {
237
+ return own !== '' && own !== '0';
238
+ }
239
+ return Boolean(process.env['AI_AGENT'] || process.env['COPILOT_AGENT']);
240
+ }
229
241
  export function isInteractive() {
230
- return Boolean(process.stdin.isTTY && process.stderr.isTTY);
242
+ return Boolean(process.stdin.isTTY && process.stderr.isTTY) && !drivenByAgent();
243
+ }
244
+ // A banner is for whoever is sitting there, and the only proof that anyone is
245
+ // sitting there is that we are about to ask them something. Commands whose
246
+ // stdout is the answer hand theirs over here instead of printing it, and it
247
+ // appears if — and only if — the run turns out to need a person. Held as a
248
+ // thunk so this module stays below the banner, which is drawn with its colours.
249
+ let pending;
250
+ export function deferBanner(print) {
251
+ pending = print;
231
252
  }
232
253
  function requireTty(what, flag) {
233
254
  if (!isInteractive()) {
234
- throw usageError(`cannot ask for ${what} without a terminal`, `pass ${flag} instead`);
255
+ const why = drivenByAgent() ? 'when an agent is running zen' : 'without a terminal';
256
+ throw usageError(`cannot ask for ${what} ${why}`, `pass ${flag} instead`);
235
257
  }
258
+ const banner = pending;
259
+ pending = undefined;
260
+ banner?.();
236
261
  }
237
262
  export async function ask(question, fallback) {
238
263
  requireTty(question, '--yes or the matching flag');
@@ -0,0 +1,84 @@
1
+ import { type AgentState, type PayloadResolver, type TrajectoryNode } from '@zenera/neo';
2
+ export interface TraceEntry {
3
+ /** diagram id — `n1`, `n2`, …, in the order the run appended nodes */
4
+ key: string;
5
+ node: TrajectoryNode;
6
+ depth: number;
7
+ /** the branch this ran in, or null on the trunk */
8
+ branch: string | null;
9
+ /** hidden from the model's context by a later compaction */
10
+ covered: boolean;
11
+ /** the id of the compaction that hid it, when it is on the same level */
12
+ coveredBy?: string;
13
+ children: TraceBranch[];
14
+ turnStart: number | null;
15
+ startMs: number | null;
16
+ endMs: number | null;
17
+ }
18
+ export interface TraceBranch {
19
+ name: string;
20
+ agent: string;
21
+ status: string;
22
+ entries: TraceEntry[];
23
+ startMs: number | null;
24
+ endMs: number | null;
25
+ turnStart: number | null;
26
+ /** the one branch the join actually waited for */
27
+ slowest: boolean;
28
+ }
29
+ export interface Trace {
30
+ root: TraceEntry[];
31
+ /** every entry, branches included, in key order */
32
+ entries: TraceEntry[];
33
+ byKey: Map<string, TraceEntry>;
34
+ }
35
+ export declare function traceOf(state: AgentState): Trace;
36
+ export declare function safe(text: string, max?: number): string;
37
+ export interface TraceOptions {
38
+ /** the run id to name in the header, when it differs from `state.runId` */
39
+ runId?: string;
40
+ /** the run directory, so the header can spell the command that opens a node */
41
+ dir?: string;
42
+ /** the files the run worked on */
43
+ workspace?: string;
44
+ /** the memory graph the run read, when it had one */
45
+ memory?: string;
46
+ timing?: boolean;
47
+ usage?: boolean;
48
+ /** false drops the palette: a model reads the labels, not the colours */
49
+ style?: boolean;
50
+ }
51
+ export declare function traceMermaid(state: AgentState, opts?: TraceOptions): string;
52
+ /** The node list on its own, for `--json`. */
53
+ export declare function traceIndex(trace: Trace): {
54
+ id: string;
55
+ nodeId: string;
56
+ kind: string;
57
+ agent: string;
58
+ branch: string | null;
59
+ ts: string;
60
+ label: string;
61
+ }[];
62
+ export interface NodePart {
63
+ name: string;
64
+ text: string;
65
+ }
66
+ export interface NodeDetail {
67
+ id: string;
68
+ nodeId: string;
69
+ kind: string;
70
+ agent: string;
71
+ branch: string | null;
72
+ ts: string;
73
+ label: string;
74
+ parts: NodePart[];
75
+ /** fields worth reading that are not payloads */
76
+ facts: Record<string, string>;
77
+ }
78
+ /**
79
+ * `n5`, or `n5..n9`. A range is how a reader asks about a stretch, which is
80
+ * the shape of the question the diagram provokes ("what are n14 to n38 doing").
81
+ */
82
+ export declare function parseNodeIds(words: readonly string[], known: Map<string, unknown>): string[];
83
+ export declare function nodeDetail(trace: Trace, ids: readonly string[], payloads: PayloadResolver): Promise<NodeDetail[]>;
84
+ //# sourceMappingURL=trace.d.ts.map