@akagilnc/pi-workflow-roles 0.1.2096 → 0.1.2105
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/public-cli/main.js +9 -20
- package/package.json +1 -1
- package/resources/engines/codex.md +55 -0
- package/resources/engines/kimi.md +61 -0
- package/src/public-cli/cli.ts +6 -4
- package/src/public-cli/config.ts +15 -28
package/dist/public-cli/main.js
CHANGED
|
@@ -14449,7 +14449,7 @@ function setPersistentSeatEngine(config, seat, engine) {
|
|
|
14449
14449
|
const previous = config.seats[seat];
|
|
14450
14450
|
if (previous === void 0) {
|
|
14451
14451
|
throw new Error(
|
|
14452
|
-
`config seat ${seat} has no persistent model; set provider/model:thinking before engine`
|
|
14452
|
+
`config seat ${seat} has no persistent model; set provider/model[:thinking] before engine`
|
|
14453
14453
|
);
|
|
14454
14454
|
}
|
|
14455
14455
|
if (engine === void 0) {
|
|
@@ -14518,19 +14518,6 @@ function parseModelSpec(spec, fallbackThinking) {
|
|
|
14518
14518
|
const model = modelPart.slice(slash + 1);
|
|
14519
14519
|
return thinking === void 0 ? { provider, model } : { provider, model, thinking };
|
|
14520
14520
|
}
|
|
14521
|
-
function parsePersistentModelSpec(spec) {
|
|
14522
|
-
const parsed = parseModelSpec(spec);
|
|
14523
|
-
if (parsed.thinking === void 0) {
|
|
14524
|
-
throw new Error(
|
|
14525
|
-
`model specification requires a thinking level (provider/model:thinking), got ${spec}`
|
|
14526
|
-
);
|
|
14527
|
-
}
|
|
14528
|
-
return {
|
|
14529
|
-
provider: parsed.provider,
|
|
14530
|
-
model: parsed.model,
|
|
14531
|
-
thinking: parsed.thinking
|
|
14532
|
-
};
|
|
14533
|
-
}
|
|
14534
14521
|
function formatModelSpec(selection) {
|
|
14535
14522
|
const base = `${selection.provider}/${selection.model}`;
|
|
14536
14523
|
return selection.thinking === void 0 ? base : `${base}:${selection.thinking}`;
|
|
@@ -14578,13 +14565,15 @@ function parseSeatModelConfig(value, seat) {
|
|
|
14578
14565
|
if (typeof raw.model !== "string" || raw.model.trim() === "") {
|
|
14579
14566
|
throw new Error(`config seat ${seat} requires model`);
|
|
14580
14567
|
}
|
|
14581
|
-
if (
|
|
14582
|
-
|
|
14568
|
+
if (raw.thinking !== void 0) {
|
|
14569
|
+
if (typeof raw.thinking !== "string" || !THINKING_LEVELS.has(raw.thinking)) {
|
|
14570
|
+
throw new Error(`config seat ${seat} requires a valid thinking level`);
|
|
14571
|
+
}
|
|
14583
14572
|
}
|
|
14584
14573
|
const parsed = {
|
|
14585
14574
|
provider: raw.provider,
|
|
14586
14575
|
model: raw.model,
|
|
14587
|
-
thinking: raw.thinking
|
|
14576
|
+
...raw.thinking === void 0 ? {} : { thinking: raw.thinking }
|
|
14588
14577
|
};
|
|
14589
14578
|
if (raw.engine !== void 0) {
|
|
14590
14579
|
if (typeof raw.engine !== "string") {
|
|
@@ -27117,7 +27106,7 @@ function renderHelp() {
|
|
|
27117
27106
|
lines.push(
|
|
27118
27107
|
"",
|
|
27119
27108
|
"Role options: ak-role help <command>",
|
|
27120
|
-
"Persistent config: ak-role config set <seat> <provider/model:thinking>",
|
|
27109
|
+
"Persistent config: ak-role config set <seat> <provider/model[:thinking]>",
|
|
27121
27110
|
"Persistent engine (judge|reviewer): ak-role config set-engine <seat> <name> | unset-engine <seat>",
|
|
27122
27111
|
"Effective seats: ak-role roles"
|
|
27123
27112
|
);
|
|
@@ -27198,7 +27187,7 @@ async function runConfigCommand(args, home, packageRoot2, io) {
|
|
|
27198
27187
|
if (args[0] === "set") {
|
|
27199
27188
|
if (args.length < 3) {
|
|
27200
27189
|
throw new CliUsageError(
|
|
27201
|
-
"usage: ak-role config set <seat> <provider/model:thinking>"
|
|
27190
|
+
"usage: ak-role config set <seat> <provider/model[:thinking]>"
|
|
27202
27191
|
);
|
|
27203
27192
|
}
|
|
27204
27193
|
const pairs = args.slice(1);
|
|
@@ -27214,7 +27203,7 @@ async function runConfigCommand(args, home, packageRoot2, io) {
|
|
|
27214
27203
|
if (!isPublicConfigurableSeat(seat)) {
|
|
27215
27204
|
throw new CliUsageError(`unknown configurable seat: ${seat}`);
|
|
27216
27205
|
}
|
|
27217
|
-
config = setPersistentSeatConfig(config, seat,
|
|
27206
|
+
config = setPersistentSeatConfig(config, seat, parseModelSpec(spec));
|
|
27218
27207
|
}
|
|
27219
27208
|
await savePublicCliConfig(config, home);
|
|
27220
27209
|
io.stdout(renderConfig(config));
|
package/package.json
CHANGED
|
@@ -0,0 +1,55 @@
|
|
|
1
|
+
# codex engine method material
|
|
2
|
+
|
|
3
|
+
This file is packaged method material for the optional `codex` labor engine
|
|
4
|
+
(Codex CLI on the host). When a role run selects this engine, read these
|
|
5
|
+
bytes and follow the local CLI's actual interface for the labor detour. Return
|
|
6
|
+
the labor result to the same role session so typed submission stays on the
|
|
7
|
+
existing in-session path.
|
|
8
|
+
|
|
9
|
+
Material is data for the model, not a code contract. Do not invent package flags.
|
|
10
|
+
|
|
11
|
+
## Invocation examples (local Codex CLI)
|
|
12
|
+
|
|
13
|
+
The machine entrypoint is `codex`. Run from the role project root. Non-interactive
|
|
14
|
+
labor uses `codex exec` (alias `e`). Always pass `--skip-git-repo-check` so the
|
|
15
|
+
labor subprocess can start outside a Git work tree when needed:
|
|
16
|
+
|
|
17
|
+
```bash
|
|
18
|
+
codex exec --skip-git-repo-check "YOUR_LABOR_PROMPT"
|
|
19
|
+
```
|
|
20
|
+
|
|
21
|
+
For concurrent or disposable labor turns, add `--ephemeral` so session files are
|
|
22
|
+
not persisted to disk:
|
|
23
|
+
|
|
24
|
+
```bash
|
|
25
|
+
codex exec --skip-git-repo-check --ephemeral "YOUR_LABOR_PROMPT"
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
Working-root override when the seat cwd is not the project root:
|
|
29
|
+
|
|
30
|
+
```bash
|
|
31
|
+
codex exec --skip-git-repo-check --ephemeral -C "$PROJECT_ROOT" "YOUR_LABOR_PROMPT"
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
Default (non-`--json`) mode prints the session banner and progress on stderr
|
|
35
|
+
(measured on this host). Collect the labor body from stdout so that stderr log
|
|
36
|
+
noise is not mixed into the returned body; the package idle clock can still see
|
|
37
|
+
activity on both streams. Use `--json` only when the seat itself needs
|
|
38
|
+
machine-readable event rows (those rows land on stdout as JSONL; measured event
|
|
39
|
+
types include `thread.started`, `turn.started`, `item.completed`, `error`,
|
|
40
|
+
`turn.failed`):
|
|
41
|
+
|
|
42
|
+
```bash
|
|
43
|
+
codex exec --skip-git-repo-check --ephemeral --json "YOUR_LABOR_PROMPT"
|
|
44
|
+
```
|
|
45
|
+
|
|
46
|
+
Prefer `codex exec --help` on the host over any remembered flag set. Do not wrap
|
|
47
|
+
this engine behind `ak-role` flags. Later host quota/auth failures are separate
|
|
48
|
+
from argv acceptance — re-check the local CLI if a turn fails after session start.
|
|
49
|
+
|
|
50
|
+
When the package detour tool is available, start exactly one subprocess per
|
|
51
|
+
labor invocation through it with argv assembled from this material and the
|
|
52
|
+
local CLI; return the stdout labor content to the same session for the existing
|
|
53
|
+
typed submission path. One labor turn = one process (not one process for the
|
|
54
|
+
whole role run). If the detour fails, continue labor in-session on the seat main
|
|
55
|
+
road and still submit via the existing typed path.
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
# kimi engine method material
|
|
2
|
+
|
|
3
|
+
This file is packaged method material for the optional `kimi` labor engine
|
|
4
|
+
(Kimi Code CLI on the host). When a role run selects this engine, read these
|
|
5
|
+
bytes and follow the local CLI's actual interface for the labor detour. Return
|
|
6
|
+
the labor result to the same role session so typed submission stays on the
|
|
7
|
+
existing in-session path.
|
|
8
|
+
|
|
9
|
+
Material is data for the model, not a code contract. Do not invent package flags.
|
|
10
|
+
|
|
11
|
+
## Invocation examples (local Kimi Code CLI)
|
|
12
|
+
|
|
13
|
+
The machine entrypoint on this host is installed at `~/.kimi-code/bin/kimi`
|
|
14
|
+
(put that directory on PATH, or pass the absolute path as argv[0]). Run from
|
|
15
|
+
the role project root.
|
|
16
|
+
|
|
17
|
+
Non-interactive labor uses `-p` / `--prompt` alone. On this host (kimi 0.36.1),
|
|
18
|
+
`-p` cannot be combined with `--yolo` or `--auto` — both are rejected at parse
|
|
19
|
+
time with `Cannot combine --prompt with --yolo.` / `... --auto.`. Do not add
|
|
20
|
+
those flags to prompt-mode argv:
|
|
21
|
+
|
|
22
|
+
```bash
|
|
23
|
+
kimi -p "YOUR_LABOR_PROMPT"
|
|
24
|
+
```
|
|
25
|
+
|
|
26
|
+
Pin a model alias configured in the host `config.toml` when the seat needs a
|
|
27
|
+
known Kimi model id (example alias shape measured: `kimi-code/k3-256k`):
|
|
28
|
+
|
|
29
|
+
```bash
|
|
30
|
+
kimi -m <model-alias> -p "YOUR_LABOR_PROMPT"
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
Use `--output-format stream-json` (choices measured on this host: `text`,
|
|
34
|
+
`stream-json`; default is `text`) so the package idle clock can see subprocess
|
|
35
|
+
activity while the engine works. Take the labor body from
|
|
36
|
+
`{"role":"assistant","content":...}` rows, not from `role:meta` rows:
|
|
37
|
+
|
|
38
|
+
```bash
|
|
39
|
+
kimi -p "YOUR_LABOR_PROMPT" --output-format stream-json
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
Text / default mode when stream events are not needed. Measured on this host
|
|
43
|
+
with separate fd redirects (`1>` / `2>`): stdout is the labor answer body;
|
|
44
|
+
stderr carries the version line, thinking bullets, and the trailing
|
|
45
|
+
`To resume this session:` hint. Collect the labor body from stdout only — do
|
|
46
|
+
not treat resume lines as same-stream noise to strip from stdout (they are not
|
|
47
|
+
on that stream; stripping bullet-shaped lines risks deleting answer content):
|
|
48
|
+
|
|
49
|
+
```bash
|
|
50
|
+
kimi -p "YOUR_LABOR_PROMPT" --output-format text
|
|
51
|
+
```
|
|
52
|
+
|
|
53
|
+
Prefer `kimi --help` on the host over any remembered flag set. Do not wrap this
|
|
54
|
+
engine behind `ak-role` flags.
|
|
55
|
+
|
|
56
|
+
When the package detour tool is available, start exactly one subprocess per
|
|
57
|
+
labor invocation through it with argv assembled from this material and the
|
|
58
|
+
local CLI; return the stdout labor content to the same session for the existing
|
|
59
|
+
typed submission path. One labor turn = one process (not one process for the
|
|
60
|
+
whole role run). If the detour fails, continue labor in-session on the seat main
|
|
61
|
+
road and still submit via the existing typed path.
|
package/src/public-cli/cli.ts
CHANGED
|
@@ -13,7 +13,7 @@ import {
|
|
|
13
13
|
formatModelSpec,
|
|
14
14
|
loadCredentialProviders,
|
|
15
15
|
loadPublicCliConfig,
|
|
16
|
-
|
|
16
|
+
parseModelSpec,
|
|
17
17
|
resolveEffectiveSeat,
|
|
18
18
|
savePublicCliConfig,
|
|
19
19
|
isEngineAxisSeat,
|
|
@@ -418,7 +418,7 @@ function renderHelp(): string {
|
|
|
418
418
|
lines.push(
|
|
419
419
|
"",
|
|
420
420
|
"Role options: ak-role help <command>",
|
|
421
|
-
"Persistent config: ak-role config set <seat> <provider/model:thinking>",
|
|
421
|
+
"Persistent config: ak-role config set <seat> <provider/model[:thinking]>",
|
|
422
422
|
"Persistent engine (judge|reviewer): ak-role config set-engine <seat> <name> | unset-engine <seat>",
|
|
423
423
|
"Effective seats: ak-role roles",
|
|
424
424
|
);
|
|
@@ -507,7 +507,7 @@ async function runConfigCommand(
|
|
|
507
507
|
if (args[0] === "set") {
|
|
508
508
|
if (args.length < 3) {
|
|
509
509
|
throw new CliUsageError(
|
|
510
|
-
"usage: ak-role config set <seat> <provider/model:thinking>",
|
|
510
|
+
"usage: ak-role config set <seat> <provider/model[:thinking]>",
|
|
511
511
|
);
|
|
512
512
|
}
|
|
513
513
|
// Bulk: repeated seat spec pairs after `set`
|
|
@@ -524,7 +524,9 @@ async function runConfigCommand(
|
|
|
524
524
|
if (!isPublicConfigurableSeat(seat)) {
|
|
525
525
|
throw new CliUsageError(`unknown configurable seat: ${seat}`);
|
|
526
526
|
}
|
|
527
|
-
|
|
527
|
+
// #384: persistent seat config shares the invocation model grammar.
|
|
528
|
+
// Bare provider/model stores as-is; :thinking suffix still required only when colon present.
|
|
529
|
+
config = setPersistentSeatConfig(config, seat, parseModelSpec(spec));
|
|
528
530
|
}
|
|
529
531
|
await savePublicCliConfig(config, home);
|
|
530
532
|
io.stdout(renderConfig(config));
|
package/src/public-cli/config.ts
CHANGED
|
@@ -23,7 +23,7 @@ export type CredentialProviders = {
|
|
|
23
23
|
|
|
24
24
|
export type SeatModelConfig = ModelRef;
|
|
25
25
|
|
|
26
|
-
/** Persistent seat row:
|
|
26
|
+
/** Persistent seat row: provider/model[:thinking] + optional engine axis (#356/#384). */
|
|
27
27
|
export type PersistentSeatConfig = SeatModelConfig & {
|
|
28
28
|
engine?: string;
|
|
29
29
|
};
|
|
@@ -123,7 +123,7 @@ export function isEngineAxisSeat(seat: string): seat is "judge" | "reviewer" {
|
|
|
123
123
|
|
|
124
124
|
/**
|
|
125
125
|
* Set or clear persistent engine on Judge or Reviewer (#356 / #378).
|
|
126
|
-
* Engine-only seats are rejected — model
|
|
126
|
+
* Engine-only seats are rejected — provider/model[:thinking] remains required first.
|
|
127
127
|
*/
|
|
128
128
|
export function setPersistentSeatEngine(
|
|
129
129
|
config: PublicCliConfig,
|
|
@@ -136,7 +136,7 @@ export function setPersistentSeatEngine(
|
|
|
136
136
|
const previous = config.seats[seat];
|
|
137
137
|
if (previous === undefined) {
|
|
138
138
|
throw new Error(
|
|
139
|
-
`config seat ${seat} has no persistent model; set provider/model:thinking before engine`,
|
|
139
|
+
`config seat ${seat} has no persistent model; set provider/model[:thinking] before engine`,
|
|
140
140
|
);
|
|
141
141
|
}
|
|
142
142
|
if (engine === undefined) {
|
|
@@ -226,30 +226,12 @@ export function parseModelSpec(
|
|
|
226
226
|
}
|
|
227
227
|
const provider = modelPart.slice(0, slash);
|
|
228
228
|
const model = modelPart.slice(slash + 1);
|
|
229
|
-
// #346: bare provider/model is legal
|
|
230
|
-
// Persistent config set still requires thinking via parsePersistentModelSpec.
|
|
229
|
+
// #346/#384: bare provider/model is legal — do not invent thinking.
|
|
231
230
|
return thinking === undefined
|
|
232
231
|
? { provider, model }
|
|
233
232
|
: { provider, model, thinking };
|
|
234
233
|
}
|
|
235
234
|
|
|
236
|
-
/** Persistent seat config keeps the three-part provider/model:thinking grammar. */
|
|
237
|
-
export function parsePersistentModelSpec(spec: string): SeatModelConfig & {
|
|
238
|
-
thinking: PublicThinkingLevel;
|
|
239
|
-
} {
|
|
240
|
-
const parsed = parseModelSpec(spec);
|
|
241
|
-
if (parsed.thinking === undefined) {
|
|
242
|
-
throw new Error(
|
|
243
|
-
`model specification requires a thinking level (provider/model:thinking), got ${spec}`,
|
|
244
|
-
);
|
|
245
|
-
}
|
|
246
|
-
return {
|
|
247
|
-
provider: parsed.provider,
|
|
248
|
-
model: parsed.model,
|
|
249
|
-
thinking: parsed.thinking,
|
|
250
|
-
};
|
|
251
|
-
}
|
|
252
|
-
|
|
253
235
|
export function formatModelSpec(selection: SeatModelConfig): string {
|
|
254
236
|
const base = `${selection.provider}/${selection.model}`;
|
|
255
237
|
return selection.thinking === undefined ? base : `${base}:${selection.thinking}`;
|
|
@@ -308,16 +290,21 @@ function parseSeatModelConfig(value: unknown, seat: string): PersistentSeatConfi
|
|
|
308
290
|
if (typeof raw.model !== "string" || raw.model.trim() === "") {
|
|
309
291
|
throw new Error(`config seat ${seat} requires model`);
|
|
310
292
|
}
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
|
|
315
|
-
|
|
293
|
+
// #384: thinking is optional on persistent seats; when present it must be typed.
|
|
294
|
+
if (raw.thinking !== undefined) {
|
|
295
|
+
if (
|
|
296
|
+
typeof raw.thinking !== "string" ||
|
|
297
|
+
!THINKING_LEVELS.has(raw.thinking as PublicThinkingLevel)
|
|
298
|
+
) {
|
|
299
|
+
throw new Error(`config seat ${seat} requires a valid thinking level`);
|
|
300
|
+
}
|
|
316
301
|
}
|
|
317
302
|
const parsed: PersistentSeatConfig = {
|
|
318
303
|
provider: raw.provider,
|
|
319
304
|
model: raw.model,
|
|
320
|
-
|
|
305
|
+
...(raw.thinking === undefined
|
|
306
|
+
? {}
|
|
307
|
+
: { thinking: raw.thinking as PublicThinkingLevel }),
|
|
321
308
|
};
|
|
322
309
|
if (raw.engine !== undefined) {
|
|
323
310
|
// Shape only: engine must be a string field. Path-safety syntax is deferred to
|