@intentius/chant-lexicon-fountain 0.106.1 → 0.106.3

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,7 +1,7 @@
1
1
  {
2
2
  "algorithm": "sha256",
3
3
  "artifacts": {
4
- "manifest.json": "a8525549701de716ae91d92c3965e91ab8993ec47b4b30ae9c1e5746a6918bc4",
4
+ "manifest.json": "d991df566d8002caaa016de270498899957eae346f481467997be3bd0e339def",
5
5
  "meta.json": "3301437a2a56eaf1a5cc8f6eabb18a40767f916e09701b2d9bf20aba4066738c",
6
6
  "types/index.d.ts": "cf6b634fe0a8e9e96f1d9d07e3df53838def2683dc93dbe3c7fd971c6d3908ae",
7
7
  "rules/ftn001-no-secret-literals.ts": "a417b194cd7039911cca9a0f14c49b042dfa6b1ee48517f7c2e22b16590a8599",
@@ -23,5 +23,5 @@
23
23
  "skills/chant-fountain-ops.md": "4e72f0a0c7477a9e98f85ea45e49ba69e8a699f9c13ba0f0cf1cb20a88151373",
24
24
  "skills/chant-fountain-locked-sandboxes.md": "7404ece96f2a3bc9105942fd3b6db156a3537db7e34c8cf2faa9ba87f5512567"
25
25
  },
26
- "composite": "ee0015b352b6395456b2c8a5099b69666d65efb9afa333b117390452bdc9081a"
26
+ "composite": "6f4edb83df0d0f55abea6e8fbed09896f4a6a94a73e6f6a81aa21ccb093a916e"
27
27
  }
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "fountain",
3
- "version": "0.106.1",
3
+ "version": "0.106.3",
4
4
  "chantVersion": ">=0.1.0",
5
5
  "namespace": "Fountain",
6
6
  "specVersion": "v0.21.0"
@@ -27,6 +27,14 @@ export interface HostedRunPromptOptions {
27
27
  env?: string;
28
28
  /** `--param name=value`, one flag per entry, in order (#3539). */
29
29
  params?: Record<string, unknown>;
30
+ /**
31
+ * `--work <item>` and `--holder <name>` (#3555): the work item the run is
32
+ * for and who holds its lease. The sandbox's run takes the lease.
33
+ */
34
+ work?: {
35
+ item?: string;
36
+ holder?: string;
37
+ };
30
38
  /** Flags after `--on local`, as `[flag, value]`; each value is quoted as needed. */
31
39
  flags?: Array<[string, string]>;
32
40
  /** Words appended as they are, already spelled for the command line. */
@@ -35,7 +43,8 @@ export interface HostedRunPromptOptions {
35
43
  /**
36
44
  * The prompt a hosted run is posted as: {@link runPrompt}, then `--env <env>`
37
45
  * when the caller named one (#3232), then each `--param` (#3539), then
38
- * `--on local` (#3225), then any further flags.
46
+ * `--work` and `--holder` (#3555), then `--on local` (#3225), then any
47
+ * further flags.
39
48
  *
40
49
  * `--env` carries the environment the caller asked for into the sandbox,
41
50
  * where `chant acp` hands it to the run as `currentOpRun().env`. `--param`
@@ -47,10 +56,10 @@ export interface HostedRunPromptOptions {
47
56
  *
48
57
  * A turn still matches {@link runPrompt} by prefix (`turnRunsOp`), and a
49
58
  * steward's Schedule keeps the bare line. An `--env` value that is not one
50
- * plain word is refused by name rather than posted; a `--param` or flag value
51
- * is quoted ({@link quoteArg}).
59
+ * plain word is refused by name rather than posted, as is a `--work` or
60
+ * `--holder` value the sandbox's parser would not read as a value (empty, or
61
+ * starting with `-`); a `--param`, `--work`, `--holder` or flag value is
62
+ * quoted ({@link quoteArg}).
52
63
  */
53
64
  export declare function hostedRunPrompt(op: string, opts?: HostedRunPromptOptions): string;
54
- /** The `--env` a posted prompt carries, or undefined. */
55
- export declare function envOfPrompt(prompt: string | undefined): string | undefined;
56
65
  //# sourceMappingURL=run-prompt.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"run-prompt.d.ts","sourceRoot":"","sources":["../../src/op/run-prompt.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH;;;GAGG;AACH,wBAAgB,SAAS,CAAC,EAAE,EAAE,MAAM,GAAG,MAAM,CAE5C;AAeD;;;;;GAKG;AACH,wBAAgB,QAAQ,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAG9C;AAED,4EAA4E;AAC5E,MAAM,WAAW,sBAAsB;IACrC,4DAA4D;IAC5D,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,kEAAkE;IAClE,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IACjC,oFAAoF;IACpF,KAAK,CAAC,EAAE,KAAK,CAAC,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAAC;IAChC,wEAAwE;IACxE,KAAK,CAAC,EAAE,MAAM,EAAE,CAAC;CAClB;AAED;;;;;;;;;;;;;;;;;GAiBG;AACH,wBAAgB,eAAe,CAAC,EAAE,EAAE,MAAM,EAAE,IAAI,GAAE,sBAA2B,GAAG,MAAM,CAkBrF;AASD,yDAAyD;AACzD,wBAAgB,WAAW,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,GAAG,MAAM,GAAG,SAAS,CAK1E"}
1
+ {"version":3,"file":"run-prompt.d.ts","sourceRoot":"","sources":["../../src/op/run-prompt.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH;;;GAGG;AACH,wBAAgB,SAAS,CAAC,EAAE,EAAE,MAAM,GAAG,MAAM,CAE5C;AAeD;;;;;GAKG;AACH,wBAAgB,QAAQ,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAG9C;AAED,4EAA4E;AAC5E,MAAM,WAAW,sBAAsB;IACrC,4DAA4D;IAC5D,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,kEAAkE;IAClE,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IACjC;;;OAGG;IACH,IAAI,CAAC,EAAE;QAAE,IAAI,CAAC,EAAE,MAAM,CAAC;QAAC,MAAM,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC;IAC1C,oFAAoF;IACpF,KAAK,CAAC,EAAE,KAAK,CAAC,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAAC;IAChC,wEAAwE;IACxE,KAAK,CAAC,EAAE,MAAM,EAAE,CAAC;CAClB;AAED;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,wBAAgB,eAAe,CAAC,EAAE,EAAE,MAAM,EAAE,IAAI,GAAE,sBAA2B,GAAG,MAAM,CA4BrF"}
@@ -3,7 +3,7 @@
3
3
  *
4
4
  * `chant run <op> --on fountain` hands the run to a fountain teammate instead
5
5
  * of executing it here. This module is the client for that: it posts the
6
- * command line `chant run <op> [--env <env>] [--param k=v ...] --on local` ({@link hostedRunPrompt})
6
+ * command line `chant run <op> [--env <env>] [--param k=v ...] [--work <id>] [--holder <name>] --on local` ({@link hostedRunPrompt})
7
7
  * as a prompt on the steward's thread, tails the
8
8
  * conversation's SSE stream, and reports what comes back through the
9
9
  * {@link OpRuntimeProvider} contract core defines in
@@ -63,8 +63,8 @@
63
63
  import { type ChantConfig } from "@intentius/chant/config";
64
64
  import type { OpRunRecord, OpRunState, OpRunStatus, OpRuntimeProvider, StepRecord } from "@intentius/chant/op";
65
65
  import { type FountainHttp } from "./activities/fountain-apply.js";
66
- import { runPrompt, hostedRunPrompt, envOfPrompt, quoteArg } from "./run-prompt.js";
67
- export { runPrompt, hostedRunPrompt, envOfPrompt, quoteArg };
66
+ import { runPrompt, hostedRunPrompt, quoteArg } from "./run-prompt.js";
67
+ export { runPrompt, hostedRunPrompt, quoteArg };
68
68
  /** One server-sent event, already framed. `data` is the raw payload text. */
69
69
  export interface FountainSseEvent {
70
70
  /** The event id, which becomes the next connection's `Last-Event-ID`. */
@@ -209,13 +209,17 @@ export declare function runStateOfTurn(conversationStatus?: string, turnState?:
209
209
  */
210
210
  export declare function createFountainOpRuntime(opts?: FountainOpRuntimeOptions): OpRuntimeProvider;
211
211
  /**
212
- * The `--env` and `--param`s a posted prompt carries, read with the same
213
- * quote-aware split `chant acp` uses. A prompt that does not split (an
214
- * unterminated quote) carries neither.
212
+ * The `--env`, `--param`s, `--work` and `--holder` a posted prompt carries,
213
+ * read with the same quote-aware split `chant acp` uses. A prompt that does
214
+ * not split (an unterminated quote) carries none of them.
215
215
  */
216
216
  export declare function flagsOfPrompt(prompt: string | undefined): {
217
217
  env?: string;
218
218
  params?: Record<string, string>;
219
+ work?: {
220
+ item?: string;
221
+ holder?: string;
222
+ };
219
223
  };
220
224
  interface TailOptions {
221
225
  sse: FountainSse;
@@ -1 +1 @@
1
- {"version":3,"file":"runtime.d.ts","sourceRoot":"","sources":["../../src/op/runtime.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"runtime.d.ts","sourceRoot":"","sources":["../../src/op/runtime.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@intentius/chant-lexicon-fountain",
3
- "version": "0.106.1",
3
+ "version": "0.106.3",
4
4
  "type": "module",
5
5
  "description": "Fountain lexicon for chant — sandboxed agent environments, vaults, and agents as typed estate",
6
6
  "license": "Apache-2.0",
@@ -50,7 +50,7 @@
50
50
  "bundle": "tsx src/package-cli.ts"
51
51
  },
52
52
  "peerDependencies": {
53
- "@intentius/chant": "^0.106.1",
53
+ "@intentius/chant": "^0.106.3",
54
54
  "typescript": "^5.9.3",
55
55
  "zod": "^4.3.6"
56
56
  },
@@ -48,6 +48,11 @@ export interface HostedRunPromptOptions {
48
48
  env?: string;
49
49
  /** `--param name=value`, one flag per entry, in order (#3539). */
50
50
  params?: Record<string, unknown>;
51
+ /**
52
+ * `--work <item>` and `--holder <name>` (#3555): the work item the run is
53
+ * for and who holds its lease. The sandbox's run takes the lease.
54
+ */
55
+ work?: { item?: string; holder?: string };
51
56
  /** Flags after `--on local`, as `[flag, value]`; each value is quoted as needed. */
52
57
  flags?: Array<[string, string]>;
53
58
  /** Words appended as they are, already spelled for the command line. */
@@ -57,7 +62,8 @@ export interface HostedRunPromptOptions {
57
62
  /**
58
63
  * The prompt a hosted run is posted as: {@link runPrompt}, then `--env <env>`
59
64
  * when the caller named one (#3232), then each `--param` (#3539), then
60
- * `--on local` (#3225), then any further flags.
65
+ * `--work` and `--holder` (#3555), then `--on local` (#3225), then any
66
+ * further flags.
61
67
  *
62
68
  * `--env` carries the environment the caller asked for into the sandbox,
63
69
  * where `chant acp` hands it to the run as `currentOpRun().env`. `--param`
@@ -69,8 +75,10 @@ export interface HostedRunPromptOptions {
69
75
  *
70
76
  * A turn still matches {@link runPrompt} by prefix (`turnRunsOp`), and a
71
77
  * steward's Schedule keeps the bare line. An `--env` value that is not one
72
- * plain word is refused by name rather than posted; a `--param` or flag value
73
- * is quoted ({@link quoteArg}).
78
+ * plain word is refused by name rather than posted, as is a `--work` or
79
+ * `--holder` value the sandbox's parser would not read as a value (empty, or
80
+ * starting with `-`); a `--param`, `--work`, `--holder` or flag value is
81
+ * quoted ({@link quoteArg}).
74
82
  */
75
83
  export function hostedRunPrompt(op: string, opts: HostedRunPromptOptions = {}): string {
76
84
  const parts = [runPrompt(op)];
@@ -86,6 +94,16 @@ export function hostedRunPrompt(op: string, opts: HostedRunPromptOptions = {}):
86
94
  for (const [name, value] of Object.entries(opts.params ?? {})) {
87
95
  parts.push(`--param ${quoteArg(`${name}=${paramText(value)}`)}`);
88
96
  }
97
+ for (const [flag, value] of [["--work", opts.work?.item], ["--holder", opts.work?.holder]] as const) {
98
+ if (value === undefined) continue;
99
+ if (value === "" || value.startsWith("-")) {
100
+ throw new Error(
101
+ `fountain runtime: ${flag} "${value}" cannot be posted to the steward: chant reads a value that is empty ` +
102
+ `or starts with "-" as a missing one`,
103
+ );
104
+ }
105
+ parts.push(`${flag} ${quoteArg(value)}`);
106
+ }
89
107
  parts.push("--on local");
90
108
  for (const [flag, value] of opts.flags ?? []) parts.push(`${flag} ${quoteArg(value)}`);
91
109
  for (const part of opts.extra ?? []) parts.push(part);
@@ -98,11 +116,3 @@ function paramText(value: unknown): string {
98
116
  if (value === undefined || value === null) return "";
99
117
  return typeof value === "object" ? JSON.stringify(value) : String(value);
100
118
  }
101
-
102
- /** The `--env` a posted prompt carries, or undefined. */
103
- export function envOfPrompt(prompt: string | undefined): string | undefined {
104
- const words = (prompt ?? "").trim().split(/\s+/);
105
- const at = words.indexOf("--env");
106
- const env = at >= 0 ? words[at + 1] : undefined;
107
- return env && !env.startsWith("-") ? env : undefined;
108
- }
@@ -197,6 +197,13 @@ describe("quoteArg and flagsOfPrompt (#3539)", () => {
197
197
  });
198
198
  expect(flagsOfPrompt("chant run x --env=prod --param=a=1")).toEqual({ env: "prod", params: { a: "1" } });
199
199
  expect(flagsOfPrompt("chant run x --on local")).toEqual({});
200
+ // #3555: --work and --holder too.
201
+ expect(flagsOfPrompt('chant run x --work ISSUE-7 --holder "box steward" --on local')).toEqual({
202
+ work: { item: "ISSUE-7", holder: "box steward" },
203
+ });
204
+ expect(flagsOfPrompt("chant run x --work=ISSUE-7")).toEqual({ work: { item: "ISSUE-7" } });
205
+ // An env that is quoted is read as one value, where a whitespace split read half of it.
206
+ expect(flagsOfPrompt('chant run x --env "prod east"')).toEqual({ env: "prod east" });
200
207
  expect(flagsOfPrompt('chant run x --env "unterminated')).toEqual({});
201
208
  expect(flagsOfPrompt(undefined)).toEqual({});
202
209
  });
@@ -328,13 +335,49 @@ describe("start", () => {
328
335
  expect(parsed.ok && parsed.command.args.on).toBe("local");
329
336
  });
330
337
 
331
- it("refuses --work by name before posting anything (#3539)", async () => {
338
+ // #3555: `--work` and `--holder` ride on the posted line, so an Op whose
339
+ // work lease leaves the item to the run can run on fountain; the sandbox's
340
+ // parser reads both back.
341
+ it("posts --work and --holder on the command line (#3555)", async () => {
342
+ const { http, calls } = fakeHttp(
343
+ stewardRoutes({
344
+ "POST /api/team/agent-1/messages": { status: 202, json: { data: { conversation_id: "conv-1" } } },
345
+ }),
346
+ );
347
+ const { sse } = fakeSse([
348
+ [
349
+ sseEvent("1", { stream: "stdout", blocks: [{ kind: "text", body: JSON.stringify(RECORD) }] }),
350
+ sseEvent("2", { stream: "stage", stage: "turn", state: "done" }),
351
+ ],
352
+ ]);
353
+ const runtime = createFountainOpRuntime({
354
+ config: CONFIG, endpoint: "https://fountain.example.com", token: "t", http, sse, now: fakeClock(),
355
+ });
356
+ expect(runtime.carriesWork).toBe(true);
357
+
358
+ const handle = await runtime.start(OP, { env: "staging", work: { item: "ISSUE-7", holder: "box steward" } });
359
+ await handle.result();
360
+
361
+ const post = calls.find((c) => c.method === "POST");
362
+ const prompt = (post?.body as { prompt: string }).prompt;
363
+ expect(prompt).toBe('chant run alb-deploy --env staging --work ISSUE-7 --holder "box steward" --on local');
364
+
365
+ const { parseChantCommandLine } = await import("../acp/command-line");
366
+ const parsed = await parseChantCommandLine(prompt);
367
+ expect(parsed.ok && parsed.command.kind === "op-run" && parsed.command.op).toBe("alb-deploy");
368
+ expect(parsed.ok && parsed.command.args.work).toBe("ISSUE-7");
369
+ expect(parsed.ok && parsed.command.args.holder).toBe("box steward");
370
+ expect(parsed.ok && parsed.command.args.on).toBe("local");
371
+ });
372
+
373
+ it("refuses a --work the sandbox would read as missing, by name, before posting anything (#3555)", async () => {
332
374
  const { http, calls } = fakeHttp(stewardRoutes({}));
333
375
  const runtime = createFountainOpRuntime({
334
376
  config: CONFIG, endpoint: "https://fountain.example.com", token: "t", http, now: fakeClock(),
335
377
  });
336
378
 
337
- await expect(runtime.start(OP, { work: { item: "ISSUE-7" } })).rejects.toThrow(/--work and --holder are not posted/);
379
+ await expect(runtime.start(OP, { work: { item: "-7" } })).rejects.toThrow(/--work "-7" cannot be posted/);
380
+ await expect(runtime.start(OP, { work: { holder: "" } })).rejects.toThrow(/--holder "" cannot be posted/);
338
381
  expect(calls).toEqual([]);
339
382
  });
340
383
 
@@ -1194,6 +1237,34 @@ describe("resolveGate", () => {
1194
1237
  });
1195
1238
  });
1196
1239
 
1240
+ // #3555: the gated turn's work item and holder ride on the re-run, so the
1241
+ // re-run of an Op that needs a work item is told it again.
1242
+ it("carries the gated turn's --work and --holder onto the re-run prompt", async () => {
1243
+ const { http, calls } = fakeHttp(
1244
+ stewardRoutes({
1245
+ ...routes,
1246
+ "GET /api/conversations/conv-1/turns": {
1247
+ status: 200,
1248
+ json: {
1249
+ data: [{ id: "turn-1", prompt: 'chant run alb-deploy --work ISSUE-7 --holder "box steward" --on local', state: "done" }],
1250
+ },
1251
+ },
1252
+ }),
1253
+ );
1254
+ const runtime = createFountainOpRuntime({
1255
+ config: CONFIG, endpoint: "https://fountain.example.com", token: "t", http, now: fakeClock(),
1256
+ });
1257
+
1258
+ await runtime.resolveGate!("alb-deploy", "release", resolution);
1259
+
1260
+ const post = calls.find((c) => c.path === "/api/conversations/conv-1/prompts");
1261
+ expect(post?.body).toEqual({
1262
+ prompt:
1263
+ 'chant run alb-deploy --work ISSUE-7 --holder "box steward" --on local ' +
1264
+ "--approver alex --url https://github.com/o/r/pull/1",
1265
+ });
1266
+ });
1267
+
1197
1268
  it("reports conversation_busy rather than retrying the prompt", async () => {
1198
1269
  const { http, calls } = fakeHttp(
1199
1270
  stewardRoutes({
package/src/op/runtime.ts CHANGED
@@ -3,7 +3,7 @@
3
3
  *
4
4
  * `chant run <op> --on fountain` hands the run to a fountain teammate instead
5
5
  * of executing it here. This module is the client for that: it posts the
6
- * command line `chant run <op> [--env <env>] [--param k=v ...] --on local` ({@link hostedRunPrompt})
6
+ * command line `chant run <op> [--env <env>] [--param k=v ...] [--work <id>] [--holder <name>] --on local` ({@link hostedRunPrompt})
7
7
  * as a prompt on the steward's thread, tails the
8
8
  * conversation's SSE stream, and reports what comes back through the
9
9
  * {@link OpRuntimeProvider} contract core defines in
@@ -73,10 +73,10 @@ import {
73
73
  } from "./activities/fountain-apply";
74
74
  import { resolveAgentId } from "./activities/fountain-run";
75
75
  import { stewardForOp } from "../composites/steward";
76
- import { runPrompt, hostedRunPrompt, envOfPrompt, quoteArg } from "./run-prompt";
76
+ import { runPrompt, hostedRunPrompt, quoteArg } from "./run-prompt";
77
77
  import { tokenize } from "../acp/command-line";
78
78
 
79
- export { runPrompt, hostedRunPrompt, envOfPrompt, quoteArg };
79
+ export { runPrompt, hostedRunPrompt, quoteArg };
80
80
 
81
81
  // ── The SSE seam ──────────────────────────────────────────────────────────
82
82
 
@@ -745,6 +745,10 @@ export function createFountainOpRuntime(opts: FountainOpRuntimeOptions = {}): Op
745
745
 
746
746
  return {
747
747
  name: "fountain",
748
+ // `--work` and `--holder` ride on the posted line (#3555), so an Op whose
749
+ // work lease leaves the item to the run can run here; the sandbox's run
750
+ // takes the lease.
751
+ carriesWork: true,
748
752
 
749
753
  async start(op: OpConfig, startOpts: OpRunStartOptions): Promise<OpRunHandle> {
750
754
  known.set(op.name, op);
@@ -753,12 +757,12 @@ export function createFountainOpRuntime(opts: FountainOpRuntimeOptions = {}): Op
753
757
  selectProfile(startOpts.profile);
754
758
  // Before any request: an `--env` the command line cannot carry is
755
759
  // refused here, by name, rather than dropped (#3232). `--param` rides
756
- // on the line (#3539); `--work` is refused, since the posted line does
757
- // not carry the lease the caller named.
758
- refuseWork(op.name, startOpts.work);
760
+ // on the line (#3539), and so do `--work` and `--holder` (#3555): the
761
+ // run in the sandbox takes the work lease the caller named.
759
762
  const prompt = hostedRunPrompt(op.name, {
760
763
  env: startOpts.env,
761
764
  ...(startOpts.params ? { params: startOpts.params } : {}),
765
+ ...(startOpts.work ? { work: startOpts.work } : {}),
762
766
  });
763
767
  const http = await rest();
764
768
  const steward = await resolveSteward(op, startOpts.params);
@@ -928,15 +932,20 @@ export function createFountainOpRuntime(opts: FountainOpRuntimeOptions = {}): Op
928
932
  // a space stays one value (#3539). The re-run runs in the environment
929
933
  // the approver named (`chant run approve ... --env`, #3539), or else the
930
934
  // one the gated run did: the `--env` on the op's latest turn (#3232).
931
- // The gated turn's `--param`s ride along too, and `--on local` as on
932
- // every posted run (#3225).
935
+ // The gated turn's `--param`s, `--work` and `--holder` ride along too
936
+ // (#3555), and `--on local` as on every posted run (#3225).
933
937
  const flags: Array<[string, string]> = [];
934
938
  if (resolution.resolvedBy) flags.push(["--approver", resolution.resolvedBy]);
935
939
  if (resolution.url) flags.push(["--url", resolution.url]);
936
940
  const gated = flagsOfPrompt(found?.turns[0]?.prompt);
937
941
  const env = resolveOpts?.env !== undefined && resolveOpts.env !== "" ? resolveOpts.env : gated.env;
938
942
  const { status, json } = await http("POST", `/api/conversations/${conversationId}/prompts`, {
939
- prompt: hostedRunPrompt(op, { env, ...(gated.params ? { params: gated.params } : {}), flags }),
943
+ prompt: hostedRunPrompt(op, {
944
+ env,
945
+ ...(gated.params ? { params: gated.params } : {}),
946
+ ...(gated.work ? { work: gated.work } : {}),
947
+ flags,
948
+ }),
940
949
  });
941
950
 
942
951
  if (status === 400 && errorCode(json) === "conversation_busy") {
@@ -953,25 +962,15 @@ export function createFountainOpRuntime(opts: FountainOpRuntimeOptions = {}): Op
953
962
  }
954
963
 
955
964
  /**
956
- * Refuse `--work`/`--holder` on a hosted run, by name (#3539). The posted
957
- * line does not carry them, so the run in the sandbox would hold no lease, or
958
- * one the caller did not name. Core's `chant run` refuses them before any
959
- * runtime is reached; this covers a caller that holds the provider directly.
960
- */
961
- function refuseWork(op: string, work: OpRunStartOptions["work"]): void {
962
- if (!work || (work.item === undefined && work.holder === undefined)) return;
963
- throw new Error(
964
- `fountain runtime: --work and --holder are not posted to the steward, so the hosted run of "${op}" ` +
965
- `would not hold the lease named here. Run it with --on local to hold the lease in this process.`,
966
- );
967
- }
968
-
969
- /**
970
- * The `--env` and `--param`s a posted prompt carries, read with the same
971
- * quote-aware split `chant acp` uses. A prompt that does not split (an
972
- * unterminated quote) carries neither.
965
+ * The `--env`, `--param`s, `--work` and `--holder` a posted prompt carries,
966
+ * read with the same quote-aware split `chant acp` uses. A prompt that does
967
+ * not split (an unterminated quote) carries none of them.
973
968
  */
974
- export function flagsOfPrompt(prompt: string | undefined): { env?: string; params?: Record<string, string> } {
969
+ export function flagsOfPrompt(prompt: string | undefined): {
970
+ env?: string;
971
+ params?: Record<string, string>;
972
+ work?: { item?: string; holder?: string };
973
+ } {
975
974
  let words: string[];
976
975
  try {
977
976
  words = tokenize(prompt ?? "");
@@ -979,6 +978,7 @@ export function flagsOfPrompt(prompt: string | undefined): { env?: string; param
979
978
  return {};
980
979
  }
981
980
  let env: string | undefined;
981
+ const work: { item?: string; holder?: string } = {};
982
982
  const params: Record<string, string> = {};
983
983
  let any = false;
984
984
  for (let i = 0; i < words.length; i++) {
@@ -989,20 +989,26 @@ export function flagsOfPrompt(prompt: string | undefined): { env?: string; param
989
989
  if (eq > 0) {
990
990
  flag = word.slice(0, eq);
991
991
  value = word.slice(eq + 1);
992
- } else if (word === "--env" || word === "--param") {
992
+ } else if (word === "--env" || word === "--param" || word === "--work" || word === "--holder") {
993
993
  value = words[i + 1];
994
994
  if (value === undefined || value.startsWith("-")) continue;
995
995
  i++;
996
996
  }
997
997
  if (value === undefined) continue;
998
998
  if (flag === "--env") env = value;
999
+ else if (flag === "--work") work.item = value;
1000
+ else if (flag === "--holder") work.holder = value;
999
1001
  else if (flag === "--param") {
1000
1002
  const at = value.indexOf("=");
1001
1003
  params[at === -1 ? value : value.slice(0, at)] = at === -1 ? "" : value.slice(at + 1);
1002
1004
  any = true;
1003
1005
  }
1004
1006
  }
1005
- return { ...(env ? { env } : {}), ...(any ? { params } : {}) };
1007
+ return {
1008
+ ...(env ? { env } : {}),
1009
+ ...(any ? { params } : {}),
1010
+ ...(work.item !== undefined || work.holder !== undefined ? { work } : {}),
1011
+ };
1006
1012
  }
1007
1013
 
1008
1014
  /** Was `--durable-requests` asked for on this invocation? */