@eigenpal/cli 0.4.17 → 0.5.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,6 +1,6 @@
1
1
  ---
2
2
  name: eigenpal
3
- description: Build, run, and iterate on Eigenpal workflows from the command line. The workflow engine, evaluators, dataset folders, and execution introspection are all controlled via `eigenpal` subcommands. The server is the source of truth — local files are inputs you push.
3
+ description: Build, run, and iterate on Eigenpal workflows and agents from the command line. Use `eigenpal workflow` for YAML workflows, datasets, evaluators, executions, and experiments. Use `eigenpal agent` for agent workspaces, executions, feedback, traces, files, and expected artifacts.
4
4
  license: Apache-2.0
5
5
  compatibility: Requires eigenpal CLI.
6
6
  metadata:
@@ -11,104 +11,85 @@ metadata:
11
11
 
12
12
  # Eigenpal
13
13
 
14
- Eigenpal is a workflow engine. A workflow is a DAG of steps
15
- (parsing, extraction, scripting, etc.). Iteration happens locally with the
16
- `eigenpal` CLI; **execution + datasets + experiments live on the server**.
14
+ Eigenpal has two major CLI surfaces:
17
15
 
18
- This skill is the schema reference. The CLI does the actual work.
16
+ - `eigenpal workflow` — build and operate YAML workflows: definitions,
17
+ datasets, evaluators, executions, experiments, versions, and schema
18
+ introspection.
19
+ - `eigenpal agent` — build and operate agent workspaces: agent files, triggers,
20
+ executions, traces, feedback, expected artifacts, and reruns.
19
21
 
20
- ## Iteration loop (end-to-end)
22
+ Use long command names in generated commands and documentation. They are more
23
+ readable and cost very little for agents to type. Some short aliases exist for
24
+ interactive users; understand them if you see them, but do not prefer them:
21
25
 
22
- ```
23
- 1. eigenpal init workflow my-extraction --template pdf-extraction
24
- 2. edit workflow.yaml + evaluators.yaml + dataset/examples/*/expected/output.json
25
- 3. eigenpal workflow validate # local: all three checks, no server contact
26
- 4. eigenpal workflow push --file workflow.yaml # creates wf_… on first push
27
- 5. eigenpal workflow execution run my-extraction sample-name # one-off run for debugging
28
- 6. eigenpal workflow evaluators push <workflow-id> --file evaluators.yaml
29
- 7. eigenpal workflow dataset push <workflow-id> --file dataset/ --mode replace
30
- 8. eigenpal workflow experiment run <workflow-id> # → { batchId, executionIds }
31
- 9. eigenpal workflow experiment status <workflow-id> <batch-id>
32
- 10. eigenpal workflow experiment results <workflow-id> <batch-id> --format csv --out r.csv
33
- ```
34
-
35
- > **`push` BEFORE `execution run`.** The CLI no longer ships YAML at run
36
- > time — only saved workflows execute. `execution run <workflow-id>` reads
37
- > the definition from the server, so any local edit to `workflow.yaml`
38
- > must be `push`ed first or the run will use the previous version. If
39
- > the workflow has never been pushed, `execution run` exits with
40
- > `Workflow "<arg>" not found on the server. Push it first.`
26
+ - `agent exec` = `agent execution`
27
+ - `agent execution fb` = `agent execution feedback`
28
+ - `agent execution artifact` = `agent execution artifacts`
29
+ - `workflow exec` = `workflow execution`
30
+ - `workflow exp` = `workflow experiment`
31
+ - `ls` = `list` anywhere in the CLI
32
+ - `diff` = `compare` anywhere in the CLI
41
33
 
42
- ## Identifying a workflow
34
+ For exact flags and defaults, prefer the generated references:
43
35
 
44
- Every command that takes `<workflow-id>` expects a **`wf_xxx` id** — the
45
- opaque, server-generated identifier printed by `workflow push` and
46
- `workflow list`. Stable across renames; this is the form to use in
47
- scripts and CI.
36
+ - [`reference/cli/workflow.md`](reference/cli/workflow.md)
37
+ - [`reference/cli/agent.md`](reference/cli/agent.md)
48
38
 
49
- As a typing convenience the workflow's slug (the YAML's `name:` field)
50
- is also accepted — the CLI resolves it server-side. The resolver
51
- detects the form by the `wf_` prefix:
39
+ ## Pick The Surface
52
40
 
53
- | Argument starts with… | Looked up via |
54
- | --------------------- | ------------------------------------------------- |
55
- | `wf_…` | `GET /api/v1/workflows/<id>` |
56
- | anything else | `GET /api/v1/workflows?name=<slug>` (exact match) |
41
+ Choose `workflow` when the work is about a workflow definition, dataset,
42
+ evaluator, experiment, or workflow execution.
57
43
 
58
- Workflow names are constrained to `[a-z0-9][a-z0-9_-]*` (lowercase
59
- letters, digits, `_`, `-`; 1–64 chars), so every slug is terminal-safe
60
- and url-safe by construction — no shell quoting required.
61
-
62
- ```bash
63
- # Both work; prefer the id form in scripts.
64
- eigenpal workflow execution run wf_abc123 sample-1
65
- eigenpal workflow execution run my-extraction sample-1
66
- ```
44
+ Choose `agent` when the work is about an agent workspace, agent file, trigger,
45
+ agent execution, trace, feedback entry, expected artifact, or rerun.
67
46
 
68
- If the workflow hasn't been pushed yet, the resolver fails fast:
69
- `Workflow "<arg>" not found on the server. Push it first, or run \`eigenpal workflow list\` to see what's available.`
47
+ Agents and workflows are related, but their iteration loops are different:
48
+ workflow experiments evaluate datasets with evaluators; agent workflows do not
49
+ currently expose that same experiment/evaluator loop through the CLI.
70
50
 
71
- **Other id types — not interchangeable with workflow id:**
72
-
73
- - `workflow execution {get,watch,cancel,compare} <executionId>` — `exec_…`
74
- - `workflow experiment compare <batchA> <batchB>` — batch ids (`evb_…`)
75
- - `workflow dataset example {get,update,delete} <wf-id> <exampleId>` — second positional is the example id (`evx_…`)
76
-
77
- ## Common recipes
78
-
79
- ### From zero — new workflow from a template
51
+ ## Workflow Iteration Loop
80
52
 
81
53
  ```bash
82
- eigenpal init workflow invoices --template pdf-extraction # scaffolds workflow.yaml + dataset/ + evaluators.yaml
54
+ # 1. Create or edit the local project.
55
+ eigenpal init workflow invoices --template pdf-extraction
83
56
  cd invoices
84
- eigenpal workflow validate # confirm scaffold is valid before pushing
85
- eigenpal workflow push --file workflow.yaml
86
- # → ✓ Created wf_abc123 (`eigenpal workflow list` to see it again)
87
- ```
57
+ $EDITOR workflow.yaml
88
58
 
89
- ### Author + validate a workflow
90
-
91
- ```bash
92
- # Pick the right step types BEFORE writing the workflow
59
+ # 2. Inspect schemas before guessing config fields.
93
60
  eigenpal workflow step-type list --search extract
94
- eigenpal workflow step-type get ai.extract | jq '.configSchema.properties'
61
+ eigenpal workflow step-type get ai.extract --json | jq '.configSchema.properties'
95
62
 
96
- # Validate locally (zod parse + step-type lookup, no server)
63
+ # 3. Validate and push the workflow definition.
97
64
  eigenpal workflow validate ./workflow.yaml
65
+ eigenpal workflow push --file workflow.yaml
98
66
 
99
- # Push (creates on first call; same name + new version appends to history)
100
- eigenpal workflow push --file workflow.yaml --workflow-id wf_abc123
67
+ # 4. Run one example while iterating.
68
+ eigenpal workflow execution run <workflow-id> <example-name>
69
+ eigenpal workflow execution watch <execution-id>
70
+ eigenpal workflow execution get <execution-id> --json
101
71
 
102
- # Update an existing workflow with explicit / auto-bumped semver:
103
- eigenpal workflow push --file workflow.yaml --workflow-id wf_abc123 --set-version 2.0.0
104
- eigenpal workflow push --file workflow.yaml --workflow-id wf_abc123 --bump patch # patch | minor | major
72
+ # 5. Manage the dataset and evaluators when ready to evaluate.
73
+ eigenpal workflow dataset validate ./dataset
74
+ eigenpal workflow dataset push <workflow-id> --file ./dataset --mode replace
75
+ eigenpal workflow evaluators validate ./evaluators.yaml
76
+ eigenpal workflow evaluators push <workflow-id> --file ./evaluators.yaml
77
+
78
+ # 6. Run and inspect a batch experiment.
79
+ eigenpal workflow experiment run <workflow-id>
80
+ eigenpal workflow experiment watch <workflow-id> <batch-id>
81
+ eigenpal workflow experiment results <workflow-id> <batch-id> --format csv --out results.csv
105
82
  ```
106
83
 
107
- The validator emits structured field-path errors with a hint pointing at
108
- `step-type get <type>` for the offending step. Follow the hint.
84
+ Workflow commands that take `<workflow-id>` accept the stable `wf_...` id. Many
85
+ also accept the workflow slug for convenience, but use the id in scripts.
86
+
87
+ Useful workflow ids are not interchangeable:
109
88
 
110
- Version bumping rules (`--bump` vs `--set-version` vs YAML `version:`)
111
- live in [`reference/workflow-yaml.md`](reference/workflow-yaml.md#validate-before-pushing).
89
+ - `<workflow-id>` identifies a workflow (`wf_...`).
90
+ - `<execution-id>` identifies one workflow execution.
91
+ - `<batch-id>` identifies one experiment batch.
92
+ - `<example-id>` identifies one dataset example.
112
93
 
113
94
  ### Organize workflows into folders
114
95
 
@@ -126,435 +107,274 @@ Missing folders in the path are created automatically.
126
107
  Default to creating workflows at the top level. Do not move a workflow into
127
108
  a folder unless the user specifically asks for that placement.
128
109
 
129
- ### Iterate fast on one step (no server, no DAG)
130
-
131
- Tightest possible loop — local sandbox, milliseconds per run. Today
132
- covers `transform.script` and `ai.extract`. For any other step type,
133
- fall back to `workflow execution run` against the server.
110
+ ## Agent Iteration Loop
134
111
 
135
112
  ```bash
136
- eigenpal workflow step exec transform.script \
137
- --config-json '{"function":"function script(items) { return items.reduce((s,i)=>s+i.v,0); }"}' \
138
- --inputs items=@items.json
139
- # 3
113
+ # 1. Find the agent and inspect its files.
114
+ eigenpal agent list
115
+ eigenpal agent file list <agent-id-or-slug>
116
+ eigenpal agent file get <agent-id-or-slug> agent/instructions.md --out instructions.md
117
+
118
+ # 2. Find executions that need attention.
119
+ eigenpal agent execution list <agent-id-or-slug> \
120
+ --feedback-status open \
121
+ --feedback-rating fail \
122
+ --since-last-resolved \
123
+ --include feedback,expected \
124
+ --compact
125
+
126
+ # 3. Pull the execution context locally.
127
+ eigenpal agent execution pull <agent-execution-id> --include all --out ./review/<agent-execution-id>
128
+ eigenpal agent execution artifacts list <agent-execution-id>
129
+ eigenpal agent execution trace <agent-execution-id> --out ./review/<agent-execution-id>/trace.jsonl
130
+
131
+ # 4. Edit and preview agent files.
132
+ $EDITOR instructions.md
133
+ eigenpal agent file diff <agent-id-or-slug> agent/instructions.md instructions.md
134
+ eigenpal agent file put <agent-id-or-slug> agent/instructions.md instructions.md --preview
135
+ eigenpal agent file put <agent-id-or-slug> agent/instructions.md instructions.md
136
+
137
+ # 5. Rerun and compare.
138
+ eigenpal agent execution rerun <agent-execution-id> --wait
139
+ eigenpal agent execution compare <new-agent-execution-id> \
140
+ --expected-from <source-agent-execution-id> \
141
+ --normalize-dates
142
+ eigenpal agent execution compare <new-agent-execution-id> \
143
+ --baseline-from <source-agent-execution-id> \
144
+ --normalize-dates
145
+
146
+ # 6. Resolve feedback once verified.
147
+ eigenpal agent execution feedback resolve <source-agent-execution-id> \
148
+ --message "Fixed and verified in <new-agent-execution-id>."
140
149
  ```
141
150
 
142
- See [`reference/step-exec.md`](reference/step-exec.md) for the full
143
- grammar — inputs, config, output schema, exit codes.
151
+ Agent commands commonly accept `<agent-id-or-slug>`. Agent execution commands
152
+ take an agent execution id. Execution pulls and comparisons write review
153
+ artifacts under `.eigenpal/artifacts/...` by default.
144
154
 
145
- ### Cancel a long-running execution
155
+ ## Workflow Recipes
146
156
 
147
- ```bash
148
- eigenpal workflow execution cancel exec_abc # TTY: silent; CI: needs --yes
149
- eigenpal workflow execution cancel exec_abc --yes # CI / pipes
150
- ```
151
-
152
- The worker finishes the current step, then stops — the check happens
153
- between every step transition, including inside `control.foreach` /
154
- `control.parallel` / `control.block` bodies. Already-terminal
155
- executions (completed/failed/cancelled) exit 0 with an info line. Safe
156
- to retry.
157
-
158
- ### Compare two experiment batches (no workflow id needed)
157
+ ### Author And Validate A Workflow
159
158
 
160
159
  ```bash
161
- eigenpal workflow experiment compare evb_old evb_new --regression-threshold 0.05
162
- ```
163
-
164
- Output is two stacked tables: a per-evaluator aggregate (rows per evaluator
165
- with mean Δ, regressions, improvements — sorted biggest mover first) followed
166
- by a per-(example, evaluator) detail table. No need to write a Python
167
- aggregator on top.
168
-
169
- ```bash
170
- # JSON exposes both layers — `summary.byEvaluator` for the rollup,
171
- # `rows` for the full per-example detail.
172
- eigenpal workflow experiment compare evb_old evb_new --json | jq '.summary.byEvaluator'
173
- ```
174
-
175
- Unlike its siblings, `compare` takes no `<workflow-id>` — the server resolves
176
- the owning workflow from each batch id. Both batches must live in the
177
- same workflow within your tenant. See [`reference/debugging.md`](reference/debugging.md#6-compare-two-experiment-batches)
178
- for sort flags + `--json` shape.
179
-
180
- ### Author + validate evaluators
181
-
182
- ```bash
183
- # Inspect what evaluator types exist + their config shape
184
- cat packages/cli/src/skill/reference/evaluators.md # or read this skill's `reference/`
185
-
186
- # Validate locally (every evaluator entry parsed against its discriminated-union schema)
187
- eigenpal workflow evaluators validate ./evaluators.yaml
188
-
189
- # Push (overwrites the workflow's evaluator config)
190
- eigenpal workflow evaluators push <workflow-id> --file evaluators.yaml
160
+ eigenpal workflow step-type list
161
+ eigenpal workflow step-type get <step-type> --json
162
+ eigenpal workflow validate ./workflow.yaml
163
+ eigenpal workflow push --file workflow.yaml
191
164
  ```
192
165
 
193
- Always set `description:` on every evaluator entry. It's a short, plain-language
194
- sentence (≤500 chars; aim for one line) explaining what the evaluator measures
195
- and why it matters, written for a non-technical reviewer in the dashboard.
196
- Skip model names, thresholds, and dot-paths; those belong in `config`. See
197
- [`reference/evaluators.md`](reference/evaluators.md#writing-descriptions-for-stakeholders).
166
+ The validator reports structured field-path errors. If the error hints at a
167
+ step type, inspect that type with `eigenpal workflow step-type get <type>`.
198
168
 
199
- ### Build + validate + upload a dataset
169
+ ### Manage A Dataset
200
170
 
201
171
  ```bash
202
- # Folder layout: dataset/examples/<name>/{input/arguments.json, input/<file-arg>/<file>, expected/output.json, meta.json}
203
- eigenpal workflow dataset validate ./dataset # rejects bad folder names, arg-name collisions, etc.
204
-
205
- # Push. `replace` wipes server-side examples for this workflow first; `append` adds.
206
- eigenpal workflow dataset push <workflow-id> --file ./dataset --mode replace
207
- # Watch the `expectedSet` count in the final NDJSON `done` event — if 0, evals run un-graded.
172
+ eigenpal workflow dataset validate ./dataset
173
+ eigenpal workflow dataset push <workflow-id> --file ./dataset --mode append
174
+ eigenpal workflow dataset list <workflow-id>
175
+ eigenpal workflow dataset pull <workflow-id> --out dataset.zip
208
176
  ```
209
177
 
210
- To inspect or round-trip the server's current dataset:
211
-
212
- ```bash
213
- eigenpal workflow dataset list <workflow-id>
214
- eigenpal workflow dataset pull <workflow-id> --out current.zip # round-trip back to local
178
+ Dataset archives use this folder shape:
179
+
180
+ ```text
181
+ dataset/
182
+ └── examples/
183
+ └── <example-name>/
184
+ ├── input/
185
+ │ ├── arguments.json
186
+ │ └── <file-argument-name>/<file>
187
+ ├── expected/output.json
188
+ └── meta.json
215
189
  ```
216
190
 
217
- ### Edit one example without re-uploading the whole dataset
191
+ For one-off changes, use the per-example commands instead of re-uploading the
192
+ whole dataset:
218
193
 
219
194
  ```bash
220
- # Inspect one example end-to-end (triggerInput + expectedOutput + metadata):
221
- eigenpal workflow dataset example get <workflow-id> <example-id>
222
- eigenpal workflow dataset example get <workflow-id> <example-id> --json | jq '.expectedOutput'
223
-
224
- # Capture a corrected output as the new ground truth (the most common one):
225
- # 1. Look at what the workflow returned
226
- eigenpal workflow execution get exec_… --json | jq '.output.data' > /tmp/correct.json
227
- # 2. Patch that example's expected output in place
228
- eigenpal workflow dataset example update <workflow-id> <example-id> \
229
- --expected-file /tmp/correct.json
230
-
231
- # Add one new example to a known dataset:
232
- eigenpal workflow dataset example create <workflow-id> \
233
- --name missing-required-field \
234
- --input-json '{"language":"en"}' \
235
- --expected-file /tmp/expected.json \
236
- --annotation "edge case: required field absent from input"
237
-
238
- # Drop a bad example by id (CI requires --yes):
195
+ eigenpal workflow dataset example get <workflow-id> <example-id> --json
196
+ eigenpal workflow dataset example update <workflow-id> <example-id> --expected-file expected.json
197
+ eigenpal workflow dataset example create <workflow-id> --name edge-case --input-json '{"language":"en"}'
239
198
  eigenpal workflow dataset example delete <workflow-id> <example-id> --yes
240
199
  ```
241
200
 
242
- `example update` is a partial PATCH — any flag you omit is left alone. Pass
243
- `--annotation ""` to clear an annotation. For bulk changes, edit the local
244
- dataset folder and re-push with `dataset push --mode replace`.
245
-
246
- ### Run an experiment + collect results
201
+ ### Run And Compare Workflow Executions
247
202
 
248
203
  ```bash
249
- # Kick off — runs every example in the dataset against every evaluator.
250
- eigenpal workflow experiment run <workflow-id> # → { batchId, executionIds }
251
-
252
- # Or restrict to one example:
253
- eigenpal workflow experiment run <workflow-id> --example-id evx_…
204
+ eigenpal workflow execution run <workflow-id> <example-name>
205
+ eigenpal workflow execution watch <execution-id>
206
+ eigenpal workflow execution get <execution-id> --include input,output,error --json
207
+ eigenpal workflow execution list <workflow-id> --status failed --limit 10
208
+ eigenpal workflow execution compare <execution-id-a> <execution-id-b>
209
+ eigenpal workflow execution cancel <execution-id> --yes
254
210
  ```
255
211
 
256
- **Recommended:** use `experiment watch` — it polls until terminal AND auto-pulls
257
- results to disk in one command. Replaces the old "run → status (poll) → results"
258
- chain so agents don't have to write a custom poller, parse `executions[].status`,
259
- or chain `monitor + status + pull + score` shell logic.
212
+ ### Run And Compare Experiments
260
213
 
261
214
  ```bash
262
- # One command: watch until terminal, then write ./results-<batchId>.json on completion.
263
- eigenpal workflow experiment watch <workflow-id> <batch-id>
264
-
265
- # CSV output:
266
- eigenpal workflow experiment watch <workflow-id> <batch-id> --format csv
267
-
268
- # Custom destination (overrides the default ./results-<batchId>.<format>):
269
- eigenpal workflow experiment watch <workflow-id> <batch-id> --pull-on-complete ./out/r.json
270
-
271
- # Just watch, skip the pull (e.g. you only need the live tick + exit code):
272
- eigenpal workflow experiment watch <workflow-id> <batch-id> --no-pull
215
+ eigenpal workflow experiment run <workflow-id>
216
+ eigenpal workflow experiment status <workflow-id> <batch-id> --json
217
+ eigenpal workflow experiment watch <workflow-id> <batch-id> --format json
218
+ eigenpal workflow experiment results <workflow-id> <batch-id> --format csv --out results.csv
219
+ eigenpal workflow experiment compare <batch-id-a> <batch-id-b> --regression-threshold 0.05
273
220
  ```
274
221
 
275
- Exit codes match `experiment status --watch`: `0` clean, `1` any
276
- failed/cancelled/rejected execution, `2` `--max-wait` deadline reached
277
- (30 min default — re-run to keep watching).
278
-
279
- ### Monitoring scripts — use `--short` and the JSON rollup
222
+ `workflow experiment compare` resolves the owning workflow from the batch ids;
223
+ both batches must belong to the same workflow.
280
224
 
281
- When a script needs to spot-check a batch (no waiting), prefer one of the two
282
- machine-readable paths instead of folding `executions[].status` yourself.
225
+ ## Agent Recipes
283
226
 
284
- ```bash
285
- # Single line on stdout, awk-friendly:
286
- eigenpal workflow experiment status <wf> <batch> --short
287
- # → 6/6 done failed=0 cancelled=0 rejected=0 (or "in-progress" while pending)
288
-
289
- # Parse with awk:
290
- DONE_STATE=$(eigenpal workflow experiment status <wf> <batch> --short | awk '{print $2}')
291
- [ "$DONE_STATE" = "done" ] || exit 0 # not terminal yet, try again later
292
- ```
227
+ ### Inspect And Edit Agent Files
293
228
 
294
229
  ```bash
295
- # JSON includes a top-level `summary` rollup so you don't count statuses by hand:
296
- eigenpal workflow experiment status <wf> <batch> --json | jq '.summary'
297
- # → { total: 6, terminal: 6, complete: true,
298
- # completedCount: 5, failedCount: 1,
299
- # cancelledCount: 0, rejectedCount: 0,
300
- # runningCount: 0, pendingCount: 0 }
301
-
302
- # `summary.complete` is the canonical poll-completion flag.
230
+ eigenpal agent list
231
+ eigenpal agent file list <agent-id-or-slug>
232
+ eigenpal agent file list <agent-id-or-slug> --prefix agent/knowledge
233
+ eigenpal agent file get <agent-id-or-slug> agent/instructions.md --out instructions.md
234
+ eigenpal agent file diff <agent-id-or-slug> agent/instructions.md instructions.md
235
+ eigenpal agent file put <agent-id-or-slug> agent/instructions.md instructions.md --preview
236
+ eigenpal agent file put <agent-id-or-slug> agent/instructions.md instructions.md
303
237
  ```
304
238
 
305
- `--short` and `--json` are mutually exclusive with `--watch` — for live
306
- streaming use `experiment watch` instead.
239
+ Use `--preview` before writing substantial changes; it shows how the target file
240
+ would change.
307
241
 
308
- If you need the raw eval-results export after watching with `--no-pull`, or
309
- to refetch results outside a watch loop, fall back to:
242
+ ### Inspect Agent Executions
310
243
 
311
244
  ```bash
312
- eigenpal workflow experiment results <workflow-id> <batch-id> --format csv --out r.csv
245
+ eigenpal agent execution list <agent-id-or-slug> --status failed --limit 10
246
+ eigenpal agent execution list <agent-id-or-slug> --feedback-rating fail --include feedback,expected
247
+ eigenpal agent execution get <agent-execution-id> --include feedback,expected,files,trace,issues --json
248
+ eigenpal agent execution pull <agent-execution-id> --include all
249
+ eigenpal agent execution artifacts list <agent-execution-id>
313
250
  ```
314
251
 
315
- ### Long documents — split → chunk → extract
316
-
317
- The canonical chain when a document is too long for one `ai.extract` call (loan
318
- contracts, SaaS agreements, RFPs). Each step preserves source `pageIndex` so
319
- the final extracted fields trace back to the originating page.
320
-
321
- ```yaml
322
- - name: parse
323
- type: ai.parse
324
- with: { input: "{{ input.document }}" }
325
-
326
- # LLM-driven section split — each split carries page_range + confidence
327
- - name: sections
328
- type: ai.split
329
- with:
330
- input: "{{ steps.parse.output }}"
331
- sections:
332
- - { name: header, description: "Title page + parties block" }
333
- - { name: priloha2, description: "Príloha 2 odkladacie podmienky", required: true }
334
-
335
- # Optional: chunk a long section before extraction (regex-anchored, keeps page refs)
336
- - name: chunks
337
- type: transform.text-chunker
338
- with:
339
- input: "{{ steps.sections.output.splits[1] }}" # priloha2 split
340
- maxChars: 8000
341
- overlap: 500
342
- splitOn: ['(?:^|\\n)\\s*\\d+\\.\\d+\\s+', '\\n\\n+', '\\n']
343
-
344
- # Deterministic field extraction — counterpart to ai.extract; matches carry _evidence.pageIndex
345
- - name: header_fields
346
- type: transform.regex-extract
347
- with:
348
- input: "{{ steps.parse.output }}"
349
- fields:
350
- contractNumber:
351
- pattern: 'č\\.\\s*(\\d{1,4}/\\w+/\\d{4})'
352
- normalize: strip-spaces
353
- signatureDate:
354
- pattern: 'uzavretá\\s+dňa\\s+(\\d{1,2})\\.(\\d{1,2})\\.(\\d{4})'
355
- format: iso-date
356
- currency:
357
- pattern: '\\b(EUR|USD|CZK)\\b'
358
- default: EUR
359
- flags: i
360
- ```
252
+ Use `--compact` on execution lists when you only need triage rows.
361
253
 
362
- Discovery from the CLI:
254
+ ### Download Agent Traces
363
255
 
364
256
  ```bash
365
- eigenpal workflow step-type get ai.split | jq '.configSchema.properties'
366
- eigenpal workflow step-type get transform.text-chunker | jq '.configSchema.properties'
367
- eigenpal workflow step-type get transform.regex-extract | jq '.configSchema.properties'
257
+ eigenpal agent execution trace <agent-execution-id> --out trace.jsonl
258
+ eigenpal agent execution trace <agent-execution-id> | jq -r 'select(.toolName? or .tool_name? or .tool?)'
259
+ eigenpal agent execution trace <agent-execution-id> | rg 'error|tool'
368
260
  ```
369
261
 
370
- Pick the right operator for the job:
371
-
372
- | Goal | Operator |
373
- | ---------------------------------------- | ------------------------- |
374
- | Extract structured data with an LLM | `ai.extract` |
375
- | Pull fields by regex (no LLM) | `transform.regex-extract` |
376
- | Split a doc into named sections (LLM) | `ai.split` |
377
- | Cut text by regex boundary + overlap | `transform.text-chunker` |
262
+ `trace` streams the raw JSONL to stdout by default. Use shell tools such as
263
+ `jq`, `rg`, or `awk` for filtering; use `--out` when you want to save the file.
378
264
 
379
- ### Debug a failing workflow
265
+ ### Manage Agent Feedback And Expected Artifacts
380
266
 
381
267
  ```bash
382
- # 1. Re-run a single example against the saved workflow (must be pushed first).
383
- # <workflow-id> accepts a `wf_…` id (preferred for scripts) or the slug.
384
- eigenpal workflow execution run <workflow-id> <example-name>
268
+ eigenpal agent execution feedback get <agent-execution-id>
269
+ eigenpal agent execution feedback update <agent-execution-id> \
270
+ --status open \
271
+ --rating fail \
272
+ --message "Expected the filing date to be extracted."
273
+ eigenpal agent execution feedback resolve <agent-execution-id> \
274
+ --message "Fixed and verified."
275
+ eigenpal agent execution feedback clear <agent-execution-id> --yes
276
+
277
+ eigenpal agent execution expected list <agent-execution-id>
278
+ eigenpal agent execution expected upload <agent-execution-id> --file expected.json --name expected.json
279
+ eigenpal agent execution expected copy-output <agent-execution-id> --output-file result.json --name expected.json
280
+ eigenpal agent execution expected pull <agent-execution-id> --out expected/
281
+ ```
385
282
 
386
- # 2. Or pull a recorded failure from the server
387
- eigenpal workflow execution list <workflow-id> --status failed --limit 5
388
- eigenpal workflow execution get exec_… # full payload, all steps
389
- eigenpal workflow execution get exec_… --step extract --include input,output,error
283
+ Feedback is attached to one execution. Expected artifacts are the references
284
+ used when comparing future runs.
390
285
 
391
- # 3. Compare two runs (e.g. before/after a workflow change)
392
- eigenpal workflow execution compare <exec-a> <exec-b>
286
+ ### Rerun And Compare Agent Executions
393
287
 
394
- # 4. Wait for a kicked-off run to finish (use this whenever you need
395
- # to block until terminal — adaptive polling, 30-min auto-detach)
396
- eigenpal workflow execution watch exec_…
288
+ ```bash
289
+ eigenpal agent execution rerun <agent-execution-id> --wait
290
+ eigenpal agent execution compare <new-agent-execution-id> --expected-from <source-agent-execution-id>
291
+ eigenpal agent execution compare <new-agent-execution-id> --baseline-from <source-agent-execution-id>
292
+ eigenpal agent execution compare <new-agent-execution-id> \
293
+ --expected-from <source-agent-execution-id> \
294
+ --normalize-dates \
295
+ --fail-on-diff
397
296
  ```
398
297
 
399
- See [`reference/debugging.md`](reference/debugging.md) for common failure
400
- modes (`validation_failed`, `template_resolution_failed`, `script_timeout`,
401
- `step_type_unknown`) and how to skip flaky external steps via
402
- `meta.json` overrides.
403
-
404
- ## Output convention
298
+ Use `--expected-from` to compare a new output against stored expected artifacts.
299
+ Use `--baseline-from` to compare a new output against another execution's actual
300
+ output.
405
301
 
406
- Every command splits its output:
302
+ ## Output And Exit Codes
407
303
 
408
- - **stdout** = data — JSON payloads, table rows, file contents from
409
- `pull` / `experiment results`. Pipe-safe.
410
- - **stderr** = status — `✓` / `✗` / `ℹ` / `!` lines. Silenced by
411
- `-q` / `--quiet` (errors and warnings always fire; stdout never
412
- silenced).
413
-
414
- The `--json` flag (on every `list` / `get` / mutating command) flips
415
- the human-readable table on stdout to the raw server payload — pipe
416
- through real `jq` to project:
304
+ Most `list`, `get`, and mutating commands support `--json`. Prefer JSON when a
305
+ script or agent needs to inspect the result with `jq`.
417
306
 
418
307
  ```bash
419
- eigenpal workflow execution list wf_abc --json | jq '.data[0].id'
420
- eigenpal workflow execution get exec_abc --json | jq '.stepExecutions[].status'
308
+ eigenpal workflow execution list <workflow-id> --json | jq '.data[0].id'
309
+ eigenpal agent execution list <agent-id-or-slug> --json | jq '.executions[0].id'
421
310
  ```
422
311
 
423
- ### Exit codes
312
+ General exit-code convention:
424
313
 
425
314
  | Code | Meaning |
426
315
  | --- | --- |
427
316
  | 0 | Success. |
428
- | 1 | Runtime error — network, server 5xx, command-specific failure (e.g. `experiment status` (with or without `--watch`) reports a terminal batch where at least one execution failed or was cancelled). |
429
- | 2 | Misuse or recoverable failure — bad flag, `step exec --output-schema` violation, `execution watch --max-wait` deadline, `step exec` against an unsupported step type. |
430
-
431
- Exit 2 means "fix your invocation and re-run." Exit 1 means something
432
- broke upstream — check the error.
433
-
434
- ## Where the schemas live
435
-
436
- The CLI ships JSON Schema for every step type and every evaluator type.
437
- Don't guess fields — introspect:
438
-
439
- ```bash
440
- eigenpal workflow step-type list # full step catalog
441
- eigenpal workflow step-type get ai.extract # config + output schema
442
- eigenpal workflow evaluator-type list # full evaluator catalog
443
- eigenpal workflow evaluator-type get llm-judge # config schema
317
+ | 1 | Runtime or command failure. |
318
+ | 2 | Invalid invocation, unsupported option, or timeout/deadline condition. |
319
+
320
+ Status and progress messages go to stderr. Data intended for piping goes to
321
+ stdout.
322
+
323
+ ## Schema And Reference Files
324
+
325
+ Workflow schemas:
326
+
327
+ - [`reference/workflow-yaml.md`](reference/workflow-yaml.md) — workflow file shape
328
+ - [`reference/step-types.md`](reference/step-types.md) — step-type catalog
329
+ - [`reference/step-exec.md`](reference/step-exec.md) — single-step execution command
330
+ - [`reference/dataset-format.md`](reference/dataset-format.md) — dataset folder format
331
+ - [`reference/evaluators.md`](reference/evaluators.md) — evaluator configuration
332
+ - [`reference/debugging.md`](reference/debugging.md) — workflow execution debugging
333
+
334
+ CLI command references:
335
+
336
+ - [`reference/cli/workflow.md`](reference/cli/workflow.md)
337
+ - [`reference/cli/agent.md`](reference/cli/agent.md)
338
+ - [`reference/cli/auth.md`](reference/cli/auth.md)
339
+ - [`reference/cli/status.md`](reference/cli/status.md)
340
+
341
+ Use `eigenpal --help` for the grouped command overview and
342
+ `eigenpal <command> --help` for live command help.
343
+
344
+ ## CLI Surface
345
+
346
+ ```text
347
+ eigenpal
348
+ ├── auth
349
+ │ ├── login
350
+ │ ├── list
351
+ │ └── use
352
+ ├── status
353
+ ├── workflow
354
+ │ ├── list
355
+ │ ├── pull
356
+ │ ├── push
357
+ │ ├── validate
358
+ │ ├── move
359
+ │ ├── clear-local
360
+ │ ├── dataset
361
+ │ ├── evaluators
362
+ │ ├── execution
363
+ │ ├── experiment
364
+ │ ├── versions
365
+ │ ├── step-type
366
+ │ └── evaluator-type
367
+ ├── agent
368
+ │ ├── list
369
+ │ ├── get
370
+ │ ├── push
371
+ │ ├── pull
372
+ │ ├── file
373
+ │ ├── trigger
374
+ │ ├── execution
375
+ │ └── experiment
376
+ └── skill
377
+ ├── install
378
+ ├── uninstall
379
+ └── list
444
380
  ```
445
-
446
- For workflow / evaluators / dataset shape, see this skill's `reference/`:
447
-
448
- - [`reference/workflow-yaml.md`](reference/workflow-yaml.md) — top-level shape, triggers, inputs, steps, output, template expressions
449
- - [`reference/step-types.md`](reference/step-types.md) — step-type catalog + when to reach for each
450
- - [`reference/step-exec.md`](reference/step-exec.md) — local single-step iteration (`workflow step exec`) — inputs, config, output schema, exit codes
451
- - [`reference/dataset-format.md`](reference/dataset-format.md) — `dataset/examples/<name>/{input,expected,meta}` folder convention
452
- - [`reference/evaluators.md`](reference/evaluators.md) — evaluators.yaml schema + judge patterns
453
- - [`reference/debugging.md`](reference/debugging.md) — execution introspection + common failures
454
- - [`reference/cli/`](reference/cli/) — full flag reference per command (autogenerated from the live Commander tree, never lies)
455
-
456
- ## Validation errors carry hints
457
-
458
- Every server-side validation failure returns a structured envelope:
459
-
460
- ```json
461
- {
462
- "issues": [
463
- { "field": "steps.2.config.passThreshold",
464
- "message": "Required, got undefined", "code": "invalid_value" }
465
- ],
466
- "hint": "Failing step is type `eval.llm-judge`. Run `eigenpal workflow step-type get eval.llm-judge` to inspect its config schema."
467
- }
468
- ```
469
-
470
- The CLI renders this with the field column aligned and the hint inline —
471
- follow the hint, the schema lookup is one command away.
472
-
473
- ## Don't reach for
474
-
475
- - `eval-local` / similar local-mirror commands — they don't exist. Drive
476
- the dataset by editing the local folder and pushing with
477
- `workflow dataset push --mode replace`, OR use the per-example CRUD
478
- (`dataset example {create,update,delete,get}`) when you only need to
479
- flip one row.
480
- - The `manifest.json` dataset format — legacy, the import endpoint rejects
481
- it. Always use the folder convention.
482
-
483
- ## CLI surface
484
-
485
- ```bash
486
- # Auth + tenant switching
487
- eigenpal auth login # add a profile (or update existing tenant's)
488
- eigenpal auth list # see all profiles, current marked ●
489
- eigenpal auth use [profile] # switch active (interactive picker if no arg)
490
- eigenpal status # active tenant, user, key id, workflow count
491
-
492
- # Definition
493
- eigenpal workflow list
494
- eigenpal workflow push --file workflow.yaml [--workflow-id <workflow-id>]
495
- eigenpal workflow pull <workflow-id>
496
- eigenpal workflow validate [path]
497
- eigenpal workflow move <wf-id> --folder billing/invoices # use --folder / for root
498
-
499
- # Evaluators
500
- eigenpal workflow evaluators push <workflow-id> --file evaluators.yaml
501
- eigenpal workflow evaluators pull <workflow-id>
502
- eigenpal workflow evaluators validate [path]
503
-
504
- # Dataset
505
- eigenpal workflow dataset push <workflow-id> --file dataset/ [--mode {append|replace}] # default: append
506
- eigenpal workflow dataset pull <workflow-id> --out dataset.zip
507
- eigenpal workflow dataset list <workflow-id>
508
- eigenpal workflow dataset validate [path]
509
- eigenpal workflow dataset example create <workflow-id> --name <n> [--input-file] [--expected-file] [--annotation]
510
- eigenpal workflow dataset example update <workflow-id> <example-id> [--name] [--input-file] [--expected-file] [--annotation] [--row-order]
511
- eigenpal workflow dataset example delete <workflow-id> <example-id> --yes
512
- eigenpal workflow dataset example get <workflow-id> <example-id> # full row + metadata
513
-
514
- # All-in-one validation against the templated project layout
515
- eigenpal workflow validate # ./workflow.yaml + ./evaluators.yaml + ./dataset/
516
-
517
- # Local artifacts
518
- eigenpal workflow clear-local # delete local execution artifacts (no server impact)
519
-
520
- # Experiments (batch eval runs)
521
- eigenpal workflow experiment run <workflow-id> [--example-id <id> ...]
522
- eigenpal workflow experiment status <workflow-id> <batch-id> [--watch] [--short] [--json] # exit 1 on terminal w/ failures, 2 on --max-wait. --json includes top-level `summary` rollup.
523
- eigenpal workflow experiment watch <workflow-id> <batch-id> [--format csv|json] [--pull-on-complete <path>] [--no-pull] # poll + auto-pull results in one shot
524
- eigenpal workflow experiment results <workflow-id> [batch-id] --format {csv|json} --out r.csv
525
- eigenpal workflow experiment list <workflow-id>
526
- eigenpal workflow experiment compare <batch-a> <batch-b> [--regression-threshold] [--sort] # no --workflow-id; prints per-evaluator aggregate + per-row table
527
-
528
- # Step-type / evaluator-type introspection
529
- eigenpal workflow step-type list
530
- eigenpal workflow step-type get <type>
531
- eigenpal workflow evaluator-type list
532
- eigenpal workflow evaluator-type get <type>
533
-
534
- # Local single-step iteration (no server)
535
- eigenpal workflow step exec <type> [--config-json | --config-file] [--inputs k=v...] [--output-schema]
536
-
537
- # Execution (one-off run + read-side debugging + cancellation)
538
- eigenpal workflow execution run <workflow-id> [examples...]
539
- eigenpal workflow execution get <exec-id>
540
- eigenpal workflow execution list <workflow-id> [--status running|failed|completed]
541
- eigenpal workflow execution watch <exec-id> # 2s/5s adaptive polling
542
- eigenpal workflow execution compare <exec-a> <exec-b>
543
- eigenpal workflow execution cancel <exec-id> # tells the worker to stop between steps; safe to retry
544
-
545
- # Versions
546
- eigenpal workflow versions list <workflow-id> # pushed semver history (newest first)
547
- eigenpal workflow versions restore <workflow-id> <version-id> # re-activate a prior version as the live one
548
-
549
- # Tooling
550
- eigenpal skill install # interactive multiselect for Claude Code, Cursor, …
551
- eigenpal skill uninstall [toolIds...] # name one or more tools, or pass --all
552
- eigenpal skill list # show what's installed where
553
- ```
554
-
555
- `eigenpal --help` for the grouped overview, `eigenpal <command> --help`
556
- for any specific command. The full per-command flag reference is also
557
- bundled at [`reference/cli/`](reference/cli/) (autogenerated from the
558
- live Commander tree, so it never lies). Read those when you need the
559
- exact spelling / default / data type for a flag without round-tripping
560
- to `--help`.