agent-relay-server 0.114.0 → 0.116.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.
Files changed (159) hide show
  1. package/docs/openapi.json +39 -1
  2. package/package.json +3 -3
  3. package/public/assets/MessageBubble-BJllE_2c.js +4 -0
  4. package/public/assets/MessageBubble-BJllE_2c.js.map +1 -0
  5. package/public/assets/PlanGraphPanel-CoK024n9.js +2 -0
  6. package/public/assets/PlanGraphPanel-CoK024n9.js.map +1 -0
  7. package/public/assets/{activity-Dw15HMdi.js → activity-CBjg7NSP.js} +2 -2
  8. package/public/assets/{activity-Dw15HMdi.js.map → activity-CBjg7NSP.js.map} +1 -1
  9. package/public/assets/{agent-profiles-DNtXbS77.js → agent-profiles-DzkjQaCS.js} +2 -2
  10. package/public/assets/{agent-profiles-DNtXbS77.js.map → agent-profiles-DzkjQaCS.js.map} +1 -1
  11. package/public/assets/agents-Bu1i1jH-.js +2 -0
  12. package/public/assets/{agents-DOwnLE42.js.map → agents-Bu1i1jH-.js.map} +1 -1
  13. package/public/assets/{analytics-CRwxJWuV.js → analytics-Cc2GoEq_.js} +3 -3
  14. package/public/assets/{analytics-CRwxJWuV.js.map → analytics-Cc2GoEq_.js.map} +1 -1
  15. package/public/assets/{automation-BQk8XQEj.js → automation-CcMveyvi.js} +2 -2
  16. package/public/assets/{automation-BQk8XQEj.js.map → automation-CcMveyvi.js.map} +1 -1
  17. package/public/assets/{badge-oaCc6hVH.js → badge-BhUZ1cAb.js} +2 -2
  18. package/public/assets/{badge-oaCc6hVH.js.map → badge-BhUZ1cAb.js.map} +1 -1
  19. package/public/assets/branch-state-badge-CYWBVZDI.js +2 -0
  20. package/public/assets/{branch-state-badge-JDaHO2fG.js.map → branch-state-badge-CYWBVZDI.js.map} +1 -1
  21. package/public/assets/{button-Cx0NiToX.js → button-C-V4oij1.js} +2 -2
  22. package/public/assets/{button-Cx0NiToX.js.map → button-C-V4oij1.js.map} +1 -1
  23. package/public/assets/{card-DkHdS68K.js → card-DAkf5Kzw.js} +2 -2
  24. package/public/assets/{card-DkHdS68K.js.map → card-DAkf5Kzw.js.map} +1 -1
  25. package/public/assets/{channels-wQha9YA6.js → channels-IdC7jyLt.js} +2 -2
  26. package/public/assets/{channels-wQha9YA6.js.map → channels-IdC7jyLt.js.map} +1 -1
  27. package/public/assets/chat-CP4x6Gcr.js +2 -0
  28. package/public/assets/{chat-BTmgzO_g.js.map → chat-CP4x6Gcr.js.map} +1 -1
  29. package/public/assets/{connectors-BF-XDm0s.js → connectors-Dngl_FJz.js} +2 -2
  30. package/public/assets/{connectors-BF-XDm0s.js.map → connectors-Dngl_FJz.js.map} +1 -1
  31. package/public/assets/{copy-button-CsCBPQzj.js → copy-button-BStzXgtd.js} +2 -2
  32. package/public/assets/{copy-button-CsCBPQzj.js.map → copy-button-BStzXgtd.js.map} +1 -1
  33. package/public/assets/{dist-BJnh7VkB.js → dist-CBMWGhWc.js} +2 -2
  34. package/public/assets/{dist-BJnh7VkB.js.map → dist-CBMWGhWc.js.map} +1 -1
  35. package/public/assets/{dist-Pak9TL_I.js → dist-CDZZxxJq.js} +2 -2
  36. package/public/assets/{dist-Pak9TL_I.js.map → dist-CDZZxxJq.js.map} +1 -1
  37. package/public/assets/{dist-AbnkNPcD.js → dist-CQ0Z-TDi.js} +2 -2
  38. package/public/assets/{dist-AbnkNPcD.js.map → dist-CQ0Z-TDi.js.map} +1 -1
  39. package/public/assets/{dist-REUlCFee.js → dist-ChDX_t12.js} +2 -2
  40. package/public/assets/{dist-REUlCFee.js.map → dist-ChDX_t12.js.map} +1 -1
  41. package/public/assets/{dist-DLOrqIs-.js → dist-CmFeEXMe.js} +2 -2
  42. package/public/assets/{dist-DLOrqIs-.js.map → dist-CmFeEXMe.js.map} +1 -1
  43. package/public/assets/{dist-DBti5--U.js → dist-Cs8X0P1d.js} +2 -2
  44. package/public/assets/{dist-DBti5--U.js.map → dist-Cs8X0P1d.js.map} +1 -1
  45. package/public/assets/dist-D2jvo5oA.js +2 -0
  46. package/public/assets/{dist-QY_EIkcd.js.map → dist-D2jvo5oA.js.map} +1 -1
  47. package/public/assets/{dist-1g1lCjVb.js → dist-DV83j9tm.js} +2 -2
  48. package/public/assets/{dist-1g1lCjVb.js.map → dist-DV83j9tm.js.map} +1 -1
  49. package/public/assets/{dist-DJpDTmGg.js → dist-DyNJNwpi.js} +2 -2
  50. package/public/assets/{dist-DJpDTmGg.js.map → dist-DyNJNwpi.js.map} +1 -1
  51. package/public/assets/dist-mm7c7nBt.js +2 -0
  52. package/public/assets/{dist-DjJMNrsj.js.map → dist-mm7c7nBt.js.map} +1 -1
  53. package/public/assets/dist-y03IwOrd.js +2 -0
  54. package/public/assets/{dist-C7VlX6hz.js.map → dist-y03IwOrd.js.map} +1 -1
  55. package/public/assets/{es2015-GhJvD7eR.js → es2015-VnZ2kVIz.js} +2 -2
  56. package/public/assets/{es2015-GhJvD7eR.js.map → es2015-VnZ2kVIz.js.map} +1 -1
  57. package/public/assets/formatted-body-impl-CBHoD82a.js +3 -0
  58. package/public/assets/formatted-body-impl-CBHoD82a.js.map +1 -0
  59. package/public/assets/{index-DYwuv_Na.css → index-DcmG5gLR.css} +1 -1
  60. package/public/assets/index-DocqZ4Q0.js +23 -0
  61. package/public/assets/index-DocqZ4Q0.js.map +1 -0
  62. package/public/assets/{input-CPfrBmej.js → input-CtLT7WXi.js} +2 -2
  63. package/public/assets/{input-CPfrBmej.js.map → input-CtLT7WXi.js.map} +1 -1
  64. package/public/assets/{insights-DwS0svZy.js → insights-Du9X-nwA.js} +2 -2
  65. package/public/assets/{insights-DwS0svZy.js.map → insights-Du9X-nwA.js.map} +1 -1
  66. package/public/assets/{integrations-De1_UHQE.js → integrations-BlSadMFC.js} +2 -2
  67. package/public/assets/{integrations-De1_UHQE.js.map → integrations-BlSadMFC.js.map} +1 -1
  68. package/public/assets/{lib-Bi-xeh6t.js → lib-BLoevhQO.js} +3 -3
  69. package/public/assets/{lib-Bi-xeh6t.js.map → lib-BLoevhQO.js.map} +1 -1
  70. package/public/assets/lucide-react-Dc3ZwCBi.js +9 -0
  71. package/public/assets/{lucide-react-De5edQpl.js.map → lucide-react-Dc3ZwCBi.js.map} +1 -1
  72. package/public/assets/{maintenance-B5qrcsDt.js → maintenance-KeCPGZG4.js} +2 -2
  73. package/public/assets/{maintenance-B5qrcsDt.js.map → maintenance-KeCPGZG4.js.map} +1 -1
  74. package/public/assets/{managed-agents-BGMWAUfG.js → managed-agents-YKqARLQn.js} +4 -4
  75. package/public/assets/{managed-agents-BGMWAUfG.js.map → managed-agents-YKqARLQn.js.map} +1 -1
  76. package/public/assets/{markdown-preview-impl-DsZ4Ek80.js → markdown-preview-impl-Bo8ql-lO.js} +2 -2
  77. package/public/assets/{markdown-preview-impl-DsZ4Ek80.js.map → markdown-preview-impl-Bo8ql-lO.js.map} +1 -1
  78. package/public/assets/memory-BlftQACU.js +2 -0
  79. package/public/assets/{memory-CouN7Y4r.js.map → memory-BlftQACU.js.map} +1 -1
  80. package/public/assets/{messages-D9mYFxhU.js → messages-DQu0Np7r.js} +2 -2
  81. package/public/assets/{messages-D9mYFxhU.js.map → messages-DQu0Np7r.js.map} +1 -1
  82. package/public/assets/{orchestrators-B_SD_mhI.js → orchestrators-CW00iA0W.js} +2 -2
  83. package/public/assets/{orchestrators-B_SD_mhI.js.map → orchestrators-CW00iA0W.js.map} +1 -1
  84. package/public/assets/{overview-C8hVsCqz.js → overview-DyiH9eVP.js} +2 -2
  85. package/public/assets/{overview-C8hVsCqz.js.map → overview-DyiH9eVP.js.map} +1 -1
  86. package/public/assets/{pairs-B6vWKXnX.js → pairs-Ee8Npq67.js} +2 -2
  87. package/public/assets/{pairs-B6vWKXnX.js.map → pairs-Ee8Npq67.js.map} +1 -1
  88. package/public/assets/{projects-C2gHOdEY.js → projects-CqeJsfB6.js} +2 -2
  89. package/public/assets/{projects-C2gHOdEY.js.map → projects-CqeJsfB6.js.map} +1 -1
  90. package/public/assets/{prompt-settings-D4SXk0af.js → prompt-settings-0fHJtGD5.js} +2 -2
  91. package/public/assets/{prompt-settings-D4SXk0af.js.map → prompt-settings-0fHJtGD5.js.map} +1 -1
  92. package/public/assets/{react-dom-FNIdlE_z.js → react-dom-cLkVFBsS.js} +2 -2
  93. package/public/assets/{react-dom-FNIdlE_z.js.map → react-dom-cLkVFBsS.js.map} +1 -1
  94. package/public/assets/{registry-CMPhWcx3.js → registry-QTLN8Jy-.js} +2 -2
  95. package/public/assets/{registry-CMPhWcx3.js.map → registry-QTLN8Jy-.js.map} +1 -1
  96. package/public/assets/{security-C1fE4DVg.js → security-B0FTbGXU.js} +2 -2
  97. package/public/assets/{security-C1fE4DVg.js.map → security-B0FTbGXU.js.map} +1 -1
  98. package/public/assets/{select-D9j1MBVi.js → select-DhY0OvwP.js} +2 -2
  99. package/public/assets/{select-D9j1MBVi.js.map → select-DhY0OvwP.js.map} +1 -1
  100. package/public/assets/settings-B2UEpdBi.js +6 -0
  101. package/public/assets/{settings-CduSwUr9.js.map → settings-B2UEpdBi.js.map} +1 -1
  102. package/public/assets/store-DwgQJjEv.js +9 -0
  103. package/public/assets/store-DwgQJjEv.js.map +1 -0
  104. package/public/assets/tasks-BvDfBcxZ.js +2 -0
  105. package/public/assets/tasks-BvDfBcxZ.js.map +1 -0
  106. package/public/assets/{teams-ZEXvcAz_.js → teams-CIqsg55S.js} +2 -2
  107. package/public/assets/{teams-ZEXvcAz_.js.map → teams-CIqsg55S.js.map} +1 -1
  108. package/public/assets/{terminal-viewer-impl-tktfofs3.js → terminal-viewer-impl-Cig30gnt.js} +3 -3
  109. package/public/assets/{terminal-viewer-impl-tktfofs3.js.map → terminal-viewer-impl-Cig30gnt.js.map} +1 -1
  110. package/public/assets/types-DSwhOFcJ.js.map +1 -1
  111. package/public/assets/{use-keyboard-viewport-wzkGlTqU.js → use-keyboard-viewport-DucYmqmP.js} +2 -2
  112. package/public/assets/{use-keyboard-viewport-wzkGlTqU.js.map → use-keyboard-viewport-DucYmqmP.js.map} +1 -1
  113. package/public/assets/{user-avatar-_Dq16BWV.js → user-avatar-Ct6HEqZm.js} +2 -2
  114. package/public/assets/{user-avatar-_Dq16BWV.js.map → user-avatar-Ct6HEqZm.js.map} +1 -1
  115. package/public/assets/{work-queue-Bk8g7t9K.js → work-queue-XWcDwe8G.js} +2 -2
  116. package/public/assets/{work-queue-Bk8g7t9K.js.map → work-queue-XWcDwe8G.js.map} +1 -1
  117. package/public/assets/workspaces-EI4N2N7L.js +3 -0
  118. package/public/assets/{workspaces-D2bYW3zl.js.map → workspaces-EI4N2N7L.js.map} +1 -1
  119. package/public/index.html +21 -21
  120. package/runner/plugins/claude/.claude-plugin/plugin.json +1 -1
  121. package/scripts/orchestrator-spawn-smoke.ts +30 -13
  122. package/src/branch-landed.ts +14 -1
  123. package/src/config-store.ts +15 -3
  124. package/src/db/mappers.ts +3 -0
  125. package/src/db/migrations.ts +41 -2
  126. package/src/db/plans.ts +11 -0
  127. package/src/db/schema.ts +3 -1
  128. package/src/db/task-entity.ts +78 -3
  129. package/src/mcp/index.ts +1 -1
  130. package/src/mcp-plan-tools.ts +3 -0
  131. package/src/mcp-task-tools.ts +16 -7
  132. package/src/routes/index.ts +2 -1
  133. package/src/routes/plans.ts +12 -2
  134. package/src/routes/tasks.ts +13 -5
  135. package/src/services/plan-graph.ts +8 -1
  136. package/src/services/spawn-agent.ts +25 -22
  137. package/src/services/task-entity.ts +6 -1
  138. package/public/assets/MessageBubble-CxqPFLGP.js +0 -4
  139. package/public/assets/MessageBubble-CxqPFLGP.js.map +0 -1
  140. package/public/assets/PlanGraphPanel-gQ_lb6zP.js +0 -2
  141. package/public/assets/PlanGraphPanel-gQ_lb6zP.js.map +0 -1
  142. package/public/assets/agents-DOwnLE42.js +0 -2
  143. package/public/assets/branch-state-badge-JDaHO2fG.js +0 -2
  144. package/public/assets/chat-BTmgzO_g.js +0 -2
  145. package/public/assets/dist-C7VlX6hz.js +0 -2
  146. package/public/assets/dist-DjJMNrsj.js +0 -2
  147. package/public/assets/dist-QY_EIkcd.js +0 -2
  148. package/public/assets/formatted-body-impl-2ZWd80_S.js +0 -3
  149. package/public/assets/formatted-body-impl-2ZWd80_S.js.map +0 -1
  150. package/public/assets/index-D4mb_LKw.js +0 -23
  151. package/public/assets/index-D4mb_LKw.js.map +0 -1
  152. package/public/assets/lucide-react-De5edQpl.js +0 -9
  153. package/public/assets/memory-CouN7Y4r.js +0 -2
  154. package/public/assets/settings-CduSwUr9.js +0 -6
  155. package/public/assets/store-Bk6Lku_S.js +0 -9
  156. package/public/assets/store-Bk6Lku_S.js.map +0 -1
  157. package/public/assets/tasks-Bi456f7f.js +0 -2
  158. package/public/assets/tasks-Bi456f7f.js.map +0 -1
  159. package/public/assets/workspaces-D2bYW3zl.js +0 -3
@@ -12,7 +12,7 @@ import {
12
12
  assignTaskEntityAgent,
13
13
  createTaskEntity,
14
14
  getTaskEntity,
15
- listTaskEntities,
15
+ listTaskEntitySummaries,
16
16
  recordTaskEntityGate,
17
17
  removeTaskEntityDependency,
18
18
  removeTaskEntityRef,
@@ -80,23 +80,26 @@ export const TASK_TOOLS = [
80
80
  type: "object",
81
81
  properties: {
82
82
  title: { type: "string" },
83
+ label: { type: "string", description: "alias for title; concise task label" },
83
84
  intent: { type: "string", description: "original prompt / why this task exists" },
84
85
  complexity: { type: "string", enum: TASK_DISPATCH_COMPLEXITIES, description: "coarse task complexity; defaults to moderate" },
85
86
  context: { type: "string", description: "optional context needed to understand or execute the task" },
86
87
  doneWhen: { type: "string", description: "exit predicate / acceptance for execution" },
87
88
  teamId: { type: "string" },
89
+ projectId: { type: "string" },
90
+ repo: { type: "string", description: "owner/repo for the task's project/repository" },
88
91
  dispatch: DISPATCH_SCHEMA,
89
92
  issueRefs: { type: "array", items: { type: "string" }, description: "#n, owner/repo#n, GitHub URL, or issue_<id>" },
90
93
  defaultRepo: { type: "string", description: "owner/repo for bare #n issue refs" },
91
94
  dependsOn: { type: "array", items: { type: "integer", minimum: 1 } },
92
95
  },
93
- required: ["title", "intent"],
96
+ required: ["intent"],
94
97
  additionalProperties: false,
95
98
  },
96
99
  },
97
100
  { name: "relay_task_get", description: "Fetch a deliverable Task with its issue links, dependency edges, and current gate state.", requiredScopes: ["task:read"], inputSchema: { type: "object", properties: { taskId: TASK_ID_PROP }, required: ["taskId"], additionalProperties: false } },
98
- { name: "relay_task_list", description: "List deliverable Tasks, optionally filtered by execution status, deliverable stage, or team.", requiredScopes: ["task:read"], inputSchema: { type: "object", properties: { status: { type: "string", enum: DELIVERABLE_STATUS_ENUM }, deliverableStage: { type: "string", enum: TASK_DELIVERABLE_STAGES }, teamId: { type: "string" }, limit: { type: "integer", minimum: 1, maximum: 500 } }, additionalProperties: false } },
99
- { name: "relay_task_update", description: "Update a deliverable Task's editable fields (title, intent, complexity, context, latest steer, doneWhen, dispatch, team).", requiredScopes: ["task:write"], inputSchema: { type: "object", properties: { taskId: TASK_ID_PROP, title: { type: "string" }, intent: { type: "string" }, complexity: { type: "string", enum: TASK_DISPATCH_COMPLEXITIES }, context: { type: "string" }, latestSteer: { type: "string" }, doneWhen: { type: "string" }, dispatch: DISPATCH_SCHEMA, teamId: { type: "string" } }, required: ["taskId"], additionalProperties: false } },
101
+ { name: "relay_task_list", description: "List lean deliverable Task summaries, optionally filtered by execution status, deliverable stage, team, project, or repo. Does not return full intent.", requiredScopes: ["task:read"], inputSchema: { type: "object", properties: { status: { type: "string", enum: DELIVERABLE_STATUS_ENUM }, deliverableStage: { type: "string", enum: TASK_DELIVERABLE_STAGES }, teamId: { type: "string" }, projectId: { type: "string" }, repo: { type: "string" }, limit: { type: "integer", minimum: 1, maximum: 500 } }, additionalProperties: false } },
102
+ { name: "relay_task_update", description: "Update a deliverable Task's editable fields (title/label, intent, complexity, context, latest steer, doneWhen, dispatch, team, project/repo).", requiredScopes: ["task:write"], inputSchema: { type: "object", properties: { taskId: TASK_ID_PROP, title: { type: "string" }, label: { type: "string" }, intent: { type: "string" }, complexity: { type: "string", enum: TASK_DISPATCH_COMPLEXITIES }, context: { type: "string" }, latestSteer: { type: "string" }, doneWhen: { type: "string" }, dispatch: DISPATCH_SCHEMA, teamId: { type: "string" }, projectId: { type: "string" }, repo: { type: "string" } }, required: ["taskId"], additionalProperties: false } },
100
103
  { name: "relay_task_set_status", description: "Transition execution status (open|claimed|in_progress|blocked|done|failed|canceled). blockedBy is required when status is 'blocked'. Appends to the audit ledger; never touches the claim lease.", requiredScopes: ["task:write"], inputSchema: { type: "object", properties: { taskId: TASK_ID_PROP, status: { type: "string", enum: DELIVERABLE_STATUS_ENUM }, blockedBy: { type: "array", items: BLOCKER_SCHEMA }, note: { type: "string" } }, required: ["taskId", "status"], additionalProperties: false } },
101
104
  { name: "relay_task_set_stage", description: "Set the deliverable-position stage (none→uncommitted→committed-on-branch→landed-on-main→deploying→deployed). Normally driven by the land/deploy pipeline; exposed for manual/test use.", requiredScopes: ["task:write"], inputSchema: { type: "object", properties: { taskId: TASK_ID_PROP, deliverableStage: { type: "string", enum: TASK_DELIVERABLE_STAGES }, branch: { type: "string" }, commit: COMMIT_SCHEMA }, required: ["taskId", "deliverableStage"], additionalProperties: false } },
102
105
  { name: "relay_task_record_gate", description: "Record a quality-gate run (typecheck, test, file-size, api-spec, smoke, …) in the append-only ledger. Idempotent by runId; latest run per gate wins.", requiredScopes: ["task:write"], inputSchema: { type: "object", properties: { taskId: TASK_ID_PROP, gate: { type: "string" }, status: { type: "string", enum: TASK_GATE_STATUSES }, detail: { type: "string" }, commitSha: { type: "string" }, runId: { type: "string" } }, required: ["taskId", "gate", "status"], additionalProperties: false } },
@@ -129,12 +132,14 @@ export function relayTaskTool(auth: McpAuthLike, name: string, args: Record<stri
129
132
 
130
133
  if (name === "relay_task_create") {
131
134
  const created = createTaskEntity({
132
- title: cleanString(args.title, "title", { required: true, max: 500 })!,
135
+ title: cleanString(args.title ?? args.label, "title", { required: true, max: 500 })!,
133
136
  intent: cleanString(args.intent, "intent", { required: true, max: 1_000_000 })!,
134
137
  complexity: optionalEnum(args.complexity, "complexity", TASK_DISPATCH_COMPLEXITIES),
135
138
  context: cleanString(args.context, "context", { max: 1_000_000 }),
136
139
  doneWhen: cleanString(args.doneWhen, "doneWhen", { max: 1_000_000 }),
137
140
  teamId: cleanString(args.teamId, "teamId", { max: 200 }),
141
+ projectId: cleanString(args.projectId, "projectId", { max: 120 }),
142
+ repo: cleanString(args.repo, "repo", { max: 500 }),
138
143
  dispatch: args.dispatch as TaskDispatch | undefined,
139
144
  createdBy: actor,
140
145
  });
@@ -155,17 +160,19 @@ export function relayTaskTool(auth: McpAuthLike, name: string, args: Record<stri
155
160
  }
156
161
  if (name === "relay_task_list") {
157
162
  return {
158
- tasks: listTaskEntities({
163
+ tasks: listTaskEntitySummaries({
159
164
  status: optionalEnum(args.status, "status", DELIVERABLE_STATUS_ENUM),
160
165
  deliverableStage: optionalEnum(args.deliverableStage, "deliverableStage", TASK_DELIVERABLE_STAGES),
161
166
  teamId: cleanString(args.teamId, "teamId", { max: 200 }),
167
+ projectId: cleanString(args.projectId, "projectId", { max: 120 }),
168
+ repo: cleanString(args.repo, "repo", { max: 500 }),
162
169
  limit: typeof args.limit === "number" ? args.limit : undefined,
163
170
  }),
164
171
  };
165
172
  }
166
173
  if (name === "relay_task_update") {
167
174
  return updateTaskEntity(taskIdArg(args.taskId), {
168
- ...(args.title !== undefined ? { title: cleanString(args.title, "title", { max: 500 }) } : {}),
175
+ ...(args.title !== undefined || args.label !== undefined ? { title: cleanString(args.title ?? args.label, "title", { max: 500 }) } : {}),
169
176
  ...(args.intent !== undefined ? { intent: cleanString(args.intent, "intent", { max: 1_000_000 }) ?? "" } : {}),
170
177
  ...(args.complexity !== undefined ? { complexity: optionalEnum(args.complexity, "complexity", TASK_DISPATCH_COMPLEXITIES) } : {}),
171
178
  ...(args.context !== undefined ? { context: cleanString(args.context, "context", { max: 1_000_000 }) ?? "" } : {}),
@@ -173,6 +180,8 @@ export function relayTaskTool(auth: McpAuthLike, name: string, args: Record<stri
173
180
  ...(args.doneWhen !== undefined ? { doneWhen: cleanString(args.doneWhen, "doneWhen", { max: 1_000_000 }) ?? "" } : {}),
174
181
  ...(args.dispatch !== undefined ? { dispatch: args.dispatch as TaskDispatch } : {}),
175
182
  ...(args.teamId !== undefined ? { teamId: cleanString(args.teamId, "teamId", { max: 200 }) ?? "" } : {}),
183
+ ...(args.projectId !== undefined ? { projectId: cleanString(args.projectId, "projectId", { max: 120 }) ?? "" } : {}),
184
+ ...(args.repo !== undefined ? { repo: cleanString(args.repo, "repo", { max: 500 }) ?? "" } : {}),
176
185
  actor,
177
186
  }) as unknown as Record<string, unknown>;
178
187
  }
@@ -33,7 +33,7 @@ import { getHostDirectories, postAgent, postAgentSpawn, postRouteAdvice } from "
33
33
  import { getInsightsConfigRoute, getInsightsObservationsRoute, postInsightsObservationRoute, putInsightsConfigRoute } from "./insights";
34
34
  import { getOrchestratorDirectories, getOrchestratorFileRead, getOrchestratorFileStat, getOrchestratorFilesList, getOrchestratorLogs, getOrchestratorProviders, getOrchestratorSessions, getOrchestratorTerminal, getOrchestratorVersion, getOrchestratorWorkspaceProbe, postOrchestratorCreateDirectory, postOrchestratorTerminalInput, postOrchestratorTerminalResize } from "./orchestrator-proxy";
35
35
  import { getPairById, getPairs, postAcceptPair, postHangupPair, postPair, postPairMessage, postRejectPair } from "./pairs";
36
- import { getPlanByIdRoute, getPlansRoute } from "./plans";
36
+ import { getPlanByIdRoute, getPlansRoute, patchPlanArchiveRoute } from "./plans";
37
37
  import { getBlackboardEntryRoute, getBlackboardRoute } from "./blackboard";
38
38
  import { deleteIssueAssociationRoute, getIssueAssociationEntityIssuesRoute, getIssueAssociationIssueEntitiesRoute, postIssueAssociationRoute } from "./issue-associations";
39
39
  import { getAgentIssueActivityRoute, getIssueActivityAgentsRoute, postIssueActivityRoute } from "./issue-activity";
@@ -384,6 +384,7 @@ const routes: Route[] = [
384
384
  route("POST", "/api/pairs/:id/messages", postPairMessage),
385
385
  route("GET", "/api/plans", getPlansRoute),
386
386
  route("GET", "/api/plans/:id", getPlanByIdRoute),
387
+ route("PATCH", "/api/plans/:id/archive", patchPlanArchiveRoute),
387
388
  route("GET", "/api/blackboard", getBlackboardRoute),
388
389
  route("GET", "/api/blackboard/:id", getBlackboardEntryRoute),
389
390
  route("POST", "/api/issue-associations", postIssueAssociationRoute),
@@ -1,6 +1,7 @@
1
- import { getPlanGraph } from "../services/plan-graph";
1
+ import { archivePlanGraph, getPlanGraph } from "../services/plan-graph";
2
+ import { authContextFromRequest } from "../services/auth-context";
2
3
  import { cleanString } from "../validation";
3
- import { error, json, parseQueryInt, type Handler } from "./_shared";
4
+ import { error, json, parseBody, parseQueryInt, type Handler } from "./_shared";
4
5
 
5
6
  export const getPlansRoute: Handler = (req) => {
6
7
  const url = new URL(req.url);
@@ -32,3 +33,12 @@ export const getPlanByIdRoute: Handler = (_req, params) => {
32
33
  const plan = getPlanGraph({ planId: id });
33
34
  return plan ? json(plan) : error("plan not found", 404);
34
35
  };
36
+
37
+ export const patchPlanArchiveRoute: Handler = async (req, params) => {
38
+ const id = cleanString(params.id, "id", { required: true, max: 120 })!;
39
+ const parsed = await parseBody<{ archived?: unknown }>(req);
40
+ if (!parsed.ok) return error(parsed.error);
41
+ const archived = parsed.body?.archived;
42
+ if (typeof archived !== "boolean") return error("archived must be a boolean");
43
+ return json(archivePlanGraph(id, archived, authContextFromRequest(req)));
44
+ };
@@ -9,7 +9,7 @@ import { ValidationError, claimTask, getMessage, getTask, listTaskEvents, listTa
9
9
  import { readTaskMemoryEnvelope } from "../db/task-memory";
10
10
  import {
11
11
  addTaskEntityDependency, addTaskEntityRef, assignTaskEntityAgent, createTaskEntity, getTaskEntity,
12
- listTaskEntities, recordTaskEntityGate, removeTaskEntityDependency, removeTaskEntityRef, setTaskEntityStage, setTaskEntityStatus, taskEntityHistory, updateTaskEntity,
12
+ listTaskEntitySummaries, recordTaskEntityGate, removeTaskEntityDependency, removeTaskEntityRef, setTaskEntityStage, setTaskEntityStatus, taskEntityHistory, updateTaskEntity,
13
13
  } from "../services/task-entity";
14
14
  import { CommentThroughError, commentOnTaskThrough, taskCloseBridge } from "../services/task-issue-weave";
15
15
  import { captureTaskResultMemory, injectMemoryForTaskClaim } from "../memory-service";
@@ -52,11 +52,13 @@ export const getTasks: Handler = (req) => {
52
52
  // durable Tasks (optionally filtered by deliverable stage / team).
53
53
  const kind = url.searchParams.get("kind") ?? undefined;
54
54
  if (kind === "deliverable") {
55
- return json(listTaskEntities({
55
+ return json(listTaskEntitySummaries({
56
56
  status: url.searchParams.get("status") ?? undefined,
57
57
  deliverableStage: url.searchParams.get("deliverableStage") ?? undefined,
58
58
  teamId: url.searchParams.get("teamId") ?? undefined,
59
59
  ownerAgentId: url.searchParams.get("ownerAgentId") ?? undefined,
60
+ projectId: url.searchParams.get("projectId") ?? undefined,
61
+ repo: url.searchParams.get("repo") ?? undefined,
60
62
  limit: limitRaw ?? 100,
61
63
  }));
62
64
  }
@@ -73,11 +75,13 @@ export const getTaskEntities: Handler = (req) => {
73
75
  const url = new URL(req.url);
74
76
  const limitRaw = parseQueryInt(url.searchParams.get("limit"), { min: 1, max: 500 });
75
77
  if (Number.isNaN(limitRaw)) return error("limit must be an integer between 1 and 500");
76
- return json(listTaskEntities({
78
+ return json(listTaskEntitySummaries({
77
79
  status: url.searchParams.get("status") ?? undefined,
78
80
  deliverableStage: url.searchParams.get("deliverableStage") ?? undefined,
79
81
  teamId: url.searchParams.get("teamId") ?? undefined,
80
82
  createdBy: url.searchParams.get("createdBy") ?? undefined,
83
+ projectId: url.searchParams.get("projectId") ?? undefined,
84
+ repo: url.searchParams.get("repo") ?? undefined,
81
85
  limit: limitRaw ?? 100,
82
86
  }));
83
87
  };
@@ -91,12 +95,14 @@ export const postTaskCreate: Handler = async (req) => {
91
95
  if (!isRecord(body)) return error("JSON object body required");
92
96
  try {
93
97
  const created = createTaskEntity({
94
- title: body.title as string,
98
+ title: (body.title ?? body.label) as string,
95
99
  intent: cleanString(body.intent, "intent", { required: true, max: MAX_BODY_BYTES })!,
96
100
  complexity: optionalEnum(body.complexity, "complexity", TASK_DISPATCH_COMPLEXITIES),
97
101
  context: cleanString(body.context, "context", { max: MAX_BODY_BYTES }),
98
102
  doneWhen: cleanString(body.doneWhen, "doneWhen", { max: MAX_BODY_BYTES }),
99
103
  teamId: cleanString(body.teamId, "teamId", { max: 200 }),
104
+ projectId: cleanString(body.projectId, "projectId", { max: 120 }),
105
+ repo: cleanString(body.repo, "repo", { max: 500 }),
100
106
  dispatch: body.dispatch as TaskDispatch | undefined,
101
107
  createdBy: actorOf(req, body.createdBy),
102
108
  });
@@ -155,7 +161,7 @@ export const patchTaskEntity: Handler = async (req, params) => {
155
161
  if (!isRecord(body)) return error("JSON object body required");
156
162
  try {
157
163
  const detail = updateTaskEntity(id, {
158
- ...(body.title !== undefined ? { title: cleanString(body.title, "title", { max: 500 }) } : {}),
164
+ ...(body.title !== undefined || body.label !== undefined ? { title: cleanString(body.title ?? body.label, "title", { max: 500 }) } : {}),
159
165
  ...(body.intent !== undefined ? { intent: cleanString(body.intent, "intent", { max: MAX_BODY_BYTES }) ?? "" } : {}),
160
166
  ...(body.complexity !== undefined ? { complexity: optionalEnum(body.complexity, "complexity", TASK_DISPATCH_COMPLEXITIES) } : {}),
161
167
  ...(body.context !== undefined ? { context: cleanString(body.context, "context", { max: MAX_BODY_BYTES }) ?? "" } : {}),
@@ -163,6 +169,8 @@ export const patchTaskEntity: Handler = async (req, params) => {
163
169
  ...(body.doneWhen !== undefined ? { doneWhen: cleanString(body.doneWhen, "doneWhen", { max: MAX_BODY_BYTES }) ?? "" } : {}),
164
170
  ...(body.dispatch !== undefined ? { dispatch: body.dispatch as TaskDispatch } : {}),
165
171
  ...(body.teamId !== undefined ? { teamId: cleanString(body.teamId, "teamId", { max: 200 }) ?? "" } : {}),
172
+ ...(body.projectId !== undefined ? { projectId: cleanString(body.projectId, "projectId", { max: 120 }) ?? "" } : {}),
173
+ ...(body.repo !== undefined ? { repo: cleanString(body.repo, "repo", { max: 500 }) ?? "" } : {}),
166
174
  actor: actorOf(req),
167
175
  });
168
176
  return json(detail);
@@ -1,5 +1,5 @@
1
1
  import { isRecord } from "agent-relay-sdk";
2
- import { addTaskDependency, createPlanRow, deletePlan, getAgent, getEntry, getPlan, getPlanByTeam, getPlanByThread, getTaskDetail, listPlansWithBoundOwner, planThreadExists, removeTaskDependency, replacePlan, ValidationError } from "../db";
2
+ import { addTaskDependency, createPlanRow, deletePlan, getAgent, getEntry, getPlan, getPlanByTeam, getPlanByThread, getTaskDetail, listPlansWithBoundOwner, planThreadExists, removeTaskDependency, replacePlan, setPlanArchived, ValidationError } from "../db";
3
3
  import { associateIssue, planNodeIssueEntityId, removeAssociation } from "../db/issue-associations";
4
4
  import { resolveIssueRefFromString } from "../db/issue-refs";
5
5
  import { emitRelayEvent } from "../events";
@@ -394,6 +394,13 @@ export function deletePlanGraph(planId: string, ctx: AuthContext): { id: string;
394
394
  return { id: plan.id, deleted: true };
395
395
  }
396
396
 
397
+ export function archivePlanGraph(planId: string, archived: boolean, ctx: AuthContext): Plan {
398
+ const actor = actorId(ctx);
399
+ const plan = setPlanArchived(planId, archived);
400
+ emitPlan("plan.changed", plan, actor);
401
+ return plan;
402
+ }
403
+
397
404
  export function updateBoundPlanNodesForAgent(agentId: string, status: PlanStatus, actor = "server"): Plan[] {
398
405
  const updated: Plan[] = [];
399
406
  for (const plan of listPlansWithBoundOwner(agentId)) {
@@ -267,7 +267,9 @@ function spawnBrief(input: SpawnAgentInput): string | undefined {
267
267
  return undefined;
268
268
  }
269
269
 
270
- function taskTitleFromBrief(brief: string): string {
270
+ function taskTitleFromBrief(brief: string, label?: string): string {
271
+ const cleanLabel = label?.trim();
272
+ if (cleanLabel) return cleanLabel.length <= 500 ? cleanLabel : `${cleanLabel.slice(0, 497)}...`;
271
273
  const firstLine = brief.split(/\r?\n/).map((line) => line.trim()).find(Boolean) ?? "Spawned work";
272
274
  return firstLine.length <= 500 ? firstLine : `${firstLine.slice(0, 497)}...`;
273
275
  }
@@ -349,16 +351,34 @@ export async function spawnAgent(input: SpawnAgentInput, ctx: AuthContext): Prom
349
351
  // outside its cwd prefix, and MCP now honors the same bound.
350
352
  assertResourceAllowed(ctx, { scope: "agent:write", resource: { orchestratorId: orchestrator.id, cwd: resolvedCwd } });
351
353
 
354
+ // Provenance actor: the resolved caller agent when known, else the transport's label, else
355
+ // the raw token actor. Recorded in the command payload, the token mint, and the audit row.
356
+ const requestedBy = callerId ?? taskCreatorAgentId ?? input.requestedBy ?? ctx.actor.id;
357
+
358
+ // #405 — durable project binding: the project whose registered root contains the spawn cwd.
359
+ // Stamped on both the child token and an auto-scaffolded Task row so issueless spawned work
360
+ // stays filterable by project.
361
+ let callerProject = resolveProjectForCwd(resolvedCwd);
362
+ try {
363
+ const seeded = autoSeedProjectForCwd(resolvedCwd, requestedBy);
364
+ callerProject = seeded?.project ?? callerProject;
365
+ if (seeded?.ingestError) {
366
+ console.warn(`project auto-seed failed to ingest CLAUDE.md for ${resolvedCwd}: ${seeded.ingestError.message}`);
367
+ }
368
+ } catch (err) {
369
+ if (!callerProject) console.warn(`project auto-seed skipped for ${resolvedCwd}: ${errMessage(err)}`);
370
+ }
371
+
352
372
  if (shouldAutoScaffoldTask(input, profileName)) {
353
373
  const brief = spawnBrief(input)!;
354
- const taskRequestedBy = callerId ?? input.requestedBy ?? ctx.actor.id;
355
374
  linkedTask = createTaskEntity({
356
- title: taskTitleFromBrief(brief),
375
+ title: taskTitleFromBrief(brief, input.label),
357
376
  intent: brief,
358
377
  latestSteer: input.steer,
359
- createdBy: taskRequestedBy,
378
+ createdBy: requestedBy,
360
379
  source: "spawn",
361
- target: taskRequestedBy,
380
+ target: requestedBy,
381
+ ...(callerProject ? { projectId: callerProject.id, repo: callerProject.issueRepo } : {}),
362
382
  });
363
383
  input = { ...input, taskId: linkedTask.id };
364
384
  autoScaffoldedTask = { id: linkedTask.id, autoScaffolded: true, nudge: AUTO_SCAFFOLD_TASK_NUDGE };
@@ -474,26 +494,9 @@ export async function spawnAgent(input: SpawnAgentInput, ctx: AuthContext): Prom
474
494
  };
475
495
  }
476
496
 
477
- // Provenance actor: the resolved caller agent when known, else the transport's label, else
478
- // the raw token actor. Recorded in the command payload, the token mint, and the audit row.
479
- const requestedBy = callerId ?? taskCreatorAgentId ?? input.requestedBy ?? ctx.actor.id;
480
497
  const callerTeam = lineageAgentId ? (lineageAgent?.teamId ? { id: lineageAgent.teamId } : ensureTeam(lineageAgentId)) : undefined;
481
498
  if (lineageAgentId && callerTeam && !lineageAgent?.teamId) setAgentTeam(lineageAgentId, callerTeam.id);
482
499
 
483
- // #405 — durable project binding: the project whose registered root contains the spawn cwd.
484
- // Stamped on the child token's constraints (identity-only, like teamId) so callerProject(auth)
485
- // resolves it. Absent (graceful) when the cwd is inside no registered root.
486
- let callerProject = resolveProjectForCwd(resolvedCwd);
487
- try {
488
- const seeded = autoSeedProjectForCwd(resolvedCwd, requestedBy);
489
- callerProject = seeded?.project ?? callerProject;
490
- if (seeded?.ingestError) {
491
- console.warn(`project auto-seed failed to ingest CLAUDE.md for ${resolvedCwd}: ${seeded.ingestError.message}`);
492
- }
493
- } catch (err) {
494
- if (!callerProject) console.warn(`project auto-seed skipped for ${resolvedCwd}: ${errMessage(err)}`);
495
- }
496
-
497
500
  // #409 + #463 + #557 — the instruction-sources half of the launch-assembly contract.
498
501
  // composeSpawnInstructions is the single home that composes the prompt material handed to
499
502
  // providers (project preamble → profile system → profile append → caller/fork context) and
@@ -8,6 +8,7 @@ import {
8
8
  assignTaskAgent,
9
9
  createDeliverableTask,
10
10
  getTaskDetail,
11
+ listDeliverableTaskSummaries,
11
12
  listDeliverableTasks,
12
13
  listTaskEvents,
13
14
  recordGate,
@@ -28,7 +29,7 @@ import {
28
29
  type UpdateDeliverableTaskInput,
29
30
  } from "../db";
30
31
  import { emitTaskChanged } from "../sse";
31
- import type { Task, TaskDetail, TaskEvent, TaskGateState } from "../types";
32
+ import type { Task, TaskDetail, TaskEvent, TaskGateState, TaskListItem } from "../types";
32
33
  import { removeSubscriptionsForTask } from "../db/notification-subscriptions";
33
34
  import { stageSatisfiesDoneWhen } from "./task-done-when";
34
35
  import { autoSubscribeTaskCoordinator, emitTaskSemanticNotification, taskTransitionForStage, taskTransitionForStatus } from "./task-semantic-events";
@@ -54,6 +55,10 @@ export function listTaskEntities(filter: ListDeliverableTasksFilter = {}): Task[
54
55
  return listDeliverableTasks(filter);
55
56
  }
56
57
 
58
+ export function listTaskEntitySummaries(filter: ListDeliverableTasksFilter = {}): TaskListItem[] {
59
+ return listDeliverableTaskSummaries(filter);
60
+ }
61
+
57
62
  export function updateTaskEntity(id: number, input: UpdateDeliverableTaskInput): TaskDetail {
58
63
  const detail = updateDeliverableTask(id, input);
59
64
  emitTaskChanged(detail, "task.updated");
@@ -1,4 +0,0 @@
1
- import{r as e}from"./chunk-CilyBKbf.js";import{At as t,En as n,Gn as r,H as i,Kn as a,Nn as o,Qn as s,R as c,Rn as l,S as u,Sn as d,Tn as f,Ut as p,V as m,_ as h,a as g,bn as _,cn as v,dn as y,en as b,er as x,h as S,kt as C,l as ee,nr as te,o as ne,pn as re,pr as w,pt as T,r as E,tn as D,ut as O,vn as k,wn as A,x as j,xn as ie}from"./lucide-react-De5edQpl.js";import{r as M,t as N,y as P}from"./store-Bk6Lku_S.js";import{o as F}from"./types-DSwhOFcJ.js";import{E as I,H as ae,N as L,P as R,R as oe,S as se,V as ce,_ as le,d as ue,f as de,k as z,q as B,rt as V,v as fe}from"./display-_5kFrHJh.js";import{O as H,n as pe,o as me,s as U,t as he}from"./index-D4mb_LKw.js";import{t as ge}from"./user-avatar-_Dq16BWV.js";var W=e(w(),1),_e={online:`came online`,offline:`went offline`,shutdown:`shut down`,restarted:`restarted`,"compaction-requested":`compaction requested`,compacting:`compaction started`,compacted:`context compacted`,"compaction-stalled":`compaction stalled — may need manual intervention`,"clear-requested":`clear requested`,"clearing-context":`clear started`,"context-cleared":`context cleared`,"clear-stalled":`context clear stalled — may need manual intervention`,"shutting-down":`shutting down`},ve=new Set(Object.keys(_e)),ye=3e3;function G(e){return new Date(e.occurredAt??e.createdAt).getTime()}function be(e){if(e.kind!==`session`)return null;let t=e.payload?.session;return!t||t.type!==`narration`&&t.type!==`reasoning`&&t.type!==`tool`?null:{id:e.id,kind:t.type,label:typeof t.label==`string`?t.label:void 0,text:e.body,ts:G(e),turnId:typeof t.turnId==`string`?t.turnId:void 0}}function xe(e){if(e.kind!==`session`)return null;let t=e.payload?.session;if(t?.type!==`notice`)return null;let n=typeof t.label==`string`&&t.label?t.label:`compacted`;return{id:`notice-${e.id}`,status:n,timestamp:G(e)}}function Se(e){if(e.kind!==`session`)return null;let t=e.payload?.session;if(t?.type!==`relay-injection`)return null;let n=t.relayInjection&&typeof t.relayInjection==`object`&&!Array.isArray(t.relayInjection)?t.relayInjection:{},r=typeof n.category==`string`&&[`memory`,`instructions`,`tools`,`comms`,`knowledge`,`context`].includes(n.category)?n.category:`context`,i=typeof n.timestamp==`number`&&Number.isFinite(n.timestamp)?n.timestamp:G(e),a=n.detail&&typeof n.detail==`object`&&!Array.isArray(n.detail)?n.detail:{};return{id:e.id,category:r,summary:typeof n.summary==`string`&&n.summary.trim()?n.summary:e.body,detail:a,agentId:typeof n.agentId==`string`&&n.agentId?n.agentId:e.from,timestamp:i}}function Ce(e){if(e.kind!==`session`)return null;let t=e.payload?.session;if(t?.type!==`prompt-resolution`)return null;let n=t.promptResolution&&typeof t.promptResolution==`object`&&!Array.isArray(t.promptResolution)?t.promptResolution:{},r=n.kind===`questions`||n.kind===`plan`||n.kind===`command`||n.kind===`tool`?n.kind:`tool`,i=typeof n.title==`string`&&n.title.trim()?n.title:`Prompt resolved`,a=typeof n.decisionLabel==`string`&&n.decisionLabel.trim()?n.decisionLabel:typeof t.label==`string`&&t.label.trim()?t.label:`Resolved`,o=n.answers&&typeof n.answers==`object`&&!Array.isArray(n.answers)?n.answers:{};return{id:e.id,title:i,kind:r,body:typeof n.promptBody==`string`?n.promptBody:typeof n.body==`string`?n.body:e.body,toolName:typeof n.toolName==`string`&&n.toolName.trim()?n.toolName:i,decisionLabel:a,questions:we(n.questions,o,a),timestamp:G(e)}}function we(e,t,n){let r=(Array.isArray(e)?e:[]).map((e,r)=>{let i=e&&typeof e==`object`&&!Array.isArray(e)?e:{},a=typeof i.question==`string`&&i.question.trim()?i.question.trim():typeof i.header==`string`&&i.header.trim()?i.header.trim():`Question ${r+1}`,o=t[a]??t[String(i.question??``)]??t[String(i.header??``)];return{question:a,answer:typeof o==`string`&&o.trim()?o.trim():n}});return r.length?r:Object.entries(t).map(([e,t])=>({question:e,answer:t}))}function Te(e,t){let n=e.trim();for(let e of t){let t=e.trim();if(t){if(n===t)break;n.startsWith(`${t}\n\n`)&&(n=n.slice(t.length+2).trimStart())}}return n.trim()||e.trim()}function Ee(e){return e.kind===`system`&&e.from===`system`}var De=new Set([`agent.ready`,`agent.exited`,`agent.spawn_failed`]);function K(e){let t=new Date(e);return`${t.getFullYear()}-${String(t.getMonth()+1).padStart(2,`0`)}-${String(t.getDate()).padStart(2,`0`)}`}function Oe(e){let t=e.filter(e=>ve.has(e.status)).slice().sort((e,t)=>e.timestamp-t.timestamp),n=[];for(let e of t)n.some(t=>t.id===e.id)||n.some(t=>t.status===e.status&&Math.abs(t.timestamp-e.timestamp)<=ye)||n.push(e);return n}function ke(e,t,n,r=[],i){let a=[];for(let e of r){let t=e.entries.reduce((e,t)=>Math.min(e,B(t.originalCreatedAt)),1/0),n=Number.isFinite(t)?t-1:e.importedAt;a.push({ts:n,entry:{type:`import-boundary`,history:e,timestamp:n}});for(let t of e.entries)a.push({ts:B(t.originalCreatedAt),entry:{type:`imported-message`,history:e,entry:t}})}if(n){let e=new Date(n).getTime();Number.isFinite(e)&&a.push({ts:e,entry:{type:`created`,timestamp:e}})}if(i?.spawnedBy){let e=n?new Date(n).getTime():0,t=Number.isFinite(e)?e:0;a.push({ts:t,entry:{type:`agent-action`,direction:`spawned-by`,agentId:i.spawnedBy.agentId,provider:i.spawnedBy.provider,status:`ready`,timestamp:t}})}let o=i?.spawnedBy?.agentId,s=null,c=1/0;for(let t of e){if(t.kind===`session`||Ee(t)||I(t)||!(t.from===`user`||o!==void 0&&t.from===o)||!z(t).trim())continue;let e=G(t);e<c&&(c=e,s=t.id)}let l=new Map,u=new Map,d=new Map;for(let t of e){if(t.kind!==`session`)continue;let e=t.payload?.session;if(e?.type===`narration`&&typeof e.turnId==`string`){let n=u.get(e.turnId)??[];n.push({id:t.id,body:t.body.trim()}),u.set(e.turnId,n)}else if(e?.type===`response`&&typeof e.turnId==`string`){let n=l.get(e.turnId)??[];n.push(t.body.trim()),l.set(e.turnId,n)}}let f=new Map;for(let[e,t]of l){let n=(u.get(e)??[]).map(e=>e.body);f.set(e,t.map(e=>Te(e,n)))}for(let t of e){if(t.kind!==`session`)continue;let e=t.payload?.session;if(e?.type!==`response`||typeof e.turnId!=`string`)continue;let n=Te(t.body,(u.get(e.turnId)??[]).map(e=>e.body));n&&n!==t.body&&d.set(t.id,n)}let p=new Set;for(let[e,t]of f){let n=u.get(e)??[];for(let e of t)for(let t=n.length-1;t>=0;t--){let r=n[t];if(!p.has(r.id)&&ae(e,r.body)){p.add(r.id);break}}}let m=new Map,h=[];for(let t of e){if(Ee(t)){let e=typeof t.payload?.kind==`string`?t.payload.kind:``;if(De.has(e)){let n=t.payload,r=typeof n.agentId==`string`?n.agentId:``,i=G(t);if(!r){a.push({ts:i,entry:{type:`notice`,msg:t}});continue}let o=e===`agent.ready`?`ready`:e===`agent.exited`?`exited`:`failed`,s=m.get(r);if(s)s.entry.status=o,typeof n.reason==`string`&&(s.entry.reason=n.reason),s.entry.timestamp=i,s.ts=i;else{let e={ts:i,entry:{type:`agent-action`,direction:`spawned-child`,agentId:r,provider:typeof n.provider==`string`?n.provider:void 0,status:o,reason:typeof n.reason==`string`?n.reason:void 0,timestamp:i}};m.set(r,e),a.push(e)}continue}a.push({ts:G(t),entry:{type:`notice`,msg:t}});continue}let e=xe(t);if(e){h.push(e);continue}let n=be(t);if(n){if(n.kind===`narration`&&p.has(n.id))continue;a.push({ts:n.ts,entry:{type:`activity`,steps:[n],timestamp:n.ts}});continue}let r=Se(t);if(r){a.push({ts:r.timestamp,entry:{type:`relay-injection`,event:r}});continue}let i=Ce(t);if(i){a.push({ts:i.timestamp,entry:{type:`prompt-resolution`,event:i}});continue}if(t.kind===`session`){let e=t.payload?.session;if(e?.type===`response`&&typeof e.turnId==`string`){let e=d.get(t.id);if(e&&e!==t.body){a.push({ts:G(t),entry:{type:`message`,msg:{...t,body:e}}});continue}}}let o=t.id===s?`initial-prompt`:`message`;a.push({ts:G(t),entry:{type:o,msg:t}})}for(let e of Oe([...t,...h]))a.push({ts:e.timestamp,entry:{type:`status`,event:e}});let g={created:0,date:1,"import-boundary":2,"imported-message":3,"initial-prompt":4,message:4,activity:4,notice:4,"agent-action":4,"relay-injection":4,"prompt-resolution":4,status:5};a.sort((e,t)=>{let n=e.ts-t.ts;return Math.abs(n)<3e3&&g[e.entry.type]-g[t.entry.type]||n});let _=[],v=``;for(let{ts:e,entry:t}of a){if(t.type===`created`){_.push(t);continue}let n=K(e);if(n!==v&&(_.push({type:`date`,date:n,timestamp:e}),v=n),t.type===`activity`){let e=_[_.length-1];if(e&&e.type===`activity`&&Me(e,t)){e.steps.push(...t.steps);continue}}_.push(t)}return _}function Ae(e){return e.type===`message`?`msg-${e.msg.id}`:e.type===`initial-prompt`?`initprompt-${e.msg.id}`:e.type===`notice`?`notice-${e.msg.id}`:e.type===`relay-injection`?`relay-injection-${e.event.id}`:e.type===`prompt-resolution`?`prompt-resolution-${e.event.id}`:e.type===`agent-action`?`agent-action-${e.direction}-${e.agentId}`:e.type===`activity`?`act-${e.steps[0]?.id??e.timestamp}`:e.type===`import-boundary`?`import-${e.history.id}`:e.type===`imported-message`?`import-msg-${e.history.id}-${e.entry.originalMessageId}-${e.entry.position}`:e.type===`status`?`status-${e.event.id}`:e.type===`date`?`date-${e.date}`:`created-${e.timestamp}`}function je(e){return e.type===`message`||e.type===`initial-prompt`||e.type===`notice`?(e.msg.subject?`${e.msg.subject} `:``)+z(e.msg):e.type===`imported-message`?z(e.entry.message):e.type===`activity`?e.steps.map(e=>[e.label,e.text].filter(Boolean).join(` `)).join(`
2
- `):e.type===`relay-injection`?`${e.event.category} ${e.event.summary}\n${JSON.stringify(e.event.detail)}`:e.type===`prompt-resolution`?[e.event.title,e.event.decisionLabel,e.event.body,...e.event.questions.map(e=>`${e.question} ${e.answer}`)].filter(Boolean).join(`
3
- `):``}function Me(e,t){let n=e.steps[e.steps.length-1]?.turnId,r=t.steps[0]?.turnId;return n&&r?n===r:!n&&!r}function Ne(e){return e<1024?`${e} B`:e<1024*1024?`${(e/1024).toFixed(1)} KB`:`${(e/1024/1024).toFixed(1)} MB`}function Pe(e,t){if(t.startsWith(`/`))return t;let n=`${e.replace(/\/+$/,``)}/${t}`.split(`/`),r=[];for(let e of n)!e||e===`.`||(e===`..`?r.pop():r.push(e));return`/`+r.join(`/`)}function Fe(e){let t=e.replace(/\/+$/,``),n=t.lastIndexOf(`/`);return n>0?t.slice(0,n):`/`}function Ie(e,t){return e.filter(e=>e.status===`online`&&oe(t,e.baseDir)).sort((e,t)=>L(t.baseDir).length-L(e.baseDir).length)[0]||e.find(e=>e.status===`online`)}function Le(){return typeof window<`u`&&window.matchMedia(`(min-width: 1280px)`).matches}function Re(){return typeof window<`u`&&!!window.getSelection()?.toString()}function ze(e){let t=e.payload?.attachments;return Array.isArray(t)?t.filter(e=>!!(e&&typeof e==`object`&&typeof e.artifactId==`string`)):[]}var Be=[`👍`,`❤️`,`✅`,`👀`];function Ve(e){let t=new Map;for(let n of e.reactions||[]){let e=R(n.emoji),r=t.get(e)??{emoji:e,count:0,mine:!1,actors:[]};r.count+=1,r.mine=r.mine||n.actorId===`user`,r.actors.push(n.actorId),t.set(e,r)}return[...t.values()].sort((e,t)=>t.count-e.count||e.emoji.localeCompare(t.emoji))}function q(e){return I(e)}function He(e,t){let r=e.readBy||[],i=e.resolvedToAgent||t||e.to,a=i?r.includes(i):!1,o=r.some(e=>e!==V);if(a||o){let e=a?i:r.find(e=>e!==V);return{label:`read`,title:e?`Read by ${e}`:`Read by agent`,tone:`ok`,icon:n}}if(e.deliveryStatus===`delivered`)return{label:`delivered`,title:`Delivered to agent inbox`,tone:`ok`,icon:n};if(e.deliveryStatus===`queued`)return{label:`queued`,title:`Queued until the target agent is available`,tone:`warn`,icon:v};if(e.deliveryStatus===`failed`||e.deliveryStatus===`dead`){let t=e.deliveryPoisonReason||e.deliveryLastError||e.deliveryStatus;return{label:e.deliveryStatus,title:t,tone:`danger`,icon:_}}return{label:`sent`,title:`Accepted by Relay`,tone:`muted`,icon:f}}function Ue(e){let t=B(e.createdAt);return(e.reactions||[]).reduce((e,t)=>Math.max(e,B(t.updatedAt||t.createdAt)),t)}function We(e){return e?e.messages.reduce((e,t)=>Math.max(e,Ue(t)),0):0}function Ge(e,t,n){return(e-t)*n}function Ke(e){if(!e)return 0;let t=0;for(let n of e.messages)se(n)&&(t=Math.max(t,B(n.createdAt)));return t}function J(e){return new Date(e).toLocaleTimeString([],{hour:`2-digit`,minute:`2-digit`})}function qe(e){for(let t of e)t.previewUrl&&URL.revokeObjectURL(t.previewUrl)}function Je(e,t,n,r){if(e?.teamId)return{teamId:e.teamId};let i=[...t];n&&!i.some(e=>e.id===n.id)&&i.push(n);let a=i.filter(e=>e.threadId).reverse(),o=a.find(e=>!!r[M(e.threadId,e.channel)])??a[0];return o?.threadId?{threadId:o.threadId,...o.channel?{channel:o.channel}:{}}:null}var Y=x(),Ye={online:`text-emerald-400`,offline:`text-zinc-400`,shutdown:`text-zinc-400`,restarted:`text-blue-400`,"compaction-requested":`text-zinc-400`,compacting:`text-amber-400`,compacted:`text-amber-400`,"compaction-stalled":`text-red-400`,"clear-requested":`text-zinc-400`,"clearing-context":`text-amber-400`,"context-cleared":`text-amber-400`,"clear-stalled":`text-red-400`,"shutting-down":`text-zinc-400`};function Xe(e){let t=new Date,[n,r,i]=e.split(`-`).map(Number),a=new Date(n,r-1,i);if(e===K(t.getTime()))return`Today`;let o=new Date(t);return o.setDate(o.getDate()-1),e===K(o.getTime())?`Yesterday`:a.toLocaleDateString(void 0,{weekday:`short`,month:`short`,day:`numeric`,year:a.getFullYear()===t.getFullYear()?void 0:`numeric`})}function Ze({event:e}){return(0,Y.jsxs)(`div`,{className:`flex items-center justify-center gap-2 py-2 my-1`,children:[(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`}),(0,Y.jsxs)(`div`,{className:`flex items-center gap-1.5 text-xs text-muted-foreground`,children:[(0,Y.jsx)(y,{className:s(`w-2 h-2 fill-current`,Ye[e.status]||`text-zinc-400`)}),(0,Y.jsx)(`span`,{children:_e[e.status]||e.status}),(0,Y.jsx)(`span`,{className:`text-muted-foreground/60`,children:J(e.timestamp)})]}),(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`})]})}var Qe={"branch.landed":C,"context.warning":S,"agent.context_threshold":S,"agent.resume_budget_exhausted":S,"agent.rate_limit_resume":i},$e={"branch.landed":`branch landed`,"context.warning":`context warning`,"agent.context_threshold":`context threshold reached`};function et(e){return e&&(e.includes(`.`)?e.slice(e.indexOf(`.`)+1):e).replace(/[._-]+/g,` `).trim()||`system signal`}function X({agentId:e,fallbackLabel:t,className:n,noIcon:r}){let i=N(t=>t.agentsById[e])||null,a=N(e=>e.openInboxThread),o=N(e=>e.switchView),c=i?ue(i):t||e;return(0,Y.jsxs)(`button`,{type:`button`,className:s(`inline-flex max-w-full items-center gap-1 rounded px-1 text-muted-foreground transition-colors hover:bg-muted/50 hover:text-foreground`,n),onClick:t=>{t.stopPropagation(),a(e),o(`chat`)},title:`Open chat for ${c}`,children:[!r&&(0,Y.jsx)(H,{agent:i,className:`w-4 h-4 text-[10px]`}),(0,Y.jsx)(`span`,{className:`max-w-[160px] truncate`,children:c})]})}function tt({msg:e}){let t=e.payload??{},n=rt(e),r=typeof t.sha==`string`?t.sha:``,i=r?r.slice(0,7):``,a=typeof t.author==`string`?t.author:``,o=typeof t.branch==`string`?t.branch:``,s=typeof t.base==`string`?t.base:``,c=t.pushed;return(0,Y.jsxs)(`div`,{className:`flex items-center justify-center gap-2 py-2 my-1`,children:[(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`}),(0,Y.jsxs)(`div`,{className:`flex max-w-full flex-wrap items-center justify-center gap-x-1.5 gap-y-0.5 rounded-full border border-emerald-600/35 bg-emerald-500/10 px-2.5 py-1 text-xs text-emerald-700 dark:border-emerald-500/25 dark:text-emerald-300/90`,children:[(0,Y.jsx)(C,{className:`h-3 w-3 shrink-0 text-emerald-600 dark:text-emerald-400`}),(0,Y.jsx)(`span`,{className:`text-emerald-700 dark:text-emerald-300`,children:`branch landed`}),o&&s&&(0,Y.jsxs)(`span`,{className:`font-mono text-emerald-700/80 dark:text-emerald-200/70`,title:`${o} → ${s}`,children:[o,(0,Y.jsx)(`span`,{className:`opacity-50`,children:` → `}),s]}),i&&(0,Y.jsx)(`span`,{className:`rounded bg-emerald-500/15 px-1 font-mono text-emerald-800 dark:text-emerald-200`,title:r,children:i}),a&&(0,Y.jsxs)(`span`,{className:`inline-flex items-center gap-1 text-emerald-700/80 dark:text-emerald-300/80`,children:[(0,Y.jsx)(`span`,{className:`opacity-70`,children:`by`}),(0,Y.jsx)(X,{agentId:a,className:`text-emerald-700 hover:text-emerald-900 dark:text-emerald-300/90 dark:hover:text-emerald-100`})]}),c===!1&&(0,Y.jsx)(`span`,{className:`text-amber-600 dark:text-amber-300/80`,title:`Local-only land — not pushed to origin`,children:`· local only`}),n&&(0,Y.jsxs)(`span`,{className:`max-w-[220px] truncate text-emerald-700/70 dark:text-emerald-300/70`,title:n,children:[`· because `,n]}),(0,Y.jsx)(`span`,{className:`text-emerald-700/60 dark:text-emerald-300/50`,children:J(e.occurredAt??e.createdAt)})]}),(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`})]})}function nt({msg:e}){let t=typeof e.payload?.kind==`string`?e.payload.kind:``;if(t===`branch.landed`)return(0,Y.jsx)(tt,{msg:e});let n=Qe[t]??c,r=$e[t]??et(t),i=rt(e);return(0,Y.jsxs)(`div`,{className:`flex items-center justify-center gap-2 py-2 my-1`,children:[(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`}),(0,Y.jsxs)(`div`,{className:`flex items-center gap-1.5 rounded-full border border-border bg-muted/30 px-2.5 py-1 text-xs text-muted-foreground`,children:[(0,Y.jsx)(n,{className:`h-3 w-3`}),(0,Y.jsx)(`span`,{children:r}),i&&(0,Y.jsxs)(`span`,{className:`max-w-[220px] truncate text-muted-foreground/80`,title:i,children:[`· because `,i]}),(0,Y.jsx)(`span`,{className:`text-muted-foreground/60`,children:J(e.occurredAt??e.createdAt)})]}),(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`})]})}function rt(e){let t=e.payload?.routing;if(!t||typeof t!=`object`||Array.isArray(t))return``;let n=t.reason;return typeof n==`string`?n:``}var it={"spawned-child":{ready:`spawned`,exited:`spawned · exited`,failed:`spawn failed`},"spawned-by":{ready:`spawned by`,exited:`spawned by`,failed:`spawned by`}},at={"spawned-child-ready":m,"spawned-child-exited":O,"spawned-child-failed":_,"spawned-by-ready":a,"spawned-by-exited":a,"spawned-by-failed":a},ot={"spawned-child-ready":`text-emerald-400`,"spawned-child-exited":`text-zinc-400`,"spawned-child-failed":`text-red-400`,"spawned-by-ready":`text-blue-400`,"spawned-by-exited":`text-blue-400`,"spawned-by-failed":`text-blue-400`};function st({entry:e}){let t=`${e.direction}-${e.status}`,n=it[e.direction]?.[e.status]??e.direction,r=at[t]??c,i=ot[t]??`text-muted-foreground`,a=e.status===`failed`;return(0,Y.jsxs)(`div`,{className:`flex items-center justify-center gap-2 py-2 my-1`,children:[(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`}),(0,Y.jsxs)(`div`,{className:s(`flex items-center gap-1.5 rounded-full border bg-muted/30 px-2.5 py-1 text-xs`,a?`border-red-500/30`:`border-border`),children:[(0,Y.jsx)(r,{className:s(`h-3 w-3 shrink-0`,i)}),(0,Y.jsx)(`span`,{className:`text-muted-foreground`,children:n}),(0,Y.jsx)(X,{agentId:e.agentId}),e.reason&&a&&(0,Y.jsxs)(`span`,{className:`text-red-400/80 max-w-[120px] truncate`,title:e.reason,children:[`— `,e.reason]}),(0,Y.jsx)(`span`,{className:`text-muted-foreground/60 shrink-0`,children:J(e.timestamp)})]}),(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`})]})}var ct={memory:o,instructions:p,tools:ne,comms:c,knowledge:l,context:D},lt={memory:`border-emerald-500/25 bg-emerald-500/10 text-emerald-300`,instructions:`border-sky-500/25 bg-sky-500/10 text-sky-300`,tools:`border-amber-500/25 bg-amber-500/10 text-amber-300`,comms:`border-violet-500/25 bg-violet-500/10 text-violet-300`,knowledge:`border-cyan-500/25 bg-cyan-500/10 text-cyan-300`,context:`border-zinc-500/25 bg-zinc-500/10 text-zinc-300`};function ut(e){try{return JSON.stringify(e,null,2)}catch{return String(e)}}function dt({entry:e}){let[t,n]=(0,W.useState)(!1),r=e.event,i=ct[r.category]??j;return(0,Y.jsx)(`div`,{className:`flex justify-center py-2 my-1`,children:(0,Y.jsxs)(`div`,{className:s(`w-full max-w-[85%] md:max-w-[75%] rounded-lg border px-2.5 py-1.5 text-xs shadow-sm`,lt[r.category]??lt.context),children:[(0,Y.jsxs)(`button`,{type:`button`,className:`flex w-full min-w-0 items-center gap-1.5 text-left`,onClick:()=>n(e=>!e),children:[(0,Y.jsx)(i,{className:`h-3.5 w-3.5 shrink-0`}),(0,Y.jsx)(`span`,{className:`shrink-0 font-medium`,children:r.category}),(0,Y.jsx)(`span`,{className:`min-w-0 flex-1 truncate text-foreground/80`,children:r.summary}),(0,Y.jsx)(`span`,{className:`shrink-0 text-muted-foreground/60`,children:J(r.timestamp)}),(0,Y.jsx)(d,{className:s(`h-3.5 w-3.5 shrink-0 transition-transform`,t&&`rotate-90`)})]}),t&&(0,Y.jsx)(`pre`,{className:`mt-2 max-h-72 overflow-auto rounded-md border border-border/60 bg-background/75 p-2 font-mono text-[11px] leading-relaxed text-muted-foreground whitespace-pre-wrap break-words`,children:ut(r.detail)})]})})}function ft({blockedLabel:e,onInterrupt:t}){return e?(0,Y.jsx)(`div`,{className:`flex justify-start mb-3 animate-in fade-in slide-in-from-bottom-1 duration-150`,children:(0,Y.jsxs)(`div`,{className:`flex h-9 items-center gap-2 rounded-2xl rounded-bl-sm bg-card ring-1 ring-red-500/30 px-4`,children:[(0,Y.jsx)(_,{className:`w-3.5 h-3.5 text-red-400`}),(0,Y.jsxs)(`span`,{className:`text-xs text-red-300`,children:[`blocked: `,e]})]})}):(0,Y.jsx)(`div`,{className:`flex justify-start mb-3 animate-in fade-in slide-in-from-bottom-1 duration-150`,children:(0,Y.jsxs)(`div`,{className:`flex h-9 items-center gap-2 rounded-2xl rounded-bl-sm bg-card ring-1 ring-foreground/10 px-4`,children:[(0,Y.jsxs)(`div`,{className:`flex items-center gap-1`,children:[(0,Y.jsx)(`span`,{className:`w-1.5 h-1.5 rounded-full bg-yellow-400 animate-[pulse_1.4s_ease-in-out_infinite]`}),(0,Y.jsx)(`span`,{className:`w-1.5 h-1.5 rounded-full bg-yellow-400 animate-[pulse_1.4s_ease-in-out_0.2s_infinite]`}),(0,Y.jsx)(`span`,{className:`w-1.5 h-1.5 rounded-full bg-yellow-400 animate-[pulse_1.4s_ease-in-out_0.4s_infinite]`})]}),(0,Y.jsx)(`span`,{className:`text-xs text-muted-foreground`,children:`working`}),t&&(0,Y.jsxs)(`button`,{onClick:t,title:`Interrupt`,className:`ml-1 flex items-center gap-1 rounded-full px-1.5 py-0.5 text-xs text-muted-foreground hover:text-red-300 hover:bg-red-500/10 transition-colors`,children:[(0,Y.jsx)(re,{className:`w-3.5 h-3.5`}),`Stop`]})]})})}var Z=`agent-relay:chat-hide-tools`,Q=(()=>{let e=new Set,t=(()=>{try{return window.localStorage.getItem(Z)===`on`}catch{return!1}})(),n=()=>e.forEach(e=>e());return typeof window<`u`&&window.addEventListener(`storage`,e=>{e.key===Z&&(t=e.newValue===`on`,n())}),{subscribe(t){return e.add(t),()=>e.delete(t)},get:()=>t,toggle(){t=!t;try{window.localStorage.setItem(Z,t?`on`:`off`)}catch{}n()}}})();function pt(){return[(0,W.useSyncExternalStore)(Q.subscribe,Q.get,()=>!1),Q.toggle]}function mt({steps:e,showReasoning:t,issueRepo:n}){let[r,i]=pt(),a=t?e:e.filter(e=>e.kind!==`reasoning`);if(!a.length)return null;let c=a.filter(e=>e.kind===`tool`).length;return(0,Y.jsx)(`div`,{className:`flex justify-start mb-2`,children:(0,Y.jsxs)(`div`,{className:`max-w-[85%] md:max-w-[75%] min-w-0 space-y-1.5`,children:[a.map(e=>e.kind===`narration`?(0,Y.jsx)(U,{text:e.text,issueRepo:n,className:`text-sm leading-relaxed break-words text-foreground/90 min-w-0`},e.id):e.kind===`reasoning`?(0,Y.jsxs)(`div`,{className:`flex items-start gap-1.5 text-xs leading-relaxed text-muted-foreground/80`,children:[(0,Y.jsx)(o,{className:`w-3.5 h-3.5 mt-0.5 shrink-0 opacity-70`}),(0,Y.jsx)(U,{text:e.text,issueRepo:n,className:`italic break-words min-w-0`})]},e.id):r?null:(0,Y.jsxs)(`div`,{className:`flex items-start gap-1.5 text-xs leading-relaxed text-muted-foreground`,children:[(0,Y.jsx)(h,{className:`w-3 h-3 mt-0.5 shrink-0 opacity-70`}),(0,Y.jsxs)(`span`,{className:`min-w-0 break-words`,children:[(0,Y.jsx)(`span`,{className:`font-medium`,children:e.label||`tool`}),e.text&&e.text.trim()&&e.text.trim()!==(e.label??``).trim()?(0,Y.jsxs)(`span`,{className:`opacity-70`,children:[` — `,e.text]}):null]})]},e.id)),c>0&&(0,Y.jsxs)(`button`,{onClick:i,className:`flex items-center gap-1 text-[11px] text-muted-foreground/50 hover:text-muted-foreground transition-colors text-left`,children:[(0,Y.jsx)(d,{className:s(`w-3 h-3 shrink-0 transition-transform`,!r&&`rotate-90`)}),(0,Y.jsx)(`span`,{children:r?`show ${c} tool step${c===1?``:`s`}`:`hide tool steps`})]})]})})}function ht({entry:e}){let{event:t}=e,n=t.kind===`questions`,r=n?t.title:t.kind===`plan`?`Plan prompt`:`${t.toolName} permission`;return(0,Y.jsx)(`div`,{className:`flex justify-center py-1.5`,children:(0,Y.jsxs)(`div`,{className:`w-full max-w-2xl rounded-md border border-border bg-muted/20 px-3 py-2 text-sm`,children:[(0,Y.jsxs)(`div`,{className:`flex items-center gap-2 text-xs text-muted-foreground`,children:[(0,Y.jsx)(k,{className:`h-3.5 w-3.5 text-emerald-500`}),(0,Y.jsx)(`span`,{className:`font-medium text-foreground`,children:r}),(0,Y.jsx)(`span`,{children:t.decisionLabel}),(0,Y.jsx)(`span`,{className:`ml-auto shrink-0 text-muted-foreground/60`,children:J(t.timestamp)})]}),n&&t.questions.length>0?(0,Y.jsx)(`div`,{className:`mt-2 space-y-1.5`,children:t.questions.map((e,t)=>(0,Y.jsxs)(`div`,{className:`grid gap-0.5`,children:[(0,Y.jsx)(`div`,{className:`text-xs text-muted-foreground`,children:e.question}),(0,Y.jsx)(`div`,{className:`text-sm text-foreground`,children:e.answer})]},`${e.question}-${t}`))}):t.body.trim()?(0,Y.jsx)(`div`,{className:`mt-2 max-h-48 overflow-auto rounded border border-border/70 bg-background/40 px-2 py-1.5 text-sm`,children:(0,Y.jsx)(U,{text:t.body})}):null]})})}function gt({date:e}){return(0,Y.jsxs)(`div`,{className:`flex items-center justify-center gap-3 py-3 my-1`,children:[(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`}),(0,Y.jsx)(`span`,{className:`text-xs font-medium text-muted-foreground`,children:Xe(e)}),(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`})]})}function _t({timestamp:e}){let t=new Date(e).toLocaleString(void 0,{month:`short`,day:`numeric`,year:`numeric`,hour:`2-digit`,minute:`2-digit`});return(0,Y.jsxs)(`div`,{className:`flex items-center justify-center gap-2 py-2 my-1`,children:[(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`}),(0,Y.jsxs)(`span`,{className:`text-xs text-muted-foreground/60`,children:[`created `,t]}),(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`})]})}function vt({history:e}){let n=e.sourceAgentLabel||e.sourcePeerId,r=e.entries.length;return(0,Y.jsxs)(`div`,{className:`flex items-center justify-center gap-2 py-2 my-1`,children:[(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`}),(0,Y.jsxs)(`div`,{className:`flex items-center gap-1.5 rounded-full border border-dashed border-border bg-muted/30 px-2 py-1 text-[11px] text-muted-foreground`,children:[(0,Y.jsx)(t,{className:`h-3 w-3`}),(0,Y.jsxs)(`span`,{children:[`forked history from `,n]}),(0,Y.jsxs)(`span`,{className:`text-muted-foreground/60`,children:[r,` `,r===1?`entry`:`entries`]})]}),(0,Y.jsx)(`div`,{className:`h-px flex-1 bg-border`})]})}function yt({entry:e,sourceLabel:t,issueRepo:n}){let r=e.message,i=z(r),a=e.originalFrom===V;return(0,Y.jsx)(`div`,{className:s(`flex mb-3 opacity-80`,a?`justify-end`:`justify-start`),children:(0,Y.jsx)(`div`,{className:`max-w-[85%] md:max-w-[75%]`,children:(0,Y.jsxs)(`div`,{className:s(`rounded-2xl border border-dashed px-3.5 py-2 text-sm select-text`,a?`border-primary/25 bg-primary/10 text-foreground rounded-br-sm`:`border-border bg-card/70 rounded-bl-sm`),children:[(0,Y.jsxs)(`div`,{className:s(`mb-1 text-[10px] uppercase tracking-normal`,a?`text-primary/70`:`text-muted-foreground`),children:[`forked history · `,a?`you`:t||e.originalFrom]}),(0,Y.jsx)(U,{text:i,rawBody:r.body,issueRepo:n,className:`leading-relaxed`}),(0,Y.jsxs)(`p`,{className:s(`mt-1 flex items-center justify-end gap-1.5 text-xs`,a?`text-primary/60`:`text-muted-foreground`),children:[(0,Y.jsxs)(`span`,{className:`opacity-40`,children:[`#`,e.originalMessageId]}),(0,Y.jsx)(`span`,{children:J(e.originalCreatedAt)})]})]})})})}function $({msg:e,issueRepo:t}){let n=z(e),r=J(e.occurredAt??e.createdAt);return(0,Y.jsx)(`div`,{"data-msg-id":e.id,className:`mb-3`,children:(0,Y.jsxs)(`div`,{className:`rounded-xl border border-primary/30 bg-primary/[0.06] px-3.5 py-2.5 shadow-sm`,children:[(0,Y.jsxs)(`div`,{className:`mb-1.5 flex items-center gap-1.5 text-[11px] font-semibold uppercase tracking-wide text-primary/80`,children:[(0,Y.jsx)(j,{className:`h-3.5 w-3.5`}),(0,Y.jsx)(`span`,{children:`Initial prompt`}),(0,Y.jsx)(`span`,{className:`ml-auto text-[10px] font-normal normal-case text-muted-foreground/60`,children:r})]}),(0,Y.jsx)(U,{text:n,rawBody:e.body,issueRepo:t,className:`text-sm leading-relaxed text-foreground`})]})})}function bt({scrollEl:e,timeline:t}){let[n,r]=(0,W.useState)(!0),[i,a]=(0,W.useState)(null),[o,c]=(0,W.useState)(null),[l,u]=(0,W.useState)(!1),d=(0,W.useMemo)(()=>{for(let e=t.length-1;e>=0;e--){let n=t[e];if(!(!n||n.type!==`message`&&n.type!==`initial-prompt`)&&n.msg.from===`user`)return{id:n.msg.id,body:z(n.msg)}}return null},[t]);if((0,W.useEffect)(()=>{if(!d||!e){r(!0);return}let t=null,n=null,i=()=>{let i=e.querySelector(`[data-msg-id="${d.id}"]`);if(!i){t?.disconnect(),t=null,n=null,r(!1);return}let a=i.getBoundingClientRect(),o=e.getBoundingClientRect();u(a.top<o.top),i!==n&&(t?.disconnect(),n=i,t=new IntersectionObserver(([e])=>{e&&r(e.isIntersecting)},{root:e,threshold:0}),t.observe(i))};return i(),e.addEventListener(`scroll`,i,{passive:!0}),()=>{t?.disconnect(),e.removeEventListener(`scroll`,i)}},[d?.id,e]),n||!d||!d.body.trim())return null;let f=i?.id===d.id?i.value:!1,p=o?.id===d.id?o.value:!1;function m(){!e||!d||e.querySelector(`[data-msg-id="${d.id}"]`)?.scrollIntoView({behavior:`smooth`,block:`center`})}let h=l?`↑`:`↓`;return p?(0,Y.jsx)(`div`,{className:`flex shrink-0 bg-card/45 border-b border-border`,children:(0,Y.jsxs)(`button`,{type:`button`,className:`w-full flex items-center justify-center gap-1.5 py-1 text-[11px] text-primary/60 hover:text-primary transition-colors`,onClick:()=>c({id:d.id,value:!1}),children:[(0,Y.jsx)(`span`,{children:`Your prompt`}),(0,Y.jsx)(A,{className:`w-3 h-3`})]})}):(0,Y.jsxs)(`section`,{className:`flex shrink-0 flex-col border-b border-border bg-card/45 px-3 py-2`,children:[(0,Y.jsxs)(`div`,{className:`flex items-center gap-2 text-[11px] text-muted-foreground mb-0.5`,children:[(0,Y.jsx)(`span`,{className:`font-medium text-primary/70`,children:`Your prompt`}),(0,Y.jsxs)(`button`,{type:`button`,className:`ml-auto hover:text-foreground transition-colors`,onClick:m,children:[h,` scroll to original`]}),(0,Y.jsx)(`button`,{type:`button`,className:`hover:text-foreground transition-colors`,onClick:()=>c({id:d.id,value:!0}),title:`Minimize`,children:(0,Y.jsx)(ie,{className:`w-3 h-3`})})]}),(0,Y.jsx)(`p`,{className:s(`text-sm text-foreground leading-snug cursor-pointer`,!f&&`line-clamp-2`),onClick:()=>a({id:d.id,value:!f}),children:d.body})]})}function xt(){return(0,W.useSyncExternalStore)(e=>P.subscribe(e),()=>P.getPlayingKey(),()=>null)}function St({msg:e,peer:t}){return(0,Y.jsx)($,{msg:e,issueRepo:N(e=>e.agentsById[t]?.issueRepo)})}function Ct({agent:e,onClick:t}){let n=!!(t&&e);return(0,Y.jsx)(`button`,{type:`button`,title:e?e.label||e.name||e.id:void 0,onClick:t,disabled:!n,className:s(`shrink-0 self-end transition-opacity`,n?`cursor-pointer hover:opacity-80`:`cursor-default opacity-60`),children:(0,Y.jsx)(H,{agent:e})})}function wt({agentId:e,onOpen:t}){let n=N(t=>t.agentsById[e]??null);return(0,Y.jsx)(Ct,{agent:n,onClick:n?()=>t(n):void 0})}function Tt({attachment:e,outbound:t}){let n=e.kind===`image`,r=e.title||e.artifactId,[i,a]=(0,W.useState)(null),[o,c]=(0,W.useState)(null),[l,u]=(0,W.useState)(!1),[d,f]=(0,W.useState)(!1);(0,W.useEffect)(()=>{let t=!1,n=null;async function r(){u(!0),c(null),a(null);try{let r=await te(`/artifacts/${encodeURIComponent(e.artifactId)}/content`);if(t)return;n=URL.createObjectURL(r),a(n)}catch(e){t||c(e.message)}finally{t||u(!1)}}return r(),()=>{t=!0,n&&URL.revokeObjectURL(n)}},[e.artifactId]);function m(){if(!i)return;let e=document.createElement(`a`);e.href=i,e.download=r,document.body.appendChild(e),e.click(),e.remove()}return n?(0,Y.jsxs)(Y.Fragment,{children:[(0,Y.jsx)(`button`,{type:`button`,onClick:()=>i&&f(!0),disabled:!i,className:`group/img mt-2 block overflow-hidden rounded-md border border-foreground/10 bg-black/10 text-left disabled:cursor-default relative`,children:i?(0,Y.jsxs)(Y.Fragment,{children:[(0,Y.jsx)(`img`,{src:i,alt:r,loading:`lazy`,className:`block max-h-72 max-w-full object-contain`}),(0,Y.jsx)(`span`,{className:`absolute inset-0 flex items-center justify-center bg-black/0 group-hover/img:bg-black/30 transition-colors`,children:(0,Y.jsx)(E,{className:`w-6 h-6 text-white opacity-0 group-hover/img:opacity-100 transition-opacity drop-shadow-md`})})]}):(0,Y.jsxs)(`span`,{className:s(`flex min-h-20 items-center gap-2 px-3 py-2 text-xs`,o?`text-red-400`:`text-muted-foreground`),children:[l?(0,Y.jsx)(T,{className:`h-4 w-4 animate-spin`}):(0,Y.jsx)(_,{className:`h-4 w-4`}),o||`Loading image`]})}),i&&(0,Y.jsx)(he,{open:d,onOpenChange:f,children:(0,Y.jsxs)(pe,{className:`max-w-[95vw] max-h-[95vh] w-auto p-0 bg-black/95 border-zinc-800 gap-0 overflow-hidden`,showCloseButton:!1,children:[(0,Y.jsx)(me,{className:`sr-only`,children:r}),(0,Y.jsxs)(`div`,{className:`relative flex items-center justify-center min-h-[200px]`,children:[(0,Y.jsx)(`img`,{src:i,alt:r,className:`max-w-[93vw] max-h-[90vh] object-contain`}),(0,Y.jsxs)(`div`,{className:`absolute top-2 right-2 flex gap-1`,children:[(0,Y.jsx)(`button`,{type:`button`,onClick:m,className:`rounded-md bg-black/60 hover:bg-black/80 p-2 text-white transition-colors`,title:`Download`,children:(0,Y.jsx)(b,{className:`w-4 h-4`})}),(0,Y.jsx)(`button`,{type:`button`,onClick:()=>f(!1),className:`rounded-md bg-black/60 hover:bg-black/80 p-2 text-white transition-colors`,title:`Close`,children:(0,Y.jsx)(g,{className:`w-4 h-4`})})]})]})]})})]}):(0,Y.jsxs)(`button`,{type:`button`,onClick:m,disabled:!i,className:s(`mt-2 flex w-full items-center gap-2 rounded-md border px-2.5 py-2 text-left text-xs transition-colors disabled:cursor-default disabled:opacity-70`,t?`border-primary-foreground/20 bg-primary-foreground/10 hover:bg-primary-foreground/15`:`border-border bg-background hover:bg-muted`),children:[l?(0,Y.jsx)(T,{className:`h-4 w-4 shrink-0 animate-spin`}):o?(0,Y.jsx)(_,{className:`h-4 w-4 shrink-0 text-red-400`}):(0,Y.jsx)(p,{className:`h-4 w-4 shrink-0`}),(0,Y.jsx)(`span`,{className:s(`min-w-0 flex-1 truncate`,o&&`text-red-400`),children:o||r}),(0,Y.jsx)(b,{className:`h-3.5 w-3.5 shrink-0`})]})}function Et({open:e,onToggle:t,onReact:n}){return(0,Y.jsxs)(`div`,{className:`relative shrink-0`,children:[(0,Y.jsx)(`button`,{type:`button`,title:`Add reaction`,onClick:t,className:s(`inline-flex h-5 w-6 items-center justify-center rounded-full border border-border bg-popover text-muted-foreground shadow-sm transition hover:bg-muted hover:text-foreground`,e?`opacity-100`:`opacity-0 pointer-events-none md:group-hover/msg:opacity-100 md:group-hover/msg:pointer-events-auto`),children:(0,Y.jsx)(u,{className:`h-3 w-3`})}),e&&(0,Y.jsx)(`div`,{className:`absolute bottom-full left-0 z-30 mb-1 flex gap-0.5 rounded-full border border-border bg-popover p-0.5 shadow-md`,children:Be.map(e=>(0,Y.jsx)(`button`,{type:`button`,title:`React ${e}`,onClick:()=>n(e),className:`inline-flex h-6 w-7 items-center justify-center rounded-full text-xs transition-colors hover:bg-muted`,children:e},e))})]})}function Dt({msg:e,peer:t}){let[n,i]=(0,W.useState)(!1),o=N(e=>e.agentsById),c=N(e=>e.openAgentDetail),l=e.from===t,u=(l?e.to:e.from)||``,f=o[l?t:u]?.issueRepo??o[t]?.issueRepo,p=!u||u===`broadcast`||u.includes(`:`),m=z(e),h=J(e.occurredAt??e.createdAt),g=l?r:a,_=o[e.from??``]??null;function v(e){e.stopPropagation(),_&&c(_)}return(0,Y.jsx)(`div`,{"data-msg-id":e.id,className:`flex justify-center mb-1.5`,children:(0,Y.jsxs)(`div`,{className:`w-full max-w-[94%] rounded-md border border-border/50 bg-muted/15 px-2.5 py-1`,children:[(0,Y.jsxs)(`div`,{className:`flex items-center gap-1.5 text-xs cursor-pointer select-none`,onClick:()=>i(e=>!e),children:[(0,Y.jsx)(d,{className:s(`h-3 w-3 shrink-0 text-muted-foreground/60 transition-transform`,n&&`rotate-90`)}),(0,Y.jsx)(`button`,{type:`button`,title:_?_.label||_.name||_.id:void 0,disabled:!_,onClick:v,className:s(`shrink-0 transition-opacity`,_?`cursor-pointer hover:opacity-80`:`cursor-default opacity-60`),children:(0,Y.jsx)(H,{agent:_,className:`!w-4 !h-4 !rounded-sm opacity-70`})}),(0,Y.jsx)(g,{className:`h-3 w-3 shrink-0 text-muted-foreground/70`}),(0,Y.jsxs)(`span`,{className:`shrink-0 text-muted-foreground`,children:[`Message `,l?`to`:`from`]}),p?(0,Y.jsx)(`span`,{className:`shrink-0 font-medium text-muted-foreground`,children:de(u,o)}):(0,Y.jsx)(X,{agentId:u,className:`shrink-0 px-0.5 text-foreground/80`,noIcon:!0}),!n&&(0,Y.jsx)(`span`,{className:`min-w-0 flex-1 truncate text-muted-foreground/50`,children:m}),(0,Y.jsx)(`span`,{className:`ml-auto shrink-0 text-muted-foreground/40`,children:h})]}),n&&(0,Y.jsx)(`div`,{className:`mt-1.5 pl-5`,children:(0,Y.jsx)(U,{text:m,rawBody:e.body,issueRepo:f,className:`text-sm leading-relaxed text-foreground/90`})})]})})}var Ot=(0,W.memo)(function({msg:e,peer:t,showAvatar:n=!1,onOpenReferencedPath:r,onPreviewReferencedPath:i,onPreviewReferencedPathEnd:a}){if(!F(e.from)&&!F(e.to))return(0,Y.jsx)(Dt,{msg:e,peer:t});let o=e.kind===`session`?e.payload?.session:void 0;if(o?.type===`prompt`&&o?.origin===`provider`)return(0,Y.jsx)(St,{msg:e,peer:t});let c=F(e.from),l=N(e=>e.reactToMessage),u=N(e=>e.voiceTtsEnabled),d=xt(),f=N(e=>{let n=e.agentsById[t]?.meta?.cwd;return typeof n==`string`?n:``}),p=N(e=>e.agentsById[t]?.issueRepo),m=N(e=>e.usersById),h=N(e=>e.users.length>1),g=c?ce(e.from,m):void 0,_=N(e=>e.openAgentDetail);N(e=>e.openTaskDetailById);let[v,y]=(0,W.useState)(!1),b=(0,W.useRef)(null),x=(0,W.useRef)(null),S=(0,W.useRef)(!1),C=z(e),te=J(e.occurredAt??e.createdAt),ne=ze(e),w=Ve(e),T=c?He(e,t):null,E=T?.icon,D=d===String(e.id),O=u&&!c&&!q(e)&&C.trim().length>0;function k(t){t.stopPropagation(),D?P.bargeIn():P.speak(e.body,String(e.id))}(0,W.useEffect)(()=>{if(!v)return;function e(e){Re()||b.current&&!b.current.contains(e.target)&&y(!1)}return document.addEventListener(`mousedown`,e),document.addEventListener(`touchstart`,e),()=>{document.removeEventListener(`mousedown`,e),document.removeEventListener(`touchstart`,e)}},[v]);function A(e){return Pe(f||`/`,e)}function j(e,t){let n=A(e);r?.(n,t)}function ie(e,t,n){let r=A(e);i?.(r,t,n)}function M(t){l(e,t),y(!1)}function I(e){e.button===0&&(x.current={x:e.clientX,y:e.clientY},S.current=!1)}function ae(e){let t=x.current;t&&(Math.abs(e.clientX-t.x)>3||Math.abs(e.clientY-t.y)>3)&&(S.current=!0)}function L(t){if(!(q(e)||c)&&!t.target.closest(`a,button,input,textarea,select,[role="button"]`)){if(S.current||Re()){S.current=!1;return}y(e=>!e)}}let R=n&&!q(e);return(0,Y.jsxs)(`div`,{"data-msg-id":e.id,className:s(`group/msg flex mb-3 items-end`,c?`justify-end`:`justify-start`,R&&`gap-1.5`),children:[!c&&R&&(0,Y.jsx)(wt,{agentId:t,onOpen:_}),(0,Y.jsxs)(`div`,{ref:b,className:s(`relative`,R?`max-w-[calc(85%-2rem)] md:max-w-[calc(75%-2rem)]`:`max-w-[85%] md:max-w-[75%]`),children:[O&&(0,Y.jsx)(`button`,{type:`button`,title:D?`Stop playback`:`Play aloud`,onClick:k,className:s(`absolute -top-2 -right-2 z-20 inline-flex h-6 w-6 items-center justify-center rounded-full border bg-popover shadow-sm transition`,D?`border-primary/50 text-primary opacity-100`:`border-border text-muted-foreground opacity-70 hover:bg-muted hover:text-foreground hover:opacity-100 [@media(hover:hover)]:md:opacity-0 [@media(hover:hover)]:md:group-hover/msg:opacity-100`),children:D?(0,Y.jsx)(re,{className:`h-3.5 w-3.5 animate-pulse`}):(0,Y.jsx)(ee,{className:`h-3.5 w-3.5`})}),(0,Y.jsxs)(`div`,{className:s(`rounded-2xl px-3.5 py-2 text-sm select-text`,!c&&!q(e)&&`cursor-pointer`,c?`bg-primary text-primary-foreground rounded-br-sm`:`bg-card ring-1 ring-foreground/10 rounded-bl-sm`),onPointerDown:I,onPointerMove:ae,onClick:L,children:[c&&h&&(0,Y.jsx)(`p`,{className:s(`text-[11px] font-semibold mb-0.5 text-right`,le(e.from)),children:fe(e.from,m)}),e.subject&&(0,Y.jsx)(`p`,{className:s(`text-xs font-semibold mb-1`,c?`text-primary-foreground/70`:`text-muted-foreground`),children:e.subject}),(0,Y.jsx)(U,{text:C,rawBody:e.body,issueRepo:p,className:`leading-relaxed`,onPrimary:c,onOpenPath:j,onPreviewPath:ie,onPreviewPathEnd:a,resolvePathTitle:(e,t)=>`${A(e)}${t?`:${t}`:``}`}),ne.map(t=>(0,Y.jsx)(Tt,{attachment:t,outbound:c},`${e.id}-${t.artifactId}-${t.role||``}`)),(0,Y.jsxs)(`p`,{className:s(`text-xs mt-1 flex items-center gap-1.5`,c?`justify-end text-primary-foreground/60`:`justify-end text-muted-foreground`),children:[(0,Y.jsxs)(`span`,{className:`opacity-40`,children:[`#`,e.id]}),(0,Y.jsx)(`span`,{children:te}),T&&E&&(0,Y.jsxs)(`span`,{className:s(`inline-flex items-center gap-1`,T.tone===`ok`&&`text-emerald-300`,T.tone===`warn`&&`text-amber-200`,T.tone===`danger`&&`text-red-200`),title:T.title,children:[(0,Y.jsx)(E,{className:`h-3 w-3`}),T.label]})]})]}),!q(e)&&w.length>0&&(0,Y.jsxs)(`div`,{className:s(`flex flex-wrap items-center gap-0.5 -mt-1 relative z-10`,c?`justify-end pr-2`:`justify-start pl-2`),children:[!c&&(0,Y.jsx)(Et,{open:v,onToggle:()=>y(e=>!e),onReact:M}),w.map(e=>(0,Y.jsxs)(`button`,{type:`button`,title:e.actors.join(`, `),onClick:()=>M(e.emoji),className:s(`inline-flex h-5 items-center gap-0.5 rounded-full border px-1.5 text-[11px] shadow-sm transition-colors`,e.mine?`border-primary/40 bg-primary/10 text-primary`:`border-border bg-background hover:bg-muted text-foreground`),children:[(0,Y.jsx)(`span`,{children:e.emoji}),e.count>1&&(0,Y.jsx)(`span`,{children:e.count})]},e.emoji))]}),!q(e)&&!c&&w.length===0&&(0,Y.jsx)(`div`,{className:`absolute -bottom-2.5 left-1 z-20`,children:(0,Y.jsx)(Et,{open:v,onToggle:()=>y(e=>!e),onReact:M})})]}),c&&R&&(0,Y.jsx)(`span`,{className:`shrink-0 self-end opacity-60`,children:(0,Y.jsx)(ge,{user:g,address:e.from,distinct:h})})]})});export{We as C,je as E,Le as S,Ae as T,Ke as _,_t as a,Je as b,yt as c,ht as d,dt as f,Ne as g,Ge as h,ft as i,$ as l,bt as m,mt as n,gt as o,Ze as p,st as r,vt as s,Ot as t,nt as u,Ie as v,ke as w,qe as x,Fe as y};
4
- //# sourceMappingURL=MessageBubble-CxqPFLGP.js.map