subharness 0.0.1 → 0.0.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.
Files changed (120) hide show
  1. package/LICENSE +201 -21
  2. package/README.md +51 -18
  3. package/dist/adapters/claude-process.d.ts +10 -0
  4. package/dist/adapters/claude-process.js +58 -0
  5. package/dist/adapters/claude-process.js.map +1 -0
  6. package/dist/adapters/claude.js +52 -10
  7. package/dist/adapters/claude.js.map +1 -1
  8. package/dist/adapters/codex-input.d.ts +2 -0
  9. package/dist/adapters/codex-input.js +14 -0
  10. package/dist/adapters/codex-input.js.map +1 -0
  11. package/dist/adapters/codex-permissions.d.ts +13 -0
  12. package/dist/adapters/codex-permissions.js +30 -0
  13. package/dist/adapters/codex-permissions.js.map +1 -0
  14. package/dist/adapters/codex.js +12 -6
  15. package/dist/adapters/codex.js.map +1 -1
  16. package/dist/adapters/fx-auth.js +3 -0
  17. package/dist/adapters/fx-auth.js.map +1 -1
  18. package/dist/adapters/fx-permissions.d.ts +3 -0
  19. package/dist/adapters/fx-permissions.js +128 -0
  20. package/dist/adapters/fx-permissions.js.map +1 -0
  21. package/dist/adapters/fx.js +4 -0
  22. package/dist/adapters/fx.js.map +1 -1
  23. package/dist/cli/args.d.ts +3 -1
  24. package/dist/cli/args.js +18 -12
  25. package/dist/cli/args.js.map +1 -1
  26. package/dist/cli/dashboard-client.d.ts +3 -0
  27. package/dist/cli/dashboard-client.js +78 -0
  28. package/dist/cli/dashboard-client.js.map +1 -0
  29. package/dist/cli/dashboard-layout.d.ts +21 -0
  30. package/dist/cli/dashboard-layout.js +211 -0
  31. package/dist/cli/dashboard-layout.js.map +1 -0
  32. package/dist/cli/dashboard-renderer.d.ts +30 -0
  33. package/dist/cli/dashboard-renderer.js +80 -0
  34. package/dist/cli/dashboard-renderer.js.map +1 -0
  35. package/dist/cli/dashboard.d.ts +31 -0
  36. package/dist/cli/dashboard.js +81 -0
  37. package/dist/cli/dashboard.js.map +1 -0
  38. package/dist/cli/help.d.ts +1 -1
  39. package/dist/cli/help.js +35 -9
  40. package/dist/cli/help.js.map +1 -1
  41. package/dist/cli/main.js +19 -6
  42. package/dist/cli/main.js.map +1 -1
  43. package/dist/cli/output.js +10 -1
  44. package/dist/cli/output.js.map +1 -1
  45. package/dist/config/access.js +4 -4
  46. package/dist/config/access.js.map +1 -1
  47. package/dist/config/loader.js +2 -2
  48. package/dist/config/loader.js.map +1 -1
  49. package/dist/runtime/client.d.ts +5 -1
  50. package/dist/runtime/client.js +91 -40
  51. package/dist/runtime/client.js.map +1 -1
  52. package/dist/runtime/coordinator.d.ts +7 -1
  53. package/dist/runtime/coordinator.js +72 -8
  54. package/dist/runtime/coordinator.js.map +1 -1
  55. package/dist/runtime/daemon.js +100 -18
  56. package/dist/runtime/daemon.js.map +1 -1
  57. package/dist/runtime/dashboard-workspace.d.ts +2 -0
  58. package/dist/runtime/dashboard-workspace.js +38 -0
  59. package/dist/runtime/dashboard-workspace.js.map +1 -0
  60. package/dist/runtime/dashboard.d.ts +28 -0
  61. package/dist/runtime/dashboard.js +19 -0
  62. package/dist/runtime/dashboard.js.map +1 -0
  63. package/dist/runtime/readiness.d.ts +4 -0
  64. package/dist/runtime/readiness.js +17 -0
  65. package/dist/runtime/readiness.js.map +1 -0
  66. package/dist/runtime/select-native.d.ts +2 -1
  67. package/dist/runtime/select-native.js +5 -3
  68. package/dist/runtime/select-native.js.map +1 -1
  69. package/dist/runtime/service.d.ts +1 -1
  70. package/dist/runtime/service.js +10 -3
  71. package/dist/runtime/service.js.map +1 -1
  72. package/dist/runtime/startup-lock.d.ts +5 -0
  73. package/dist/runtime/startup-lock.js +37 -0
  74. package/dist/runtime/startup-lock.js.map +1 -0
  75. package/dist/runtime/startup-protocol.d.ts +17 -0
  76. package/dist/runtime/startup-protocol.js +23 -0
  77. package/dist/runtime/startup-protocol.js.map +1 -0
  78. package/dist/runtime/state.d.ts +1 -2
  79. package/dist/runtime/state.js +8 -43
  80. package/dist/runtime/state.js.map +1 -1
  81. package/dist/runtime/types.d.ts +16 -2
  82. package/dist/runtime/types.js.map +1 -1
  83. package/dist/runtime/worker-client.d.ts +7 -2
  84. package/dist/runtime/worker-client.js +69 -12
  85. package/dist/runtime/worker-client.js.map +1 -1
  86. package/dist/runtime/worker-server.d.ts +7 -0
  87. package/dist/runtime/worker-server.js +101 -0
  88. package/dist/runtime/worker-server.js.map +1 -0
  89. package/dist/runtime/worker.js +2 -66
  90. package/dist/runtime/worker.js.map +1 -1
  91. package/dist/sdk/definitions.js +23 -13
  92. package/dist/sdk/definitions.js.map +1 -1
  93. package/dist/sdk/permission-validation.d.ts +4 -0
  94. package/dist/sdk/permission-validation.js +55 -0
  95. package/dist/sdk/permission-validation.js.map +1 -0
  96. package/dist/sdk/types.d.ts +14 -0
  97. package/dist/sdk/types.js.map +1 -1
  98. package/package.json +17 -17
  99. package/sdk/access-config.md +4 -2
  100. package/sdk/adapter-contract.md +14 -2
  101. package/sdk/agent-skill.md +38 -0
  102. package/sdk/agent.md +6 -2
  103. package/sdk/cli/dashboard-design.md +40 -0
  104. package/sdk/cli/index.md +47 -13
  105. package/sdk/cli/output.md +21 -3
  106. package/sdk/completion-notifications.md +9 -5
  107. package/sdk/config.md +33 -8
  108. package/sdk/distribution.md +21 -7
  109. package/sdk/evals.md +171 -0
  110. package/sdk/fx.md +4 -3
  111. package/sdk/harnesses.md +6 -0
  112. package/sdk/index.md +2 -0
  113. package/sdk/message-delivery.md +6 -2
  114. package/sdk/permissions.md +65 -0
  115. package/sdk/plugins/sub-agents.md +7 -4
  116. package/sdk/pr-integration.md +37 -0
  117. package/sdk/project-team.md +13 -8
  118. package/sdk/sessions.md +1 -1
  119. package/sdk/tools.md +2 -0
  120. package/sdk/v1-runtime.md +22 -7
@@ -2,12 +2,17 @@ import { randomUUID } from 'node:crypto';
2
2
  import { waitForChange } from './observation.js';
3
3
  import { AgentError, errorInfo } from '../errors.js';
4
4
  import { terminal } from './types.js';
5
+ import { dashboardHarness, dashboardTitle } from './dashboard.js';
6
+ import { resolveDashboardWorkspace } from './dashboard-workspace.js';
5
7
  export class Coordinator {
6
8
  factory;
9
+ now;
7
10
  sessions = new Map();
8
11
  tasks = new Map();
9
- constructor(factory) {
12
+ dashboardHistory;
13
+ constructor(factory, now = Date.now) {
10
14
  this.factory = factory;
15
+ this.now = now;
11
16
  }
12
17
  parentContext(token) {
13
18
  const session = [...this.sessions.values()].find(session => session.token === token);
@@ -18,8 +23,10 @@ export class Coordinator {
18
23
  }
19
24
  run(input) {
20
25
  this.validateAdmission(undefined, input.prompt, input.parentToken);
26
+ const selected = 'kind' in input.reference ? input.reference.harness.kind : undefined;
21
27
  const session = { id: `ses_${randomUUID()}`, token: randomUUID(), input,
22
- tasks: [], paused: false, commands: Promise.resolve(), controls: 0 };
28
+ tasks: [], paused: false, commands: Promise.resolve(), controls: 0, harness: dashboardHarness(selected),
29
+ workspace: resolveDashboardWorkspace(input.cwd) };
23
30
  this.sessions.set(session.id, session);
24
31
  return this.admit(session, input.prompt, false, input.parentToken);
25
32
  }
@@ -41,6 +48,7 @@ export class Coordinator {
41
48
  }
42
49
  try {
43
50
  await (await session.driver).steer(prompt);
51
+ this.touch(task);
44
52
  return { version: 1, type: 'accepted', sessionId: id, taskId: task.id, delivery: 'steer' };
45
53
  }
46
54
  catch (error) {
@@ -91,6 +99,38 @@ export class Coordinator {
91
99
  truncated: !full && response.text.length > 4000
92
100
  } } : {}) };
93
101
  }
102
+ async dashboard() {
103
+ // New sessions join the next snapshot; every serialized row has resolved context.
104
+ const admitted = [...this.sessions.values()];
105
+ const workspaces = new Map(await Promise.all(admitted.map(async (session) => [session.id, await session.workspace])));
106
+ const current = [];
107
+ for (const session of admitted) {
108
+ const id = session.active ?? session.tasks[0];
109
+ if (!id)
110
+ continue;
111
+ const task = this.task(id);
112
+ if (task.state === 'failed' || !terminal(task.state))
113
+ current.push(task);
114
+ }
115
+ // Map insertion order records admission order; stable sorting preserves its reversed ties.
116
+ this.dashboardHistory ??= [...this.tasks.values()].reverse().filter(task => terminal(task.state))
117
+ .sort((first, second) => second.finishedAt - first.finishedAt);
118
+ const visible = new Set(current.map(task => task.id));
119
+ const tasks = [...current, ...this.dashboardHistory.filter(task => workspaces.has(task.sessionId) && !visible.has(task.id))];
120
+ const sessions = tasks.map(task => ({ sessionId: task.sessionId, taskId: task.id,
121
+ harness: this.session(task.sessionId).harness, title: task.title, state: task.state,
122
+ workspace: workspaces.get(task.sessionId), updatedAt: task.updatedAt,
123
+ ...(task.dispatchedAt === undefined ? {} : { dispatchedAt: task.dispatchedAt }),
124
+ ...(task.failedAt === undefined ? {} : { failedAt: task.failedAt }),
125
+ ...(task.finishedAt === undefined ? {} : { finishedAt: task.finishedAt }) }));
126
+ return { version: 1, type: 'dashboard', history: true, grouping: true, sessions };
127
+ }
128
+ finish(task, state, at = this.now(), updatedAt = at) {
129
+ task.state = state;
130
+ task.finishedAt = at;
131
+ task.updatedAt = updatedAt;
132
+ this.dashboardHistory = undefined;
133
+ }
94
134
  queue(id) {
95
135
  const session = this.session(id);
96
136
  const summary = (task) => ({ taskId: task.id, state: task.state, description: task.prompt.slice(0, 120) });
@@ -108,7 +148,10 @@ export class Coordinator {
108
148
  throw new AgentError('CANCEL_FAILED', 'Confirm cancellation of the affected executions before recovery.');
109
149
  task.stopping = false;
110
150
  task.error = undefined;
151
+ task.failedAt = undefined;
152
+ task.finishedAt = undefined;
111
153
  session.paused = false;
154
+ this.dashboardHistory = undefined;
112
155
  void this.execute(task, '', true);
113
156
  return { version: 1, type: 'started', sessionId: id, taskId: task.id, state: task.state, resumed: true };
114
157
  });
@@ -165,7 +208,8 @@ export class Coordinator {
165
208
  throw new Error('Cancellation unconfirmed');
166
209
  }
167
210
  catch {
168
- task.state = 'failed';
211
+ task.failedAt = this.now();
212
+ this.finish(task, 'failed', task.failedAt);
169
213
  task.error = { code: 'CANCEL_FAILED', message: 'Native execution could not be confirmed stopped.' };
170
214
  task.stopUnconfirmed = true;
171
215
  session.paused = true;
@@ -173,7 +217,7 @@ export class Coordinator {
173
217
  throw new AgentError('CANCEL_FAILED', task.error.message);
174
218
  }
175
219
  task.nativeActive = false;
176
- task.state = outcome;
220
+ this.finish(task, outcome);
177
221
  task.stopUnconfirmed = false;
178
222
  task.error = undefined;
179
223
  if (session.active === task.id) {
@@ -185,8 +229,10 @@ export class Coordinator {
185
229
  }
186
230
  admit(session, prompt, front = false, parentToken) {
187
231
  const parent = this.validateAdmission(session, prompt, parentToken, front);
188
- const task = { id: `tsk_${randomUUID()}`, sessionId: session.id, prompt,
189
- parentId: parent?.id, state: 'queued', responses: [], children: new Set(), inbox: [], nativeActive: false, stopping: false, changed: new Set() };
232
+ const blockedByTaskId = session.paused ? session.active : undefined;
233
+ const task = { id: `tsk_${randomUUID()}`, sessionId: session.id, prompt, title: dashboardTitle(prompt),
234
+ parentId: parent?.id, state: 'queued', responses: [], children: new Set(), inbox: [], nativeActive: false,
235
+ stopping: false, updatedAt: this.now(), changed: new Set() };
190
236
  this.tasks.set(task.id, task);
191
237
  parent?.children.add(task.id);
192
238
  if (front)
@@ -194,7 +240,8 @@ export class Coordinator {
194
240
  else
195
241
  session.tasks.push(task.id);
196
242
  this.dispatch(session);
197
- return { version: 1, type: 'started', sessionId: session.id, taskId: task.id, state: task.state };
243
+ return { version: 1, type: 'started', sessionId: session.id, taskId: task.id, state: task.state,
244
+ ...(blockedByTaskId ? { paused: true, blockedByTaskId } : {}) };
198
245
  }
199
246
  validateAdmission(session, prompt, parentToken, replacement = false) {
200
247
  if (typeof prompt !== 'string' || !prompt.trim() || Buffer.byteLength(prompt) > 1024 * 1024)
@@ -224,11 +271,21 @@ export class Coordinator {
224
271
  }
225
272
  async execute(task, prompt, recovering = false) {
226
273
  const session = this.session(task.sessionId);
274
+ const dispatchedAt = this.now();
275
+ task.dispatchedAt ??= dispatchedAt;
276
+ this.touch(task, dispatchedAt);
227
277
  task.state = 'running';
228
278
  task.nativeActive = true;
229
279
  try {
230
280
  session.driver ??= this.factory({ ...session.input, sessionId: session.id, token: session.token });
231
281
  const driver = await session.driver;
282
+ if (driver.selectedHarness) {
283
+ const harness = dashboardHarness(driver.selectedHarness);
284
+ if (session.harness !== harness) {
285
+ session.harness = harness;
286
+ this.touch(task);
287
+ }
288
+ }
232
289
  if (task.stopping)
233
290
  return;
234
291
  const text = recovering ? await driver.resume() : await driver.turn(prompt);
@@ -238,6 +295,11 @@ export class Coordinator {
238
295
  throw new AgentError('OUTPUT_TOO_LARGE', 'The response exceeds 1 MiB.');
239
296
  task.nativeActive = false;
240
297
  task.state = this.pending(task) ? 'waiting' : 'completed';
298
+ const respondedAt = this.now();
299
+ if (task.state === 'completed')
300
+ this.finish(task, 'completed', respondedAt);
301
+ else
302
+ this.touch(task, respondedAt);
241
303
  task.responses.push({ version: 1, type: 'response', sessionId: session.id, taskId: task.id,
242
304
  responseId: `rsp_${randomUUID()}`, state: task.state, text });
243
305
  this.notify(task);
@@ -252,11 +314,12 @@ export class Coordinator {
252
314
  catch (error) {
253
315
  if (task.stopping)
254
316
  return;
317
+ task.failedAt = this.now();
255
318
  task.nativeActive = false;
256
319
  task.stopping = true;
257
320
  const stopped = await Promise.allSettled([...task.children].map(id => this.task(id)).filter(child => !terminal(child.state) || child.stopUnconfirmed).map(child => this.stop(child, 'cancelled')));
258
321
  task.stopUnconfirmed = stopped.some(result => result.status === 'rejected');
259
- task.state = 'failed';
322
+ this.finish(task, 'failed', task.failedAt, this.now());
260
323
  task.error = task.stopUnconfirmed
261
324
  ? { code: 'CANCEL_FAILED', message: 'Descendant execution could not be confirmed stopped.' } : errorInfo(error);
262
325
  session.paused = true;
@@ -286,6 +349,7 @@ export class Coordinator {
286
349
  results.map(result => `${result.taskId} [${result.state}]:\n${result.text}`).join('\n\n');
287
350
  void this.execute(task, prompt);
288
351
  }
352
+ touch(task, at = this.now()) { task.updatedAt = at; }
289
353
  notify(task) { for (const resolve of task.changed)
290
354
  resolve(); task.changed.clear(); }
291
355
  task(id) { const task = this.tasks.get(id); if (!task)
@@ -1 +1 @@
1
- {"version":3,"file":"coordinator.js","sourceRoot":"","sources":["../../src/runtime/coordinator.ts"],"names":[],"mappings":"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","sourcesContent":["import { randomUUID } from 'node:crypto';\nimport { waitForChange } from './observation.js';\nimport { AgentError, errorInfo } from '../errors.js';\nimport { terminal, type DriverFactory, type Observation, type Receipt, type Session, type SessionInput, type Task, type Delivery } from './types.js';\n\nexport class Coordinator {\n private sessions = new Map<string, Session>();\n private tasks = new Map<string, Task>();\n constructor(private readonly factory: DriverFactory) {}\n\n parentContext(token: string) {\n const session = [...this.sessions.values()].find(session => session.token === token);\n const task = session?.active ? this.task(session.active) : undefined;\n if (!session || !task || task.stopping || terminal(task.state))\n throw new AgentError('INVALID_PARENT', 'The parent context is no longer active.');\n return {taskId: task.id, reference: session.input.reference, cwd: session.input.cwd};\n }\n\n run(input: SessionInput): Receipt {\n this.validateAdmission(undefined, input.prompt, input.parentToken);\n const session: Session = { id: `ses_${randomUUID()}`, token: randomUUID(), input,\n tasks: [], paused: false, commands: Promise.resolve(), controls: 0 };\n this.sessions.set(session.id, session);\n return this.admit(session, input.prompt, false, input.parentToken);\n }\n\n async send(id: string, prompt: string, delivery: Delivery, parentToken?: string): Promise<Receipt> {\n const session = this.session(id);\n const operation = async (): Promise<Receipt> => {\n if (!['queue', 'steer', 'interrupt'].includes(delivery)) throw new AgentError('INVALID_ARGUMENT', 'Unknown delivery mode.');\n this.validateAdmission(session, prompt, parentToken, delivery !== 'queue');\n if (delivery === 'queue') return this.admit(session, prompt, false, parentToken);\n const task = session.active ? this.task(session.active) : undefined;\n if (delivery === 'steer') {\n if (!task || terminal(task.state) || task.stopping) throw new AgentError('NO_ACTIVE_TASK', 'There is no active task accepting steering.');\n if (!task.nativeActive) {\n void this.execute(task, prompt);\n return {version: 1, type: 'accepted', sessionId: id, taskId: task.id, delivery: 'steer'};\n }\n try {\n await (await session.driver!).steer(prompt);\n return {version: 1, type: 'accepted', sessionId: id, taskId: task.id, delivery: 'steer'};\n } catch (error) {\n if (!(error instanceof AgentError) || error.code !== 'UNSUPPORTED_DELIVERY') throw error;\n }\n }\n if (task && (!terminal(task.state) || task.stopUnconfirmed || task.state === 'failed')) await this.stop(task, 'interrupted');\n session.paused = false;\n const receipt = this.admit(session, prompt, true, parentToken);\n return {...receipt, requestedDelivery: delivery, delivery: 'interrupt'};\n };\n return this.command(session, operation);\n }\n\n async observe(id: string, after?: string, readerToken?: string, signal?: AbortSignal): Promise<Observation> {\n const task = this.task(id);\n const position = after ? task.responses.findIndex(response => response.responseId === after) : -1;\n if (after && position === -1) throw new AgentError('UNKNOWN_RESPONSE', 'The response does not belong to this task.');\n for (;;) {\n const response = task.responses[position + 1];\n if (response) {\n if (terminal(response.state)) this.acknowledge(task, readerToken);\n return response;\n }\n if (terminal(task.state)) {\n this.acknowledge(task, readerToken);\n return { version: 1, type: 'terminal', taskId: id,\n sessionId: task.sessionId, state: task.state, ...(task.error ? {error:task.error} : {}) };\n }\n await waitForChange(task.changed, signal);\n }\n }\n\n private acknowledge(task: Task, readerToken?: string) {\n if (!readerToken || !task.parentId || task.stopUnconfirmed) return;\n const parent = this.task(task.parentId);\n if (this.session(parent.sessionId).token === readerToken && parent.nativeActive)\n parent.inbox = parent.inbox.filter(result => result.taskId !== task.id);\n }\n\n status(id: string, full = false) {\n const task = this.task(id), response = task.responses.at(-1);\n return { version: 1, type: 'status', taskId: id, sessionId: task.sessionId, state: task.state,\n ...(task.error ? {error: task.error} : {}), ...(response ? { response: {\n responseId: response.responseId, text: full ? response.text : response.text.slice(0, 4000),\n truncated: !full && response.text.length > 4000 }} : {}) };\n }\n\n queue(id: string) {\n const session = this.session(id);\n const summary = (task: Task) => ({taskId: task.id, state: task.state, description: task.prompt.slice(0, 120)});\n return {version: 1, type: 'queue', sessionId: id, paused: session.paused,\n ...(session.active ? {active: summary(this.task(session.active))} : {}),\n tasks: session.tasks.map(id => summary(this.task(id)))};\n }\n\n async resume(id: string): Promise<Receipt> {\n const session = this.session(id);\n return this.command(session, async () => {\n const task = session.active ? this.task(session.active) : undefined;\n if (!task || task.state !== 'failed') throw new AgentError('NOT_FAILED', 'This session has no failed task to resume.');\n if (task.stopUnconfirmed || task.stopPromise) throw new AgentError('CANCEL_FAILED', 'Confirm cancellation of the affected executions before recovery.');\n task.stopping = false; task.error = undefined; session.paused = false;\n void this.execute(task, '', true);\n return {version: 1, type: 'started', sessionId: id, taskId: task.id, state: task.state, resumed: true};\n });\n }\n\n async close() {\n await Promise.allSettled([...this.sessions.values()].map(async session => (await session.driver)?.close()));\n }\n\n async cancel(id: string): Promise<Receipt> {\n const task = this.task(id);\n return this.command(this.session(task.sessionId), async () => {\n if (!terminal(task.state) || task.stopUnconfirmed) await this.stop(task, 'cancelled');\n else if (task.state === 'failed') {\n const session = this.session(task.sessionId);\n if (session.active === task.id) { session.active = undefined; session.paused = false; }\n }\n return {version: 1, type: 'cancelled', taskId: id, sessionId: task.sessionId, state: task.state};\n });\n }\n\n private command<T>(session: Session, operation: () => Promise<T>): Promise<T> {\n session.controls++;\n const result = session.commands.then(operation, operation).finally(() => {\n session.controls--;\n this.dispatch(session);\n });\n session.commands = result.catch(() => undefined);\n return result;\n }\n\n private stop(task: Task, outcome: 'cancelled' | 'interrupted'): Promise<void> {\n if (task.stopPromise) return task.stopPromise;\n task.stopPromise = this.finishStop(task, outcome).finally(() => {\n task.stopPromise = undefined;\n this.dispatch(this.session(task.sessionId));\n });\n return task.stopPromise;\n }\n\n private async finishStop(task: Task, outcome: 'cancelled' | 'interrupted') {\n const session = this.session(task.sessionId);\n task.stopping = true;\n session.tasks = session.tasks.filter(id => id !== task.id);\n try {\n const stops = [...task.children].map(id => this.task(id)).filter(child => !terminal(child.state) || child.stopUnconfirmed).map(child => this.stop(child, 'cancelled'));\n if (task.nativeActive && session.driver) stops.push(session.driver.then(async driver => {\n await driver.interrupt(); task.nativeActive = false;\n }));\n const outcomes = await Promise.allSettled(stops);\n if (outcomes.some(outcome => outcome.status === 'rejected')) throw new Error('Cancellation unconfirmed');\n } catch {\n task.state = 'failed'; task.error = {code:'CANCEL_FAILED', message:'Native execution could not be confirmed stopped.'};\n task.stopUnconfirmed = true;\n session.paused = true; this.notify(task);\n throw new AgentError('CANCEL_FAILED', task.error.message);\n }\n task.nativeActive = false; task.state = outcome; task.stopUnconfirmed = false; task.error = undefined;\n if (session.active === task.id) { session.active = undefined; session.paused = false; }\n this.notify(task); this.deliver(task);\n }\n\n private admit(session: Session, prompt: string, front = false, parentToken?: string): Receipt {\n const parent = this.validateAdmission(session, prompt, parentToken, front);\n const task: Task = { id: `tsk_${randomUUID()}`, sessionId: session.id, prompt,\n parentId: parent?.id, state: 'queued', responses: [], children: new Set(), inbox: [], nativeActive: false, stopping: false, changed: new Set() };\n this.tasks.set(task.id, task);\n parent?.children.add(task.id);\n if (front) session.tasks.unshift(task.id); else session.tasks.push(task.id);\n this.dispatch(session);\n return {version: 1, type: 'started', sessionId: session.id, taskId: task.id, state: task.state};\n }\n\n private validateAdmission(session: Session | undefined, prompt: string, parentToken?: string, replacement = false) {\n if (typeof prompt !== 'string' || !prompt.trim() || Buffer.byteLength(prompt) > 1024 * 1024)\n throw new AgentError('INVALID_ARGUMENT', 'Prompt must contain text and cannot exceed 1 MiB.');\n if (!replacement && session && session.tasks.length >= 100) throw new AgentError('QUEUE_FULL', 'The session already has 100 queued tasks.');\n const parent = parentToken ? this.task(this.parentContext(parentToken).taskId) : undefined;\n let depth = 0, ancestor = parent;\n while (ancestor) {\n if (ancestor.sessionId === session?.id) throw new AgentError('INVALID_PARENT', 'A managed task cannot queue work in its own or an ancestor session.');\n depth++; ancestor = ancestor.parentId ? this.task(ancestor.parentId) : undefined;\n }\n if (depth > 8) throw new AgentError('DELEGATION_LIMIT', 'Maximum delegation depth is 8.');\n return parent;\n }\n\n private dispatch(session: Session) {\n if (session.active || session.paused || session.controls) return;\n const id = session.tasks.shift();\n if (!id) return;\n session.active = id;\n void this.execute(this.task(id), this.task(id).prompt);\n }\n\n private async execute(task: Task, prompt: string, recovering = false) {\n const session = this.session(task.sessionId);\n task.state = 'running'; task.nativeActive = true;\n try {\n session.driver ??= this.factory({...session.input, sessionId: session.id, token: session.token});\n const driver = await session.driver;\n if (task.stopping) return;\n const text = recovering ? await driver.resume() : await driver.turn(prompt);\n if (task.stopping) return;\n if (Buffer.byteLength(text) > 1024 * 1024) throw new AgentError('OUTPUT_TOO_LARGE', 'The response exceeds 1 MiB.');\n task.nativeActive = false;\n task.state = this.pending(task) ? 'waiting' : 'completed';\n task.responses.push({version: 1, type: 'response', sessionId: session.id, taskId: task.id,\n responseId: `rsp_${randomUUID()}`, state: task.state, text});\n this.notify(task);\n if (task.state === 'completed') {\n session.active = undefined;\n this.deliver(task);\n this.dispatch(session);\n } else this.continueParent(task);\n } catch (error) {\n if (task.stopping) return;\n task.nativeActive = false;\n task.stopping = true;\n const stopped = await Promise.allSettled([...task.children].map(id => this.task(id)).filter(child => !terminal(child.state) || child.stopUnconfirmed).map(child => this.stop(child, 'cancelled')));\n task.stopUnconfirmed = stopped.some(result => result.status === 'rejected');\n task.state = 'failed'; task.error = task.stopUnconfirmed\n ? {code:'CANCEL_FAILED', message:'Descendant execution could not be confirmed stopped.'} : errorInfo(error);\n session.paused = true; this.notify(task); this.deliver(task);\n }\n }\n\n private pending(task: Task) {\n return task.inbox.length > 0 || [...task.children].some(id => !terminal(this.task(id).state) || this.task(id).stopUnconfirmed);\n }\n\n private deliver(child: Task) {\n if (!child.parentId || child.stopUnconfirmed) return;\n const parent = this.task(child.parentId);\n if (parent.stopping || terminal(parent.state)) return;\n parent.inbox.push({taskId: child.id, state: child.state,\n text: child.error?.message ?? child.responses.at(-1)?.text ?? child.state});\n // Let an attached child command acknowledge delivery through its native tool output first.\n setImmediate(() => this.continueParent(parent));\n }\n\n private continueParent(task: Task) {\n if (task.nativeActive || task.stopping || terminal(task.state) || !task.inbox.length) return;\n const results = task.inbox.splice(0);\n const prompt = 'Delegated task outcomes (continue the current task):\\n' +\n results.map(result => `${result.taskId} [${result.state}]:\\n${result.text}`).join('\\n\\n');\n void this.execute(task, prompt);\n }\n\n private notify(task: Task) { for (const resolve of task.changed) resolve(); task.changed.clear(); }\n private task(id: string) { const task = this.tasks.get(id); if (!task) throw new AgentError('UNKNOWN_TASK', 'Task is unavailable in this coordinator.'); return task; }\n private session(id: string) { const session = this.sessions.get(id); if (!session) throw new AgentError('UNKNOWN_SESSION', 'Session is unavailable in this coordinator.'); return session; }\n}\n"]}
1
+ {"version":3,"file":"coordinator.js","sourceRoot":"","sources":["../../src/runtime/coordinator.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AACzC,OAAO,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAC;AACjD,OAAO,EAAE,UAAU,EAAE,SAAS,EAAE,MAAM,cAAc,CAAC;AACrD,OAAO,EAAE,QAAQ,EAAiH,MAAM,YAAY,CAAC;AACrJ,OAAO,EAAE,gBAAgB,EAAE,cAAc,EAA0B,MAAM,gBAAgB,CAAC;AAC1F,OAAO,EAAE,yBAAyB,EAAE,MAAM,0BAA0B,CAAC;AAErE,MAAM,OAAO,WAAW;IAIO,OAAO;IAAkC,GAAG;IAHjE,QAAQ,GAAG,IAAI,GAAG,EAAmB,CAAC;IACtC,KAAK,GAAG,IAAI,GAAG,EAAgB,CAAC;IAChC,gBAAgB,CAAU;IAClC,YAA6B,OAAsB,EAAmB,GAAG,GAAiB,IAAI,CAAC,GAAG;uBAArE,OAAO;mBAAkC,GAAG;IAA4B,CAAC;IAEtG,aAAa,CAAC,KAAa;QACzB,MAAM,OAAO,GAAG,CAAC,GAAG,IAAI,CAAC,QAAQ,CAAC,MAAM,EAAE,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,EAAE,CAAC,OAAO,CAAC,KAAK,KAAK,KAAK,CAAC,CAAC;QACrF,MAAM,IAAI,GAAG,OAAO,EAAE,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;QACrE,IAAI,CAAC,OAAO,IAAI,CAAC,IAAI,IAAI,IAAI,CAAC,QAAQ,IAAI,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC;YAC5D,MAAM,IAAI,UAAU,CAAC,gBAAgB,EAAE,yCAAyC,CAAC,CAAC;QACpF,OAAO,EAAC,MAAM,EAAE,IAAI,CAAC,EAAE,EAAE,SAAS,EAAE,OAAO,CAAC,KAAK,CAAC,SAAS,EAAE,GAAG,EAAE,OAAO,CAAC,KAAK,CAAC,GAAG,EAAC,CAAC;IACvF,CAAC;IAED,GAAG,CAAC,KAAmB;QACrB,IAAI,CAAC,iBAAiB,CAAC,SAAS,EAAE,KAAK,CAAC,MAAM,EAAE,KAAK,CAAC,WAAW,CAAC,CAAC;QACnE,MAAM,QAAQ,GAAG,MAAM,IAAI,KAAK,CAAC,SAAS,CAAC,CAAC,CAAC,KAAK,CAAC,SAAS,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,SAAS,CAAC;QACtF,MAAM,OAAO,GAAY,EAAE,EAAE,EAAE,OAAO,UAAU,EAAE,EAAE,EAAE,KAAK,EAAE,UAAU,EAAE,EAAE,KAAK;YAC9E,KAAK,EAAE,EAAE,EAAE,MAAM,EAAE,KAAK,EAAE,QAAQ,EAAE,OAAO,CAAC,OAAO,EAAE,EAAE,QAAQ,EAAE,CAAC,EAAE,OAAO,EAAE,gBAAgB,CAAC,QAAQ,CAAC;YACvG,SAAS,EAAE,yBAAyB,CAAC,KAAK,CAAC,GAAG,CAAC,EAAE,CAAC;QACpD,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,OAAO,CAAC,EAAE,EAAE,OAAO,CAAC,CAAC;QACvC,OAAO,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,KAAK,CAAC,MAAM,EAAE,KAAK,EAAE,KAAK,CAAC,WAAW,CAAC,CAAC;IACrE,CAAC;IAED,KAAK,CAAC,IAAI,CAAC,EAAU,EAAE,MAAc,EAAE,QAAkB,EAAE,WAAoB;QAC7E,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC;QACjC,MAAM,SAAS,GAAG,KAAK,IAAsB,EAAE;YAC7C,IAAI,CAAC,CAAC,OAAO,EAAE,OAAO,EAAE,WAAW,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC;gBAAE,MAAM,IAAI,UAAU,CAAC,kBAAkB,EAAE,wBAAwB,CAAC,CAAC;YAC5H,IAAI,CAAC,iBAAiB,CAAC,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,QAAQ,KAAK,OAAO,CAAC,CAAC;YAC3E,IAAI,QAAQ,KAAK,OAAO;gBAAE,OAAO,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,WAAW,CAAC,CAAC;YACjF,MAAM,IAAI,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;YACpE,IAAI,QAAQ,KAAK,OAAO,EAAE,CAAC;gBACzB,IAAI,CAAC,IAAI,IAAI,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,IAAI,CAAC,QAAQ;oBAAE,MAAM,IAAI,UAAU,CAAC,gBAAgB,EAAE,6CAA6C,CAAC,CAAC;gBAC1I,IAAI,CAAC,IAAI,CAAC,YAAY,EAAE,CAAC;oBACvB,KAAK,IAAI,CAAC,OAAO,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;oBAChC,OAAO,EAAC,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,UAAU,EAAE,SAAS,EAAE,EAAE,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,EAAE,QAAQ,EAAE,OAAO,EAAC,CAAC;gBAC3F,CAAC;gBACD,IAAI,CAAC;oBACH,MAAM,CAAC,MAAM,OAAO,CAAC,MAAO,CAAC,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC;oBAC5C,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;oBACjB,OAAO,EAAC,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,UAAU,EAAE,SAAS,EAAE,EAAE,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,EAAE,QAAQ,EAAE,OAAO,EAAC,CAAC;gBAC3F,CAAC;gBAAC,OAAO,KAAK,EAAE,CAAC;oBACf,IAAI,CAAC,CAAC,KAAK,YAAY,UAAU,CAAC,IAAI,KAAK,CAAC,IAAI,KAAK,sBAAsB;wBAAE,MAAM,KAAK,CAAC;gBAC3F,CAAC;YACH,CAAC;YACD,IAAI,IAAI,IAAI,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,IAAI,CAAC,eAAe,IAAI,IAAI,CAAC,KAAK,KAAK,QAAQ,CAAC;gBAAE,MAAM,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,aAAa,CAAC,CAAC;YAC7H,OAAO,CAAC,MAAM,GAAG,KAAK,CAAC;YACvB,MAAM,OAAO,GAAG,IAAI,CAAC,KAAK,CAAC,OAAO,EAAE,MAAM,EAAE,IAAI,EAAE,WAAW,CAAC,CAAC;YAC/D,OAAO,EAAC,GAAG,OAAO,EAAE,iBAAiB,EAAE,QAAQ,EAAE,QAAQ,EAAE,WAAW,EAAC,CAAC;QAC1E,CAAC,CAAC;QACF,OAAO,IAAI,CAAC,OAAO,CAAC,OAAO,EAAE,SAAS,CAAC,CAAC;IAC1C,CAAC;IAED,KAAK,CAAC,OAAO,CAAC,EAAU,EAAE,KAAc,EAAE,WAAoB,EAAE,MAAoB;QAClF,MAAM,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QAC3B,MAAM,QAAQ,GAAG,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,SAAS,CAAC,SAAS,CAAC,QAAQ,CAAC,EAAE,CAAC,QAAQ,CAAC,UAAU,KAAK,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;QAClG,IAAI,KAAK,IAAI,QAAQ,KAAK,CAAC,CAAC;YAAE,MAAM,IAAI,UAAU,CAAC,kBAAkB,EAAE,4CAA4C,CAAC,CAAC;QACrH,SAAS,CAAC;YACR,MAAM,QAAQ,GAAG,IAAI,CAAC,SAAS,CAAC,QAAQ,GAAG,CAAC,CAAC,CAAC;YAC9C,IAAI,QAAQ,EAAE,CAAC;gBACb,IAAI,QAAQ,CAAC,QAAQ,CAAC,KAAK,CAAC;oBAAE,IAAI,CAAC,WAAW,CAAC,IAAI,EAAE,WAAW,CAAC,CAAC;gBAClE,OAAO,QAAQ,CAAC;YAClB,CAAC;YACD,IAAI,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,EAAE,CAAC;gBACzB,IAAI,CAAC,WAAW,CAAC,IAAI,EAAE,WAAW,CAAC,CAAC;gBACpC,OAAO,EAAE,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,UAAU,EAAE,MAAM,EAAE,EAAE;oBAC/C,SAAS,EAAE,IAAI,CAAC,SAAS,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,EAAE,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,EAAC,KAAK,EAAC,IAAI,CAAC,KAAK,EAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC;YAC9F,CAAC;YACD,MAAM,aAAa,CAAC,IAAI,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC;QAC5C,CAAC;IACH,CAAC;IAEO,WAAW,CAAC,IAAU,EAAE,WAAoB;QAClD,IAAI,CAAC,WAAW,IAAI,CAAC,IAAI,CAAC,QAAQ,IAAI,IAAI,CAAC,eAAe;YAAE,OAAO;QACnE,MAAM,MAAM,GAAG,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;QACxC,IAAI,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC,KAAK,KAAK,WAAW,IAAI,MAAM,CAAC,YAAY;YAC7E,MAAM,CAAC,KAAK,GAAG,MAAM,CAAC,KAAK,CAAC,MAAM,CAAC,MAAM,CAAC,EAAE,CAAC,MAAM,CAAC,MAAM,KAAK,IAAI,CAAC,EAAE,CAAC,CAAC;IAC5E,CAAC;IAED,MAAM,CAAC,EAAU,EAAE,IAAI,GAAG,KAAK;QAC7B,MAAM,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,EAAE,QAAQ,GAAG,IAAI,CAAC,SAAS,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC;QAC7D,OAAO,EAAE,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,QAAQ,EAAE,MAAM,EAAE,EAAE,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK;YAC3F,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,EAAC,KAAK,EAAE,IAAI,CAAC,KAAK,EAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,GAAG,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,QAAQ,EAAE;oBACrE,UAAU,EAAE,QAAQ,CAAC,UAAU,EAAE,IAAI,EAAE,IAAI,CAAC,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,EAAE,IAAI,CAAC;oBAC1F,SAAS,EAAE,CAAC,IAAI,IAAI,QAAQ,CAAC,IAAI,CAAC,MAAM,GAAG,IAAI;iBAAE,EAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC;IACjE,CAAC;IAED,KAAK,CAAC,SAAS;QACb,kFAAkF;QAClF,MAAM,QAAQ,GAAG,CAAC,GAAG,IAAI,CAAC,QAAQ,CAAC,MAAM,EAAE,CAAC,CAAC;QAC7C,MAAM,UAAU,GAAG,IAAI,GAAG,CAAC,MAAM,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,GAAG,CAAC,KAAK,EAAC,OAAO,EAAC,EAAE,CACxE,CAAC,OAAO,CAAC,EAAE,EAAE,MAAM,OAAO,CAAC,SAAS,CAAU,CAAC,CAAC,CAAC,CAAC;QACpD,MAAM,OAAO,GAAW,EAAE,CAAC;QAC3B,KAAK,MAAM,OAAO,IAAI,QAAQ,EAAE,CAAC;YAC/B,MAAM,EAAE,GAAG,OAAO,CAAC,MAAM,IAAI,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;YAC9C,IAAI,CAAC,EAAE;gBAAE,SAAS;YAClB,MAAM,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;YAC3B,IAAI,IAAI,CAAC,KAAK,KAAK,QAAQ,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC;gBAAE,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QAC3E,CAAC;QACD,2FAA2F;QAC3F,IAAI,CAAC,gBAAgB,KAAK,CAAC,GAAG,IAAI,CAAC,KAAK,CAAC,MAAM,EAAE,CAAC,CAAC,OAAO,EAAE,CAAC,MAAM,CAAC,IAAI,CAAC,EAAE,CAAC,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;aAC9F,IAAI,CAAC,CAAC,KAAK,EAAE,MAAM,EAAE,EAAE,CAAC,MAAM,CAAC,UAAW,GAAG,KAAK,CAAC,UAAW,CAAC,CAAC;QACnE,MAAM,OAAO,GAAG,IAAI,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC;QACtD,MAAM,KAAK,GAAG,CAAC,GAAG,OAAO,EAAE,GAAG,IAAI,CAAC,gBAAgB,CAAC,MAAM,CAAC,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,GAAG,CAAC,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC;QAC7H,MAAM,QAAQ,GAAG,KAAK,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,EAAC,SAAS,EAAE,IAAI,CAAC,SAAS,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE;YAC7E,OAAO,EAAE,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC,OAAO,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK;YACnF,SAAS,EAAE,UAAU,CAAC,GAAG,CAAC,IAAI,CAAC,SAAS,CAAE,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS;YACrE,GAAG,CAAC,IAAI,CAAC,YAAY,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAC,YAAY,EAAE,IAAI,CAAC,YAAY,EAAC,CAAC;YAC7E,GAAG,CAAC,IAAI,CAAC,QAAQ,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAC,QAAQ,EAAE,IAAI,CAAC,QAAQ,EAAC,CAAC;YACjE,GAAG,CAAC,IAAI,CAAC,UAAU,KAAK,SAAS,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAC,UAAU,EAAE,IAAI,CAAC,UAAU,EAAC,CAAC,EAAC,CAAC,CAAC,CAAC;QAC7E,OAAO,EAAC,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,WAAW,EAAE,OAAO,EAAE,IAAI,EAAE,QAAQ,EAAE,IAAI,EAAE,QAAQ,EAAC,CAAC;IAClF,CAAC;IAEO,MAAM,CAAC,IAAU,EAAE,KAA2D,EAAE,EAAE,GAAG,IAAI,CAAC,GAAG,EAAE,EAAE,SAAS,GAAG,EAAE;QACrH,IAAI,CAAC,KAAK,GAAG,KAAK,CAAC;QACnB,IAAI,CAAC,UAAU,GAAG,EAAE,CAAC;QACrB,IAAI,CAAC,SAAS,GAAG,SAAS,CAAC;QAC3B,IAAI,CAAC,gBAAgB,GAAG,SAAS,CAAC;IACpC,CAAC;IAED,KAAK,CAAC,EAAU;QACd,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC;QACjC,MAAM,OAAO,GAAG,CAAC,IAAU,EAAE,EAAE,CAAC,CAAC,EAAC,MAAM,EAAE,IAAI,CAAC,EAAE,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,EAAE,WAAW,EAAE,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,GAAG,CAAC,EAAC,CAAC,CAAC;QAC/G,OAAO,EAAC,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,OAAO,EAAE,SAAS,EAAE,EAAE,EAAE,MAAM,EAAE,OAAO,CAAC,MAAM;YACtE,GAAG,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,EAAC,MAAM,EAAE,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,EAAC,CAAC,CAAC,CAAC,EAAE,CAAC;YACvE,KAAK,EAAE,OAAO,CAAC,KAAK,CAAC,GAAG,CAAC,EAAE,CAAC,EAAE,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,EAAC,CAAC;IAC5D,CAAC;IAED,KAAK,CAAC,MAAM,CAAC,EAAU;QACrB,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,EAAE,CAAC,CAAC;QACjC,OAAO,IAAI,CAAC,OAAO,CAAC,OAAO,EAAE,KAAK,IAAI,EAAE;YACtC,MAAM,IAAI,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;YACpE,IAAI,CAAC,IAAI,IAAI,IAAI,CAAC,KAAK,KAAK,QAAQ;gBAAE,MAAM,IAAI,UAAU,CAAC,YAAY,EAAE,4CAA4C,CAAC,CAAC;YACvH,IAAI,IAAI,CAAC,eAAe,IAAI,IAAI,CAAC,WAAW;gBAAE,MAAM,IAAI,UAAU,CAAC,eAAe,EAAE,kEAAkE,CAAC,CAAC;YACxJ,IAAI,CAAC,QAAQ,GAAG,KAAK,CAAC;YAAC,IAAI,CAAC,KAAK,GAAG,SAAS,CAAC;YAAC,IAAI,CAAC,QAAQ,GAAG,SAAS,CAAC;YAAC,IAAI,CAAC,UAAU,GAAG,SAAS,CAAC;YAAC,OAAO,CAAC,MAAM,GAAG,KAAK,CAAC;YAC9H,IAAI,CAAC,gBAAgB,GAAG,SAAS,CAAC;YAClC,KAAK,IAAI,CAAC,OAAO,CAAC,IAAI,EAAE,EAAE,EAAE,IAAI,CAAC,CAAC;YAClC,OAAO,EAAC,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,SAAS,EAAE,SAAS,EAAE,EAAE,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,EAAE,OAAO,EAAE,IAAI,EAAC,CAAC;QACzG,CAAC,CAAC,CAAC;IACL,CAAC;IAED,KAAK,CAAC,KAAK;QACT,MAAM,OAAO,CAAC,UAAU,CAAC,CAAC,GAAG,IAAI,CAAC,QAAQ,CAAC,MAAM,EAAE,CAAC,CAAC,GAAG,CAAC,KAAK,EAAC,OAAO,EAAC,EAAE,CAAC,CAAC,MAAM,OAAO,CAAC,MAAM,CAAC,EAAE,KAAK,EAAE,CAAC,CAAC,CAAC;IAC9G,CAAC;IAED,KAAK,CAAC,MAAM,CAAC,EAAU;QACrB,MAAM,IAAI,GAAG,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QAC3B,OAAO,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,SAAS,CAAC,EAAE,KAAK,IAAI,EAAE;YAC3D,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,IAAI,CAAC,eAAe;gBAAE,MAAM,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,WAAW,CAAC,CAAC;iBACjF,IAAI,IAAI,CAAC,KAAK,KAAK,QAAQ,EAAE,CAAC;gBACjC,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;gBAC7C,IAAI,OAAO,CAAC,MAAM,KAAK,IAAI,CAAC,EAAE,EAAE,CAAC;oBAAC,OAAO,CAAC,MAAM,GAAG,SAAS,CAAC;oBAAC,OAAO,CAAC,MAAM,GAAG,KAAK,CAAC;gBAAC,CAAC;YACzF,CAAC;YACD,OAAO,EAAC,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,WAAW,EAAE,MAAM,EAAE,EAAE,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,EAAC,CAAC;QACnG,CAAC,CAAC,CAAC;IACL,CAAC;IAEO,OAAO,CAAI,OAAgB,EAAE,SAA2B;QAC9D,OAAO,CAAC,QAAQ,EAAE,CAAC;QACnB,MAAM,MAAM,GAAG,OAAO,CAAC,QAAQ,CAAC,IAAI,CAAC,SAAS,EAAE,SAAS,CAAC,CAAC,OAAO,CAAC,GAAG,EAAE;YACtE,OAAO,CAAC,QAAQ,EAAE,CAAC;YACnB,IAAI,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;QACzB,CAAC,CAAC,CAAC;QACH,OAAO,CAAC,QAAQ,GAAG,MAAM,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,SAAS,CAAC,CAAC;QACjD,OAAO,MAAM,CAAC;IAChB,CAAC;IAEO,IAAI,CAAC,IAAU,EAAE,OAAoC;QAC3D,IAAI,IAAI,CAAC,WAAW;YAAE,OAAO,IAAI,CAAC,WAAW,CAAC;QAC9C,IAAI,CAAC,WAAW,GAAG,IAAI,CAAC,UAAU,CAAC,IAAI,EAAE,OAAO,CAAC,CAAC,OAAO,CAAC,GAAG,EAAE;YAC7D,IAAI,CAAC,WAAW,GAAG,SAAS,CAAC;YAC7B,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC;QAC9C,CAAC,CAAC,CAAC;QACH,OAAO,IAAI,CAAC,WAAW,CAAC;IAC1B,CAAC;IAEO,KAAK,CAAC,UAAU,CAAC,IAAU,EAAE,OAAoC;QACvE,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;QAC7C,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC;QACrB,OAAO,CAAC,KAAK,GAAG,OAAO,CAAC,KAAK,CAAC,MAAM,CAAC,EAAE,CAAC,EAAE,CAAC,EAAE,KAAK,IAAI,CAAC,EAAE,CAAC,CAAC;QAC3D,IAAI,CAAC;YACH,MAAM,KAAK,GAAG,CAAC,GAAG,IAAI,CAAC,QAAQ,CAAC,CAAC,GAAG,CAAC,EAAE,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,eAAe,CAAC,CAAC,GAAG,CAAC,KAAK,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,EAAE,WAAW,CAAC,CAAC,CAAC;YACvK,IAAI,IAAI,CAAC,YAAY,IAAI,OAAO,CAAC,MAAM;gBAAE,KAAK,CAAC,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,IAAI,CAAC,KAAK,EAAC,MAAM,EAAC,EAAE;oBACrF,MAAM,MAAM,CAAC,SAAS,EAAE,CAAC;oBAAC,IAAI,CAAC,YAAY,GAAG,KAAK,CAAC;gBACtD,CAAC,CAAC,CAAC,CAAC;YACJ,MAAM,QAAQ,GAAG,MAAM,OAAO,CAAC,UAAU,CAAC,KAAK,CAAC,CAAC;YACjD,IAAI,QAAQ,CAAC,IAAI,CAAC,OAAO,CAAC,EAAE,CAAC,OAAO,CAAC,MAAM,KAAK,UAAU,CAAC;gBAAE,MAAM,IAAI,KAAK,CAAC,0BAA0B,CAAC,CAAC;QAC3G,CAAC;QAAC,MAAM,CAAC;YACP,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;YAC3B,IAAI,CAAC,MAAM,CAAC,IAAI,EAAE,QAAQ,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC;YAAC,IAAI,CAAC,KAAK,GAAG,EAAC,IAAI,EAAC,eAAe,EAAE,OAAO,EAAC,kDAAkD,EAAC,CAAC;YAC5I,IAAI,CAAC,eAAe,GAAG,IAAI,CAAC;YAC5B,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC;YAAC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;YACzC,MAAM,IAAI,UAAU,CAAC,eAAe,EAAE,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;QAC5D,CAAC;QACD,IAAI,CAAC,YAAY,GAAG,KAAK,CAAC;QAAC,IAAI,CAAC,MAAM,CAAC,IAAI,EAAE,OAAO,CAAC,CAAC;QAAC,IAAI,CAAC,eAAe,GAAG,KAAK,CAAC;QAAC,IAAI,CAAC,KAAK,GAAG,SAAS,CAAC;QAC5G,IAAI,OAAO,CAAC,MAAM,KAAK,IAAI,CAAC,EAAE,EAAE,CAAC;YAAC,OAAO,CAAC,MAAM,GAAG,SAAS,CAAC;YAAC,OAAO,CAAC,MAAM,GAAG,KAAK,CAAC;QAAC,CAAC;QACvF,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;QAAC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;IACxC,CAAC;IAEO,KAAK,CAAC,OAAgB,EAAE,MAAc,EAAE,KAAK,GAAG,KAAK,EAAE,WAAoB;QACjF,MAAM,MAAM,GAAG,IAAI,CAAC,iBAAiB,CAAC,OAAO,EAAE,MAAM,EAAE,WAAW,EAAE,KAAK,CAAC,CAAC;QAC3E,MAAM,eAAe,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,SAAS,CAAC;QACpE,MAAM,IAAI,GAAS,EAAE,EAAE,EAAE,OAAO,UAAU,EAAE,EAAE,EAAE,SAAS,EAAE,OAAO,CAAC,EAAE,EAAE,MAAM,EAAE,KAAK,EAAE,cAAc,CAAC,MAAM,CAAC;YAC1G,QAAQ,EAAE,MAAM,EAAE,EAAE,EAAE,KAAK,EAAE,QAAQ,EAAE,SAAS,EAAE,EAAE,EAAE,QAAQ,EAAE,IAAI,GAAG,EAAE,EAAE,KAAK,EAAE,EAAE,EAAE,YAAY,EAAE,KAAK;YACzG,QAAQ,EAAE,KAAK,EAAE,SAAS,EAAE,IAAI,CAAC,GAAG,EAAE,EAAE,OAAO,EAAE,IAAI,GAAG,EAAE,EAAE,CAAC;QAC/D,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,EAAE,IAAI,CAAC,CAAC;QAC9B,MAAM,EAAE,QAAQ,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QAC9B,IAAI,KAAK;YAAE,OAAO,CAAC,KAAK,CAAC,OAAO,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;;YAAM,OAAO,CAAC,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;QAC5E,IAAI,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;QACvB,OAAO,EAAC,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,SAAS,EAAE,SAAS,EAAE,OAAO,CAAC,EAAE,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK;YAC5F,GAAG,CAAC,eAAe,CAAC,CAAC,CAAC,EAAC,MAAM,EAAE,IAAI,EAAE,eAAe,EAAC,CAAC,CAAC,CAAC,EAAE,CAAC,EAAC,CAAC;IACjE,CAAC;IAEO,iBAAiB,CAAC,OAA4B,EAAE,MAAc,EAAE,WAAoB,EAAE,WAAW,GAAG,KAAK;QAC/G,IAAI,OAAO,MAAM,KAAK,QAAQ,IAAI,CAAC,MAAM,CAAC,IAAI,EAAE,IAAI,MAAM,CAAC,UAAU,CAAC,MAAM,CAAC,GAAG,IAAI,GAAG,IAAI;YACzF,MAAM,IAAI,UAAU,CAAC,kBAAkB,EAAE,mDAAmD,CAAC,CAAC;QAChG,IAAI,CAAC,WAAW,IAAI,OAAO,IAAI,OAAO,CAAC,KAAK,CAAC,MAAM,IAAI,GAAG;YAAE,MAAM,IAAI,UAAU,CAAC,YAAY,EAAE,2CAA2C,CAAC,CAAC;QAC5I,MAAM,MAAM,GAAG,WAAW,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,CAAC,WAAW,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;QAC3F,IAAI,KAAK,GAAG,CAAC,EAAE,QAAQ,GAAG,MAAM,CAAC;QACjC,OAAO,QAAQ,EAAE,CAAC;YAChB,IAAI,QAAQ,CAAC,SAAS,KAAK,OAAO,EAAE,EAAE;gBAAE,MAAM,IAAI,UAAU,CAAC,gBAAgB,EAAE,qEAAqE,CAAC,CAAC;YACtJ,KAAK,EAAE,CAAC;YAAC,QAAQ,GAAG,QAAQ,CAAC,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;QACnF,CAAC;QACD,IAAI,KAAK,GAAG,CAAC;YAAE,MAAM,IAAI,UAAU,CAAC,kBAAkB,EAAE,gCAAgC,CAAC,CAAC;QAC1F,OAAO,MAAM,CAAC;IAChB,CAAC;IAEO,QAAQ,CAAC,OAAgB;QAC/B,IAAI,OAAO,CAAC,MAAM,IAAI,OAAO,CAAC,MAAM,IAAI,OAAO,CAAC,QAAQ;YAAE,OAAO;QACjE,MAAM,EAAE,GAAG,OAAO,CAAC,KAAK,CAAC,KAAK,EAAE,CAAC;QACjC,IAAI,CAAC,EAAE;YAAE,OAAO;QAChB,OAAO,CAAC,MAAM,GAAG,EAAE,CAAC;QACpB,KAAK,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,EAAE,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,MAAM,CAAC,CAAC;IACzD,CAAC;IAEO,KAAK,CAAC,OAAO,CAAC,IAAU,EAAE,MAAc,EAAE,UAAU,GAAG,KAAK;QAClE,MAAM,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;QAC7C,MAAM,YAAY,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;QAChC,IAAI,CAAC,YAAY,KAAK,YAAY,CAAC;QACnC,IAAI,CAAC,KAAK,CAAC,IAAI,EAAE,YAAY,CAAC,CAAC;QAC/B,IAAI,CAAC,KAAK,GAAG,SAAS,CAAC;QAAC,IAAI,CAAC,YAAY,GAAG,IAAI,CAAC;QACjD,IAAI,CAAC;YACH,OAAO,CAAC,MAAM,KAAK,IAAI,CAAC,OAAO,CAAC,EAAC,GAAG,OAAO,CAAC,KAAK,EAAE,SAAS,EAAE,OAAO,CAAC,EAAE,EAAE,KAAK,EAAE,OAAO,CAAC,KAAK,EAAC,CAAC,CAAC;YACjG,MAAM,MAAM,GAAG,MAAM,OAAO,CAAC,MAAM,CAAC;YACpC,IAAI,MAAM,CAAC,eAAe,EAAE,CAAC;gBAC3B,MAAM,OAAO,GAAG,gBAAgB,CAAC,MAAM,CAAC,eAAe,CAAC,CAAC;gBACzD,IAAI,OAAO,CAAC,OAAO,KAAK,OAAO,EAAE,CAAC;oBAAC,OAAO,CAAC,OAAO,GAAG,OAAO,CAAC;oBAAC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;gBAAC,CAAC;YACnF,CAAC;YACD,IAAI,IAAI,CAAC,QAAQ;gBAAE,OAAO;YAC1B,MAAM,IAAI,GAAG,UAAU,CAAC,CAAC,CAAC,MAAM,MAAM,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC,MAAM,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;YAC5E,IAAI,IAAI,CAAC,QAAQ;gBAAE,OAAO;YAC1B,IAAI,MAAM,CAAC,UAAU,CAAC,IAAI,CAAC,GAAG,IAAI,GAAG,IAAI;gBAAE,MAAM,IAAI,UAAU,CAAC,kBAAkB,EAAE,6BAA6B,CAAC,CAAC;YACnH,IAAI,CAAC,YAAY,GAAG,KAAK,CAAC;YAC1B,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,WAAW,CAAC;YAC1D,MAAM,WAAW,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;YAC/B,IAAI,IAAI,CAAC,KAAK,KAAK,WAAW;gBAAE,IAAI,CAAC,MAAM,CAAC,IAAI,EAAE,WAAW,EAAE,WAAW,CAAC,CAAC;;gBACvE,IAAI,CAAC,KAAK,CAAC,IAAI,EAAE,WAAW,CAAC,CAAC;YACnC,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,EAAC,OAAO,EAAE,CAAC,EAAE,IAAI,EAAE,UAAU,EAAE,SAAS,EAAE,OAAO,CAAC,EAAE,EAAE,MAAM,EAAE,IAAI,CAAC,EAAE;gBACvF,UAAU,EAAE,OAAO,UAAU,EAAE,EAAE,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,EAAE,IAAI,EAAC,CAAC,CAAC;YAC/D,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;YAClB,IAAI,IAAI,CAAC,KAAK,KAAK,WAAW,EAAE,CAAC;gBAC/B,OAAO,CAAC,MAAM,GAAG,SAAS,CAAC;gBAC3B,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;gBACnB,IAAI,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;YACzB,CAAC;;gBAAM,IAAI,CAAC,cAAc,CAAC,IAAI,CAAC,CAAC;QACnC,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,IAAI,IAAI,CAAC,QAAQ;gBAAE,OAAO;YAC1B,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;YAC3B,IAAI,CAAC,YAAY,GAAG,KAAK,CAAC;YAC1B,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC;YACrB,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,UAAU,CAAC,CAAC,GAAG,IAAI,CAAC,QAAQ,CAAC,CAAC,GAAG,CAAC,EAAE,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,EAAE,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,eAAe,CAAC,CAAC,GAAG,CAAC,KAAK,CAAC,EAAE,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,EAAE,WAAW,CAAC,CAAC,CAAC,CAAC;YACnM,IAAI,CAAC,eAAe,GAAG,OAAO,CAAC,IAAI,CAAC,MAAM,CAAC,EAAE,CAAC,MAAM,CAAC,MAAM,KAAK,UAAU,CAAC,CAAC;YAC5E,IAAI,CAAC,MAAM,CAAC,IAAI,EAAE,QAAQ,EAAE,IAAI,CAAC,QAAQ,EAAE,IAAI,CAAC,GAAG,EAAE,CAAC,CAAC;YAAC,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC,eAAe;gBACvF,CAAC,CAAC,EAAC,IAAI,EAAC,eAAe,EAAE,OAAO,EAAC,sDAAsD,EAAC,CAAC,CAAC,CAAC,SAAS,CAAC,KAAK,CAAC,CAAC;YAC9G,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC;YAAC,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;YAAC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;QAC/D,CAAC;IACH,CAAC;IAEO,OAAO,CAAC,IAAU;QACxB,OAAO,IAAI,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC,QAAQ,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,KAAK,CAAC,IAAI,IAAI,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC,eAAe,CAAC,CAAC;IACjI,CAAC;IAEO,OAAO,CAAC,KAAW;QACzB,IAAI,CAAC,KAAK,CAAC,QAAQ,IAAI,KAAK,CAAC,eAAe;YAAE,OAAO;QACrD,MAAM,MAAM,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC;QACzC,IAAI,MAAM,CAAC,QAAQ,IAAI,QAAQ,CAAC,MAAM,CAAC,KAAK,CAAC;YAAE,OAAO;QACtD,MAAM,CAAC,KAAK,CAAC,IAAI,CAAC,EAAC,MAAM,EAAE,KAAK,CAAC,EAAE,EAAE,KAAK,EAAE,KAAK,CAAC,KAAK;YACrD,IAAI,EAAE,KAAK,CAAC,KAAK,EAAE,OAAO,IAAI,KAAK,CAAC,SAAS,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,EAAE,IAAI,IAAI,KAAK,CAAC,KAAK,EAAC,CAAC,CAAC;QAC9E,2FAA2F;QAC3F,YAAY,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,cAAc,CAAC,MAAM,CAAC,CAAC,CAAC;IAClD,CAAC;IAEO,cAAc,CAAC,IAAU;QAC/B,IAAI,IAAI,CAAC,YAAY,IAAI,IAAI,CAAC,QAAQ,IAAI,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,MAAM;YAAE,OAAO;QAC7F,MAAM,OAAO,GAAG,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;QACrC,MAAM,MAAM,GAAG,wDAAwD;YACrE,OAAO,CAAC,GAAG,CAAC,MAAM,CAAC,EAAE,CAAC,GAAG,MAAM,CAAC,MAAM,KAAK,MAAM,CAAC,KAAK,OAAO,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;QAC5F,KAAK,IAAI,CAAC,OAAO,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;IAClC,CAAC;IAEO,KAAK,CAAC,IAAU,EAAE,EAAE,GAAG,IAAI,CAAC,GAAG,EAAE,IAAI,IAAI,CAAC,SAAS,GAAG,EAAE,CAAC,CAAC,CAAC;IAC3D,MAAM,CAAC,IAAU,IAAI,KAAK,MAAM,OAAO,IAAI,IAAI,CAAC,OAAO;QAAE,OAAO,EAAE,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC;IAC3F,IAAI,CAAC,EAAU,IAAI,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI;QAAE,MAAM,IAAI,UAAU,CAAC,cAAc,EAAE,0CAA0C,CAAC,CAAC,CAAC,OAAO,IAAI,CAAC,CAAC,CAAC;IAC/J,OAAO,CAAC,EAAU,IAAI,MAAM,OAAO,GAAG,IAAI,CAAC,QAAQ,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,OAAO;QAAE,MAAM,IAAI,UAAU,CAAC,iBAAiB,EAAE,6CAA6C,CAAC,CAAC,CAAC,OAAO,OAAO,CAAC,CAAC,CAAC;CAC7L","sourcesContent":["import { randomUUID } from 'node:crypto';\nimport { waitForChange } from './observation.js';\nimport { AgentError, errorInfo } from '../errors.js';\nimport { terminal, type DriverFactory, type Observation, type Receipt, type Session, type SessionInput, type Task, type Delivery } from './types.js';\nimport { dashboardHarness, dashboardTitle, type DashboardSnapshot } from './dashboard.js';\nimport { resolveDashboardWorkspace } from './dashboard-workspace.js';\n\nexport class Coordinator {\n private sessions = new Map<string, Session>();\n private tasks = new Map<string, Task>();\n private dashboardHistory?: Task[];\n constructor(private readonly factory: DriverFactory, private readonly now: () => number = Date.now) {}\n\n parentContext(token: string) {\n const session = [...this.sessions.values()].find(session => session.token === token);\n const task = session?.active ? this.task(session.active) : undefined;\n if (!session || !task || task.stopping || terminal(task.state))\n throw new AgentError('INVALID_PARENT', 'The parent context is no longer active.');\n return {taskId: task.id, reference: session.input.reference, cwd: session.input.cwd};\n }\n\n run(input: SessionInput): Receipt {\n this.validateAdmission(undefined, input.prompt, input.parentToken);\n const selected = 'kind' in input.reference ? input.reference.harness.kind : undefined;\n const session: Session = { id: `ses_${randomUUID()}`, token: randomUUID(), input,\n tasks: [], paused: false, commands: Promise.resolve(), controls: 0, harness: dashboardHarness(selected),\n workspace: resolveDashboardWorkspace(input.cwd) };\n this.sessions.set(session.id, session);\n return this.admit(session, input.prompt, false, input.parentToken);\n }\n\n async send(id: string, prompt: string, delivery: Delivery, parentToken?: string): Promise<Receipt> {\n const session = this.session(id);\n const operation = async (): Promise<Receipt> => {\n if (!['queue', 'steer', 'interrupt'].includes(delivery)) throw new AgentError('INVALID_ARGUMENT', 'Unknown delivery mode.');\n this.validateAdmission(session, prompt, parentToken, delivery !== 'queue');\n if (delivery === 'queue') return this.admit(session, prompt, false, parentToken);\n const task = session.active ? this.task(session.active) : undefined;\n if (delivery === 'steer') {\n if (!task || terminal(task.state) || task.stopping) throw new AgentError('NO_ACTIVE_TASK', 'There is no active task accepting steering.');\n if (!task.nativeActive) {\n void this.execute(task, prompt);\n return {version: 1, type: 'accepted', sessionId: id, taskId: task.id, delivery: 'steer'};\n }\n try {\n await (await session.driver!).steer(prompt);\n this.touch(task);\n return {version: 1, type: 'accepted', sessionId: id, taskId: task.id, delivery: 'steer'};\n } catch (error) {\n if (!(error instanceof AgentError) || error.code !== 'UNSUPPORTED_DELIVERY') throw error;\n }\n }\n if (task && (!terminal(task.state) || task.stopUnconfirmed || task.state === 'failed')) await this.stop(task, 'interrupted');\n session.paused = false;\n const receipt = this.admit(session, prompt, true, parentToken);\n return {...receipt, requestedDelivery: delivery, delivery: 'interrupt'};\n };\n return this.command(session, operation);\n }\n\n async observe(id: string, after?: string, readerToken?: string, signal?: AbortSignal): Promise<Observation> {\n const task = this.task(id);\n const position = after ? task.responses.findIndex(response => response.responseId === after) : -1;\n if (after && position === -1) throw new AgentError('UNKNOWN_RESPONSE', 'The response does not belong to this task.');\n for (;;) {\n const response = task.responses[position + 1];\n if (response) {\n if (terminal(response.state)) this.acknowledge(task, readerToken);\n return response;\n }\n if (terminal(task.state)) {\n this.acknowledge(task, readerToken);\n return { version: 1, type: 'terminal', taskId: id,\n sessionId: task.sessionId, state: task.state, ...(task.error ? {error:task.error} : {}) };\n }\n await waitForChange(task.changed, signal);\n }\n }\n\n private acknowledge(task: Task, readerToken?: string) {\n if (!readerToken || !task.parentId || task.stopUnconfirmed) return;\n const parent = this.task(task.parentId);\n if (this.session(parent.sessionId).token === readerToken && parent.nativeActive)\n parent.inbox = parent.inbox.filter(result => result.taskId !== task.id);\n }\n\n status(id: string, full = false) {\n const task = this.task(id), response = task.responses.at(-1);\n return { version: 1, type: 'status', taskId: id, sessionId: task.sessionId, state: task.state,\n ...(task.error ? {error: task.error} : {}), ...(response ? { response: {\n responseId: response.responseId, text: full ? response.text : response.text.slice(0, 4000),\n truncated: !full && response.text.length > 4000 }} : {}) };\n }\n\n async dashboard(): Promise<DashboardSnapshot> {\n // New sessions join the next snapshot; every serialized row has resolved context.\n const admitted = [...this.sessions.values()];\n const workspaces = new Map(await Promise.all(admitted.map(async session =>\n [session.id, await session.workspace] as const)));\n const current: Task[] = [];\n for (const session of admitted) {\n const id = session.active ?? session.tasks[0];\n if (!id) continue;\n const task = this.task(id);\n if (task.state === 'failed' || !terminal(task.state)) current.push(task);\n }\n // Map insertion order records admission order; stable sorting preserves its reversed ties.\n this.dashboardHistory ??= [...this.tasks.values()].reverse().filter(task => terminal(task.state))\n .sort((first, second) => second.finishedAt! - first.finishedAt!);\n const visible = new Set(current.map(task => task.id));\n const tasks = [...current, ...this.dashboardHistory.filter(task => workspaces.has(task.sessionId) && !visible.has(task.id))];\n const sessions = tasks.map(task => ({sessionId: task.sessionId, taskId: task.id,\n harness: this.session(task.sessionId).harness, title: task.title, state: task.state,\n workspace: workspaces.get(task.sessionId)!, updatedAt: task.updatedAt,\n ...(task.dispatchedAt === undefined ? {} : {dispatchedAt: task.dispatchedAt}),\n ...(task.failedAt === undefined ? {} : {failedAt: task.failedAt}),\n ...(task.finishedAt === undefined ? {} : {finishedAt: task.finishedAt})}));\n return {version: 1, type: 'dashboard', history: true, grouping: true, sessions};\n }\n\n private finish(task: Task, state: 'completed' | 'failed' | 'cancelled' | 'interrupted', at = this.now(), updatedAt = at) {\n task.state = state;\n task.finishedAt = at;\n task.updatedAt = updatedAt;\n this.dashboardHistory = undefined;\n }\n\n queue(id: string) {\n const session = this.session(id);\n const summary = (task: Task) => ({taskId: task.id, state: task.state, description: task.prompt.slice(0, 120)});\n return {version: 1, type: 'queue', sessionId: id, paused: session.paused,\n ...(session.active ? {active: summary(this.task(session.active))} : {}),\n tasks: session.tasks.map(id => summary(this.task(id)))};\n }\n\n async resume(id: string): Promise<Receipt> {\n const session = this.session(id);\n return this.command(session, async () => {\n const task = session.active ? this.task(session.active) : undefined;\n if (!task || task.state !== 'failed') throw new AgentError('NOT_FAILED', 'This session has no failed task to resume.');\n if (task.stopUnconfirmed || task.stopPromise) throw new AgentError('CANCEL_FAILED', 'Confirm cancellation of the affected executions before recovery.');\n task.stopping = false; task.error = undefined; task.failedAt = undefined; task.finishedAt = undefined; session.paused = false;\n this.dashboardHistory = undefined;\n void this.execute(task, '', true);\n return {version: 1, type: 'started', sessionId: id, taskId: task.id, state: task.state, resumed: true};\n });\n }\n\n async close() {\n await Promise.allSettled([...this.sessions.values()].map(async session => (await session.driver)?.close()));\n }\n\n async cancel(id: string): Promise<Receipt> {\n const task = this.task(id);\n return this.command(this.session(task.sessionId), async () => {\n if (!terminal(task.state) || task.stopUnconfirmed) await this.stop(task, 'cancelled');\n else if (task.state === 'failed') {\n const session = this.session(task.sessionId);\n if (session.active === task.id) { session.active = undefined; session.paused = false; }\n }\n return {version: 1, type: 'cancelled', taskId: id, sessionId: task.sessionId, state: task.state};\n });\n }\n\n private command<T>(session: Session, operation: () => Promise<T>): Promise<T> {\n session.controls++;\n const result = session.commands.then(operation, operation).finally(() => {\n session.controls--;\n this.dispatch(session);\n });\n session.commands = result.catch(() => undefined);\n return result;\n }\n\n private stop(task: Task, outcome: 'cancelled' | 'interrupted'): Promise<void> {\n if (task.stopPromise) return task.stopPromise;\n task.stopPromise = this.finishStop(task, outcome).finally(() => {\n task.stopPromise = undefined;\n this.dispatch(this.session(task.sessionId));\n });\n return task.stopPromise;\n }\n\n private async finishStop(task: Task, outcome: 'cancelled' | 'interrupted') {\n const session = this.session(task.sessionId);\n task.stopping = true;\n session.tasks = session.tasks.filter(id => id !== task.id);\n try {\n const stops = [...task.children].map(id => this.task(id)).filter(child => !terminal(child.state) || child.stopUnconfirmed).map(child => this.stop(child, 'cancelled'));\n if (task.nativeActive && session.driver) stops.push(session.driver.then(async driver => {\n await driver.interrupt(); task.nativeActive = false;\n }));\n const outcomes = await Promise.allSettled(stops);\n if (outcomes.some(outcome => outcome.status === 'rejected')) throw new Error('Cancellation unconfirmed');\n } catch {\n task.failedAt = this.now();\n this.finish(task, 'failed', task.failedAt); task.error = {code:'CANCEL_FAILED', message:'Native execution could not be confirmed stopped.'};\n task.stopUnconfirmed = true;\n session.paused = true; this.notify(task);\n throw new AgentError('CANCEL_FAILED', task.error.message);\n }\n task.nativeActive = false; this.finish(task, outcome); task.stopUnconfirmed = false; task.error = undefined;\n if (session.active === task.id) { session.active = undefined; session.paused = false; }\n this.notify(task); this.deliver(task);\n }\n\n private admit(session: Session, prompt: string, front = false, parentToken?: string): Receipt {\n const parent = this.validateAdmission(session, prompt, parentToken, front);\n const blockedByTaskId = session.paused ? session.active : undefined;\n const task: Task = { id: `tsk_${randomUUID()}`, sessionId: session.id, prompt, title: dashboardTitle(prompt),\n parentId: parent?.id, state: 'queued', responses: [], children: new Set(), inbox: [], nativeActive: false,\n stopping: false, updatedAt: this.now(), changed: new Set() };\n this.tasks.set(task.id, task);\n parent?.children.add(task.id);\n if (front) session.tasks.unshift(task.id); else session.tasks.push(task.id);\n this.dispatch(session);\n return {version: 1, type: 'started', sessionId: session.id, taskId: task.id, state: task.state,\n ...(blockedByTaskId ? {paused: true, blockedByTaskId} : {})};\n }\n\n private validateAdmission(session: Session | undefined, prompt: string, parentToken?: string, replacement = false) {\n if (typeof prompt !== 'string' || !prompt.trim() || Buffer.byteLength(prompt) > 1024 * 1024)\n throw new AgentError('INVALID_ARGUMENT', 'Prompt must contain text and cannot exceed 1 MiB.');\n if (!replacement && session && session.tasks.length >= 100) throw new AgentError('QUEUE_FULL', 'The session already has 100 queued tasks.');\n const parent = parentToken ? this.task(this.parentContext(parentToken).taskId) : undefined;\n let depth = 0, ancestor = parent;\n while (ancestor) {\n if (ancestor.sessionId === session?.id) throw new AgentError('INVALID_PARENT', 'A managed task cannot queue work in its own or an ancestor session.');\n depth++; ancestor = ancestor.parentId ? this.task(ancestor.parentId) : undefined;\n }\n if (depth > 8) throw new AgentError('DELEGATION_LIMIT', 'Maximum delegation depth is 8.');\n return parent;\n }\n\n private dispatch(session: Session) {\n if (session.active || session.paused || session.controls) return;\n const id = session.tasks.shift();\n if (!id) return;\n session.active = id;\n void this.execute(this.task(id), this.task(id).prompt);\n }\n\n private async execute(task: Task, prompt: string, recovering = false) {\n const session = this.session(task.sessionId);\n const dispatchedAt = this.now();\n task.dispatchedAt ??= dispatchedAt;\n this.touch(task, dispatchedAt);\n task.state = 'running'; task.nativeActive = true;\n try {\n session.driver ??= this.factory({...session.input, sessionId: session.id, token: session.token});\n const driver = await session.driver;\n if (driver.selectedHarness) {\n const harness = dashboardHarness(driver.selectedHarness);\n if (session.harness !== harness) { session.harness = harness; this.touch(task); }\n }\n if (task.stopping) return;\n const text = recovering ? await driver.resume() : await driver.turn(prompt);\n if (task.stopping) return;\n if (Buffer.byteLength(text) > 1024 * 1024) throw new AgentError('OUTPUT_TOO_LARGE', 'The response exceeds 1 MiB.');\n task.nativeActive = false;\n task.state = this.pending(task) ? 'waiting' : 'completed';\n const respondedAt = this.now();\n if (task.state === 'completed') this.finish(task, 'completed', respondedAt);\n else this.touch(task, respondedAt);\n task.responses.push({version: 1, type: 'response', sessionId: session.id, taskId: task.id,\n responseId: `rsp_${randomUUID()}`, state: task.state, text});\n this.notify(task);\n if (task.state === 'completed') {\n session.active = undefined;\n this.deliver(task);\n this.dispatch(session);\n } else this.continueParent(task);\n } catch (error) {\n if (task.stopping) return;\n task.failedAt = this.now();\n task.nativeActive = false;\n task.stopping = true;\n const stopped = await Promise.allSettled([...task.children].map(id => this.task(id)).filter(child => !terminal(child.state) || child.stopUnconfirmed).map(child => this.stop(child, 'cancelled')));\n task.stopUnconfirmed = stopped.some(result => result.status === 'rejected');\n this.finish(task, 'failed', task.failedAt, this.now()); task.error = task.stopUnconfirmed\n ? {code:'CANCEL_FAILED', message:'Descendant execution could not be confirmed stopped.'} : errorInfo(error);\n session.paused = true; this.notify(task); this.deliver(task);\n }\n }\n\n private pending(task: Task) {\n return task.inbox.length > 0 || [...task.children].some(id => !terminal(this.task(id).state) || this.task(id).stopUnconfirmed);\n }\n\n private deliver(child: Task) {\n if (!child.parentId || child.stopUnconfirmed) return;\n const parent = this.task(child.parentId);\n if (parent.stopping || terminal(parent.state)) return;\n parent.inbox.push({taskId: child.id, state: child.state,\n text: child.error?.message ?? child.responses.at(-1)?.text ?? child.state});\n // Let an attached child command acknowledge delivery through its native tool output first.\n setImmediate(() => this.continueParent(parent));\n }\n\n private continueParent(task: Task) {\n if (task.nativeActive || task.stopping || terminal(task.state) || !task.inbox.length) return;\n const results = task.inbox.splice(0);\n const prompt = 'Delegated task outcomes (continue the current task):\\n' +\n results.map(result => `${result.taskId} [${result.state}]:\\n${result.text}`).join('\\n\\n');\n void this.execute(task, prompt);\n }\n\n private touch(task: Task, at = this.now()) { task.updatedAt = at; }\n private notify(task: Task) { for (const resolve of task.changed) resolve(); task.changed.clear(); }\n private task(id: string) { const task = this.tasks.get(id); if (!task) throw new AgentError('UNKNOWN_TASK', 'Task is unavailable in this coordinator.'); return task; }\n private session(id: string) { const session = this.sessions.get(id); if (!session) throw new AgentError('UNKNOWN_SESSION', 'Session is unavailable in this coordinator.'); return session; }\n}\n"]}
@@ -1,28 +1,110 @@
1
- import { randomBytes } from 'node:crypto';
1
+ import { randomBytes, randomUUID } from 'node:crypto';
2
2
  import { join, resolve } from 'node:path';
3
3
  import { writeFile, rename, unlink } from 'node:fs/promises';
4
4
  import { Coordinator } from './coordinator.js';
5
5
  import { createWorker } from './worker-client.js';
6
6
  import { startService } from './service.js';
7
- import { privateDirectory, stateDirectory } from './state.js';
7
+ import { acquireStartupOwnership } from './startup-lock.js';
8
+ import { privateDirectory, readEndpoint, stateDirectory } from './state.js';
9
+ import { isStartupRetirementRequest } from './startup-protocol.js';
8
10
  const directory = resolve(stateDirectory());
9
11
  await privateDirectory(directory);
10
- const engine = new Coordinator(input => createWorker({ ...input, env: { ...input.env, AGENT_STATE_DIR: directory } }));
11
- const token = randomBytes(32).toString('hex');
12
- const service = await startService(engine, token);
13
- const endpointFile = join(directory, 'coordinator.json');
14
- const temporary = endpointFile + `.${process.pid}`;
15
- await writeFile(temporary, JSON.stringify({ url: service.url, token, pid: process.pid }), { mode: 0o600 });
16
- await rename(temporary, endpointFile);
17
- let closing = false;
18
- async function close() {
19
- if (closing)
12
+ const requestedTimeout = Number(process.argv[2]);
13
+ const lockTimeout = Number.isSafeInteger(requestedTimeout) && requestedTimeout >= 0 ? requestedTimeout : 15_000;
14
+ let service;
15
+ let outcome;
16
+ let retirementRequested = false;
17
+ process.on('message', message => {
18
+ if (!isStartupRetirementRequest(message))
20
19
  return;
21
- closing = true;
22
- await service.close();
23
- await unlink(endpointFile).catch(() => { });
24
- process.exit();
20
+ retirementRequested = true;
21
+ if (outcome)
22
+ void report(outcome);
23
+ });
24
+ async function startCandidate() {
25
+ let ownership;
26
+ let temporary;
27
+ try {
28
+ ownership = acquireStartupOwnership(directory, lockTimeout);
29
+ if (retirementRequested || await readEndpoint(directory))
30
+ return { version: 1, type: 'startup-outcome', state: 'retired' };
31
+ const engine = new Coordinator(input => createWorker({ ...input, env: { ...input.env, AGENT_STATE_DIR: directory } }));
32
+ const token = randomBytes(32).toString('hex');
33
+ const instanceId = randomUUID();
34
+ service = await startService(engine, token, instanceId);
35
+ if (retirementRequested) {
36
+ await closeUnpublished();
37
+ return { version: 1, type: 'startup-outcome', state: 'retired' };
38
+ }
39
+ const endpointFile = join(directory, 'coordinator.json');
40
+ temporary = endpointFile + `.${process.pid}`;
41
+ const endpoint = { url: service.url, token, pid: process.pid, instanceId };
42
+ await writeFile(temporary, JSON.stringify(endpoint), { mode: 0o600 });
43
+ if (retirementRequested) {
44
+ await unlink(temporary).catch(() => { });
45
+ await closeUnpublished();
46
+ return { version: 1, type: 'startup-outcome', state: 'retired' };
47
+ }
48
+ // A retirement request received while rename is in flight must observe publication.
49
+ await rename(temporary, endpointFile);
50
+ temporary = undefined;
51
+ return { version: 1, type: 'startup-outcome', state: 'published', endpoint };
52
+ }
53
+ catch (error) {
54
+ if (temporary)
55
+ await unlink(temporary).catch(() => { });
56
+ await closeUnpublished();
57
+ throw error;
58
+ }
59
+ finally {
60
+ ownership?.release();
61
+ }
62
+ }
63
+ async function closeUnpublished() {
64
+ if (!service)
65
+ return;
66
+ const active = service;
67
+ service = undefined;
68
+ await active.close();
69
+ }
70
+ async function report(message) {
71
+ if (!process.send || !process.connected)
72
+ return;
73
+ await new Promise(resolveMessage => {
74
+ try {
75
+ process.send(message, () => resolveMessage());
76
+ }
77
+ catch {
78
+ resolveMessage();
79
+ }
80
+ });
81
+ }
82
+ let startupError;
83
+ try {
84
+ outcome = await startCandidate();
85
+ }
86
+ catch (error) {
87
+ startupError = error;
88
+ outcome = { version: 1, type: 'startup-outcome', state: 'retired' };
89
+ }
90
+ await report(outcome);
91
+ if (outcome.state === 'retired') {
92
+ if (process.connected)
93
+ process.disconnect?.();
94
+ if (startupError)
95
+ throw startupError;
96
+ }
97
+ else if (service) {
98
+ const activeService = service;
99
+ let closing = false;
100
+ async function close() {
101
+ if (closing)
102
+ return;
103
+ closing = true;
104
+ await activeService.close();
105
+ process.exit();
106
+ }
107
+ process.on('SIGTERM', () => void close());
108
+ process.on('SIGINT', () => void close());
25
109
  }
26
- process.on('SIGTERM', () => void close());
27
- process.on('SIGINT', () => void close());
28
110
  //# sourceMappingURL=daemon.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"daemon.js","sourceRoot":"","sources":["../../src/runtime/daemon.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAE,MAAM,aAAa,CAAC;AAC1C,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAC1C,OAAO,EAAE,SAAS,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,kBAAkB,CAAC;AAC7D,OAAO,EAAE,WAAW,EAAE,MAAM,kBAAkB,CAAC;AAC/C,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,YAAY,EAAE,MAAM,cAAc,CAAC;AAC5C,OAAO,EAAE,gBAAgB,EAAE,cAAc,EAAE,MAAM,YAAY,CAAC;AAE9D,MAAM,SAAS,GAAG,OAAO,CAAC,cAAc,EAAE,CAAC,CAAC;AAC5C,MAAM,gBAAgB,CAAC,SAAS,CAAC,CAAC;AAClC,MAAM,MAAM,GAAG,IAAI,WAAW,CAAC,KAAK,CAAC,EAAE,CAAC,YAAY,CAAC,EAAC,GAAG,KAAK,EAAC,GAAG,EAAC,EAAC,GAAG,KAAK,CAAC,GAAG,EAAC,eAAe,EAAC,SAAS,EAAC,EAAC,CAAC,CAAC,CAAC;AAC/G,MAAM,KAAK,GAAG,WAAW,CAAC,EAAE,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC;AAC9C,MAAM,OAAO,GAAG,MAAM,YAAY,CAAC,MAAM,EAAC,KAAK,CAAC,CAAC;AACjD,MAAM,YAAY,GAAG,IAAI,CAAC,SAAS,EAAC,kBAAkB,CAAC,CAAC;AACxD,MAAM,SAAS,GAAG,YAAY,GAAG,IAAI,OAAO,CAAC,GAAG,EAAE,CAAC;AACnD,MAAM,SAAS,CAAC,SAAS,EAAE,IAAI,CAAC,SAAS,CAAC,EAAC,GAAG,EAAC,OAAO,CAAC,GAAG,EAAC,KAAK,EAAC,GAAG,EAAC,OAAO,CAAC,GAAG,EAAC,CAAC,EAAC,EAAC,IAAI,EAAC,KAAK,EAAC,CAAC,CAAC;AACjG,MAAM,MAAM,CAAC,SAAS,EAAC,YAAY,CAAC,CAAC;AACrC,IAAI,OAAO,GAAG,KAAK,CAAC;AACpB,KAAK,UAAU,KAAK;IAClB,IAAI,OAAO;QAAE,OAAO;IAAC,OAAO,GAAG,IAAI,CAAC;IACpC,MAAM,OAAO,CAAC,KAAK,EAAE,CAAC;IACtB,MAAM,MAAM,CAAC,YAAY,CAAC,CAAC,KAAK,CAAC,GAAG,EAAE,GAAE,CAAC,CAAC,CAAC;IAC3C,OAAO,CAAC,IAAI,EAAE,CAAC;AACjB,CAAC;AACD,OAAO,CAAC,EAAE,CAAC,SAAS,EAAC,GAAE,EAAE,CAAA,KAAK,KAAK,EAAE,CAAC,CAAC;AACvC,OAAO,CAAC,EAAE,CAAC,QAAQ,EAAC,GAAE,EAAE,CAAA,KAAK,KAAK,EAAE,CAAC,CAAC","sourcesContent":["import { randomBytes } from 'node:crypto';\nimport { join, resolve } from 'node:path';\nimport { writeFile, rename, unlink } from 'node:fs/promises';\nimport { Coordinator } from './coordinator.js';\nimport { createWorker } from './worker-client.js';\nimport { startService } from './service.js';\nimport { privateDirectory, stateDirectory } from './state.js';\n\nconst directory = resolve(stateDirectory());\nawait privateDirectory(directory);\nconst engine = new Coordinator(input => createWorker({...input,env:{...input.env,AGENT_STATE_DIR:directory}}));\nconst token = randomBytes(32).toString('hex');\nconst service = await startService(engine,token);\nconst endpointFile = join(directory,'coordinator.json');\nconst temporary = endpointFile + `.${process.pid}`;\nawait writeFile(temporary, JSON.stringify({url:service.url,token,pid:process.pid}),{mode:0o600});\nawait rename(temporary,endpointFile);\nlet closing = false;\nasync function close() {\n if (closing) return; closing = true;\n await service.close();\n await unlink(endpointFile).catch(() => {});\n process.exit();\n}\nprocess.on('SIGTERM',()=>void close());\nprocess.on('SIGINT',()=>void close());\n"]}
1
+ {"version":3,"file":"daemon.js","sourceRoot":"","sources":["../../src/runtime/daemon.ts"],"names":[],"mappings":"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","sourcesContent":["import { randomBytes, randomUUID } from 'node:crypto';\nimport { join, resolve } from 'node:path';\nimport { writeFile, rename, unlink } from 'node:fs/promises';\nimport { Coordinator } from './coordinator.js';\nimport { createWorker } from './worker-client.js';\nimport { startService } from './service.js';\nimport { acquireStartupOwnership } from './startup-lock.js';\nimport { privateDirectory, readEndpoint, stateDirectory } from './state.js';\nimport { isStartupRetirementRequest, type StartupOutcome } from './startup-protocol.js';\n\nconst directory = resolve(stateDirectory());\nawait privateDirectory(directory);\nconst requestedTimeout = Number(process.argv[2]);\nconst lockTimeout = Number.isSafeInteger(requestedTimeout) && requestedTimeout >= 0 ? requestedTimeout : 15_000;\nlet service: Awaited<ReturnType<typeof startService>> | undefined;\nlet outcome: StartupOutcome | undefined;\nlet retirementRequested = false;\nprocess.on('message',message => {\n if (!isStartupRetirementRequest(message)) return;\n retirementRequested = true;\n if (outcome) void report(outcome);\n});\n\nasync function startCandidate(): Promise<StartupOutcome> {\n let ownership: ReturnType<typeof acquireStartupOwnership> | undefined;\n let temporary: string | undefined;\n try {\n ownership = acquireStartupOwnership(directory,lockTimeout);\n if (retirementRequested || await readEndpoint(directory))\n return {version:1,type:'startup-outcome',state:'retired'};\n const engine = new Coordinator(input => createWorker({...input,env:{...input.env,AGENT_STATE_DIR:directory}}));\n const token = randomBytes(32).toString('hex');\n const instanceId = randomUUID();\n service = await startService(engine,token,instanceId);\n if (retirementRequested) {\n await closeUnpublished();\n return {version:1,type:'startup-outcome',state:'retired'};\n }\n const endpointFile = join(directory,'coordinator.json');\n temporary = endpointFile + `.${process.pid}`;\n const endpoint = {url:service.url,token,pid:process.pid,instanceId};\n await writeFile(temporary,JSON.stringify(endpoint),{mode:0o600});\n if (retirementRequested) {\n await unlink(temporary).catch(()=>{});\n await closeUnpublished();\n return {version:1,type:'startup-outcome',state:'retired'};\n }\n // A retirement request received while rename is in flight must observe publication.\n await rename(temporary,endpointFile);\n temporary = undefined;\n return {version:1,type:'startup-outcome',state:'published',endpoint};\n } catch (error) {\n if (temporary) await unlink(temporary).catch(()=>{});\n await closeUnpublished();\n throw error;\n } finally {\n ownership?.release();\n }\n}\n\nasync function closeUnpublished() {\n if (!service) return;\n const active = service;\n service = undefined;\n await active.close();\n}\n\nasync function report(message: StartupOutcome) {\n if (!process.send || !process.connected) return;\n await new Promise<void>(resolveMessage => {\n try { process.send!(message,()=>resolveMessage()); }\n catch { resolveMessage(); }\n });\n}\n\nlet startupError: unknown;\ntry { outcome = await startCandidate(); }\ncatch (error) {\n startupError = error;\n outcome = {version:1,type:'startup-outcome',state:'retired'};\n}\nawait report(outcome);\n\nif (outcome.state === 'retired') {\n if (process.connected) process.disconnect?.();\n if (startupError) throw startupError;\n} else if (service) {\n const activeService = service;\n let closing = false;\n async function close() {\n if (closing) return; closing = true;\n await activeService.close();\n process.exit();\n }\n process.on('SIGTERM',()=>void close());\n process.on('SIGINT',()=>void close());\n}\n"]}
@@ -0,0 +1,2 @@
1
+ import type { DashboardWorkspace } from './dashboard.js';
2
+ export declare function resolveDashboardWorkspace(cwd: string): Promise<DashboardWorkspace>;
@@ -0,0 +1,38 @@
1
+ import { execFile } from 'node:child_process';
2
+ import { realpath } from 'node:fs/promises';
3
+ import { basename, dirname, resolve } from 'node:path';
4
+ import { promisify } from 'node:util';
5
+ const execute = promisify(execFile);
6
+ const discoveryTimeout = 2_000;
7
+ async function canonical(path) {
8
+ try {
9
+ return await realpath(path);
10
+ }
11
+ catch {
12
+ return resolve(path);
13
+ }
14
+ }
15
+ function gitEnvironment() {
16
+ return Object.fromEntries(Object.entries(process.env).filter(([name]) => !name.startsWith('GIT_')));
17
+ }
18
+ export async function resolveDashboardWorkspace(cwd) {
19
+ const fallback = await canonical(cwd);
20
+ try {
21
+ const env = gitEnvironment();
22
+ // Separate results preserve newlines and trailing whitespace inside directory names.
23
+ const [checkoutOutput, commonOutput] = await Promise.all(['--show-toplevel', '--git-common-dir'].map(async (field) => {
24
+ const { stdout } = await execute('git', ['-C', fallback, 'rev-parse', '--path-format=absolute', field], { env, timeout: discoveryTimeout, maxBuffer: 64 * 1024, windowsHide: true });
25
+ return stdout.endsWith('\n') ? stdout.slice(0, -1) : stdout;
26
+ }));
27
+ if (!checkoutOutput || !commonOutput)
28
+ return { directory: fallback };
29
+ const directory = await canonical(checkoutOutput);
30
+ const common = await canonical(commonOutput);
31
+ const repository = basename(common) === '.git' ? dirname(common) : common;
32
+ return { directory, repository };
33
+ }
34
+ catch {
35
+ return { directory: fallback };
36
+ }
37
+ }
38
+ //# sourceMappingURL=dashboard-workspace.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dashboard-workspace.js","sourceRoot":"","sources":["../../src/runtime/dashboard-workspace.ts"],"names":[],"mappings":"AAAA,OAAO,EAAC,QAAQ,EAAC,MAAM,oBAAoB,CAAC;AAC5C,OAAO,EAAC,QAAQ,EAAC,MAAM,kBAAkB,CAAC;AAC1C,OAAO,EAAC,QAAQ,EAAE,OAAO,EAAE,OAAO,EAAC,MAAM,WAAW,CAAC;AACrD,OAAO,EAAC,SAAS,EAAC,MAAM,WAAW,CAAC;AAGpC,MAAM,OAAO,GAAG,SAAS,CAAC,QAAQ,CAAC,CAAC;AACpC,MAAM,gBAAgB,GAAG,KAAK,CAAC;AAE/B,KAAK,UAAU,SAAS,CAAC,IAAY;IACnC,IAAI,CAAC;QAAC,OAAO,MAAM,QAAQ,CAAC,IAAI,CAAC,CAAC;IAAC,CAAC;IACpC,MAAM,CAAC;QAAC,OAAO,OAAO,CAAC,IAAI,CAAC,CAAC;IAAC,CAAC;AACjC,CAAC;AAED,SAAS,cAAc;IACrB,OAAO,MAAM,CAAC,WAAW,CAAC,MAAM,CAAC,OAAO,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC,EAAE,EAAE,CAAC,CAAC,IAAI,CAAC,UAAU,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC;AACtG,CAAC;AAED,MAAM,CAAC,KAAK,UAAU,yBAAyB,CAAC,GAAW;IACzD,MAAM,QAAQ,GAAG,MAAM,SAAS,CAAC,GAAG,CAAC,CAAC;IACtC,IAAI,CAAC;QACH,MAAM,GAAG,GAAG,cAAc,EAAE,CAAC;QAC7B,qFAAqF;QACrF,MAAM,CAAC,cAAc,EAAE,YAAY,CAAC,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC,CAAC,iBAAiB,EAAE,kBAAkB,CAAC,CAAC,GAAG,CAAC,KAAK,EAAC,KAAK,EAAC,EAAE;YACjH,MAAM,EAAC,MAAM,EAAC,GAAG,MAAM,OAAO,CAAC,KAAK,EAAE,CAAC,IAAI,EAAE,QAAQ,EAAE,WAAW,EAAE,wBAAwB,EAAE,KAAK,CAAC,EAClG,EAAC,GAAG,EAAE,OAAO,EAAE,gBAAgB,EAAE,SAAS,EAAE,EAAE,GAAG,IAAI,EAAE,WAAW,EAAE,IAAI,EAAC,CAAC,CAAC;YAC7E,OAAO,MAAM,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC;QAC9D,CAAC,CAAC,CAAC,CAAC;QACJ,IAAI,CAAC,cAAc,IAAI,CAAC,YAAY;YAAE,OAAO,EAAC,SAAS,EAAE,QAAQ,EAAC,CAAC;QACnE,MAAM,SAAS,GAAG,MAAM,SAAS,CAAC,cAAc,CAAC,CAAC;QAClD,MAAM,MAAM,GAAG,MAAM,SAAS,CAAC,YAAY,CAAC,CAAC;QAC7C,MAAM,UAAU,GAAG,QAAQ,CAAC,MAAM,CAAC,KAAK,MAAM,CAAC,CAAC,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC;QAC1E,OAAO,EAAC,SAAS,EAAE,UAAU,EAAC,CAAC;IACjC,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,EAAC,SAAS,EAAE,QAAQ,EAAC,CAAC;IAC/B,CAAC;AACH,CAAC","sourcesContent":["import {execFile} from 'node:child_process';\nimport {realpath} from 'node:fs/promises';\nimport {basename, dirname, resolve} from 'node:path';\nimport {promisify} from 'node:util';\nimport type {DashboardWorkspace} from './dashboard.js';\n\nconst execute = promisify(execFile);\nconst discoveryTimeout = 2_000;\n\nasync function canonical(path: string) {\n try { return await realpath(path); }\n catch { return resolve(path); }\n}\n\nfunction gitEnvironment(): NodeJS.ProcessEnv {\n return Object.fromEntries(Object.entries(process.env).filter(([name]) => !name.startsWith('GIT_')));\n}\n\nexport async function resolveDashboardWorkspace(cwd: string): Promise<DashboardWorkspace> {\n const fallback = await canonical(cwd);\n try {\n const env = gitEnvironment();\n // Separate results preserve newlines and trailing whitespace inside directory names.\n const [checkoutOutput, commonOutput] = await Promise.all(['--show-toplevel', '--git-common-dir'].map(async field => {\n const {stdout} = await execute('git', ['-C', fallback, 'rev-parse', '--path-format=absolute', field],\n {env, timeout: discoveryTimeout, maxBuffer: 64 * 1024, windowsHide: true});\n return stdout.endsWith('\\n') ? stdout.slice(0, -1) : stdout;\n }));\n if (!checkoutOutput || !commonOutput) return {directory: fallback};\n const directory = await canonical(checkoutOutput);\n const common = await canonical(commonOutput);\n const repository = basename(common) === '.git' ? dirname(common) : common;\n return {directory, repository};\n } catch {\n return {directory: fallback};\n }\n}\n"]}
@@ -0,0 +1,28 @@
1
+ import type { HarnessKind } from '../sdk/types.js';
2
+ import type { TaskState } from './types.js';
3
+ export type DashboardHarness = 'codex' | 'claude' | 'fx' | 'pending';
4
+ export interface DashboardWorkspace {
5
+ directory: string;
6
+ repository?: string;
7
+ }
8
+ export interface DashboardRow {
9
+ sessionId: string;
10
+ taskId: string;
11
+ harness: DashboardHarness;
12
+ title: string;
13
+ state: TaskState;
14
+ workspace: DashboardWorkspace;
15
+ updatedAt: number;
16
+ dispatchedAt?: number;
17
+ failedAt?: number;
18
+ finishedAt?: number;
19
+ }
20
+ export interface DashboardSnapshot {
21
+ version: 1;
22
+ type: 'dashboard';
23
+ history: true;
24
+ grouping: true;
25
+ sessions: DashboardRow[];
26
+ }
27
+ export declare function dashboardHarness(kind?: HarnessKind): DashboardHarness;
28
+ export declare function dashboardTitle(prompt: string): string;
@@ -0,0 +1,19 @@
1
+ import { stripVTControlCharacters } from 'node:util';
2
+ export function dashboardHarness(kind) {
3
+ if (kind === 'claudeCode')
4
+ return 'claude';
5
+ return kind ?? 'pending';
6
+ }
7
+ export function dashboardTitle(prompt) {
8
+ const plain = stripVTControlCharacters(prompt);
9
+ for (const line of plain.split(/\r\n?|\n/u)) {
10
+ const normalized = line
11
+ .replace(/[\u0000-\u0008\u000b\u000c\u000e-\u001f\u007f-\u009f]/gu, '')
12
+ .replace(/\s+/gu, ' ')
13
+ .trim();
14
+ if (normalized)
15
+ return [...normalized].slice(0, 120).join('');
16
+ }
17
+ return '(untitled)';
18
+ }
19
+ //# sourceMappingURL=dashboard.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"dashboard.js","sourceRoot":"","sources":["../../src/runtime/dashboard.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,wBAAwB,EAAE,MAAM,WAAW,CAAC;AAgCrD,MAAM,UAAU,gBAAgB,CAAC,IAAkB;IACjD,IAAI,IAAI,KAAK,YAAY;QAAE,OAAO,QAAQ,CAAC;IAC3C,OAAO,IAAI,IAAI,SAAS,CAAC;AAC3B,CAAC;AAED,MAAM,UAAU,cAAc,CAAC,MAAc;IAC3C,MAAM,KAAK,GAAG,wBAAwB,CAAC,MAAM,CAAC,CAAC;IAC/C,KAAK,MAAM,IAAI,IAAI,KAAK,CAAC,KAAK,CAAC,WAAW,CAAC,EAAE,CAAC;QAC5C,MAAM,UAAU,GAAG,IAAI;aACpB,OAAO,CAAC,yDAAyD,EAAE,EAAE,CAAC;aACtE,OAAO,CAAC,OAAO,EAAE,GAAG,CAAC;aACrB,IAAI,EAAE,CAAC;QACV,IAAI,UAAU;YAAE,OAAO,CAAC,GAAG,UAAU,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;IAChE,CAAC;IACD,OAAO,YAAY,CAAC;AACtB,CAAC","sourcesContent":["import { stripVTControlCharacters } from 'node:util';\nimport type { HarnessKind } from '../sdk/types.js';\nimport type { TaskState } from './types.js';\n\nexport type DashboardHarness = 'codex' | 'claude' | 'fx' | 'pending';\n\nexport interface DashboardWorkspace {\n directory: string;\n repository?: string;\n}\n\nexport interface DashboardRow {\n sessionId: string;\n taskId: string;\n harness: DashboardHarness;\n title: string;\n state: TaskState;\n workspace: DashboardWorkspace;\n updatedAt: number;\n dispatchedAt?: number;\n failedAt?: number;\n finishedAt?: number;\n}\n\nexport interface DashboardSnapshot {\n version: 1;\n type: 'dashboard';\n history: true;\n grouping: true;\n sessions: DashboardRow[];\n}\n\nexport function dashboardHarness(kind?: HarnessKind): DashboardHarness {\n if (kind === 'claudeCode') return 'claude';\n return kind ?? 'pending';\n}\n\nexport function dashboardTitle(prompt: string): string {\n const plain = stripVTControlCharacters(prompt);\n for (const line of plain.split(/\\r\\n?|\\n/u)) {\n const normalized = line\n .replace(/[\\u0000-\\u0008\\u000b\\u000c\\u000e-\\u001f\\u007f-\\u009f]/gu, '')\n .replace(/\\s+/gu, ' ')\n .trim();\n if (normalized) return [...normalized].slice(0, 120).join('');\n }\n return '(untitled)';\n}\n"]}
@@ -0,0 +1,4 @@
1
+ import type { ExecutionReference } from './types.js';
2
+ import type { NativeSession } from '../adapters/types.js';
3
+ export declare function closeStartupSession(open: () => Promise<NativeSession>): Promise<void>;
4
+ export declare function checkReadiness(reference: ExecutionReference, cwd: string, env: NodeJS.ProcessEnv): Promise<void>;