@bridge4dev/runner 0.31.0 → 0.34.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -38,26 +38,52 @@ export declare const SessionDescriptorSchema: z.ZodObject<{
38
38
  * scratch anyway; the bounds here only keep nonsense off the wire.
39
39
  */
40
40
  agentPromptPath: z.ZodCatch<z.ZodOptional<z.ZodNullable<z.ZodString>>>;
41
+ /**
42
+ * Session 18: the project's git policy for agents.
43
+ *
44
+ * `.optional().catch(undefined)` for the QA-100 MAJOR-1 reason above — this
45
+ * rides inside `hello_ack` with every session on the server, so a malformed
46
+ * value must cost its own session's policy at most, never the frame.
47
+ *
48
+ * «Costs its own session's policy» is safe here BECAUSE of the polarity in
49
+ * `policy.ts`: `agentPushBan` resolves `undefined` to «refuse», so a value
50
+ * this schema drops leaves the session strictly more restricted, never less.
51
+ * That property is the whole reason `.catch(undefined)` is acceptable on a
52
+ * security field, and it is why the resolution lives in exactly one
53
+ * function rather than at each point of use.
54
+ */
55
+ agentPushBan: z.ZodCatch<z.ZodOptional<z.ZodBoolean>>;
56
+ agentProtectedBranches: z.ZodCatch<z.ZodOptional<z.ZodArray<z.ZodString, "many">>>;
57
+ agentAllowForcePush: z.ZodCatch<z.ZodOptional<z.ZodBoolean>>;
58
+ agentAllowDestructiveGit: z.ZodCatch<z.ZodOptional<z.ZodBoolean>>;
41
59
  budgetUsd: z.ZodNullable<z.ZodNumber>;
42
60
  budgetMinutes: z.ZodNullable<z.ZodNumber>;
43
61
  }, "strip", z.ZodTypeAny, {
62
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
44
63
  id: string;
45
64
  path: string;
46
65
  projectId: string;
47
- trustMode: "STRICT" | "NORMAL" | "AUTO";
48
66
  budgetUsd: number | null;
49
67
  budgetMinutes: number | null;
50
68
  agentAutoCommit?: boolean | undefined;
69
+ agentPushBan?: boolean | undefined;
51
70
  agentPromptPath?: string | null | undefined;
71
+ agentProtectedBranches?: string[] | undefined;
72
+ agentAllowForcePush?: boolean | undefined;
73
+ agentAllowDestructiveGit?: boolean | undefined;
52
74
  }, {
75
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
53
76
  id: string;
54
77
  path: string;
55
78
  projectId: string;
56
- trustMode: "STRICT" | "NORMAL" | "AUTO";
57
79
  budgetUsd: number | null;
58
80
  budgetMinutes: number | null;
59
81
  agentAutoCommit?: boolean | undefined;
82
+ agentPushBan?: unknown;
60
83
  agentPromptPath?: unknown;
84
+ agentProtectedBranches?: unknown;
85
+ agentAllowForcePush?: unknown;
86
+ agentAllowDestructiveGit?: unknown;
61
87
  }>;
62
88
  /**
63
89
  * «Run this one without the project's agent prompt.» Absent means no — both
@@ -153,14 +179,18 @@ export declare const SessionDescriptorSchema: z.ZodObject<{
153
179
  activeMsBase: number;
154
180
  extraBudgetMinutes: number | null;
155
181
  workspace: {
182
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
156
183
  id: string;
157
184
  path: string;
158
185
  projectId: string;
159
- trustMode: "STRICT" | "NORMAL" | "AUTO";
160
186
  budgetUsd: number | null;
161
187
  budgetMinutes: number | null;
162
188
  agentAutoCommit?: boolean | undefined;
189
+ agentPushBan?: boolean | undefined;
163
190
  agentPromptPath?: string | null | undefined;
191
+ agentProtectedBranches?: string[] | undefined;
192
+ agentAllowForcePush?: boolean | undefined;
193
+ agentAllowDestructiveGit?: boolean | undefined;
164
194
  };
165
195
  tickets: {
166
196
  number: number;
@@ -188,14 +218,18 @@ export declare const SessionDescriptorSchema: z.ZodObject<{
188
218
  prompt: string;
189
219
  providerSessionId: string | null;
190
220
  workspace: {
221
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
191
222
  id: string;
192
223
  path: string;
193
224
  projectId: string;
194
- trustMode: "STRICT" | "NORMAL" | "AUTO";
195
225
  budgetUsd: number | null;
196
226
  budgetMinutes: number | null;
197
227
  agentAutoCommit?: boolean | undefined;
228
+ agentPushBan?: unknown;
198
229
  agentPromptPath?: unknown;
230
+ agentProtectedBranches?: unknown;
231
+ agentAllowForcePush?: unknown;
232
+ agentAllowDestructiveGit?: unknown;
199
233
  };
200
234
  tickets: {
201
235
  number: number;
@@ -264,26 +298,52 @@ export declare const GatewayFrameSchema: z.ZodDiscriminatedUnion<"type", [z.ZodO
264
298
  * scratch anyway; the bounds here only keep nonsense off the wire.
265
299
  */
266
300
  agentPromptPath: z.ZodCatch<z.ZodOptional<z.ZodNullable<z.ZodString>>>;
301
+ /**
302
+ * Session 18: the project's git policy for agents.
303
+ *
304
+ * `.optional().catch(undefined)` for the QA-100 MAJOR-1 reason above — this
305
+ * rides inside `hello_ack` with every session on the server, so a malformed
306
+ * value must cost its own session's policy at most, never the frame.
307
+ *
308
+ * «Costs its own session's policy» is safe here BECAUSE of the polarity in
309
+ * `policy.ts`: `agentPushBan` resolves `undefined` to «refuse», so a value
310
+ * this schema drops leaves the session strictly more restricted, never less.
311
+ * That property is the whole reason `.catch(undefined)` is acceptable on a
312
+ * security field, and it is why the resolution lives in exactly one
313
+ * function rather than at each point of use.
314
+ */
315
+ agentPushBan: z.ZodCatch<z.ZodOptional<z.ZodBoolean>>;
316
+ agentProtectedBranches: z.ZodCatch<z.ZodOptional<z.ZodArray<z.ZodString, "many">>>;
317
+ agentAllowForcePush: z.ZodCatch<z.ZodOptional<z.ZodBoolean>>;
318
+ agentAllowDestructiveGit: z.ZodCatch<z.ZodOptional<z.ZodBoolean>>;
267
319
  budgetUsd: z.ZodNullable<z.ZodNumber>;
268
320
  budgetMinutes: z.ZodNullable<z.ZodNumber>;
269
321
  }, "strip", z.ZodTypeAny, {
322
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
270
323
  id: string;
271
324
  path: string;
272
325
  projectId: string;
273
- trustMode: "STRICT" | "NORMAL" | "AUTO";
274
326
  budgetUsd: number | null;
275
327
  budgetMinutes: number | null;
276
328
  agentAutoCommit?: boolean | undefined;
329
+ agentPushBan?: boolean | undefined;
277
330
  agentPromptPath?: string | null | undefined;
331
+ agentProtectedBranches?: string[] | undefined;
332
+ agentAllowForcePush?: boolean | undefined;
333
+ agentAllowDestructiveGit?: boolean | undefined;
278
334
  }, {
335
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
279
336
  id: string;
280
337
  path: string;
281
338
  projectId: string;
282
- trustMode: "STRICT" | "NORMAL" | "AUTO";
283
339
  budgetUsd: number | null;
284
340
  budgetMinutes: number | null;
285
341
  agentAutoCommit?: boolean | undefined;
342
+ agentPushBan?: unknown;
286
343
  agentPromptPath?: unknown;
344
+ agentProtectedBranches?: unknown;
345
+ agentAllowForcePush?: unknown;
346
+ agentAllowDestructiveGit?: unknown;
287
347
  }>;
288
348
  /**
289
349
  * «Run this one without the project's agent prompt.» Absent means no — both
@@ -379,14 +439,18 @@ export declare const GatewayFrameSchema: z.ZodDiscriminatedUnion<"type", [z.ZodO
379
439
  activeMsBase: number;
380
440
  extraBudgetMinutes: number | null;
381
441
  workspace: {
442
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
382
443
  id: string;
383
444
  path: string;
384
445
  projectId: string;
385
- trustMode: "STRICT" | "NORMAL" | "AUTO";
386
446
  budgetUsd: number | null;
387
447
  budgetMinutes: number | null;
388
448
  agentAutoCommit?: boolean | undefined;
449
+ agentPushBan?: boolean | undefined;
389
450
  agentPromptPath?: string | null | undefined;
451
+ agentProtectedBranches?: string[] | undefined;
452
+ agentAllowForcePush?: boolean | undefined;
453
+ agentAllowDestructiveGit?: boolean | undefined;
390
454
  };
391
455
  tickets: {
392
456
  number: number;
@@ -414,14 +478,18 @@ export declare const GatewayFrameSchema: z.ZodDiscriminatedUnion<"type", [z.ZodO
414
478
  prompt: string;
415
479
  providerSessionId: string | null;
416
480
  workspace: {
481
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
417
482
  id: string;
418
483
  path: string;
419
484
  projectId: string;
420
- trustMode: "STRICT" | "NORMAL" | "AUTO";
421
485
  budgetUsd: number | null;
422
486
  budgetMinutes: number | null;
423
487
  agentAutoCommit?: boolean | undefined;
488
+ agentPushBan?: unknown;
424
489
  agentPromptPath?: unknown;
490
+ agentProtectedBranches?: unknown;
491
+ agentAllowForcePush?: unknown;
492
+ agentAllowDestructiveGit?: unknown;
425
493
  };
426
494
  tickets: {
427
495
  number: number;
@@ -465,14 +533,18 @@ export declare const GatewayFrameSchema: z.ZodDiscriminatedUnion<"type", [z.ZodO
465
533
  activeMsBase: number;
466
534
  extraBudgetMinutes: number | null;
467
535
  workspace: {
536
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
468
537
  id: string;
469
538
  path: string;
470
539
  projectId: string;
471
- trustMode: "STRICT" | "NORMAL" | "AUTO";
472
540
  budgetUsd: number | null;
473
541
  budgetMinutes: number | null;
474
542
  agentAutoCommit?: boolean | undefined;
543
+ agentPushBan?: boolean | undefined;
475
544
  agentPromptPath?: string | null | undefined;
545
+ agentProtectedBranches?: string[] | undefined;
546
+ agentAllowForcePush?: boolean | undefined;
547
+ agentAllowDestructiveGit?: boolean | undefined;
476
548
  };
477
549
  tickets: {
478
550
  number: number;
@@ -506,14 +578,18 @@ export declare const GatewayFrameSchema: z.ZodDiscriminatedUnion<"type", [z.ZodO
506
578
  prompt: string;
507
579
  providerSessionId: string | null;
508
580
  workspace: {
581
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
509
582
  id: string;
510
583
  path: string;
511
584
  projectId: string;
512
- trustMode: "STRICT" | "NORMAL" | "AUTO";
513
585
  budgetUsd: number | null;
514
586
  budgetMinutes: number | null;
515
587
  agentAutoCommit?: boolean | undefined;
588
+ agentPushBan?: unknown;
516
589
  agentPromptPath?: unknown;
590
+ agentProtectedBranches?: unknown;
591
+ agentAllowForcePush?: unknown;
592
+ agentAllowDestructiveGit?: unknown;
517
593
  };
518
594
  tickets: {
519
595
  number: number;
@@ -606,26 +682,52 @@ export declare const GatewayFrameSchema: z.ZodDiscriminatedUnion<"type", [z.ZodO
606
682
  * scratch anyway; the bounds here only keep nonsense off the wire.
607
683
  */
608
684
  agentPromptPath: z.ZodCatch<z.ZodOptional<z.ZodNullable<z.ZodString>>>;
685
+ /**
686
+ * Session 18: the project's git policy for agents.
687
+ *
688
+ * `.optional().catch(undefined)` for the QA-100 MAJOR-1 reason above — this
689
+ * rides inside `hello_ack` with every session on the server, so a malformed
690
+ * value must cost its own session's policy at most, never the frame.
691
+ *
692
+ * «Costs its own session's policy» is safe here BECAUSE of the polarity in
693
+ * `policy.ts`: `agentPushBan` resolves `undefined` to «refuse», so a value
694
+ * this schema drops leaves the session strictly more restricted, never less.
695
+ * That property is the whole reason `.catch(undefined)` is acceptable on a
696
+ * security field, and it is why the resolution lives in exactly one
697
+ * function rather than at each point of use.
698
+ */
699
+ agentPushBan: z.ZodCatch<z.ZodOptional<z.ZodBoolean>>;
700
+ agentProtectedBranches: z.ZodCatch<z.ZodOptional<z.ZodArray<z.ZodString, "many">>>;
701
+ agentAllowForcePush: z.ZodCatch<z.ZodOptional<z.ZodBoolean>>;
702
+ agentAllowDestructiveGit: z.ZodCatch<z.ZodOptional<z.ZodBoolean>>;
609
703
  budgetUsd: z.ZodNullable<z.ZodNumber>;
610
704
  budgetMinutes: z.ZodNullable<z.ZodNumber>;
611
705
  }, "strip", z.ZodTypeAny, {
706
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
612
707
  id: string;
613
708
  path: string;
614
709
  projectId: string;
615
- trustMode: "STRICT" | "NORMAL" | "AUTO";
616
710
  budgetUsd: number | null;
617
711
  budgetMinutes: number | null;
618
712
  agentAutoCommit?: boolean | undefined;
713
+ agentPushBan?: boolean | undefined;
619
714
  agentPromptPath?: string | null | undefined;
715
+ agentProtectedBranches?: string[] | undefined;
716
+ agentAllowForcePush?: boolean | undefined;
717
+ agentAllowDestructiveGit?: boolean | undefined;
620
718
  }, {
719
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
621
720
  id: string;
622
721
  path: string;
623
722
  projectId: string;
624
- trustMode: "STRICT" | "NORMAL" | "AUTO";
625
723
  budgetUsd: number | null;
626
724
  budgetMinutes: number | null;
627
725
  agentAutoCommit?: boolean | undefined;
726
+ agentPushBan?: unknown;
628
727
  agentPromptPath?: unknown;
728
+ agentProtectedBranches?: unknown;
729
+ agentAllowForcePush?: unknown;
730
+ agentAllowDestructiveGit?: unknown;
629
731
  }>;
630
732
  /**
631
733
  * «Run this one without the project's agent prompt.» Absent means no — both
@@ -721,14 +823,18 @@ export declare const GatewayFrameSchema: z.ZodDiscriminatedUnion<"type", [z.ZodO
721
823
  activeMsBase: number;
722
824
  extraBudgetMinutes: number | null;
723
825
  workspace: {
826
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
724
827
  id: string;
725
828
  path: string;
726
829
  projectId: string;
727
- trustMode: "STRICT" | "NORMAL" | "AUTO";
728
830
  budgetUsd: number | null;
729
831
  budgetMinutes: number | null;
730
832
  agentAutoCommit?: boolean | undefined;
833
+ agentPushBan?: boolean | undefined;
731
834
  agentPromptPath?: string | null | undefined;
835
+ agentProtectedBranches?: string[] | undefined;
836
+ agentAllowForcePush?: boolean | undefined;
837
+ agentAllowDestructiveGit?: boolean | undefined;
732
838
  };
733
839
  tickets: {
734
840
  number: number;
@@ -756,14 +862,18 @@ export declare const GatewayFrameSchema: z.ZodDiscriminatedUnion<"type", [z.ZodO
756
862
  prompt: string;
757
863
  providerSessionId: string | null;
758
864
  workspace: {
865
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
759
866
  id: string;
760
867
  path: string;
761
868
  projectId: string;
762
- trustMode: "STRICT" | "NORMAL" | "AUTO";
763
869
  budgetUsd: number | null;
764
870
  budgetMinutes: number | null;
765
871
  agentAutoCommit?: boolean | undefined;
872
+ agentPushBan?: unknown;
766
873
  agentPromptPath?: unknown;
874
+ agentProtectedBranches?: unknown;
875
+ agentAllowForcePush?: unknown;
876
+ agentAllowDestructiveGit?: unknown;
767
877
  };
768
878
  tickets: {
769
879
  number: number;
@@ -805,14 +915,18 @@ export declare const GatewayFrameSchema: z.ZodDiscriminatedUnion<"type", [z.ZodO
805
915
  activeMsBase: number;
806
916
  extraBudgetMinutes: number | null;
807
917
  workspace: {
918
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
808
919
  id: string;
809
920
  path: string;
810
921
  projectId: string;
811
- trustMode: "STRICT" | "NORMAL" | "AUTO";
812
922
  budgetUsd: number | null;
813
923
  budgetMinutes: number | null;
814
924
  agentAutoCommit?: boolean | undefined;
925
+ agentPushBan?: boolean | undefined;
815
926
  agentPromptPath?: string | null | undefined;
927
+ agentProtectedBranches?: string[] | undefined;
928
+ agentAllowForcePush?: boolean | undefined;
929
+ agentAllowDestructiveGit?: boolean | undefined;
816
930
  };
817
931
  tickets: {
818
932
  number: number;
@@ -843,14 +957,18 @@ export declare const GatewayFrameSchema: z.ZodDiscriminatedUnion<"type", [z.ZodO
843
957
  prompt: string;
844
958
  providerSessionId: string | null;
845
959
  workspace: {
960
+ trustMode: "STRICT" | "NORMAL" | "AUTO";
846
961
  id: string;
847
962
  path: string;
848
963
  projectId: string;
849
- trustMode: "STRICT" | "NORMAL" | "AUTO";
850
964
  budgetUsd: number | null;
851
965
  budgetMinutes: number | null;
852
966
  agentAutoCommit?: boolean | undefined;
967
+ agentPushBan?: unknown;
853
968
  agentPromptPath?: unknown;
969
+ agentProtectedBranches?: unknown;
970
+ agentAllowForcePush?: unknown;
971
+ agentAllowDestructiveGit?: unknown;
854
972
  };
855
973
  tickets: {
856
974
  number: number;
@@ -1005,16 +1123,28 @@ export declare const GatewayFrameSchema: z.ZodDiscriminatedUnion<"type", [z.ZodO
1005
1123
  workspaceId: z.ZodString;
1006
1124
  trustMode: z.ZodOptional<z.ZodEnum<["STRICT", "NORMAL", "AUTO"]>>;
1007
1125
  agentAutoCommit: z.ZodOptional<z.ZodBoolean>;
1126
+ agentPushBan: z.ZodOptional<z.ZodBoolean>;
1127
+ agentProtectedBranches: z.ZodOptional<z.ZodArray<z.ZodString, "many">>;
1128
+ agentAllowForcePush: z.ZodOptional<z.ZodBoolean>;
1129
+ agentAllowDestructiveGit: z.ZodOptional<z.ZodBoolean>;
1008
1130
  }, "strip", z.ZodTypeAny, {
1009
1131
  type: "workspace_settings";
1010
1132
  workspaceId: string;
1011
- agentAutoCommit?: boolean | undefined;
1012
1133
  trustMode?: "STRICT" | "NORMAL" | "AUTO" | undefined;
1134
+ agentAutoCommit?: boolean | undefined;
1135
+ agentPushBan?: boolean | undefined;
1136
+ agentProtectedBranches?: string[] | undefined;
1137
+ agentAllowForcePush?: boolean | undefined;
1138
+ agentAllowDestructiveGit?: boolean | undefined;
1013
1139
  }, {
1014
1140
  type: "workspace_settings";
1015
1141
  workspaceId: string;
1016
- agentAutoCommit?: boolean | undefined;
1017
1142
  trustMode?: "STRICT" | "NORMAL" | "AUTO" | undefined;
1143
+ agentAutoCommit?: boolean | undefined;
1144
+ agentPushBan?: boolean | undefined;
1145
+ agentProtectedBranches?: string[] | undefined;
1146
+ agentAllowForcePush?: boolean | undefined;
1147
+ agentAllowDestructiveGit?: boolean | undefined;
1018
1148
  }>, z.ZodObject<{
1019
1149
  type: z.ZodLiteral<"session_settings">;
1020
1150
  sessionId: z.ZodString;
package/dist/protocol.js CHANGED
@@ -64,6 +64,31 @@ export const SessionDescriptorSchema = z.object({
64
64
  * scratch anyway; the bounds here only keep nonsense off the wire.
65
65
  */
66
66
  agentPromptPath: z.string().max(300).nullable().optional().catch(undefined),
67
+ /**
68
+ * Session 18: the project's git policy for agents.
69
+ *
70
+ * `.optional().catch(undefined)` for the QA-100 MAJOR-1 reason above — this
71
+ * rides inside `hello_ack` with every session on the server, so a malformed
72
+ * value must cost its own session's policy at most, never the frame.
73
+ *
74
+ * «Costs its own session's policy» is safe here BECAUSE of the polarity in
75
+ * `policy.ts`: `agentPushBan` resolves `undefined` to «refuse», so a value
76
+ * this schema drops leaves the session strictly more restricted, never less.
77
+ * That property is the whole reason `.catch(undefined)` is acceptable on a
78
+ * security field, and it is why the resolution lives in exactly one
79
+ * function rather than at each point of use.
80
+ */
81
+ agentPushBan: z.boolean().optional().catch(undefined),
82
+ agentProtectedBranches: z
83
+ .array(z
84
+ .string()
85
+ .max(200)
86
+ .regex(/^[A-Za-z0-9][A-Za-z0-9._\-/]*$/))
87
+ .max(20)
88
+ .optional()
89
+ .catch(undefined),
90
+ agentAllowForcePush: z.boolean().optional().catch(undefined),
91
+ agentAllowDestructiveGit: z.boolean().optional().catch(undefined),
67
92
  budgetUsd: z.number().nullable(),
68
93
  budgetMinutes: z.number().nullable(),
69
94
  }),
@@ -230,6 +255,19 @@ export const GatewayFrameSchema = z.discriminatedUnion('type', [
230
255
  workspaceId: z.string().min(1).max(64),
231
256
  trustMode: z.enum(['STRICT', 'NORMAL', 'AUTO']).optional(),
232
257
  agentAutoCommit: z.boolean().optional(),
258
+ // Session 18 — the git policy, for the same reason: read on every tool
259
+ // call, so switching «Принудительно запретить push» back on must not
260
+ // require stopping the agent first.
261
+ agentPushBan: z.boolean().optional(),
262
+ agentProtectedBranches: z
263
+ .array(z
264
+ .string()
265
+ .max(200)
266
+ .regex(/^[A-Za-z0-9][A-Za-z0-9._\-/]*$/))
267
+ .max(20)
268
+ .optional(),
269
+ agentAllowForcePush: z.boolean().optional(),
270
+ agentAllowDestructiveGit: z.boolean().optional(),
233
271
  }),
234
272
  z.object({
235
273
  type: z.literal('session_settings'),
@@ -246,6 +246,30 @@ export declare class Supervisor {
246
246
  * rewound (ticket #126).
247
247
  */
248
248
  private park;
249
+ /**
250
+ * The agent is producing output while this runner still says a human is
251
+ * expected — put `lastReported` back to RUNNING (ticket #185).
252
+ *
253
+ * This is not cosmetics on top of the API's own repair. While `lastReported`
254
+ * lies, two things break here and only here:
255
+ *
256
+ * - `isParkable()` reads WAITING_INPUT with no open question as «idle», so
257
+ * `ensureCapacity` may KILL a live agent process to hand its slot to
258
+ * another session;
259
+ * - `isBillable()` counts only RUNNING/STARTING, so `agentActiveMs` stops
260
+ * growing and the time budget never fires for work that is really happening.
261
+ *
262
+ * It happens for real: a background subagent's report wakes a new turn inside
263
+ * the agent process (SDK 0.3.226 emits a second `system:init` and a `result`
264
+ * carrying `origin: {kind:'task-notification'}`), and nothing here reports a
265
+ * turn the runner did not start. Compaction does the same, and so does a
266
+ * question this runner withdraws by itself.
267
+ *
268
+ * An open question is the one thing that must survive: there, WAITING_INPUT
269
+ * means a tool call is parked on a person, and the agent narrating around its
270
+ * own question must not take the card off the screen.
271
+ */
272
+ private noteAgentIsWorking;
249
273
  private forwardEvent;
250
274
  /**
251
275
  * The dashboard's answer to a parked question (session 12).