@arbidocs/blocks 0.4.32 → 0.4.33
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/agents/index.cjs +257 -215
- package/dist/agents/index.js +8 -6
- package/dist/agents/tasks/ConversationListView.d.ts +58 -0
- package/dist/agents/tasks/ConversationTurnSpeaker.d.ts +16 -0
- package/dist/agents/tasks/NewThreadDialog.d.ts +1 -1
- package/dist/agents/tasks/TaskActivityTimeline.d.ts +1 -1
- package/dist/agents/tasks/TaskFlow.d.ts +22 -0
- package/dist/agents/tasks/TaskInbox.d.ts +26 -0
- package/dist/agents/tasks/TaskReviewDialog.d.ts +22 -0
- package/dist/agents/tasks/TaskRowMenu.d.ts +10 -2
- package/dist/agents/tasks/TaskRunsDialog.d.ts +8 -3
- package/dist/agents/tasks/TaskStartDialog.d.ts +24 -0
- package/dist/agents/tasks/TaskTable.d.ts +1 -1
- package/dist/agents/tasks/ThreadNotifyDialog.d.ts +11 -0
- package/dist/agents/tasks/WorkflowComposer.d.ts +1 -1
- package/dist/agents/tasks/WorkflowsTable.d.ts +7 -0
- package/dist/agents/tasks/compact-thread-activity.d.ts +8 -0
- package/dist/agents/tasks/index.d.ts +10 -0
- package/dist/agents/tasks/taskComposerTypes.d.ts +16 -1
- package/dist/agents/tasks/taskRequest.d.ts +1 -0
- package/dist/agents/tasks/testGrid.d.ts +24 -0
- package/dist/agents/tasks/workflowColumns.d.ts +2 -1
- package/dist/agents/tasks/workflowRows.d.ts +6 -0
- package/dist/agents/workflows/types.d.ts +2 -0
- package/dist/auth/index.cjs +27 -27
- package/dist/auth/index.js +1 -1
- package/dist/chat/Message.d.ts +8 -2
- package/dist/chat/index.cjs +132 -120
- package/dist/chat/index.d.ts +2 -0
- package/dist/chat/index.js +2 -2
- package/dist/chat/participant-tints.d.ts +1 -0
- package/dist/chat/useRecipientDraft.d.ts +14 -0
- package/dist/{chunk-KF4EC5XU.js → chunk-24KQJYSB.js} +3 -3
- package/dist/{chunk-KF4EC5XU.js.map → chunk-24KQJYSB.js.map} +1 -1
- package/dist/{chunk-GVQOBJKR.cjs → chunk-2EAE5JP6.cjs} +7 -4
- package/dist/chunk-2EAE5JP6.cjs.map +1 -0
- package/dist/{chunk-S5HZBXZA.cjs → chunk-2QTT2RZE.cjs} +242 -2
- package/dist/chunk-2QTT2RZE.cjs.map +1 -0
- package/dist/chunk-3AFWGEDJ.cjs +53 -0
- package/dist/chunk-3AFWGEDJ.cjs.map +1 -0
- package/dist/{chunk-4XJZ6AAY.js → chunk-4AWS54US.js} +244 -6
- package/dist/chunk-4AWS54US.js.map +1 -0
- package/dist/{chunk-56BUD74K.cjs → chunk-65THHQVB.cjs} +27 -27
- package/dist/{chunk-56BUD74K.cjs.map → chunk-65THHQVB.cjs.map} +1 -1
- package/dist/{chunk-5B4PXAKI.cjs → chunk-6DNYPLCD.cjs} +21 -7
- package/dist/chunk-6DNYPLCD.cjs.map +1 -0
- package/dist/{chunk-TZ4QF7EP.js → chunk-6RXUMBTK.js} +1948 -594
- package/dist/chunk-6RXUMBTK.js.map +1 -0
- package/dist/{chunk-UTYQPVIW.cjs → chunk-7QDX2CO4.cjs} +6 -6
- package/dist/{chunk-UTYQPVIW.cjs.map → chunk-7QDX2CO4.cjs.map} +1 -1
- package/dist/{chunk-FRRDPYBR.cjs → chunk-AZ75JUIH.cjs} +74 -5
- package/dist/chunk-AZ75JUIH.cjs.map +1 -0
- package/dist/{chunk-NUPVHEJW.js → chunk-BUHKUKKB.js} +7 -4
- package/dist/chunk-BUHKUKKB.js.map +1 -0
- package/dist/chunk-C7FGONCM.js +124 -0
- package/dist/chunk-C7FGONCM.js.map +1 -0
- package/dist/{chunk-KXMDOTGW.js → chunk-DLBUFHLY.js} +10 -2
- package/dist/chunk-DLBUFHLY.js.map +1 -0
- package/dist/{chunk-ZHLMDJCO.cjs → chunk-DLVX6R6B.cjs} +62 -26
- package/dist/chunk-DLVX6R6B.cjs.map +1 -0
- package/dist/{chunk-JGZTRLKL.cjs → chunk-IA7RTPT3.cjs} +7 -4
- package/dist/chunk-IA7RTPT3.cjs.map +1 -0
- package/dist/{chunk-NJL4LIXX.js → chunk-LFGJAZ5H.js} +11 -8
- package/dist/chunk-LFGJAZ5H.js.map +1 -0
- package/dist/{chunk-IAKUTBPX.js → chunk-LYUO3E6V.js} +3 -3
- package/dist/{chunk-IAKUTBPX.js.map → chunk-LYUO3E6V.js.map} +1 -1
- package/dist/{chunk-EYPPB5CY.cjs → chunk-M2YGPC5N.cjs} +4 -4
- package/dist/{chunk-EYPPB5CY.cjs.map → chunk-M2YGPC5N.cjs.map} +1 -1
- package/dist/{chunk-5ZBP7TCD.cjs → chunk-MJCCBMM5.cjs} +10 -2
- package/dist/chunk-MJCCBMM5.cjs.map +1 -0
- package/dist/chunk-MZL67U2E.cjs +128 -0
- package/dist/chunk-MZL67U2E.cjs.map +1 -0
- package/dist/{chunk-OJSWQM4G.js → chunk-OZJ5PXA6.js} +29 -4
- package/dist/chunk-OZJ5PXA6.js.map +1 -0
- package/dist/{chunk-UBNVIIBT.js → chunk-PXFJDX2C.js} +21 -7
- package/dist/chunk-PXFJDX2C.js.map +1 -0
- package/dist/{chunk-RGHQFJOL.cjs → chunk-QFUF4A4J.cjs} +28 -2
- package/dist/chunk-QFUF4A4J.cjs.map +1 -0
- package/dist/chunk-RFXJYIDV.js +50 -0
- package/dist/chunk-RFXJYIDV.js.map +1 -0
- package/dist/{chunk-PLGVMLBD.cjs → chunk-SEQWI6E4.cjs} +1975 -610
- package/dist/chunk-SEQWI6E4.cjs.map +1 -0
- package/dist/{chunk-QN42OA5J.js → chunk-SFXVNFES.js} +4 -4
- package/dist/chunk-SFXVNFES.js.map +1 -0
- package/dist/{chunk-3NZR6PAG.js → chunk-V6U5KVAR.js} +70 -4
- package/dist/chunk-V6U5KVAR.js.map +1 -0
- package/dist/{chunk-YVIOCITQ.cjs → chunk-VUEZARW5.cjs} +3 -3
- package/dist/chunk-VUEZARW5.cjs.map +1 -0
- package/dist/{chunk-JLOYWXRB.js → chunk-VZGBCBYB.js} +3 -3
- package/dist/chunk-VZGBCBYB.js.map +1 -0
- package/dist/{chunk-ZVPTFTGV.cjs → chunk-WBDK4PIA.cjs} +11 -8
- package/dist/chunk-WBDK4PIA.cjs.map +1 -0
- package/dist/{chunk-ZORQ5M3W.cjs → chunk-WQFGG2BV.cjs} +4 -4
- package/dist/chunk-WQFGG2BV.cjs.map +1 -0
- package/dist/{chunk-C75S6USL.js → chunk-WYVCXY7R.js} +7 -4
- package/dist/chunk-WYVCXY7R.js.map +1 -0
- package/dist/{chunk-WSJVHSGN.js → chunk-XWEJ5LV2.js} +63 -27
- package/dist/chunk-XWEJ5LV2.js.map +1 -0
- package/dist/{chunk-YMHGF6R5.js → chunk-ZCF2JJFA.js} +3 -3
- package/dist/{chunk-YMHGF6R5.js.map → chunk-ZCF2JJFA.js.map} +1 -1
- package/dist/collaboration/index.cjs +45 -41
- package/dist/collaboration/index.js +1 -1
- package/dist/collaboration/mail/MailMessagePreview.d.ts +11 -0
- package/dist/collaboration/mail/index.d.ts +1 -0
- package/dist/connect/index.cjs +33 -33
- package/dist/connect/index.js +4 -4
- package/dist/facts/FactsFilterInput.d.ts +2 -46
- package/dist/facts/FactsToolbar.d.ts +5 -5
- package/dist/facts/index.cjs +27 -124
- package/dist/facts/index.cjs.map +1 -1
- package/dist/facts/index.js +13 -118
- package/dist/facts/index.js.map +1 -1
- package/dist/files/FilesPage.d.ts +1 -1
- package/dist/files/FilesToolbar.d.ts +1 -1
- package/dist/files/FolderPicker.d.ts +2 -1
- package/dist/files/ViewerChrome.d.ts +1 -1
- package/dist/files/bulk/FolderFilterButton.d.ts +3 -2
- package/dist/files/cells/BulkLabelSelect.d.ts +11 -0
- package/dist/files/cells/LabelMultiSelect.d.ts +2 -1
- package/dist/files/cells/index.d.ts +1 -0
- package/dist/files/index.cjs +109 -166
- package/dist/files/index.cjs.map +1 -1
- package/dist/files/index.js +95 -158
- package/dist/files/index.js.map +1 -1
- package/dist/home/index.cjs +19 -19
- package/dist/home/index.cjs.map +1 -1
- package/dist/home/index.js +4 -4
- package/dist/home/index.js.map +1 -1
- package/dist/index.cjs +787 -764
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.js +21 -69
- package/dist/index.js.map +1 -1
- package/dist/settings/SettingsPanel.d.ts +1 -1
- package/dist/settings/index.cjs +55 -280
- package/dist/settings/index.cjs.map +1 -1
- package/dist/settings/index.js +17 -248
- package/dist/settings/index.js.map +1 -1
- package/dist/shell/FilterInput.d.ts +46 -0
- package/dist/shell/TabHeader.d.ts +5 -1
- package/dist/shell/index.cjs +61 -48
- package/dist/shell/index.d.ts +1 -0
- package/dist/shell/index.js +3 -2
- package/dist/site/index.cjs +62 -62
- package/dist/site/index.js +2 -2
- package/dist/studio/index.cjs +74 -74
- package/dist/studio/index.js +5 -5
- package/dist/workspaces/WorkspaceCard.d.ts +2 -2
- package/dist/workspaces/index.cjs +9 -2
- package/dist/workspaces/index.cjs.map +1 -1
- package/dist/workspaces/index.js +9 -2
- package/dist/workspaces/index.js.map +1 -1
- package/package.json +3 -3
- package/src/blocks.css +4 -0
- package/src/components/grid.css +10 -0
- package/dist/chunk-3NZR6PAG.js.map +0 -1
- package/dist/chunk-4XJZ6AAY.js.map +0 -1
- package/dist/chunk-5B4PXAKI.cjs.map +0 -1
- package/dist/chunk-5ZBP7TCD.cjs.map +0 -1
- package/dist/chunk-C75S6USL.js.map +0 -1
- package/dist/chunk-FRRDPYBR.cjs.map +0 -1
- package/dist/chunk-GVQOBJKR.cjs.map +0 -1
- package/dist/chunk-JGZTRLKL.cjs.map +0 -1
- package/dist/chunk-JLOYWXRB.js.map +0 -1
- package/dist/chunk-KXMDOTGW.js.map +0 -1
- package/dist/chunk-NJL4LIXX.js.map +0 -1
- package/dist/chunk-NUPVHEJW.js.map +0 -1
- package/dist/chunk-OJSWQM4G.js.map +0 -1
- package/dist/chunk-PLGVMLBD.cjs.map +0 -1
- package/dist/chunk-QN42OA5J.js.map +0 -1
- package/dist/chunk-RGHQFJOL.cjs.map +0 -1
- package/dist/chunk-S5HZBXZA.cjs.map +0 -1
- package/dist/chunk-TZ4QF7EP.js.map +0 -1
- package/dist/chunk-UBNVIIBT.js.map +0 -1
- package/dist/chunk-WSJVHSGN.js.map +0 -1
- package/dist/chunk-YVIOCITQ.cjs.map +0 -1
- package/dist/chunk-ZHLMDJCO.cjs.map +0 -1
- package/dist/chunk-ZORQ5M3W.cjs.map +0 -1
- package/dist/chunk-ZVPTFTGV.cjs.map +0 -1
|
@@ -2,12 +2,14 @@
|
|
|
2
2
|
'use strict';
|
|
3
3
|
|
|
4
4
|
var chunkZW6FPIFC_cjs = require('./chunk-ZW6FPIFC.cjs');
|
|
5
|
-
var
|
|
6
|
-
var
|
|
7
|
-
var
|
|
8
|
-
var
|
|
5
|
+
var chunkWBDK4PIA_cjs = require('./chunk-WBDK4PIA.cjs');
|
|
6
|
+
var chunk3AFWGEDJ_cjs = require('./chunk-3AFWGEDJ.cjs');
|
|
7
|
+
var chunkIA7RTPT3_cjs = require('./chunk-IA7RTPT3.cjs');
|
|
8
|
+
var chunkMZL67U2E_cjs = require('./chunk-MZL67U2E.cjs');
|
|
9
9
|
var chunkOB5F4577_cjs = require('./chunk-OB5F4577.cjs');
|
|
10
|
-
var
|
|
10
|
+
var chunk2QTT2RZE_cjs = require('./chunk-2QTT2RZE.cjs');
|
|
11
|
+
var chunk6DNYPLCD_cjs = require('./chunk-6DNYPLCD.cjs');
|
|
12
|
+
var chunkVFUWWH52_cjs = require('./chunk-VFUWWH52.cjs');
|
|
11
13
|
var chunkC54XEN5T_cjs = require('./chunk-C54XEN5T.cjs');
|
|
12
14
|
var chunkKDG6FER6_cjs = require('./chunk-KDG6FER6.cjs');
|
|
13
15
|
var chunk2ZTONLT5_cjs = require('./chunk-2ZTONLT5.cjs');
|
|
@@ -483,7 +485,7 @@ function SchemaForm({
|
|
|
483
485
|
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cn("flex flex-col gap-4", className), "data-slot": "schema-form", children: [
|
|
484
486
|
common.map(render),
|
|
485
487
|
advanced.length > 0 && /* @__PURE__ */ jsxRuntime.jsx(
|
|
486
|
-
|
|
488
|
+
chunkWBDK4PIA_cjs.FoldSection,
|
|
487
489
|
{
|
|
488
490
|
label: l.advanced,
|
|
489
491
|
open: advancedOpen,
|
|
@@ -658,7 +660,7 @@ function WorkflowConfigDialog({
|
|
|
658
660
|
const firstField = workflow.inputs.find((f) => !f.advanced);
|
|
659
661
|
const focusPromptFirst = firstField?.type === "text" || firstField?.type === "longtext";
|
|
660
662
|
const defaultScopeRender = scopeSource ? (_field, value, onChange) => /* @__PURE__ */ jsxRuntime.jsx(
|
|
661
|
-
|
|
663
|
+
chunkWBDK4PIA_cjs.ScopePicker,
|
|
662
664
|
{
|
|
663
665
|
folders: scopeSource.folders,
|
|
664
666
|
unfiledCount: scopeSource.unfiledCount,
|
|
@@ -691,7 +693,7 @@ function WorkflowConfigDialog({
|
|
|
691
693
|
},
|
|
692
694
|
children: [
|
|
693
695
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
694
|
-
|
|
696
|
+
chunkWBDK4PIA_cjs.QuickActionDialogHeader,
|
|
695
697
|
{
|
|
696
698
|
icon: workflow.icon && renderIcon ? renderIcon(workflow.icon) : null,
|
|
697
699
|
title: workflow.title,
|
|
@@ -709,7 +711,7 @@ function WorkflowConfigDialog({
|
|
|
709
711
|
submit();
|
|
710
712
|
},
|
|
711
713
|
children: noFiles ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
712
|
-
|
|
714
|
+
chunkWBDK4PIA_cjs.AddFilesFirst,
|
|
713
715
|
{
|
|
714
716
|
reason: l.addFilesReason,
|
|
715
717
|
action: addFilesAction,
|
|
@@ -776,7 +778,7 @@ function defaultScopeRenderer(scopeSource) {
|
|
|
776
778
|
if (!scopeSource) return void 0;
|
|
777
779
|
return function renderScope(_field, value, onChange) {
|
|
778
780
|
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
779
|
-
|
|
781
|
+
chunkWBDK4PIA_cjs.ScopePicker,
|
|
780
782
|
{
|
|
781
783
|
folders: scopeSource.folders,
|
|
782
784
|
unfiledCount: scopeSource.unfiledCount,
|
|
@@ -861,7 +863,7 @@ function WorkflowLauncher({
|
|
|
861
863
|
});
|
|
862
864
|
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className, "data-slot": "workflow-launcher", children: [
|
|
863
865
|
showTiles && /* @__PURE__ */ jsxRuntime.jsx(
|
|
864
|
-
|
|
866
|
+
chunkWBDK4PIA_cjs.StartTiles,
|
|
865
867
|
{
|
|
866
868
|
items: [...tiles, ...extraTiles],
|
|
867
869
|
caption,
|
|
@@ -943,7 +945,7 @@ function WorkflowDocumentsField({
|
|
|
943
945
|
const set = (documents2) => onChange({ ...value, documents: documents2 });
|
|
944
946
|
return /* @__PURE__ */ jsxRuntime.jsxs("div", { "data-testid": `workflow-documents-${field.name}`, className: "space-y-2", children: [
|
|
945
947
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
946
|
-
|
|
948
|
+
chunk2QTT2RZE_cjs.DocumentPicker,
|
|
947
949
|
{
|
|
948
950
|
groups: [{ id: "workspace", docs: documents }],
|
|
949
951
|
value: ids[0] ?? "",
|
|
@@ -1577,7 +1579,7 @@ function AgentCreator({
|
|
|
1577
1579
|
] })
|
|
1578
1580
|
] }),
|
|
1579
1581
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
1580
|
-
|
|
1582
|
+
chunkWBDK4PIA_cjs.FoldSection,
|
|
1581
1583
|
{
|
|
1582
1584
|
label: l.advanced,
|
|
1583
1585
|
open: advancedOpen,
|
|
@@ -3413,144 +3415,6 @@ function TaskReviewActions({
|
|
|
3413
3415
|
] })
|
|
3414
3416
|
] });
|
|
3415
3417
|
}
|
|
3416
|
-
|
|
3417
|
-
// src/agents/tasks/taskRows.ts
|
|
3418
|
-
var MAX_TASK_DEPTH = 5;
|
|
3419
|
-
var ownerExtId = (task) => task.signoff_ext_id || task.owner_ext_id || task.created_by_ext_id || null;
|
|
3420
|
-
var isPlainTodo = (task) => !task.agent_ext_id && !task.has_agent_action && !task.skill_ref;
|
|
3421
|
-
function indexTasks(tasks) {
|
|
3422
|
-
const byId = new Map(tasks.map((t) => [t.external_id, t]));
|
|
3423
|
-
const kids = /* @__PURE__ */ new Map();
|
|
3424
|
-
const parentOf = /* @__PURE__ */ new Map();
|
|
3425
|
-
for (const task of tasks) {
|
|
3426
|
-
const parent = task.parent_conversation_ext_id;
|
|
3427
|
-
if (parent && parent !== task.external_id && byId.has(parent)) {
|
|
3428
|
-
parentOf.set(task.external_id, parent);
|
|
3429
|
-
const list = kids.get(parent);
|
|
3430
|
-
if (list) list.push(task);
|
|
3431
|
-
else kids.set(parent, [task]);
|
|
3432
|
-
}
|
|
3433
|
-
}
|
|
3434
|
-
return { byId, kids, parentOf };
|
|
3435
|
-
}
|
|
3436
|
-
function descendantIds(tree, id) {
|
|
3437
|
-
const out = [];
|
|
3438
|
-
const seen = /* @__PURE__ */ new Set([id]);
|
|
3439
|
-
const stack = [id];
|
|
3440
|
-
while (stack.length) {
|
|
3441
|
-
for (const child of tree.kids.get(stack.pop()) ?? []) {
|
|
3442
|
-
if (seen.has(child.external_id)) continue;
|
|
3443
|
-
seen.add(child.external_id);
|
|
3444
|
-
out.push(child.external_id);
|
|
3445
|
-
stack.push(child.external_id);
|
|
3446
|
-
}
|
|
3447
|
-
}
|
|
3448
|
-
return out;
|
|
3449
|
-
}
|
|
3450
|
-
function subtreeLevels(tree, id, seen = /* @__PURE__ */ new Set()) {
|
|
3451
|
-
if (seen.has(id)) return 0;
|
|
3452
|
-
const next = new Set(seen).add(id);
|
|
3453
|
-
let deepest = 0;
|
|
3454
|
-
for (const child of tree.kids.get(id) ?? []) {
|
|
3455
|
-
deepest = Math.max(deepest, subtreeLevels(tree, child.external_id, next));
|
|
3456
|
-
}
|
|
3457
|
-
return 1 + deepest;
|
|
3458
|
-
}
|
|
3459
|
-
function levelOf(tree, id) {
|
|
3460
|
-
let level = 1;
|
|
3461
|
-
const seen = /* @__PURE__ */ new Set([id]);
|
|
3462
|
-
for (let at = tree.parentOf.get(id); at && !seen.has(at); at = tree.parentOf.get(at)) {
|
|
3463
|
-
seen.add(at);
|
|
3464
|
-
level += 1;
|
|
3465
|
-
}
|
|
3466
|
-
return level;
|
|
3467
|
-
}
|
|
3468
|
-
function moveTargets(tasks, task) {
|
|
3469
|
-
const tree = indexTasks(tasks);
|
|
3470
|
-
const banned = /* @__PURE__ */ new Set([task.external_id, ...descendantIds(tree, task.external_id)]);
|
|
3471
|
-
const height = subtreeLevels(tree, task.external_id);
|
|
3472
|
-
return tasks.filter(
|
|
3473
|
-
(t) => !banned.has(t.external_id) && levelOf(tree, t.external_id) + height <= MAX_TASK_DEPTH
|
|
3474
|
-
);
|
|
3475
|
-
}
|
|
3476
|
-
var sameStats = (a, b) => a === b || a !== void 0 && b !== void 0 && a.done === b.done && a.total === b.total;
|
|
3477
|
-
function buildTaskRows(tasks, filter, collapsed, compare, options = {}) {
|
|
3478
|
-
const tree = indexTasks(tasks);
|
|
3479
|
-
const { kids, parentOf } = tree;
|
|
3480
|
-
const sorted = (list) => compare ? [...list].sort(compare) : list;
|
|
3481
|
-
const query = options.query?.trim().toLowerCase() ?? "";
|
|
3482
|
-
const titleOf = options.titleOf ?? ((t) => t.title ?? "");
|
|
3483
|
-
let included = null;
|
|
3484
|
-
let matched = null;
|
|
3485
|
-
if (filter !== "all" || query) {
|
|
3486
|
-
matched = /* @__PURE__ */ new Set();
|
|
3487
|
-
included = /* @__PURE__ */ new Set();
|
|
3488
|
-
for (const task of tasks) {
|
|
3489
|
-
const statusOk = filter === "all" || asTaskStatus(task.status) === filter;
|
|
3490
|
-
const textOk = !query || `${titleOf(task)} ${task.description ?? ""}`.toLowerCase().includes(query);
|
|
3491
|
-
if (!statusOk || !textOk) continue;
|
|
3492
|
-
matched.add(task.external_id);
|
|
3493
|
-
for (let at = task.external_id; at && !included.has(at); at = parentOf.get(at)) {
|
|
3494
|
-
included.add(at);
|
|
3495
|
-
}
|
|
3496
|
-
}
|
|
3497
|
-
}
|
|
3498
|
-
const shown = (list) => included ? list.filter((t) => included.has(t.external_id)) : list;
|
|
3499
|
-
const build = (task, depth, seen) => {
|
|
3500
|
-
const nextSeen = new Set(seen).add(task.external_id);
|
|
3501
|
-
return {
|
|
3502
|
-
task,
|
|
3503
|
-
depth,
|
|
3504
|
-
context: matched ? !matched.has(task.external_id) : false,
|
|
3505
|
-
children: sorted(shown(kids.get(task.external_id) ?? [])).filter((child) => !nextSeen.has(child.external_id)).map((child) => build(child, depth + 1, nextSeen))
|
|
3506
|
-
};
|
|
3507
|
-
};
|
|
3508
|
-
const sections = new Map([
|
|
3509
|
-
...STATUS_ORDER.map((s) => [s, []]),
|
|
3510
|
-
["sorted", []]
|
|
3511
|
-
]);
|
|
3512
|
-
const sectionOf = (task) => compare ? "sorted" : asTaskStatus(task.status);
|
|
3513
|
-
const roots = tasks.filter((t) => !parentOf.has(t.external_id));
|
|
3514
|
-
for (const task of sorted(shown(roots))) {
|
|
3515
|
-
sections.get(sectionOf(task))?.push(build(task, 0, /* @__PURE__ */ new Set()));
|
|
3516
|
-
}
|
|
3517
|
-
const cache = options.cache;
|
|
3518
|
-
const used = /* @__PURE__ */ new Set();
|
|
3519
|
-
const rows = [];
|
|
3520
|
-
const walk = (node, parentId, setSize, posInSet) => {
|
|
3521
|
-
const id = node.task.external_id;
|
|
3522
|
-
const expanded = !collapsed.has(id);
|
|
3523
|
-
const all = kids.get(id);
|
|
3524
|
-
const childStats = all ? { done: all.filter((c) => asTaskStatus(c.status) === "done").length, total: all.length } : void 0;
|
|
3525
|
-
let row = {
|
|
3526
|
-
external_id: id,
|
|
3527
|
-
task: node.task,
|
|
3528
|
-
depth: node.depth,
|
|
3529
|
-
childStats,
|
|
3530
|
-
expanded,
|
|
3531
|
-
parentId,
|
|
3532
|
-
setSize,
|
|
3533
|
-
posInSet,
|
|
3534
|
-
context: node.context
|
|
3535
|
-
};
|
|
3536
|
-
const prev = cache?.get(id);
|
|
3537
|
-
if (prev && prev.task === row.task && prev.depth === row.depth && prev.expanded === row.expanded && prev.parentId === row.parentId && prev.setSize === row.setSize && prev.posInSet === row.posInSet && prev.context === row.context && sameStats(prev.childStats, row.childStats)) {
|
|
3538
|
-
row = prev;
|
|
3539
|
-
}
|
|
3540
|
-
used.add(id);
|
|
3541
|
-
cache?.set(id, row);
|
|
3542
|
-
rows.push(row);
|
|
3543
|
-
if (expanded) {
|
|
3544
|
-
node.children.forEach((child, i) => walk(child, id, node.children.length, i + 1));
|
|
3545
|
-
}
|
|
3546
|
-
};
|
|
3547
|
-
const ordered = [...STATUS_ORDER, "sorted"].flatMap((s) => sections.get(s) ?? []);
|
|
3548
|
-
ordered.forEach((node, i) => walk(node, null, ordered.length, i + 1));
|
|
3549
|
-
if (cache) {
|
|
3550
|
-
for (const id of [...cache.keys()]) if (!used.has(id)) cache.delete(id);
|
|
3551
|
-
}
|
|
3552
|
-
return rows;
|
|
3553
|
-
}
|
|
3554
3418
|
function TaskRowMenu({
|
|
3555
3419
|
task,
|
|
3556
3420
|
status,
|
|
@@ -3559,6 +3423,10 @@ function TaskRowMenu({
|
|
|
3559
3423
|
canAdmin,
|
|
3560
3424
|
canEdit,
|
|
3561
3425
|
labels,
|
|
3426
|
+
canMarkDone = canEdit,
|
|
3427
|
+
canReopen = canEdit,
|
|
3428
|
+
selected = false,
|
|
3429
|
+
onToggleSelected,
|
|
3562
3430
|
onMarkDone,
|
|
3563
3431
|
onReopen,
|
|
3564
3432
|
onAddSubtask,
|
|
@@ -3567,6 +3435,7 @@ function TaskRowMenu({
|
|
|
3567
3435
|
onMoveTo,
|
|
3568
3436
|
onChangeOwner,
|
|
3569
3437
|
onOpenActivity,
|
|
3438
|
+
onToggleShared,
|
|
3570
3439
|
onGrantAccess,
|
|
3571
3440
|
reviewActions
|
|
3572
3441
|
}) {
|
|
@@ -3587,6 +3456,7 @@ function TaskRowMenu({
|
|
|
3587
3456
|
}
|
|
3588
3457
|
) }),
|
|
3589
3458
|
/* @__PURE__ */ jsxRuntime.jsxs(ui.DropdownMenuContent, { align: "end", children: [
|
|
3459
|
+
onToggleSelected && /* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuItem, { onSelect: onToggleSelected, "data-testid": `task-select-${id}`, children: selected ? "Deselect task" : "Select task" }),
|
|
3590
3460
|
reviewActions && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "px-2 py-1.5", children: typeof reviewActions === "function" ? reviewActions(() => setOpen(false)) : reviewActions }),
|
|
3591
3461
|
isOwner && onGrantAccess && task.pending_auth_request_id && /* @__PURE__ */ jsxRuntime.jsxs(
|
|
3592
3462
|
ui.DropdownMenuItem,
|
|
@@ -3600,10 +3470,18 @@ function TaskRowMenu({
|
|
|
3600
3470
|
]
|
|
3601
3471
|
}
|
|
3602
3472
|
),
|
|
3603
|
-
isChat || !canEdit ? null : done ? /* @__PURE__ */ jsxRuntime.jsxs(
|
|
3604
|
-
|
|
3605
|
-
|
|
3606
|
-
|
|
3473
|
+
isChat || !canEdit ? null : done ? canReopen && /* @__PURE__ */ jsxRuntime.jsxs(
|
|
3474
|
+
ui.DropdownMenuItem,
|
|
3475
|
+
{
|
|
3476
|
+
disabled: busy,
|
|
3477
|
+
onSelect: onReopen,
|
|
3478
|
+
"data-testid": `task-reopen-${id}`,
|
|
3479
|
+
children: [
|
|
3480
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.RotateCcw, { className: "mr-2 size-4", "aria-hidden": true }),
|
|
3481
|
+
labels.reopen
|
|
3482
|
+
]
|
|
3483
|
+
}
|
|
3484
|
+
) : canMarkDone && /* @__PURE__ */ jsxRuntime.jsxs(
|
|
3607
3485
|
ui.DropdownMenuItem,
|
|
3608
3486
|
{
|
|
3609
3487
|
disabled: busy,
|
|
@@ -3619,6 +3497,7 @@ function TaskRowMenu({
|
|
|
3619
3497
|
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.History, { className: "mr-2 size-4", "aria-hidden": true }),
|
|
3620
3498
|
labels.activity
|
|
3621
3499
|
] }),
|
|
3500
|
+
isOwner && onToggleShared && /* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuItem, { disabled: busy, onSelect: onToggleShared, children: task.is_shared ? "Make private" : "Share with workspace" }),
|
|
3622
3501
|
canEdit && onAddSubtask && /* @__PURE__ */ jsxRuntime.jsxs(ui.DropdownMenuItem, { onSelect: onAddSubtask, "data-testid": `task-add-subtask-${id}`, children: [
|
|
3623
3502
|
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ListPlus, { className: "mr-2 size-4", "aria-hidden": true }),
|
|
3624
3503
|
labels.addSubtask
|
|
@@ -3635,7 +3514,7 @@ function TaskRowMenu({
|
|
|
3635
3514
|
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Pencil, { className: "mr-2 size-4", "aria-hidden": true }),
|
|
3636
3515
|
isChat ? labels.rename : labels.edit
|
|
3637
3516
|
] }),
|
|
3638
|
-
canEdit && /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
3517
|
+
canEdit && onDelete && /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
3639
3518
|
/* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuSeparator, {}),
|
|
3640
3519
|
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
3641
3520
|
ui.DropdownMenuItem,
|
|
@@ -3858,99 +3737,237 @@ function applyColumnWidthRules(api, gridWidth, rules) {
|
|
|
3858
3737
|
}
|
|
3859
3738
|
}
|
|
3860
3739
|
|
|
3861
|
-
// src/agents/tasks/
|
|
3862
|
-
var
|
|
3863
|
-
|
|
3864
|
-
|
|
3865
|
-
|
|
3866
|
-
|
|
3867
|
-
|
|
3868
|
-
|
|
3869
|
-
|
|
3870
|
-
|
|
3871
|
-
|
|
3872
|
-
|
|
3873
|
-
|
|
3874
|
-
|
|
3875
|
-
|
|
3876
|
-
|
|
3877
|
-
|
|
3878
|
-
|
|
3879
|
-
colStatus: "Status",
|
|
3880
|
-
me: "Me",
|
|
3881
|
-
someone: "Someone",
|
|
3882
|
-
noDue: "\u2014",
|
|
3883
|
-
colShared: "Shared",
|
|
3884
|
-
shared: "Shared with the workspace",
|
|
3885
|
-
sharedOwnerOnly: "Only the creator can change who can see this",
|
|
3886
|
-
deleteOwnerOnly: "Only the creator or workspace owner can delete this",
|
|
3887
|
-
goalMet: (met, total) => `${met}/${total} met`,
|
|
3888
|
-
subtasksDone: (done, total) => `${done}/${total} sub-tasks done`,
|
|
3889
|
-
expandSubtasks: "Show sub-tasks",
|
|
3890
|
-
collapseSubtasks: "Hide sub-tasks",
|
|
3891
|
-
selectAll: "Select all tasks",
|
|
3892
|
-
selectTask: (name) => `Select ${name}`,
|
|
3893
|
-
markDone: "Mark done",
|
|
3894
|
-
reopen: "Reopen",
|
|
3895
|
-
markDoneMany: "Mark done",
|
|
3896
|
-
markDoneManyHint: "Marks your own to-dos done. Agent work is finished by reviewing it.",
|
|
3897
|
-
deleteMany: "Delete",
|
|
3898
|
-
approve: "Approve",
|
|
3899
|
-
moveTo: "Move to\u2026",
|
|
3900
|
-
untitled: "Untitled task",
|
|
3901
|
-
fromWorkflow: (name) => `From \u201C${name}\u201D`,
|
|
3902
|
-
searchLabel: "Search tasks",
|
|
3903
|
-
searchPlaceholder: "Search tasks\u2026",
|
|
3904
|
-
expandAll: "Expand all",
|
|
3905
|
-
collapseAll: "Collapse all",
|
|
3906
|
-
moveToTitle: (name) => `Move \u201C${name}\u201D to\u2026`,
|
|
3907
|
-
moveToNone: "No parent (top level)",
|
|
3908
|
-
moveToSearch: "Search tasks\u2026",
|
|
3909
|
-
moveToEmpty: "No task to move it under.",
|
|
3910
|
-
moveToCancel: "Cancel",
|
|
3911
|
-
subtasksSelected: (count) => `${count} ${count === 1 ? "sub-task" : "sub-tasks"} included`,
|
|
3912
|
-
addSubtask: "Add sub-task",
|
|
3913
|
-
edit: "Edit",
|
|
3914
|
-
rename: "Rename",
|
|
3915
|
-
delete: "Delete",
|
|
3916
|
-
grantAccess: "Allow access and continue",
|
|
3917
|
-
allowAccess: "Allow access",
|
|
3918
|
-
moreActions: "More actions",
|
|
3919
|
-
activity: "Activity",
|
|
3920
|
-
statusHint: (status, ago, forWho) => [status, ago, forWho && `for ${forWho}`].filter(Boolean).join(" \xB7 "),
|
|
3921
|
-
status: {}
|
|
3922
|
-
};
|
|
3923
|
-
var ROW_HEIGHT = 56;
|
|
3924
|
-
var NARROW_ROW_HEIGHT = 76;
|
|
3925
|
-
var MAX_INDENT_DEPTH = 4;
|
|
3926
|
-
var ANIMATE_ROWS_UP_TO = 500;
|
|
3927
|
-
var NARROW_GRID = 640;
|
|
3928
|
-
var WIDTH_RULES = [
|
|
3929
|
-
{ colId: "shared", minWidth: 1050 },
|
|
3930
|
-
{ colId: "due", minWidth: 850 },
|
|
3931
|
-
{ colId: "outputs", minWidth: 930 },
|
|
3932
|
-
{ colId: "owner", minWidth: 730 },
|
|
3933
|
-
{ colId: "status", minWidth: NARROW_GRID }
|
|
3934
|
-
];
|
|
3935
|
-
function statusHint(task, ctx) {
|
|
3936
|
-
const { props: p, l, owner } = ctx;
|
|
3937
|
-
if (!p.formatRelative || !task.updated_at) return void 0;
|
|
3938
|
-
const key = asTaskStatus(task.status);
|
|
3939
|
-
const pill = { ...DEFAULT_TASK_STATUS_PILL_LABELS, ...p.statusPillLabels };
|
|
3940
|
-
const label = task.pending_auth_request_id ? pill.waitingForAccess : STATUS_LABELS[key];
|
|
3941
|
-
return l.statusHint(
|
|
3942
|
-
label,
|
|
3943
|
-
p.formatRelative(task.updated_at),
|
|
3944
|
-
key === "ready_for_review" ? owner(task).label : void 0
|
|
3945
|
-
);
|
|
3740
|
+
// src/agents/tasks/taskRows.ts
|
|
3741
|
+
var MAX_TASK_DEPTH = 5;
|
|
3742
|
+
var ownerExtId = (task) => task.signoff_ext_id || task.owner_ext_id || task.created_by_ext_id || null;
|
|
3743
|
+
var isPlainTodo = (task) => !task.agent_ext_id && !task.has_agent_action && !task.skill_ref;
|
|
3744
|
+
function indexTasks(tasks) {
|
|
3745
|
+
const byId = new Map(tasks.map((t) => [t.external_id, t]));
|
|
3746
|
+
const kids = /* @__PURE__ */ new Map();
|
|
3747
|
+
const parentOf = /* @__PURE__ */ new Map();
|
|
3748
|
+
for (const task of tasks) {
|
|
3749
|
+
const parent = task.parent_conversation_ext_id;
|
|
3750
|
+
if (parent && parent !== task.external_id && byId.has(parent)) {
|
|
3751
|
+
parentOf.set(task.external_id, parent);
|
|
3752
|
+
const list = kids.get(parent);
|
|
3753
|
+
if (list) list.push(task);
|
|
3754
|
+
else kids.set(parent, [task]);
|
|
3755
|
+
}
|
|
3756
|
+
}
|
|
3757
|
+
return { byId, kids, parentOf };
|
|
3946
3758
|
}
|
|
3947
|
-
function
|
|
3948
|
-
const
|
|
3949
|
-
const
|
|
3950
|
-
|
|
3951
|
-
|
|
3952
|
-
|
|
3953
|
-
|
|
3759
|
+
function descendantIds(tree, id) {
|
|
3760
|
+
const out = [];
|
|
3761
|
+
const seen = /* @__PURE__ */ new Set([id]);
|
|
3762
|
+
const stack = [id];
|
|
3763
|
+
while (stack.length) {
|
|
3764
|
+
for (const child of tree.kids.get(stack.pop()) ?? []) {
|
|
3765
|
+
if (seen.has(child.external_id)) continue;
|
|
3766
|
+
seen.add(child.external_id);
|
|
3767
|
+
out.push(child.external_id);
|
|
3768
|
+
stack.push(child.external_id);
|
|
3769
|
+
}
|
|
3770
|
+
}
|
|
3771
|
+
return out;
|
|
3772
|
+
}
|
|
3773
|
+
function subtreeLevels(tree, id, seen = /* @__PURE__ */ new Set()) {
|
|
3774
|
+
if (seen.has(id)) return 0;
|
|
3775
|
+
const next = new Set(seen).add(id);
|
|
3776
|
+
let deepest = 0;
|
|
3777
|
+
for (const child of tree.kids.get(id) ?? []) {
|
|
3778
|
+
deepest = Math.max(deepest, subtreeLevels(tree, child.external_id, next));
|
|
3779
|
+
}
|
|
3780
|
+
return 1 + deepest;
|
|
3781
|
+
}
|
|
3782
|
+
function levelOf(tree, id) {
|
|
3783
|
+
let level = 1;
|
|
3784
|
+
const seen = /* @__PURE__ */ new Set([id]);
|
|
3785
|
+
for (let at = tree.parentOf.get(id); at && !seen.has(at); at = tree.parentOf.get(at)) {
|
|
3786
|
+
seen.add(at);
|
|
3787
|
+
level += 1;
|
|
3788
|
+
}
|
|
3789
|
+
return level;
|
|
3790
|
+
}
|
|
3791
|
+
function moveTargets(tasks, task) {
|
|
3792
|
+
const tree = indexTasks(tasks);
|
|
3793
|
+
const banned = /* @__PURE__ */ new Set([task.external_id, ...descendantIds(tree, task.external_id)]);
|
|
3794
|
+
const height = subtreeLevels(tree, task.external_id);
|
|
3795
|
+
return tasks.filter(
|
|
3796
|
+
(t) => !banned.has(t.external_id) && levelOf(tree, t.external_id) + height <= MAX_TASK_DEPTH
|
|
3797
|
+
);
|
|
3798
|
+
}
|
|
3799
|
+
var sameStats = (a, b) => a === b || a !== void 0 && b !== void 0 && a.done === b.done && a.total === b.total;
|
|
3800
|
+
function buildTaskRows(tasks, filter, collapsed, compare, options = {}) {
|
|
3801
|
+
const tree = indexTasks(tasks);
|
|
3802
|
+
const { kids, parentOf } = tree;
|
|
3803
|
+
const sorted = (list) => compare ? [...list].sort(compare) : list;
|
|
3804
|
+
const query = options.query?.trim().toLowerCase() ?? "";
|
|
3805
|
+
const titleOf = options.titleOf ?? ((t) => t.title ?? "");
|
|
3806
|
+
let included = null;
|
|
3807
|
+
let matched = null;
|
|
3808
|
+
if (filter !== "all" || query) {
|
|
3809
|
+
matched = /* @__PURE__ */ new Set();
|
|
3810
|
+
included = /* @__PURE__ */ new Set();
|
|
3811
|
+
for (const task of tasks) {
|
|
3812
|
+
const statusOk = filter === "all" || asTaskStatus(task.status) === filter;
|
|
3813
|
+
const textOk = !query || `${titleOf(task)} ${task.description ?? ""}`.toLowerCase().includes(query);
|
|
3814
|
+
if (!statusOk || !textOk) continue;
|
|
3815
|
+
matched.add(task.external_id);
|
|
3816
|
+
for (let at = task.external_id; at && !included.has(at); at = parentOf.get(at)) {
|
|
3817
|
+
included.add(at);
|
|
3818
|
+
}
|
|
3819
|
+
}
|
|
3820
|
+
}
|
|
3821
|
+
const shown = (list) => included ? list.filter((t) => included.has(t.external_id)) : list;
|
|
3822
|
+
const build = (task, depth, seen) => {
|
|
3823
|
+
const nextSeen = new Set(seen).add(task.external_id);
|
|
3824
|
+
return {
|
|
3825
|
+
task,
|
|
3826
|
+
depth,
|
|
3827
|
+
context: matched ? !matched.has(task.external_id) : false,
|
|
3828
|
+
children: sorted(shown(kids.get(task.external_id) ?? [])).filter((child) => !nextSeen.has(child.external_id)).map((child) => build(child, depth + 1, nextSeen))
|
|
3829
|
+
};
|
|
3830
|
+
};
|
|
3831
|
+
const sections = new Map([
|
|
3832
|
+
...STATUS_ORDER.map((s) => [s, []]),
|
|
3833
|
+
["sorted", []]
|
|
3834
|
+
]);
|
|
3835
|
+
const sectionOf = (task) => compare ? "sorted" : asTaskStatus(task.status);
|
|
3836
|
+
const roots = tasks.filter((t) => !parentOf.has(t.external_id));
|
|
3837
|
+
for (const task of sorted(shown(roots))) {
|
|
3838
|
+
sections.get(sectionOf(task))?.push(build(task, 0, /* @__PURE__ */ new Set()));
|
|
3839
|
+
}
|
|
3840
|
+
const cache = options.cache;
|
|
3841
|
+
const used = /* @__PURE__ */ new Set();
|
|
3842
|
+
const rows = [];
|
|
3843
|
+
const walk = (node, parentId, setSize, posInSet) => {
|
|
3844
|
+
const id = node.task.external_id;
|
|
3845
|
+
const expanded = !collapsed.has(id);
|
|
3846
|
+
const all = kids.get(id);
|
|
3847
|
+
const childStats = all ? { done: all.filter((c) => asTaskStatus(c.status) === "done").length, total: all.length } : void 0;
|
|
3848
|
+
let row = {
|
|
3849
|
+
external_id: id,
|
|
3850
|
+
task: node.task,
|
|
3851
|
+
depth: node.depth,
|
|
3852
|
+
childStats,
|
|
3853
|
+
expanded,
|
|
3854
|
+
parentId,
|
|
3855
|
+
setSize,
|
|
3856
|
+
posInSet,
|
|
3857
|
+
context: node.context
|
|
3858
|
+
};
|
|
3859
|
+
const prev = cache?.get(id);
|
|
3860
|
+
if (prev && prev.task === row.task && prev.depth === row.depth && prev.expanded === row.expanded && prev.parentId === row.parentId && prev.setSize === row.setSize && prev.posInSet === row.posInSet && prev.context === row.context && sameStats(prev.childStats, row.childStats)) {
|
|
3861
|
+
row = prev;
|
|
3862
|
+
}
|
|
3863
|
+
used.add(id);
|
|
3864
|
+
cache?.set(id, row);
|
|
3865
|
+
rows.push(row);
|
|
3866
|
+
if (expanded) {
|
|
3867
|
+
node.children.forEach((child, i) => walk(child, id, node.children.length, i + 1));
|
|
3868
|
+
}
|
|
3869
|
+
};
|
|
3870
|
+
const ordered = [...STATUS_ORDER, "sorted"].flatMap((s) => sections.get(s) ?? []);
|
|
3871
|
+
ordered.forEach((node, i) => walk(node, null, ordered.length, i + 1));
|
|
3872
|
+
if (cache) {
|
|
3873
|
+
for (const id of [...cache.keys()]) if (!used.has(id)) cache.delete(id);
|
|
3874
|
+
}
|
|
3875
|
+
return rows;
|
|
3876
|
+
}
|
|
3877
|
+
|
|
3878
|
+
// src/agents/tasks/taskTableLabels.ts
|
|
3879
|
+
var DEFAULT_TASK_LIST_LABELS = {
|
|
3880
|
+
filterAll: "All",
|
|
3881
|
+
emptyTitle: "No tasks yet",
|
|
3882
|
+
emptyMessage: "Use New to add one: just type what you need, or fill in an owner and a due date. Automations that create tasks live on the Workflows page. You always decide when a task is done.",
|
|
3883
|
+
noMatches: "No tasks match.",
|
|
3884
|
+
due: (when) => when,
|
|
3885
|
+
overdue: (when) => `${when} \xB7 overdue`,
|
|
3886
|
+
agent: "Agent",
|
|
3887
|
+
colTask: "Task",
|
|
3888
|
+
colOwner: "Owner",
|
|
3889
|
+
ownerHint: "Who has the next step. They are notified when the previous step finishes.",
|
|
3890
|
+
colOutputs: "Outputs",
|
|
3891
|
+
changeOwner: "Change owner\u2026",
|
|
3892
|
+
changeOwnerTitle: (name) => `Who has the next step on \u201C${name}\u201D?`,
|
|
3893
|
+
changeOwnerMe: "Me",
|
|
3894
|
+
preparedBy: (agent) => `Prepared by ${agent}`,
|
|
3895
|
+
colDue: "Due",
|
|
3896
|
+
colStatus: "Status",
|
|
3897
|
+
me: "Me",
|
|
3898
|
+
someone: "Someone",
|
|
3899
|
+
noDue: "\u2014",
|
|
3900
|
+
colShared: "Shared",
|
|
3901
|
+
shared: "Shared with the workspace",
|
|
3902
|
+
sharedOwnerOnly: "Only the creator can change who can see this",
|
|
3903
|
+
deleteOwnerOnly: "Only the creator or workspace owner can delete this",
|
|
3904
|
+
goalMet: (met, total) => `${met}/${total} met`,
|
|
3905
|
+
subtasksDone: (done, total) => `${done}/${total} sub-tasks done`,
|
|
3906
|
+
expandSubtasks: "Show sub-tasks",
|
|
3907
|
+
collapseSubtasks: "Hide sub-tasks",
|
|
3908
|
+
selectAll: "Select all tasks",
|
|
3909
|
+
selectTask: (name) => `Select ${name}`,
|
|
3910
|
+
markDone: "Mark done",
|
|
3911
|
+
reopen: "Reopen",
|
|
3912
|
+
markDoneMany: "Mark done",
|
|
3913
|
+
markDoneManyHint: "Marks your own to-dos done. Agent work is finished by reviewing it.",
|
|
3914
|
+
deleteMany: "Delete",
|
|
3915
|
+
approve: "Approve",
|
|
3916
|
+
moveTo: "Move to\u2026",
|
|
3917
|
+
untitled: "Untitled task",
|
|
3918
|
+
fromWorkflow: (name) => `From \u201C${name}\u201D`,
|
|
3919
|
+
searchLabel: "Search tasks",
|
|
3920
|
+
searchPlaceholder: "Search tasks\u2026",
|
|
3921
|
+
expandAll: "Expand all",
|
|
3922
|
+
collapseAll: "Collapse all",
|
|
3923
|
+
moveToTitle: (name) => `Move \u201C${name}\u201D to\u2026`,
|
|
3924
|
+
moveToNone: "No parent (top level)",
|
|
3925
|
+
moveToSearch: "Search tasks\u2026",
|
|
3926
|
+
moveToEmpty: "No task to move it under.",
|
|
3927
|
+
moveToCancel: "Cancel",
|
|
3928
|
+
subtasksSelected: (count) => `${count} ${count === 1 ? "sub-task" : "sub-tasks"} included`,
|
|
3929
|
+
addSubtask: "Add sub-task",
|
|
3930
|
+
edit: "Edit",
|
|
3931
|
+
rename: "Rename",
|
|
3932
|
+
delete: "Delete",
|
|
3933
|
+
grantAccess: "Allow access and continue",
|
|
3934
|
+
allowAccess: "Allow access",
|
|
3935
|
+
moreActions: "More actions",
|
|
3936
|
+
activity: "Activity",
|
|
3937
|
+
statusHint: (status, ago, forWho) => [status, ago, forWho && `for ${forWho}`].filter(Boolean).join(" \xB7 "),
|
|
3938
|
+
status: {}
|
|
3939
|
+
};
|
|
3940
|
+
var ROW_HEIGHT = 56;
|
|
3941
|
+
var NARROW_ROW_HEIGHT = 76;
|
|
3942
|
+
var MAX_INDENT_DEPTH = 4;
|
|
3943
|
+
var ANIMATE_ROWS_UP_TO = 500;
|
|
3944
|
+
var NARROW_GRID = 640;
|
|
3945
|
+
var WIDTH_RULES = [
|
|
3946
|
+
{ colId: "shared", minWidth: 1050 },
|
|
3947
|
+
{ colId: "due", minWidth: 850 },
|
|
3948
|
+
{ colId: "outputs", minWidth: 930 },
|
|
3949
|
+
{ colId: "owner", minWidth: 730 },
|
|
3950
|
+
{ colId: "status", minWidth: NARROW_GRID }
|
|
3951
|
+
];
|
|
3952
|
+
function statusHint(task, ctx) {
|
|
3953
|
+
const { props: p, l, owner } = ctx;
|
|
3954
|
+
if (!p.formatRelative || !task.updated_at) return void 0;
|
|
3955
|
+
const key = asTaskStatus(task.status);
|
|
3956
|
+
const pill = { ...DEFAULT_TASK_STATUS_PILL_LABELS, ...p.statusPillLabels };
|
|
3957
|
+
const label = task.pending_auth_request_id ? pill.waitingForAccess : STATUS_LABELS[key];
|
|
3958
|
+
return l.statusHint(
|
|
3959
|
+
label,
|
|
3960
|
+
p.formatRelative(task.updated_at),
|
|
3961
|
+
key === "ready_for_review" ? owner(task).label : void 0
|
|
3962
|
+
);
|
|
3963
|
+
}
|
|
3964
|
+
function TaskTable(props) {
|
|
3965
|
+
const { tasks: allTasks, isLoading, busyId, header, testId } = props;
|
|
3966
|
+
const l = {
|
|
3967
|
+
...DEFAULT_TASK_LIST_LABELS,
|
|
3968
|
+
...props.labels,
|
|
3969
|
+
status: { ...STATUS_LABELS, ...props.labels?.status }
|
|
3970
|
+
};
|
|
3954
3971
|
const [filter, setFilter] = react.useState("all");
|
|
3955
3972
|
const [query, setQuery] = react.useState("");
|
|
3956
3973
|
const [collapsed, setCollapsed] = react.useState(/* @__PURE__ */ new Set());
|
|
@@ -4505,7 +4522,7 @@ function TaskTable(props) {
|
|
|
4505
4522
|
testId: "task-list-empty"
|
|
4506
4523
|
}
|
|
4507
4524
|
) : /* @__PURE__ */ jsxRuntime.jsx("div", { className: "min-h-0 flex-1", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
4508
|
-
|
|
4525
|
+
chunkIA7RTPT3_cjs.GridView,
|
|
4509
4526
|
{
|
|
4510
4527
|
testId: "task-grid",
|
|
4511
4528
|
gridId: props.gridId ?? "tasks-grid-v4",
|
|
@@ -4531,7 +4548,7 @@ function TaskTable(props) {
|
|
|
4531
4548
|
}
|
|
4532
4549
|
) }),
|
|
4533
4550
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
4534
|
-
|
|
4551
|
+
chunkIA7RTPT3_cjs.SelectionBar,
|
|
4535
4552
|
{
|
|
4536
4553
|
count: selectedTasks.length,
|
|
4537
4554
|
onClear: clearSelection,
|
|
@@ -4539,7 +4556,7 @@ function TaskTable(props) {
|
|
|
4539
4556
|
children: (isCompact) => /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
4540
4557
|
props.selectionActions?.(selectedTasks, isCompact, clearSelection),
|
|
4541
4558
|
props.onMarkDoneMany && /* @__PURE__ */ jsxRuntime.jsx(
|
|
4542
|
-
|
|
4559
|
+
chunkIA7RTPT3_cjs.SelectionBarAction,
|
|
4543
4560
|
{
|
|
4544
4561
|
icon: lucideReact.CheckCheck,
|
|
4545
4562
|
label: l.markDoneMany,
|
|
@@ -4554,7 +4571,7 @@ function TaskTable(props) {
|
|
|
4554
4571
|
}
|
|
4555
4572
|
),
|
|
4556
4573
|
props.onDeleteMany && /* @__PURE__ */ jsxRuntime.jsx(
|
|
4557
|
-
|
|
4574
|
+
chunkIA7RTPT3_cjs.SelectionBarAction,
|
|
4558
4575
|
{
|
|
4559
4576
|
icon: lucideReact.Trash2,
|
|
4560
4577
|
label: l.deleteMany,
|
|
@@ -4586,29 +4603,819 @@ function TaskTable(props) {
|
|
|
4586
4603
|
empty: l.moveToEmpty,
|
|
4587
4604
|
cancel: l.moveToCancel
|
|
4588
4605
|
},
|
|
4589
|
-
testId: "task-owner"
|
|
4606
|
+
testId: "task-owner"
|
|
4607
|
+
}
|
|
4608
|
+
),
|
|
4609
|
+
moving && props.onMove && /* @__PURE__ */ jsxRuntime.jsx(
|
|
4610
|
+
TaskMoveDialog,
|
|
4611
|
+
{
|
|
4612
|
+
open: true,
|
|
4613
|
+
onOpenChange: (open) => !open && setMoving(null),
|
|
4614
|
+
options: moveTargets(tasks, moving).map((t) => ({ id: t.external_id, label: nameOf(t) })),
|
|
4615
|
+
currentParentId: moving.parent_conversation_ext_id,
|
|
4616
|
+
onPick: (parentId) => props.onMove?.(moving, parentId),
|
|
4617
|
+
labels: {
|
|
4618
|
+
title: l.moveToTitle(nameOf(moving)),
|
|
4619
|
+
none: l.moveToNone,
|
|
4620
|
+
search: l.moveToSearch,
|
|
4621
|
+
empty: l.moveToEmpty,
|
|
4622
|
+
cancel: l.moveToCancel
|
|
4623
|
+
}
|
|
4624
|
+
}
|
|
4625
|
+
)
|
|
4626
|
+
]
|
|
4627
|
+
}
|
|
4628
|
+
);
|
|
4629
|
+
}
|
|
4630
|
+
function TaskInbox(p) {
|
|
4631
|
+
const [filterOpen, setFilterOpen] = react.useState(false);
|
|
4632
|
+
const [statusFilters, setStatusFilters] = react.useState(
|
|
4633
|
+
() => /* @__PURE__ */ new Map([["done", "exclude"]])
|
|
4634
|
+
);
|
|
4635
|
+
const [localQuery, setLocalQuery] = react.useState("");
|
|
4636
|
+
const [searchFields, setSearchFields] = react.useState(["text", "labels"]);
|
|
4637
|
+
const [selected, setSelected] = react.useState(/* @__PURE__ */ new Set());
|
|
4638
|
+
const [collapsed, setCollapsed] = react.useState(/* @__PURE__ */ new Set());
|
|
4639
|
+
const [moving, setMoving] = react.useState(null);
|
|
4640
|
+
const [handingOff, setHandingOff] = react.useState(null);
|
|
4641
|
+
const l = { ...DEFAULT_TASK_LIST_LABELS, ...p.labels };
|
|
4642
|
+
const nameOf = (t) => t.title?.trim() || t.workflow_ext_id && p.workflowNames?.[t.workflow_ext_id] || l.untitled;
|
|
4643
|
+
const all = p.tasks.filter((t) => t.status != null);
|
|
4644
|
+
const filterText = p.filterText ?? localQuery;
|
|
4645
|
+
const q = filterText.trim().toLowerCase();
|
|
4646
|
+
const included = [...statusFilters].filter(([, state]) => state === "include").map(([id]) => id);
|
|
4647
|
+
const statusMatches = (t) => statusFilters.get(asTaskStatus(t.status)) !== "exclude" && (!included.length || included.includes(asTaskStatus(t.status)));
|
|
4648
|
+
const rows = all.filter(
|
|
4649
|
+
(t) => statusMatches(t) && (!q || [
|
|
4650
|
+
searchFields.includes("text") ? `${nameOf(t)} ${t.description ?? ""}` : "",
|
|
4651
|
+
searchFields.includes("labels") && t.workflow_ext_id ? p.workflowNames?.[t.workflow_ext_id] ?? "" : ""
|
|
4652
|
+
].join(" ").toLowerCase().includes(q))
|
|
4653
|
+
);
|
|
4654
|
+
const hasActiveFilters = !!q || [...statusFilters.values()].some((state) => state != null);
|
|
4655
|
+
const selectedTasks = all.filter((t) => selected.has(t.external_id));
|
|
4656
|
+
const canEdit = (t) => t.is_owner !== false || Boolean(p.canEditShared);
|
|
4657
|
+
const markable = (t) => t.status !== "done" && t.status !== "generating" && canEdit(t) && !t.in_progress;
|
|
4658
|
+
const markableTasks = selectedTasks.filter(markable);
|
|
4659
|
+
const deletableTasks = selectedTasks.filter((t) => t.is_owner !== false || p.isWorkspaceOwner);
|
|
4660
|
+
const clearSelection = () => setSelected(/* @__PURE__ */ new Set());
|
|
4661
|
+
const toggle = (set, id) => set((old) => {
|
|
4662
|
+
const next = new Set(old);
|
|
4663
|
+
if (next.has(id)) next.delete(id);
|
|
4664
|
+
else next.add(id);
|
|
4665
|
+
return next;
|
|
4666
|
+
});
|
|
4667
|
+
p.renderPerson ?? ((value) => /* @__PURE__ */ jsxRuntime.jsx(PersonPill, { person: value }));
|
|
4668
|
+
const taskById = new Map(all.map((t) => [t.external_id, t]));
|
|
4669
|
+
const visible = new Set(rows.map((t) => t.external_id));
|
|
4670
|
+
for (const task of rows) {
|
|
4671
|
+
let id = task.parent_conversation_ext_id;
|
|
4672
|
+
const seen = /* @__PURE__ */ new Set();
|
|
4673
|
+
while (id && taskById.has(id) && !seen.has(id)) {
|
|
4674
|
+
seen.add(id);
|
|
4675
|
+
visible.add(id);
|
|
4676
|
+
id = taskById.get(id)?.parent_conversation_ext_id;
|
|
4677
|
+
}
|
|
4678
|
+
}
|
|
4679
|
+
const listed = all.filter((t) => visible.has(t.external_id));
|
|
4680
|
+
const roots = listed.filter(
|
|
4681
|
+
(t) => !t.parent_conversation_ext_id || !visible.has(t.parent_conversation_ext_id)
|
|
4682
|
+
);
|
|
4683
|
+
const workflows = (p.workflows ?? []).filter((w) => {
|
|
4684
|
+
const runs = roots.filter((t) => t.workflow_ext_id === w.external_id);
|
|
4685
|
+
return runs.length > 0 || !included.length && (!q || w.name.toLowerCase().includes(q));
|
|
4686
|
+
});
|
|
4687
|
+
const workflowIds = new Set(workflows.map((w) => w.external_id));
|
|
4688
|
+
const order = (a, b) => {
|
|
4689
|
+
const weight = (t) => t.pending_auth_request_id || t.last_error ? 0 : t.status === "ready_for_review" ? 1 : t.status === "todo" ? 2 : t.status === "generating" ? 3 : 4;
|
|
4690
|
+
return weight(a) - weight(b) || (b.updated_at ?? "").localeCompare(a.updated_at ?? "");
|
|
4691
|
+
};
|
|
4692
|
+
const renderTask = (task, depth = 0) => {
|
|
4693
|
+
const id = task.external_id;
|
|
4694
|
+
const status = asTaskStatus(task.status);
|
|
4695
|
+
const busy = p.busyId === id;
|
|
4696
|
+
const children = listed.filter((t) => t.parent_conversation_ext_id === id).sort(order);
|
|
4697
|
+
const outputs = p.outputsByTask?.[id] ?? [];
|
|
4698
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("li", { "data-testid": `task-inbox-row-${id}`, children: [
|
|
4699
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
4700
|
+
"div",
|
|
4701
|
+
{
|
|
4702
|
+
className: ui.cn(
|
|
4703
|
+
"relative flex cursor-pointer items-start gap-2 border-b py-3 hover:bg-muted/40",
|
|
4704
|
+
selected.has(id) && "bg-muted/60"
|
|
4705
|
+
),
|
|
4706
|
+
onClick: (event) => {
|
|
4707
|
+
if (!event.target.closest(
|
|
4708
|
+
'button, a, input, select, textarea, [role="menuitem"], [role="checkbox"], [role="combobox"]'
|
|
4709
|
+
)) {
|
|
4710
|
+
p.onOpenThread(id, task);
|
|
4711
|
+
}
|
|
4712
|
+
},
|
|
4713
|
+
style: { paddingLeft: `${Math.min(depth, 5) * 20}px` },
|
|
4714
|
+
children: [
|
|
4715
|
+
children.length > 0 && /* @__PURE__ */ jsxRuntime.jsx(
|
|
4716
|
+
ui.Button,
|
|
4717
|
+
{
|
|
4718
|
+
variant: "ghost",
|
|
4719
|
+
size: "icon",
|
|
4720
|
+
className: "size-7 shrink-0",
|
|
4721
|
+
"aria-label": `${collapsed.has(id) ? "Expand" : "Collapse"} ${nameOf(task)}`,
|
|
4722
|
+
onClick: () => toggle(setCollapsed, id),
|
|
4723
|
+
children: collapsed.has(id) ? /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronRight, { className: "size-4" }) : /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronDown, { className: "size-4" })
|
|
4724
|
+
}
|
|
4725
|
+
),
|
|
4726
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "min-w-0 flex-1", children: [
|
|
4727
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
4728
|
+
"button",
|
|
4729
|
+
{
|
|
4730
|
+
className: ui.cn(
|
|
4731
|
+
"block w-full text-left text-sm font-medium hover:underline",
|
|
4732
|
+
status === "done" && "text-muted-foreground"
|
|
4733
|
+
),
|
|
4734
|
+
"data-testid": `task-open-${id}`,
|
|
4735
|
+
onClick: () => p.onOpenThread(id, task),
|
|
4736
|
+
children: nameOf(task)
|
|
4737
|
+
}
|
|
4738
|
+
),
|
|
4739
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "mt-1 flex flex-wrap items-center gap-x-3 gap-y-1 text-xs text-muted-foreground", children: [
|
|
4740
|
+
status !== "todo" && status !== "ready_for_review" && /* @__PURE__ */ jsxRuntime.jsx(
|
|
4741
|
+
TaskStatusPill,
|
|
4742
|
+
{
|
|
4743
|
+
id,
|
|
4744
|
+
status: task.status,
|
|
4745
|
+
runStartedAt: task.run_started_at,
|
|
4746
|
+
lastError: task.last_error,
|
|
4747
|
+
awaitingAccess: Boolean(task.pending_auth_request_id)
|
|
4748
|
+
}
|
|
4749
|
+
),
|
|
4750
|
+
task.due_at && /* @__PURE__ */ jsxRuntime.jsxs("span", { children: [
|
|
4751
|
+
"Due ",
|
|
4752
|
+
p.formatDate(task.due_at)
|
|
4753
|
+
] }),
|
|
4754
|
+
children.length > 0 && /* @__PURE__ */ jsxRuntime.jsxs("span", { children: [
|
|
4755
|
+
all.filter((t) => t.parent_conversation_ext_id === id && t.status === "done").length,
|
|
4756
|
+
"/",
|
|
4757
|
+
all.filter((t) => t.parent_conversation_ext_id === id).length,
|
|
4758
|
+
" steps complete"
|
|
4759
|
+
] })
|
|
4760
|
+
] }),
|
|
4761
|
+
outputs.length > 0 && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "mt-2 flex flex-wrap gap-2", "aria-label": "Outputs", children: outputs.map((output) => /* @__PURE__ */ jsxRuntime.jsxs(
|
|
4762
|
+
ui.Button,
|
|
4763
|
+
{
|
|
4764
|
+
variant: "link",
|
|
4765
|
+
size: "sm",
|
|
4766
|
+
className: "h-auto max-w-full gap-1 px-0 py-1 text-xs",
|
|
4767
|
+
disabled: !p.onOpenOutput,
|
|
4768
|
+
onClick: () => p.onOpenOutput?.(output.id, task),
|
|
4769
|
+
"data-testid": `task-output-${id}-${output.id}`,
|
|
4770
|
+
children: [
|
|
4771
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.FileText, { className: "size-3.5 shrink-0" }),
|
|
4772
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate", children: output.name })
|
|
4773
|
+
]
|
|
4774
|
+
},
|
|
4775
|
+
output.id
|
|
4776
|
+
)) })
|
|
4777
|
+
] }),
|
|
4778
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex shrink-0 items-center gap-1", children: [
|
|
4779
|
+
task.pending_auth_request_id && task.is_owner !== false && p.onGrantAccess && /* @__PURE__ */ jsxRuntime.jsx(
|
|
4780
|
+
ui.Button,
|
|
4781
|
+
{
|
|
4782
|
+
size: "sm",
|
|
4783
|
+
variant: "outline",
|
|
4784
|
+
disabled: busy,
|
|
4785
|
+
onClick: () => p.onGrantAccess?.(task),
|
|
4786
|
+
children: "Allow access"
|
|
4787
|
+
}
|
|
4788
|
+
),
|
|
4789
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
4790
|
+
TaskRowMenu,
|
|
4791
|
+
{
|
|
4792
|
+
task,
|
|
4793
|
+
status,
|
|
4794
|
+
busy,
|
|
4795
|
+
isOwner: task.is_owner !== false,
|
|
4796
|
+
canAdmin: task.is_owner !== false || Boolean(p.isWorkspaceOwner),
|
|
4797
|
+
canEdit: canEdit(task),
|
|
4798
|
+
canMarkDone: markable(task),
|
|
4799
|
+
canReopen: canEdit(task),
|
|
4800
|
+
selected: selected.has(id),
|
|
4801
|
+
onToggleSelected: p.selectionActions || p.onMarkDoneMany || p.onDeleteMany ? () => toggle(setSelected, id) : void 0,
|
|
4802
|
+
labels: l,
|
|
4803
|
+
onMarkDone: () => p.onMarkDone(task),
|
|
4804
|
+
onNotify: p.onNotify ? () => p.onNotify?.(task) : void 0,
|
|
4805
|
+
onReopen: () => p.onReopen(task),
|
|
4806
|
+
onEdit: () => p.onEdit(task),
|
|
4807
|
+
onAddSubtask: p.onAddSubtask ? () => p.onAddSubtask?.(task) : void 0,
|
|
4808
|
+
onMoveTo: p.onMove ? () => setMoving(task) : void 0,
|
|
4809
|
+
onChangeOwner: status !== "ready_for_review" && p.onChangeOwner && p.people?.length ? () => setHandingOff(task) : void 0,
|
|
4810
|
+
onOpenActivity: p.onOpenActivity ? () => p.onOpenActivity?.(task) : void 0,
|
|
4811
|
+
onToggleShared: p.onToggleShared ? () => p.onToggleShared?.(task, !task.is_shared) : void 0
|
|
4812
|
+
}
|
|
4813
|
+
)
|
|
4814
|
+
] })
|
|
4815
|
+
]
|
|
4816
|
+
}
|
|
4817
|
+
),
|
|
4818
|
+
children.length > 0 && !collapsed.has(id) && /* @__PURE__ */ jsxRuntime.jsx("ul", { children: children.map((child) => renderTask(child, depth + 1)) })
|
|
4819
|
+
] }, id);
|
|
4820
|
+
};
|
|
4821
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex min-h-0 flex-1 flex-col", "data-testid": p.testId ?? "task-inbox", children: [
|
|
4822
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
4823
|
+
chunk6DNYPLCD_cjs.TabHeader,
|
|
4824
|
+
{
|
|
4825
|
+
testId: "tasks-tab-header",
|
|
4826
|
+
tabs: [
|
|
4827
|
+
{
|
|
4828
|
+
id: "tasks",
|
|
4829
|
+
label: "",
|
|
4830
|
+
count: rows.length,
|
|
4831
|
+
countPlacement: "leading",
|
|
4832
|
+
countIcon: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ListTodo, { className: "size-3.5" }),
|
|
4833
|
+
hasActiveFilters,
|
|
4834
|
+
testId: "tasks-tab",
|
|
4835
|
+
presentation: "count"
|
|
4836
|
+
}
|
|
4837
|
+
],
|
|
4838
|
+
activeTabId: "tasks",
|
|
4839
|
+
onTabChange: () => {
|
|
4840
|
+
},
|
|
4841
|
+
firstTabContent: /* @__PURE__ */ jsxRuntime.jsx(
|
|
4842
|
+
chunkMZL67U2E_cjs.FilterInput,
|
|
4843
|
+
{
|
|
4844
|
+
value: filterText,
|
|
4845
|
+
onChange: p.onFilterTextChange ?? setLocalQuery,
|
|
4846
|
+
fields: searchFields,
|
|
4847
|
+
onFieldsChange: setSearchFields,
|
|
4848
|
+
labels: { fieldNames: { text: "Task", labels: "Workflow" } },
|
|
4849
|
+
className: "w-44 max-w-[40vw]",
|
|
4850
|
+
testIds: {
|
|
4851
|
+
root: "tasks-filter",
|
|
4852
|
+
input: "tasks-filter-input",
|
|
4853
|
+
fieldsButton: "tasks-filter-fields"
|
|
4854
|
+
},
|
|
4855
|
+
filter: /* @__PURE__ */ jsxRuntime.jsx(
|
|
4856
|
+
chunk2QTT2RZE_cjs.TriStateFilterMenu,
|
|
4857
|
+
{
|
|
4858
|
+
testId: "tasks-status-filter",
|
|
4859
|
+
open: filterOpen,
|
|
4860
|
+
onOpenChange: setFilterOpen,
|
|
4861
|
+
filterStates: statusFilters,
|
|
4862
|
+
onFiltersChange: setStatusFilters,
|
|
4863
|
+
options: [
|
|
4864
|
+
{
|
|
4865
|
+
id: "todo",
|
|
4866
|
+
label: "To do",
|
|
4867
|
+
count: all.filter((t) => t.status === "todo").length
|
|
4868
|
+
},
|
|
4869
|
+
{
|
|
4870
|
+
id: "generating",
|
|
4871
|
+
label: "Generating",
|
|
4872
|
+
count: all.filter((t) => t.status === "generating").length
|
|
4873
|
+
},
|
|
4874
|
+
{
|
|
4875
|
+
id: "ready_for_review",
|
|
4876
|
+
label: "Ready for review",
|
|
4877
|
+
count: all.filter((t) => t.status === "ready_for_review").length
|
|
4878
|
+
},
|
|
4879
|
+
{
|
|
4880
|
+
id: "done",
|
|
4881
|
+
label: "Completed",
|
|
4882
|
+
count: all.filter((t) => t.status === "done").length
|
|
4883
|
+
}
|
|
4884
|
+
],
|
|
4885
|
+
groups: [
|
|
4886
|
+
{ label: "Status", options: ["todo", "generating", "ready_for_review", "done"] }
|
|
4887
|
+
],
|
|
4888
|
+
triggerClassName: "flex h-5 items-center gap-0.5 rounded px-1 text-muted-foreground hover:text-foreground pointer-coarse:h-11! pointer-coarse:min-w-11 pointer-coarse:justify-center",
|
|
4889
|
+
renderChevron: true,
|
|
4890
|
+
disableHoverOpen: true
|
|
4891
|
+
}
|
|
4892
|
+
)
|
|
4893
|
+
}
|
|
4894
|
+
),
|
|
4895
|
+
rightContent: p.onCreate ? /* @__PURE__ */ jsxRuntime.jsxs(ui.DropdownMenu, { children: [
|
|
4896
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { "data-testid": "new-task-button", children: [
|
|
4897
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Plus, { className: "mr-1 size-4" }),
|
|
4898
|
+
"New",
|
|
4899
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronDown, { className: "ml-1 size-3" })
|
|
4900
|
+
] }) }),
|
|
4901
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DropdownMenuContent, { align: "end", children: [
|
|
4902
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuItem, { onSelect: p.onCreate, children: "Task" }),
|
|
4903
|
+
p.onCreateWorkflow && /* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuItem, { onSelect: p.onCreateWorkflow, children: "Saved workflow" })
|
|
4904
|
+
] })
|
|
4905
|
+
] }) : p.header
|
|
4906
|
+
}
|
|
4907
|
+
),
|
|
4908
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "min-h-0 flex-1 overflow-y-auto", "aria-busy": p.isLoading, children: p.isLoading ? /* @__PURE__ */ jsxRuntime.jsx("p", { className: "py-12 text-center text-sm text-muted-foreground", children: "Loading work\u2026" }) : !listed.length && !workflows.length ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
4909
|
+
chunkZW6FPIFC_cjs.EmptyState,
|
|
4910
|
+
{
|
|
4911
|
+
title: q ? "No matches" : all.length ? "You\u2019re all caught up" : "No work here yet",
|
|
4912
|
+
description: "Create a task from a prompt or a saved workflow. Keep its drafts, reviews and handoffs together."
|
|
4913
|
+
}
|
|
4914
|
+
) : /* @__PURE__ */ jsxRuntime.jsxs("ul", { children: [
|
|
4915
|
+
workflows.map((w) => {
|
|
4916
|
+
const runs = roots.filter((t) => t.workflow_ext_id === w.external_id).sort(order);
|
|
4917
|
+
const editable = w.is_owner !== false || p.canEditShared;
|
|
4918
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("li", { "data-testid": `task-workflow-${w.external_id}`, children: [
|
|
4919
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-start gap-2 border-b py-3", children: [
|
|
4920
|
+
runs.length > 0 ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
4921
|
+
ui.Button,
|
|
4922
|
+
{
|
|
4923
|
+
variant: "ghost",
|
|
4924
|
+
size: "icon",
|
|
4925
|
+
className: "size-7",
|
|
4926
|
+
"aria-label": `${collapsed.has(w.external_id) ? "Expand" : "Collapse"} ${w.name}`,
|
|
4927
|
+
onClick: () => toggle(setCollapsed, w.external_id),
|
|
4928
|
+
children: collapsed.has(w.external_id) ? /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronRight, { className: "size-4" }) : /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronDown, { className: "size-4" })
|
|
4929
|
+
}
|
|
4930
|
+
) : /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Workflow, { className: "mx-1 mt-1 size-4 shrink-0 text-muted-foreground" }),
|
|
4931
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "min-w-0 flex-1", children: [
|
|
4932
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
4933
|
+
"button",
|
|
4934
|
+
{
|
|
4935
|
+
className: "block text-left text-sm font-medium hover:underline",
|
|
4936
|
+
disabled: !editable,
|
|
4937
|
+
onClick: () => p.onEditWorkflow?.(w.external_id),
|
|
4938
|
+
children: w.name
|
|
4939
|
+
}
|
|
4940
|
+
),
|
|
4941
|
+
/* @__PURE__ */ jsxRuntime.jsxs("p", { className: "mt-1 text-xs text-muted-foreground", children: [
|
|
4942
|
+
"Saved workflow \xB7 ",
|
|
4943
|
+
w.summary ?? "Run when needed",
|
|
4944
|
+
!w.active ? " \xB7 Paused" : "",
|
|
4945
|
+
runs.length ? ` \xB7 ${runs.length} ${runs.length === 1 ? "task" : "tasks"}` : ""
|
|
4946
|
+
] }),
|
|
4947
|
+
w.last_error && /* @__PURE__ */ jsxRuntime.jsx("p", { className: "mt-1 text-xs text-destructive", children: w.last_error })
|
|
4948
|
+
] }),
|
|
4949
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DropdownMenu, { children: [
|
|
4950
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
4951
|
+
ui.Button,
|
|
4952
|
+
{
|
|
4953
|
+
variant: "ghost",
|
|
4954
|
+
size: "icon",
|
|
4955
|
+
className: "size-8",
|
|
4956
|
+
"aria-label": `Actions for ${w.name}`,
|
|
4957
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.MoreHorizontal, { className: "size-4" })
|
|
4958
|
+
}
|
|
4959
|
+
) }),
|
|
4960
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DropdownMenuContent, { align: "end", children: [
|
|
4961
|
+
p.onWorkflowHistory && /* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuItem, { onSelect: () => p.onWorkflowHistory?.(w.external_id), children: "Run history" }),
|
|
4962
|
+
editable && p.onToggleWorkflow && /* @__PURE__ */ jsxRuntime.jsx(
|
|
4963
|
+
ui.DropdownMenuItem,
|
|
4964
|
+
{
|
|
4965
|
+
onSelect: () => p.onToggleWorkflow?.(w.external_id, !w.active),
|
|
4966
|
+
children: w.active ? "Pause" : "Resume"
|
|
4967
|
+
}
|
|
4968
|
+
),
|
|
4969
|
+
(w.is_owner !== false || p.isWorkspaceOwner) && p.onDeleteWorkflow && /* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuItem, { onSelect: () => p.onDeleteWorkflow?.(w.external_id), children: "Delete workflow" })
|
|
4970
|
+
] })
|
|
4971
|
+
] })
|
|
4972
|
+
] }),
|
|
4973
|
+
!collapsed.has(w.external_id) && runs.length > 0 && /* @__PURE__ */ jsxRuntime.jsx("ul", { children: runs.map((t) => renderTask(t, 1)) })
|
|
4974
|
+
] }, w.external_id);
|
|
4975
|
+
}),
|
|
4976
|
+
roots.filter((t) => !t.workflow_ext_id || !workflowIds.has(t.workflow_ext_id)).sort(order).map((t) => renderTask(t))
|
|
4977
|
+
] }) }),
|
|
4978
|
+
/* @__PURE__ */ jsxRuntime.jsx(chunkIA7RTPT3_cjs.SelectionBar, { count: selectedTasks.length, onClear: clearSelection, children: (isCompact) => /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
4979
|
+
p.selectionActions?.(selectedTasks, isCompact, clearSelection),
|
|
4980
|
+
p.onMarkDoneMany && /* @__PURE__ */ jsxRuntime.jsx(
|
|
4981
|
+
chunkIA7RTPT3_cjs.SelectionBarAction,
|
|
4982
|
+
{
|
|
4983
|
+
icon: lucideReact.CheckCheck,
|
|
4984
|
+
label: l.markDoneMany,
|
|
4985
|
+
isCompact,
|
|
4986
|
+
disabled: !markableTasks.length,
|
|
4987
|
+
onClick: () => {
|
|
4988
|
+
p.onMarkDoneMany?.(markableTasks);
|
|
4989
|
+
clearSelection();
|
|
4990
|
+
},
|
|
4991
|
+
testId: "task-bulk-done"
|
|
4992
|
+
}
|
|
4993
|
+
),
|
|
4994
|
+
p.onDeleteMany && /* @__PURE__ */ jsxRuntime.jsx(
|
|
4995
|
+
chunkIA7RTPT3_cjs.SelectionBarAction,
|
|
4996
|
+
{
|
|
4997
|
+
icon: lucideReact.Trash2,
|
|
4998
|
+
label: l.deleteMany,
|
|
4999
|
+
isCompact,
|
|
5000
|
+
disabled: !deletableTasks.length,
|
|
5001
|
+
onClick: () => {
|
|
5002
|
+
p.onDeleteMany?.(deletableTasks);
|
|
5003
|
+
clearSelection();
|
|
5004
|
+
},
|
|
5005
|
+
className: "text-red-text hover:bg-red-bg hover:text-red-text",
|
|
5006
|
+
testId: "task-bulk-delete"
|
|
5007
|
+
}
|
|
5008
|
+
)
|
|
5009
|
+
] }) }),
|
|
5010
|
+
moving && p.onMove && /* @__PURE__ */ jsxRuntime.jsx(
|
|
5011
|
+
TaskMoveDialog,
|
|
5012
|
+
{
|
|
5013
|
+
open: true,
|
|
5014
|
+
onOpenChange: (open) => !open && setMoving(null),
|
|
5015
|
+
options: moveTargets(all, moving).map((t) => ({ id: t.external_id, label: nameOf(t) })),
|
|
5016
|
+
currentParentId: moving.parent_conversation_ext_id,
|
|
5017
|
+
onPick: (id) => p.onMove?.(moving, id),
|
|
5018
|
+
labels: {
|
|
5019
|
+
title: l.moveToTitle(nameOf(moving)),
|
|
5020
|
+
none: l.moveToNone,
|
|
5021
|
+
search: l.moveToSearch,
|
|
5022
|
+
empty: l.moveToEmpty,
|
|
5023
|
+
cancel: l.moveToCancel
|
|
5024
|
+
}
|
|
5025
|
+
}
|
|
5026
|
+
),
|
|
5027
|
+
handingOff && p.onChangeOwner && /* @__PURE__ */ jsxRuntime.jsx(
|
|
5028
|
+
TaskMoveDialog,
|
|
5029
|
+
{
|
|
5030
|
+
open: true,
|
|
5031
|
+
onOpenChange: (open) => !open && setHandingOff(null),
|
|
5032
|
+
options: p.people ?? [],
|
|
5033
|
+
currentParentId: handingOff.signoff_ext_id,
|
|
5034
|
+
onPick: (id) => p.onChangeOwner?.(handingOff, id),
|
|
5035
|
+
labels: {
|
|
5036
|
+
title: l.changeOwnerTitle(nameOf(handingOff)),
|
|
5037
|
+
none: l.changeOwnerMe,
|
|
5038
|
+
search: l.moveToSearch,
|
|
5039
|
+
empty: l.moveToEmpty,
|
|
5040
|
+
cancel: l.moveToCancel
|
|
5041
|
+
},
|
|
5042
|
+
testId: "task-owner"
|
|
5043
|
+
}
|
|
5044
|
+
)
|
|
5045
|
+
] });
|
|
5046
|
+
}
|
|
5047
|
+
function EntityChip({
|
|
5048
|
+
variant = "pill",
|
|
5049
|
+
icon,
|
|
5050
|
+
label,
|
|
5051
|
+
detail,
|
|
5052
|
+
pillTooltip,
|
|
5053
|
+
showTooltip = true,
|
|
5054
|
+
href,
|
|
5055
|
+
onClick,
|
|
5056
|
+
size = "sm",
|
|
5057
|
+
labelMaxWidth,
|
|
5058
|
+
className,
|
|
5059
|
+
testId
|
|
5060
|
+
}) {
|
|
5061
|
+
if (variant === "icon") {
|
|
5062
|
+
const glyph = /* @__PURE__ */ jsxRuntime.jsx(
|
|
5063
|
+
"span",
|
|
5064
|
+
{
|
|
5065
|
+
"data-slot": "entity-chip",
|
|
5066
|
+
className: ui.cn("inline-flex items-center", (onClick || href) && "cursor-pointer", className),
|
|
5067
|
+
onClick,
|
|
5068
|
+
"data-testid": testId,
|
|
5069
|
+
children: href ? /* @__PURE__ */ jsxRuntime.jsx("a", { href, target: "_blank", rel: "noopener noreferrer", children: icon }) : icon
|
|
5070
|
+
}
|
|
5071
|
+
);
|
|
5072
|
+
if (!showTooltip) return glyph;
|
|
5073
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(ui.Tooltip, { children: [
|
|
5074
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.TooltipTrigger, { className: "inline-flex", children: glyph }),
|
|
5075
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.TooltipContent, { side: "bottom", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col gap-0.5", children: [
|
|
5076
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "font-medium", children: label }),
|
|
5077
|
+
detail && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-xs text-muted-foreground", children: detail })
|
|
5078
|
+
] }) })
|
|
5079
|
+
] });
|
|
5080
|
+
}
|
|
5081
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
5082
|
+
ui.EntityPill,
|
|
5083
|
+
{
|
|
5084
|
+
icon,
|
|
5085
|
+
label,
|
|
5086
|
+
size,
|
|
5087
|
+
shape: "rounded",
|
|
5088
|
+
href,
|
|
5089
|
+
onClick,
|
|
5090
|
+
tooltipContent: pillTooltip,
|
|
5091
|
+
labelMaxWidth,
|
|
5092
|
+
className,
|
|
5093
|
+
"data-testid": testId
|
|
5094
|
+
}
|
|
5095
|
+
);
|
|
5096
|
+
}
|
|
5097
|
+
function filterConversationRows(conversations, query, labelText, doneFilter = "exclude", visibilityFilters) {
|
|
5098
|
+
const q = query.trim().toLowerCase();
|
|
5099
|
+
return [...conversations].sort(
|
|
5100
|
+
(a, b) => (Date.parse(b.last_message_updated_at || b.updated_at || b.created_at || "") || 0) - (Date.parse(a.last_message_updated_at || a.updated_at || a.created_at || "") || 0)
|
|
5101
|
+
).filter(
|
|
5102
|
+
(row) => doneFilter === "exclude" ? row.status !== "done" : doneFilter === "include" ? row.status === "done" : true
|
|
5103
|
+
).filter((row) => {
|
|
5104
|
+
const state = row.is_shared ? visibilityFilters?.workspace : visibilityFilters?.me;
|
|
5105
|
+
const hasIncluded = visibilityFilters?.me === "include" || visibilityFilters?.workspace === "include";
|
|
5106
|
+
return state !== "exclude" && (!hasIncluded || state === "include");
|
|
5107
|
+
}).filter((row) => !q || `${row.title ?? ""} ${labelText?.(row) ?? ""}`.toLowerCase().includes(q));
|
|
5108
|
+
}
|
|
5109
|
+
function ConversationListView(p) {
|
|
5110
|
+
const liveProps = react.useRef(p);
|
|
5111
|
+
liveProps.current = p;
|
|
5112
|
+
const [query, setQuery] = react.useState("");
|
|
5113
|
+
const [selected, setSelected] = react.useState(/* @__PURE__ */ new Set());
|
|
5114
|
+
const q = `${query} ${p.filterText ?? ""}`.trim().toLowerCase();
|
|
5115
|
+
const rows = react.useMemo(
|
|
5116
|
+
() => filterConversationRows(p.conversations, q, p.labelText, p.doneFilter, p.visibilityFilters),
|
|
5117
|
+
[p.conversations, q, p.labelText, p.doneFilter, p.visibilityFilters]
|
|
5118
|
+
);
|
|
5119
|
+
const selectedRows = p.conversations.filter((c) => selected.has(c.external_id));
|
|
5120
|
+
const columns = react.useMemo(
|
|
5121
|
+
() => [
|
|
5122
|
+
{
|
|
5123
|
+
colId: "name",
|
|
5124
|
+
headerName: "Thread",
|
|
5125
|
+
flex: 1,
|
|
5126
|
+
minWidth: 180,
|
|
5127
|
+
valueGetter: ({ data }) => data?.title?.trim() || "Untitled thread",
|
|
5128
|
+
cellRenderer: ({ data }) => data && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "group flex h-full min-w-0 items-center gap-2", children: [
|
|
5129
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "min-w-0", children: liveProps.current.renderThread ? liveProps.current.renderThread(data) : /* @__PURE__ */ jsxRuntime.jsx(
|
|
5130
|
+
EntityChip,
|
|
5131
|
+
{
|
|
5132
|
+
icon: /* @__PURE__ */ jsxRuntime.jsx(ui.ThreadVisibilityIcon, { shared: data.is_shared ?? false, className: "size-4" }),
|
|
5133
|
+
label: data.title?.trim() || "Untitled thread",
|
|
5134
|
+
pillTooltip: "Open conversation",
|
|
5135
|
+
labelMaxWidth: "max-w-full",
|
|
5136
|
+
onClick: () => liveProps.current.onOpen(data),
|
|
5137
|
+
testId: `thread-open-${data.external_id}`
|
|
5138
|
+
}
|
|
5139
|
+
) }),
|
|
5140
|
+
(data.is_owner !== false || liveProps.current.canEditShared) && /* @__PURE__ */ jsxRuntime.jsx(
|
|
5141
|
+
"button",
|
|
5142
|
+
{
|
|
5143
|
+
type: "button",
|
|
5144
|
+
"aria-label": `Rename ${data.title?.trim() || "Untitled thread"}`,
|
|
5145
|
+
onClick: () => liveProps.current.onRename(data),
|
|
5146
|
+
"data-testid": `thread-rename-${data.external_id}`,
|
|
5147
|
+
className: "shrink-0 pointer-coarse:flex pointer-coarse:size-11 pointer-coarse:items-center pointer-coarse:justify-center",
|
|
5148
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(chunk3AFWGEDJ_cjs.CellHoverIcon, {})
|
|
5149
|
+
}
|
|
5150
|
+
)
|
|
5151
|
+
] })
|
|
5152
|
+
},
|
|
5153
|
+
...liveProps.current.renderLabels ? [
|
|
5154
|
+
{
|
|
5155
|
+
colId: "labels",
|
|
5156
|
+
headerName: "Labels",
|
|
5157
|
+
flex: 0.5,
|
|
5158
|
+
minWidth: 160,
|
|
5159
|
+
valueGetter: ({ data }) => data ? liveProps.current.labelText?.(data) ?? "" : "",
|
|
5160
|
+
cellRenderer: ({ data }) => data && liveProps.current.renderLabels?.(data)
|
|
5161
|
+
}
|
|
5162
|
+
] : [],
|
|
5163
|
+
...liveProps.current.renderBy || liveProps.current.renderOwner ? [
|
|
5164
|
+
{
|
|
5165
|
+
colId: liveProps.current.renderBy ? "by" : "owner",
|
|
5166
|
+
headerName: liveProps.current.renderBy ? "By" : "Owner",
|
|
5167
|
+
width: 160,
|
|
5168
|
+
cellRenderer: ({ data }) => data && (liveProps.current.renderBy || liveProps.current.renderOwner)?.(data)
|
|
5169
|
+
}
|
|
5170
|
+
] : [],
|
|
5171
|
+
{
|
|
5172
|
+
colId: "status",
|
|
5173
|
+
headerName: "Status",
|
|
5174
|
+
width: 150,
|
|
5175
|
+
valueGetter: ({ data }) => data?.status,
|
|
5176
|
+
cellRenderer: ({ data }) => data && (liveProps.current.renderStatus ? liveProps.current.renderStatus(data) : /* @__PURE__ */ jsxRuntime.jsx(TaskStatusPill, { id: data.external_id, status: data.status }))
|
|
5177
|
+
},
|
|
5178
|
+
{
|
|
5179
|
+
valueGetter: ({ data }) => data?.message_count,
|
|
5180
|
+
colId: "messages",
|
|
5181
|
+
headerName: "Messages",
|
|
5182
|
+
width: 110,
|
|
5183
|
+
valueFormatter: ({ value }) => value == null ? "\u2014" : String(value),
|
|
5184
|
+
cellClass: "text-muted-foreground"
|
|
5185
|
+
},
|
|
5186
|
+
...liveProps.current.onToggleShared ? [
|
|
5187
|
+
{
|
|
5188
|
+
colId: "visibility",
|
|
5189
|
+
headerName: "Visibility",
|
|
5190
|
+
width: 100,
|
|
5191
|
+
cellClass: "cell-hcenter",
|
|
5192
|
+
sortable: false,
|
|
5193
|
+
resizable: false,
|
|
5194
|
+
cellRenderer: ({ data }) => data && /* @__PURE__ */ jsxRuntime.jsx(
|
|
5195
|
+
ui.VisibilityToggle,
|
|
5196
|
+
{
|
|
5197
|
+
items: [data],
|
|
5198
|
+
showLabel: false,
|
|
5199
|
+
disabled: data.is_owner === false,
|
|
5200
|
+
onToggle: () => liveProps.current.onToggleShared?.(data, !data.is_shared)
|
|
5201
|
+
}
|
|
5202
|
+
)
|
|
5203
|
+
}
|
|
5204
|
+
] : [],
|
|
5205
|
+
{
|
|
5206
|
+
colId: "activity",
|
|
5207
|
+
initialSort: "desc",
|
|
5208
|
+
headerName: "Activity",
|
|
5209
|
+
width: 160,
|
|
5210
|
+
valueGetter: ({ data }) => data?.last_message_updated_at || data?.updated_at || data?.created_at || "",
|
|
5211
|
+
valueFormatter: ({ value }) => value ? liveProps.current.formatDate(value) : "\u2014",
|
|
5212
|
+
cellClass: "text-muted-foreground"
|
|
5213
|
+
}
|
|
5214
|
+
],
|
|
5215
|
+
[
|
|
5216
|
+
Boolean(p.renderThread),
|
|
5217
|
+
Boolean(p.renderLabels),
|
|
5218
|
+
Boolean(p.renderOwner),
|
|
5219
|
+
Boolean(p.renderBy),
|
|
5220
|
+
Boolean(p.renderStatus),
|
|
5221
|
+
Boolean(p.onToggleShared)
|
|
5222
|
+
]
|
|
5223
|
+
);
|
|
5224
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex min-h-0 flex-1 flex-col", "data-testid": "conversation-list-view", children: [
|
|
5225
|
+
p.showHeader !== false && /* @__PURE__ */ jsxRuntime.jsx(
|
|
5226
|
+
chunk6DNYPLCD_cjs.TabHeader,
|
|
5227
|
+
{
|
|
5228
|
+
testId: "threads-tab-header",
|
|
5229
|
+
tabs: [
|
|
5230
|
+
{
|
|
5231
|
+
id: "threads",
|
|
5232
|
+
label: "",
|
|
5233
|
+
count: rows.length,
|
|
5234
|
+
countIcon: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.MessageSquare, { className: "size-3.5" }),
|
|
5235
|
+
countPlacement: "leading",
|
|
5236
|
+
presentation: "count",
|
|
5237
|
+
hasActiveFilters: !!q
|
|
5238
|
+
}
|
|
5239
|
+
],
|
|
5240
|
+
activeTabId: "threads",
|
|
5241
|
+
onTabChange: () => {
|
|
5242
|
+
},
|
|
5243
|
+
firstTabContent: /* @__PURE__ */ jsxRuntime.jsx(
|
|
5244
|
+
chunkMZL67U2E_cjs.FilterInput,
|
|
5245
|
+
{
|
|
5246
|
+
value: query,
|
|
5247
|
+
hideFieldPicker: true,
|
|
5248
|
+
ariaLabel: "Search threads",
|
|
5249
|
+
onChange: setQuery,
|
|
5250
|
+
fields: ["text"],
|
|
5251
|
+
onFieldsChange: () => {
|
|
5252
|
+
},
|
|
5253
|
+
labels: {
|
|
5254
|
+
placeholder: "Find a thread\u2026",
|
|
5255
|
+
fieldNames: { text: "Thread" }
|
|
5256
|
+
},
|
|
5257
|
+
className: "w-44 max-w-[40vw]"
|
|
5258
|
+
}
|
|
5259
|
+
),
|
|
5260
|
+
rightContent: p.header
|
|
5261
|
+
}
|
|
5262
|
+
),
|
|
5263
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "min-h-0 flex-1", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
5264
|
+
chunkIA7RTPT3_cjs.GridView,
|
|
5265
|
+
{
|
|
5266
|
+
testId: "threads-grid",
|
|
5267
|
+
items: rows,
|
|
5268
|
+
columnDefs: columns,
|
|
5269
|
+
getItemId: (row) => row.external_id,
|
|
5270
|
+
getRowTestId: (row) => `thread-row-${row.external_id}`,
|
|
5271
|
+
onRowClick: p.onOpen,
|
|
5272
|
+
height: "100%",
|
|
5273
|
+
isLoading: p.isLoading,
|
|
5274
|
+
loadingMessage: "Loading threads\u2026",
|
|
5275
|
+
emptyState: {
|
|
5276
|
+
title: q ? "No threads match" : "No conversations yet",
|
|
5277
|
+
message: "Start a conversation with people, ARBI, or both."
|
|
5278
|
+
},
|
|
5279
|
+
selection: p.selectionActions ? {
|
|
5280
|
+
mode: "multiple",
|
|
5281
|
+
controlled: true,
|
|
5282
|
+
selected: selectedRows,
|
|
5283
|
+
onSelectionChange: (items) => setSelected(new Set(items.map((item) => item.external_id)))
|
|
5284
|
+
} : void 0,
|
|
5285
|
+
gridOptions: {
|
|
5286
|
+
suppressClickEdit: true,
|
|
5287
|
+
onCellKeyDown: (event) => {
|
|
5288
|
+
if (event.event?.key === "Enter" && "column" in event && event.column.getColId() === "name" && event.data)
|
|
5289
|
+
p.onOpen(event.data);
|
|
5290
|
+
}
|
|
5291
|
+
}
|
|
5292
|
+
}
|
|
5293
|
+
) }),
|
|
5294
|
+
p.selectionActions && /* @__PURE__ */ jsxRuntime.jsx(chunkIA7RTPT3_cjs.SelectionBar, { count: selectedRows.length, onClear: () => setSelected(/* @__PURE__ */ new Set()), children: (compact) => p.selectionActions?.(selectedRows, compact, () => setSelected(/* @__PURE__ */ new Set())) })
|
|
5295
|
+
] });
|
|
5296
|
+
}
|
|
5297
|
+
function TaskStartDialog({
|
|
5298
|
+
open,
|
|
5299
|
+
onOpenChange,
|
|
5300
|
+
workflows,
|
|
5301
|
+
isPending,
|
|
5302
|
+
error,
|
|
5303
|
+
onStart,
|
|
5304
|
+
onLater
|
|
5305
|
+
}) {
|
|
5306
|
+
const [prompt, setPrompt] = react.useState("");
|
|
5307
|
+
const [choice, setChoice] = react.useState("prompt");
|
|
5308
|
+
const [shared, setShared] = react.useState(false);
|
|
5309
|
+
const todo = choice === "todo";
|
|
5310
|
+
const workflowId = choice === "prompt" || todo ? null : choice;
|
|
5311
|
+
const valid = workflowId ? workflows.some((w) => w.external_id === workflowId) : Boolean(prompt.trim());
|
|
5312
|
+
const values = {
|
|
5313
|
+
prompt: prompt.trim(),
|
|
5314
|
+
workflowId,
|
|
5315
|
+
todo,
|
|
5316
|
+
shared
|
|
5317
|
+
};
|
|
5318
|
+
return /* @__PURE__ */ jsxRuntime.jsx(ui.Dialog, { modal: false, open, onOpenChange: (next) => !isPending && onOpenChange(next), children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
5319
|
+
ui.DialogContent,
|
|
5320
|
+
{
|
|
5321
|
+
presentation: "right",
|
|
5322
|
+
hideCloseButton: true,
|
|
5323
|
+
onInteractOutside: (event) => event.preventDefault(),
|
|
5324
|
+
className: "flex flex-col gap-0 overflow-hidden p-0 shadow-lg",
|
|
5325
|
+
"data-testid": "task-start-dialog",
|
|
5326
|
+
children: [
|
|
5327
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DialogTitle, { className: "sr-only", children: "New task" }),
|
|
5328
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DialogDescription, { className: "sr-only", children: "Describe the task, then start it now or schedule it." }),
|
|
5329
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5330
|
+
chunk6DNYPLCD_cjs.TabHeader,
|
|
5331
|
+
{
|
|
5332
|
+
tabs: [{ id: "new-task", label: "New task", presentation: "count" }],
|
|
5333
|
+
activeTabId: "new-task",
|
|
5334
|
+
onTabChange: () => {
|
|
5335
|
+
},
|
|
5336
|
+
rightContent: /* @__PURE__ */ jsxRuntime.jsx(ui.DialogClose, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "ghost", size: "icon", "aria-label": "Close", disabled: isPending, children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.X, { className: "size-4" }) }) })
|
|
4590
5337
|
}
|
|
4591
5338
|
),
|
|
4592
|
-
|
|
4593
|
-
|
|
4594
|
-
|
|
4595
|
-
|
|
4596
|
-
|
|
4597
|
-
|
|
4598
|
-
|
|
4599
|
-
|
|
4600
|
-
|
|
4601
|
-
|
|
4602
|
-
|
|
4603
|
-
|
|
4604
|
-
|
|
4605
|
-
|
|
5339
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "min-h-0 flex-1 overflow-y-auto px-3 py-3", children: [
|
|
5340
|
+
!workflowId ? /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
5341
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Label, { className: "sr-only", htmlFor: "task-start-prompt", children: todo ? "What needs doing?" : "What should ARBI do?" }),
|
|
5342
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5343
|
+
ui.Textarea,
|
|
5344
|
+
{
|
|
5345
|
+
id: "task-start-prompt",
|
|
5346
|
+
autoFocus: true,
|
|
5347
|
+
value: prompt,
|
|
5348
|
+
onChange: (event) => setPrompt(event.target.value),
|
|
5349
|
+
disabled: isPending,
|
|
5350
|
+
placeholder: "What needs doing?",
|
|
5351
|
+
className: "min-h-44 resize-y shadow-none"
|
|
5352
|
+
}
|
|
5353
|
+
)
|
|
5354
|
+
] }) : /* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm", children: workflows.find((workflow) => workflow.external_id === workflowId)?.name }),
|
|
5355
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Select, { value: choice, onValueChange: setChoice, disabled: isPending, children: [
|
|
5356
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5357
|
+
ui.SelectTrigger,
|
|
5358
|
+
{
|
|
5359
|
+
id: "task-start-source",
|
|
5360
|
+
"aria-label": "Who does the work",
|
|
5361
|
+
className: "mt-3 h-7 w-auto max-w-full border-0 bg-transparent px-1 text-xs font-normal text-muted-foreground shadow-none hover:bg-muted",
|
|
5362
|
+
children: /* @__PURE__ */ jsxRuntime.jsx(ui.SelectValue, {})
|
|
5363
|
+
}
|
|
5364
|
+
),
|
|
5365
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.SelectContent, { children: [
|
|
5366
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.SelectItem, { value: "prompt", children: "With ARBI" }),
|
|
5367
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.SelectItem, { value: "todo", children: "People only" }),
|
|
5368
|
+
workflows.map((workflow) => /* @__PURE__ */ jsxRuntime.jsx(ui.SelectItem, { value: workflow.external_id, children: workflow.name }, workflow.external_id))
|
|
5369
|
+
] })
|
|
5370
|
+
] }),
|
|
5371
|
+
error && /* @__PURE__ */ jsxRuntime.jsx("p", { role: "alert", className: "mt-3 text-sm text-destructive", children: error })
|
|
5372
|
+
] }),
|
|
5373
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-wrap items-center justify-between gap-2 border-t px-3 py-2", children: [
|
|
5374
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5375
|
+
ui.Button,
|
|
5376
|
+
{
|
|
5377
|
+
variant: "ghost",
|
|
5378
|
+
disabled: !valid || isPending,
|
|
5379
|
+
onClick: () => onLater(values),
|
|
5380
|
+
"data-testid": "task-start-later",
|
|
5381
|
+
className: "h-8 px-2 text-sm font-medium",
|
|
5382
|
+
children: "Schedule"
|
|
4606
5383
|
}
|
|
4607
|
-
|
|
4608
|
-
|
|
5384
|
+
),
|
|
5385
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "ml-auto flex items-center gap-3", children: [
|
|
5386
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5387
|
+
ui.VisibilityToggle,
|
|
5388
|
+
{
|
|
5389
|
+
items: { shared },
|
|
5390
|
+
onToggle: setShared,
|
|
5391
|
+
label: shared ? "Workspace" : "Only Me",
|
|
5392
|
+
disabled: isPending,
|
|
5393
|
+
"data-testid": "task-start-visibility"
|
|
5394
|
+
}
|
|
5395
|
+
),
|
|
5396
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5397
|
+
ui.Button,
|
|
5398
|
+
{
|
|
5399
|
+
disabled: !valid || isPending,
|
|
5400
|
+
"data-testid": "task-start-now",
|
|
5401
|
+
className: "h-8 px-3 text-sm font-medium",
|
|
5402
|
+
onClick: async () => {
|
|
5403
|
+
try {
|
|
5404
|
+
await onStart(values);
|
|
5405
|
+
setPrompt("");
|
|
5406
|
+
setChoice("prompt");
|
|
5407
|
+
setShared(false);
|
|
5408
|
+
} catch {
|
|
5409
|
+
}
|
|
5410
|
+
},
|
|
5411
|
+
children: isPending ? "Starting\u2026" : "Start now"
|
|
5412
|
+
}
|
|
5413
|
+
)
|
|
5414
|
+
] })
|
|
5415
|
+
] })
|
|
4609
5416
|
]
|
|
4610
5417
|
}
|
|
4611
|
-
);
|
|
5418
|
+
) });
|
|
4612
5419
|
}
|
|
4613
5420
|
var DEFAULT_DUE_DATE_MENU_LABELS = {
|
|
4614
5421
|
today: "Today",
|
|
@@ -4782,6 +5589,25 @@ var hasDocumentInputs = (inputs) => Object.values(inputs).some(
|
|
|
4782
5589
|
(v) => v !== null && typeof v === "object" && Array.isArray(v.documents) && (v.documents.length ?? 0) > 0
|
|
4783
5590
|
);
|
|
4784
5591
|
function workflowTaskFields(workflow, inputs, name, context) {
|
|
5592
|
+
if (workflow.documentAction) {
|
|
5593
|
+
const scope = inputs.scope && typeof inputs.scope === "object" ? inputs.scope : { labels: []};
|
|
5594
|
+
return {
|
|
5595
|
+
name: name?.trim() || workflow.title,
|
|
5596
|
+
prompt: "",
|
|
5597
|
+
skill_ref: null,
|
|
5598
|
+
skill_inputs: inputs,
|
|
5599
|
+
action: {
|
|
5600
|
+
type: workflow.documentAction,
|
|
5601
|
+
documents: {
|
|
5602
|
+
doc_ext_ids: scope.documents ?? [],
|
|
5603
|
+
label_ext_ids: scope.labels ?? [],
|
|
5604
|
+
latest: inputs.latest === true
|
|
5605
|
+
},
|
|
5606
|
+
tag_ext_ids: typeof inputs.output === "string" && inputs.output ? [inputs.output] : [],
|
|
5607
|
+
overwrite: inputs.overwrite === true
|
|
5608
|
+
}
|
|
5609
|
+
};
|
|
5610
|
+
}
|
|
4785
5611
|
for (const value of Object.values(inputs)) {
|
|
4786
5612
|
if (!value || typeof value !== "object") continue;
|
|
4787
5613
|
const scope = value;
|
|
@@ -4894,6 +5720,7 @@ function composerToWorkflowRequest({ workflow, values, plan, documentTitles }, w
|
|
|
4894
5720
|
shared: values.shared,
|
|
4895
5721
|
timezone: values.timezone,
|
|
4896
5722
|
...workflowTrigger(values, false),
|
|
5723
|
+
...fields.action ? { action: fields.action } : {},
|
|
4897
5724
|
prompt: fields.prompt,
|
|
4898
5725
|
skill_ref: fields.skill_ref,
|
|
4899
5726
|
skill_inputs: fields.skill_inputs,
|
|
@@ -4906,7 +5733,7 @@ function composerToWorkflowRequest({ workflow, values, plan, documentTitles }, w
|
|
|
4906
5733
|
});
|
|
4907
5734
|
}
|
|
4908
5735
|
function taskComposerToCreateRequest(ctx, workspaceId, forceWorkflow = false) {
|
|
4909
|
-
if (forceWorkflow || !createsWork(ctx.values)) {
|
|
5736
|
+
if (forceWorkflow || ctx.workflow.documentAction || !createsWork(ctx.values)) {
|
|
4910
5737
|
return { kind: "workflow", body: composerToWorkflowRequest(ctx, workspaceId) };
|
|
4911
5738
|
}
|
|
4912
5739
|
return ctx.values.assignee === "me" || !isAgenticWorkflow(ctx.workflow) ? { kind: "work", body: composerToWorkRequest(ctx, workspaceId) } : { kind: "query", query: composerToTaskQuery(ctx, workspaceId) };
|
|
@@ -4938,6 +5765,7 @@ function composerToWorkflowUpdate({
|
|
|
4938
5765
|
shared: values.shared,
|
|
4939
5766
|
timezone: values.timezone,
|
|
4940
5767
|
...workflowTrigger(values, true),
|
|
5768
|
+
action: fields.action ?? null,
|
|
4941
5769
|
prompt: fields.prompt,
|
|
4942
5770
|
skill_ref: fields.skill_ref,
|
|
4943
5771
|
skill_inputs: fields.skill_inputs,
|
|
@@ -4966,10 +5794,11 @@ function taskToComposerValues(task, workflows) {
|
|
|
4966
5794
|
};
|
|
4967
5795
|
}
|
|
4968
5796
|
function workflowWhen(workflow) {
|
|
5797
|
+
if (workflow.on_demand) return "now";
|
|
4969
5798
|
if (workflow.after_conversation_ext_id) return "task";
|
|
4970
5799
|
if (workflow.event_kind) return "event";
|
|
4971
5800
|
if (workflow.rrule) return "repeat";
|
|
4972
|
-
return "once";
|
|
5801
|
+
return workflow.run_at ? "once" : "now";
|
|
4973
5802
|
}
|
|
4974
5803
|
function workflowToComposerValues(workflow, workflows) {
|
|
4975
5804
|
const reminder = !workflow.prompt && !workflow.skill_ref;
|
|
@@ -4990,6 +5819,25 @@ function workflowToComposerValues(workflow, workflows) {
|
|
|
4990
5819
|
name: workflow.name,
|
|
4991
5820
|
access: workflow.auth_mode === "scheduled_permanent" ? "standing" : "ask_each_run"
|
|
4992
5821
|
};
|
|
5822
|
+
if (workflow.action) {
|
|
5823
|
+
const definition = workflows.definitions?.find(
|
|
5824
|
+
(d) => d.documentAction === workflow.action?.type
|
|
5825
|
+
);
|
|
5826
|
+
return {
|
|
5827
|
+
...base,
|
|
5828
|
+
workflowId: definition?.id ?? workflows.customWorkflowId,
|
|
5829
|
+
inputs: {
|
|
5830
|
+
scope: {
|
|
5831
|
+
folders: [],
|
|
5832
|
+
labels: workflow.action.documents?.label_ext_ids ?? [],
|
|
5833
|
+
documents: workflow.action.documents?.doc_ext_ids ?? []
|
|
5834
|
+
},
|
|
5835
|
+
output: workflow.action.tag_ext_ids?.[0] ?? "",
|
|
5836
|
+
overwrite: workflow.action.overwrite ?? false,
|
|
5837
|
+
latest: workflow.action.documents?.latest ?? false
|
|
5838
|
+
}
|
|
5839
|
+
};
|
|
5840
|
+
}
|
|
4993
5841
|
if (skill) {
|
|
4994
5842
|
return {
|
|
4995
5843
|
...base,
|
|
@@ -5013,7 +5861,7 @@ function workflowToComposerValues(workflow, workflows) {
|
|
|
5013
5861
|
var EMPTY_NEW_THREAD = {
|
|
5014
5862
|
prompt: "",
|
|
5015
5863
|
title: "",
|
|
5016
|
-
shared:
|
|
5864
|
+
shared: false,
|
|
5017
5865
|
ownerId: "",
|
|
5018
5866
|
dueAt: "",
|
|
5019
5867
|
parentId: "",
|
|
@@ -5106,12 +5954,7 @@ function NewThreadDialog({
|
|
|
5106
5954
|
);
|
|
5107
5955
|
const [values, setValues] = react.useState(seed);
|
|
5108
5956
|
const [detailsOpen, setDetailsOpen] = react.useState(hasTaskFields(seed));
|
|
5109
|
-
react.
|
|
5110
|
-
if (open) {
|
|
5111
|
-
setValues(seed);
|
|
5112
|
-
setDetailsOpen(hasTaskFields(seed));
|
|
5113
|
-
}
|
|
5114
|
-
}, [open, seed]);
|
|
5957
|
+
const [submitError, setSubmitError] = react.useState(null);
|
|
5115
5958
|
const id = chunkMHVNT4J3_cjs.testIdOr(testId, { testId: "new-thread" });
|
|
5116
5959
|
const set = (key, value) => setValues((v) => ({ ...v, [key]: value }));
|
|
5117
5960
|
const canSubmit = values.prompt.trim() !== "" && !isPending;
|
|
@@ -5127,11 +5970,12 @@ function NewThreadDialog({
|
|
|
5127
5970
|
label: t.name,
|
|
5128
5971
|
icon: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CornerDownRight, { className: GLYPH, "aria-hidden": true })
|
|
5129
5972
|
}));
|
|
5130
|
-
return /* @__PURE__ */ jsxRuntime.jsx(ui.Dialog, { open, onOpenChange, children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
5973
|
+
return /* @__PURE__ */ jsxRuntime.jsx(ui.Dialog, { modal: false, open, onOpenChange, children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
5131
5974
|
ui.DialogContent,
|
|
5132
5975
|
{
|
|
5133
|
-
presentation: "
|
|
5134
|
-
|
|
5976
|
+
presentation: "right",
|
|
5977
|
+
onInteractOutside: (event) => event.preventDefault(),
|
|
5978
|
+
className: "flex flex-col overflow-hidden p-0",
|
|
5135
5979
|
"data-testid": id,
|
|
5136
5980
|
children: [
|
|
5137
5981
|
/* @__PURE__ */ jsxRuntime.jsxs(chunk2ZTONLT5_cjs.ModalHeader, { children: [
|
|
@@ -5142,9 +5986,17 @@ function NewThreadDialog({
|
|
|
5142
5986
|
"form",
|
|
5143
5987
|
{
|
|
5144
5988
|
className: "flex min-h-0 flex-1 flex-col",
|
|
5145
|
-
onSubmit: (event) => {
|
|
5989
|
+
onSubmit: async (event) => {
|
|
5146
5990
|
event.preventDefault();
|
|
5147
|
-
if (canSubmit)
|
|
5991
|
+
if (!canSubmit) return;
|
|
5992
|
+
setSubmitError(null);
|
|
5993
|
+
try {
|
|
5994
|
+
await onSubmit(values);
|
|
5995
|
+
setValues(EMPTY_NEW_THREAD);
|
|
5996
|
+
setDetailsOpen(false);
|
|
5997
|
+
} catch (error) {
|
|
5998
|
+
setSubmitError(error instanceof Error ? error.message : "Could not create the thread");
|
|
5999
|
+
}
|
|
5148
6000
|
},
|
|
5149
6001
|
children: [
|
|
5150
6002
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex min-h-0 flex-1 flex-col gap-4 overflow-y-auto px-6 pb-4", children: [
|
|
@@ -5186,6 +6038,7 @@ function NewThreadDialog({
|
|
|
5186
6038
|
items: { shared: values.shared },
|
|
5187
6039
|
onToggle: (share) => set("shared", share),
|
|
5188
6040
|
label: l.visibility,
|
|
6041
|
+
presentation: "select",
|
|
5189
6042
|
"data-testid": `${id}-visibility`
|
|
5190
6043
|
}
|
|
5191
6044
|
) }),
|
|
@@ -5281,6 +6134,7 @@ function NewThreadDialog({
|
|
|
5281
6134
|
] })
|
|
5282
6135
|
] })
|
|
5283
6136
|
] }),
|
|
6137
|
+
submitError && /* @__PURE__ */ jsxRuntime.jsx("p", { role: "alert", className: "px-6 pb-2 text-sm text-destructive", children: submitError }),
|
|
5284
6138
|
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col-reverse gap-2 border-t border-border px-6 py-3 sm:flex-row sm:justify-end", children: [
|
|
5285
6139
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5286
6140
|
ui.Button,
|
|
@@ -5317,18 +6171,18 @@ function NewThreadDialog({
|
|
|
5317
6171
|
var DEFAULT_TASK_TRIGGER_CHIP_LABELS = {
|
|
5318
6172
|
after: (name) => `After \u201C${name}\u201D is done`,
|
|
5319
6173
|
afterUnknown: "After another task is done",
|
|
5320
|
-
onDemand: "
|
|
6174
|
+
onDemand: "Manual"
|
|
5321
6175
|
};
|
|
5322
6176
|
function TriggerIcon({ type, chained }) {
|
|
5323
|
-
const cls = "size-3.5 shrink-0";
|
|
6177
|
+
const cls = "size-3.5 shrink-0 text-muted-foreground";
|
|
5324
6178
|
if (chained) return /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Link2, { className: cls, "aria-hidden": true });
|
|
5325
6179
|
switch (type) {
|
|
5326
6180
|
case "on_demand":
|
|
5327
6181
|
return /* @__PURE__ */ jsxRuntime.jsx(lucideReact.MousePointerClick, { className: cls, "aria-hidden": true });
|
|
5328
6182
|
case "recurring":
|
|
5329
|
-
return /* @__PURE__ */ jsxRuntime.jsx(lucideReact.
|
|
6183
|
+
return /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Clock, { className: cls, "aria-hidden": true });
|
|
5330
6184
|
case "event":
|
|
5331
|
-
return /* @__PURE__ */ jsxRuntime.jsx(lucideReact.
|
|
6185
|
+
return /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Bell, { className: cls, "aria-hidden": true });
|
|
5332
6186
|
default:
|
|
5333
6187
|
return /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Clock, { className: cls, "aria-hidden": true });
|
|
5334
6188
|
}
|
|
@@ -5348,7 +6202,7 @@ function TaskTriggerChip({
|
|
|
5348
6202
|
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
5349
6203
|
"span",
|
|
5350
6204
|
{
|
|
5351
|
-
className: "inline-flex min-w-0 items-center gap-1.5 text-
|
|
6205
|
+
className: "inline-flex min-w-0 max-w-full items-center gap-1.5 text-sm font-normal text-foreground",
|
|
5352
6206
|
"data-testid": chunkMHVNT4J3_cjs.testIdOr(testId, { testId: `task-trigger-${id}` }),
|
|
5353
6207
|
"data-trigger": chained ? "task" : triggerType,
|
|
5354
6208
|
children: [
|
|
@@ -5374,12 +6228,24 @@ function workflowTriggerType(workflow) {
|
|
|
5374
6228
|
if (workflow.run_at) return "one_time";
|
|
5375
6229
|
return "on_demand";
|
|
5376
6230
|
}
|
|
6231
|
+
function workflowRunStatusLabel(status) {
|
|
6232
|
+
if (!status) return "None";
|
|
6233
|
+
const labels = {
|
|
6234
|
+
completed: "Success",
|
|
6235
|
+
success: "Success",
|
|
6236
|
+
failed: "Failed",
|
|
6237
|
+
running: "In progress",
|
|
6238
|
+
awaiting_authorization: "Awaiting access"
|
|
6239
|
+
};
|
|
6240
|
+
return labels[status] ?? status.replaceAll("_", " ");
|
|
6241
|
+
}
|
|
5377
6242
|
|
|
5378
6243
|
// src/agents/tasks/workflowColumns.tsx
|
|
5379
6244
|
var WORKFLOW_COLUMN_ORDER = [
|
|
5380
6245
|
"name",
|
|
5381
6246
|
"trigger",
|
|
5382
6247
|
"last_run",
|
|
6248
|
+
"result",
|
|
5383
6249
|
"status",
|
|
5384
6250
|
"shared",
|
|
5385
6251
|
"actions"
|
|
@@ -5392,7 +6258,6 @@ function createWorkflowColumns(o) {
|
|
|
5392
6258
|
const l = o.labels;
|
|
5393
6259
|
const base = {
|
|
5394
6260
|
sortable: false,
|
|
5395
|
-
suppressMovable: true,
|
|
5396
6261
|
cellStyle: { display: "flex", alignItems: "center" }
|
|
5397
6262
|
};
|
|
5398
6263
|
return [
|
|
@@ -5402,7 +6267,7 @@ function createWorkflowColumns(o) {
|
|
|
5402
6267
|
sortable: true,
|
|
5403
6268
|
headerName: l.colName,
|
|
5404
6269
|
flex: 3,
|
|
5405
|
-
minWidth:
|
|
6270
|
+
minWidth: 210,
|
|
5406
6271
|
valueGetter: (p) => p.data?.name.toLowerCase() ?? "",
|
|
5407
6272
|
cellRenderer: cell2(o.renderName)
|
|
5408
6273
|
},
|
|
@@ -5411,7 +6276,7 @@ function createWorkflowColumns(o) {
|
|
|
5411
6276
|
colId: "trigger",
|
|
5412
6277
|
headerName: l.colTrigger,
|
|
5413
6278
|
flex: 2.4,
|
|
5414
|
-
minWidth:
|
|
6279
|
+
minWidth: 185,
|
|
5415
6280
|
valueGetter: (p) => p.data ? o.getTriggerText(p.data) : "",
|
|
5416
6281
|
cellRenderer: cell2(o.renderTrigger)
|
|
5417
6282
|
},
|
|
@@ -5421,16 +6286,26 @@ function createWorkflowColumns(o) {
|
|
|
5421
6286
|
sortable: true,
|
|
5422
6287
|
headerName: l.colLastRun,
|
|
5423
6288
|
flex: 1.4,
|
|
5424
|
-
minWidth:
|
|
6289
|
+
minWidth: 140,
|
|
6290
|
+
cellStyle: { display: "flex", alignItems: "center", padding: 0 },
|
|
5425
6291
|
valueGetter: (p) => time(p.data?.last_fired_at),
|
|
5426
6292
|
cellRenderer: cell2(o.renderLastRun)
|
|
5427
6293
|
},
|
|
6294
|
+
{
|
|
6295
|
+
...base,
|
|
6296
|
+
colId: "result",
|
|
6297
|
+
headerName: "Result",
|
|
6298
|
+
width: 130,
|
|
6299
|
+
valueGetter: (p) => p.data?.last_run_status ?? "",
|
|
6300
|
+
cellStyle: { display: "flex", alignItems: "center", padding: 0 },
|
|
6301
|
+
cellRenderer: cell2(o.renderResult)
|
|
6302
|
+
},
|
|
5428
6303
|
{
|
|
5429
6304
|
...base,
|
|
5430
6305
|
colId: "status",
|
|
5431
6306
|
sortable: true,
|
|
5432
6307
|
headerName: l.colStatus,
|
|
5433
|
-
width:
|
|
6308
|
+
width: 120,
|
|
5434
6309
|
valueGetter: (p) => p.data ? workflowStatus(p.data) : "",
|
|
5435
6310
|
cellRenderer: cell2(o.renderStatus)
|
|
5436
6311
|
},
|
|
@@ -5448,10 +6323,8 @@ function createWorkflowColumns(o) {
|
|
|
5448
6323
|
...base,
|
|
5449
6324
|
colId: "actions",
|
|
5450
6325
|
headerName: "",
|
|
5451
|
-
|
|
5452
|
-
|
|
5453
|
-
lockPinned: true,
|
|
5454
|
-
width: 140,
|
|
6326
|
+
width: 180,
|
|
6327
|
+
minWidth: 180,
|
|
5455
6328
|
cellStyle: { display: "flex", alignItems: "center", justifyContent: "flex-end" },
|
|
5456
6329
|
cellRenderer: cell2(o.renderActions)
|
|
5457
6330
|
}
|
|
@@ -5465,7 +6338,7 @@ var DEFAULT_WORKFLOW_LIST_LABELS = {
|
|
|
5465
6338
|
colTrigger: "When",
|
|
5466
6339
|
colAction: "What it does",
|
|
5467
6340
|
colAgent: "Agent",
|
|
5468
|
-
colStatus: "
|
|
6341
|
+
colStatus: "Active",
|
|
5469
6342
|
colShared: "Shared",
|
|
5470
6343
|
colLastRun: "Last run",
|
|
5471
6344
|
colNextRun: "Next run",
|
|
@@ -5475,7 +6348,7 @@ var DEFAULT_WORKFLOW_LIST_LABELS = {
|
|
|
5475
6348
|
typeSkill: "Skill",
|
|
5476
6349
|
typeWorkflow: "Workflow",
|
|
5477
6350
|
statusActive: "Active",
|
|
5478
|
-
statusPaused: "
|
|
6351
|
+
statusPaused: "Inactive",
|
|
5479
6352
|
statusOnDemand: "On demand",
|
|
5480
6353
|
activeSwitch: (name) => `Active: \u201C${name}\u201D`,
|
|
5481
6354
|
agent: "Agent",
|
|
@@ -5505,17 +6378,18 @@ var DEFAULT_WORKFLOW_LIST_LABELS = {
|
|
|
5505
6378
|
filterSkills: "Skills",
|
|
5506
6379
|
filterWorkflows: "Workflows",
|
|
5507
6380
|
filterActive: "Active",
|
|
5508
|
-
filterPaused: "
|
|
6381
|
+
filterPaused: "Inactive",
|
|
5509
6382
|
makeActive: "Make active",
|
|
5510
|
-
makePaused: "
|
|
6383
|
+
makePaused: "Deactivate",
|
|
5511
6384
|
selectAll: "Select all",
|
|
5512
6385
|
selectWorkflow: (name) => `Select ${name}`
|
|
5513
6386
|
};
|
|
5514
|
-
var ROW_HEIGHT2 =
|
|
6387
|
+
var ROW_HEIGHT2 = 40;
|
|
5515
6388
|
function WorkflowsTable(props) {
|
|
5516
6389
|
const { workflows, isLoading, busyId, header, testId } = props;
|
|
5517
6390
|
const l = { ...DEFAULT_WORKFLOW_LIST_LABELS, ...props.labels };
|
|
5518
|
-
const [
|
|
6391
|
+
const [filterStates, setFilterStates] = react.useState(/* @__PURE__ */ new Map());
|
|
6392
|
+
const [filterOpen, setFilterOpen] = react.useState(false);
|
|
5519
6393
|
const [query, setQuery] = react.useState("");
|
|
5520
6394
|
const [selected, setSelected] = react.useState([]);
|
|
5521
6395
|
const apiRef = react.useRef(null);
|
|
@@ -5531,12 +6405,24 @@ function WorkflowsTable(props) {
|
|
|
5531
6405
|
return out;
|
|
5532
6406
|
}, [workflows, q]);
|
|
5533
6407
|
const shown = react.useMemo(
|
|
5534
|
-
() => workflows.filter((w) =>
|
|
5535
|
-
|
|
5536
|
-
|
|
6408
|
+
() => workflows.filter((w) => {
|
|
6409
|
+
if (!matches(w)) return false;
|
|
6410
|
+
for (const group of [
|
|
6411
|
+
["skills", "workflows"],
|
|
6412
|
+
["active", "paused"]
|
|
6413
|
+
]) {
|
|
6414
|
+
const included = group.filter((f) => filterStates.get(f) === "include");
|
|
6415
|
+
if (included.length && !included.some((f) => inFilter(w, f))) return false;
|
|
6416
|
+
if (group.some((f) => filterStates.get(f) === "exclude" && inFilter(w, f))) return false;
|
|
6417
|
+
}
|
|
6418
|
+
return true;
|
|
6419
|
+
}),
|
|
6420
|
+
[workflows, filterStates, q]
|
|
5537
6421
|
);
|
|
5538
6422
|
const renderPerson = props.renderPerson ?? ((p) => /* @__PURE__ */ jsxRuntime.jsx(PersonPill, { person: p }));
|
|
5539
6423
|
const actionText = (w) => {
|
|
6424
|
+
if (w.action)
|
|
6425
|
+
return w.action.type === "email_documents" ? "Email latest documents" : "AI Review";
|
|
5540
6426
|
if (isSkillRow(w))
|
|
5541
6427
|
return w.description || w.skill_ref && props.skillNames?.[w.skill_ref] || w.name;
|
|
5542
6428
|
return w.skill_ref ? props.skillNames?.[w.skill_ref] ?? w.skill_ref : w.prompt?.trim() || l.reminder;
|
|
@@ -5559,7 +6445,7 @@ function WorkflowsTable(props) {
|
|
|
5559
6445
|
"span",
|
|
5560
6446
|
{
|
|
5561
6447
|
className: ui.cn(
|
|
5562
|
-
"truncate text-sm font-
|
|
6448
|
+
"truncate text-sm font-normal",
|
|
5563
6449
|
workflowStatus(w) === "paused" && "text-muted-foreground"
|
|
5564
6450
|
),
|
|
5565
6451
|
"data-testid": `workflow-name-${w.external_id}`,
|
|
@@ -5575,7 +6461,7 @@ function WorkflowsTable(props) {
|
|
|
5575
6461
|
}
|
|
5576
6462
|
)
|
|
5577
6463
|
] }),
|
|
5578
|
-
about && /* @__PURE__ */ jsxRuntime.jsx(
|
|
6464
|
+
about && !latest.current.props.automationsOnly && /* @__PURE__ */ jsxRuntime.jsx(
|
|
5579
6465
|
"p",
|
|
5580
6466
|
{
|
|
5581
6467
|
className: "truncate text-xs text-muted-foreground",
|
|
@@ -5586,62 +6472,36 @@ function WorkflowsTable(props) {
|
|
|
5586
6472
|
] });
|
|
5587
6473
|
},
|
|
5588
6474
|
renderTrigger: (w) => {
|
|
5589
|
-
const { props: p
|
|
6475
|
+
const { props: p } = latest.current;
|
|
5590
6476
|
const after = w.after_conversation_ext_id;
|
|
5591
6477
|
const skill = isSkillRow(w);
|
|
5592
|
-
|
|
5593
|
-
|
|
5594
|
-
|
|
5595
|
-
|
|
5596
|
-
|
|
5597
|
-
|
|
5598
|
-
|
|
5599
|
-
|
|
5600
|
-
|
|
5601
|
-
|
|
5602
|
-
|
|
5603
|
-
|
|
5604
|
-
afterTaskId: after,
|
|
5605
|
-
afterTaskName: after ? p.taskNames?.[after] : void 0,
|
|
5606
|
-
labels: p.triggerChipLabels
|
|
5607
|
-
}
|
|
5608
|
-
),
|
|
5609
|
-
detail && /* @__PURE__ */ jsxRuntime.jsx(
|
|
5610
|
-
"p",
|
|
5611
|
-
{
|
|
5612
|
-
className: "truncate text-xs text-muted-foreground",
|
|
5613
|
-
"data-testid": `workflow-next-run-${w.external_id}`,
|
|
5614
|
-
children: detail
|
|
5615
|
-
}
|
|
5616
|
-
)
|
|
5617
|
-
] });
|
|
6478
|
+
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "min-w-0 leading-tight", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
6479
|
+
TaskTriggerChip,
|
|
6480
|
+
{
|
|
6481
|
+
id: w.external_id,
|
|
6482
|
+
testId: `workflow-trigger-${w.external_id}`,
|
|
6483
|
+
triggerType: workflowTriggerType(w),
|
|
6484
|
+
summary: skill ? "" : p.describeTrigger(w),
|
|
6485
|
+
afterTaskId: after,
|
|
6486
|
+
afterTaskName: after ? p.taskNames?.[after] : void 0,
|
|
6487
|
+
labels: p.triggerChipLabels
|
|
6488
|
+
}
|
|
6489
|
+
) });
|
|
5618
6490
|
},
|
|
5619
6491
|
renderStatus: (w) => {
|
|
5620
6492
|
const { props: p, l: lb } = latest.current;
|
|
5621
|
-
const status = workflowStatus(w);
|
|
5622
|
-
if (status === "on_demand") return null;
|
|
5623
6493
|
const canEdit = w.is_owner !== false || Boolean(p.canEditShared);
|
|
5624
|
-
return /* @__PURE__ */ jsxRuntime.
|
|
5625
|
-
|
|
5626
|
-
|
|
5627
|
-
|
|
5628
|
-
|
|
5629
|
-
|
|
5630
|
-
|
|
5631
|
-
|
|
5632
|
-
|
|
5633
|
-
|
|
5634
|
-
|
|
5635
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5636
|
-
"span",
|
|
5637
|
-
{
|
|
5638
|
-
className: "text-sm text-muted-foreground",
|
|
5639
|
-
"data-testid": `workflow-status-${w.external_id}`,
|
|
5640
|
-
"data-status": status,
|
|
5641
|
-
children: status === "active" ? lb.statusActive : lb.statusPaused
|
|
5642
|
-
}
|
|
5643
|
-
)
|
|
5644
|
-
] });
|
|
6494
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
6495
|
+
ui.Switch,
|
|
6496
|
+
{
|
|
6497
|
+
checked: hasTrigger(w) && !isSkillRow(w) && Boolean(w.active),
|
|
6498
|
+
disabled: !hasTrigger(w) || isSkillRow(w) || !canEdit || p.busyId === w.external_id,
|
|
6499
|
+
onCheckedChange: (next) => p.onToggleActive(w, next),
|
|
6500
|
+
className: "disabled:data-[state=unchecked]:bg-muted dark:disabled:data-[state=unchecked]:bg-muted",
|
|
6501
|
+
"aria-label": lb.activeSwitch(w.name),
|
|
6502
|
+
"data-testid": `workflow-active-${w.external_id}`
|
|
6503
|
+
}
|
|
6504
|
+
);
|
|
5645
6505
|
},
|
|
5646
6506
|
renderShared: (w) => {
|
|
5647
6507
|
const { props: p, l: lb } = latest.current;
|
|
@@ -5661,41 +6521,37 @@ function WorkflowsTable(props) {
|
|
|
5661
6521
|
},
|
|
5662
6522
|
renderLastRun: (w) => {
|
|
5663
6523
|
const { props: p, l: lb } = latest.current;
|
|
5664
|
-
|
|
5665
|
-
|
|
5666
|
-
|
|
5667
|
-
|
|
5668
|
-
|
|
5669
|
-
"
|
|
5670
|
-
|
|
5671
|
-
|
|
5672
|
-
|
|
5673
|
-
|
|
5674
|
-
|
|
5675
|
-
|
|
5676
|
-
|
|
5677
|
-
|
|
5678
|
-
|
|
5679
|
-
|
|
5680
|
-
|
|
5681
|
-
|
|
5682
|
-
|
|
5683
|
-
|
|
5684
|
-
|
|
5685
|
-
|
|
5686
|
-
|
|
5687
|
-
|
|
5688
|
-
|
|
5689
|
-
|
|
5690
|
-
|
|
5691
|
-
|
|
5692
|
-
|
|
5693
|
-
|
|
5694
|
-
|
|
5695
|
-
]
|
|
5696
|
-
}
|
|
5697
|
-
)
|
|
5698
|
-
] });
|
|
6524
|
+
const at = w.last_fired_at ?? p.lastRuns?.[w.external_id]?.at;
|
|
6525
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
6526
|
+
"button",
|
|
6527
|
+
{
|
|
6528
|
+
type: "button",
|
|
6529
|
+
className: "h-full w-full truncate px-4 text-left text-sm hover:text-primary",
|
|
6530
|
+
onClick: () => p.onViewRuns?.(w),
|
|
6531
|
+
title: "View run history",
|
|
6532
|
+
"data-testid": `workflow-last-run-${w.external_id}`,
|
|
6533
|
+
children: at ? p.formatDate(at) : lb.never
|
|
6534
|
+
}
|
|
6535
|
+
);
|
|
6536
|
+
},
|
|
6537
|
+
renderResult: (w) => {
|
|
6538
|
+
const status = w.last_run_status;
|
|
6539
|
+
const label = workflowRunStatusLabel(status);
|
|
6540
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
6541
|
+
"button",
|
|
6542
|
+
{
|
|
6543
|
+
type: "button",
|
|
6544
|
+
onClick: () => latest.current.props.onViewRuns?.(w),
|
|
6545
|
+
title: "View run history",
|
|
6546
|
+
className: ui.cn(
|
|
6547
|
+
ui.badgeVariants({ variant: "outline" }),
|
|
6548
|
+
"mx-4 cursor-pointer text-xs font-medium",
|
|
6549
|
+
status === "failed" ? "border-red-border bg-red-bg text-red-text hover:bg-red-bg/80" : status === "completed" || status === "success" ? "border-green-border bg-green-bg text-green-text hover:bg-green-bg/80" : status ? "border-primary/20 bg-primary/10 text-primary hover:bg-primary/15" : "border-border bg-muted text-muted-foreground hover:bg-muted/80"
|
|
6550
|
+
),
|
|
6551
|
+
"data-testid": `workflow-result-${w.external_id}`,
|
|
6552
|
+
children: label
|
|
6553
|
+
}
|
|
6554
|
+
);
|
|
5699
6555
|
},
|
|
5700
6556
|
renderActions: (w) => {
|
|
5701
6557
|
const { props: p, l: lb } = latest.current;
|
|
@@ -5823,61 +6679,73 @@ function WorkflowsTable(props) {
|
|
|
5823
6679
|
(w) => hasTrigger(w) && (w.is_owner !== false || props.canEditShared)
|
|
5824
6680
|
);
|
|
5825
6681
|
const clearSelection = () => setSelected([]);
|
|
5826
|
-
const hasSavedWorkflow = workflows.some((w) => !isSkillRow(w));
|
|
5827
6682
|
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
5828
6683
|
"div",
|
|
5829
6684
|
{
|
|
5830
|
-
className: "flex min-h-0 flex-1 flex-col
|
|
6685
|
+
className: "flex min-h-0 flex-1 flex-col",
|
|
5831
6686
|
"data-testid": chunkMHVNT4J3_cjs.testIdOr(testId, { testId: "workflow-list" }),
|
|
5832
6687
|
children: [
|
|
5833
|
-
|
|
5834
|
-
|
|
5835
|
-
|
|
5836
|
-
|
|
5837
|
-
[
|
|
5838
|
-
["skills", l.filterSkills],
|
|
5839
|
-
["workflows", l.filterWorkflows],
|
|
5840
|
-
["active", l.filterActive],
|
|
5841
|
-
["paused", l.filterPaused]
|
|
5842
|
-
].map(([key, label]) => {
|
|
5843
|
-
const isSelected = filter === key;
|
|
5844
|
-
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
5845
|
-
"button",
|
|
6688
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
6689
|
+
chunk6DNYPLCD_cjs.TabHeader,
|
|
6690
|
+
{
|
|
6691
|
+
testId: "automations-tab-header",
|
|
6692
|
+
tabs: [
|
|
5846
6693
|
{
|
|
5847
|
-
|
|
5848
|
-
|
|
5849
|
-
|
|
5850
|
-
|
|
5851
|
-
|
|
5852
|
-
|
|
5853
|
-
|
|
5854
|
-
),
|
|
5855
|
-
"data-testid": `workflow-filter-${key}`,
|
|
5856
|
-
children: [
|
|
5857
|
-
label,
|
|
5858
|
-
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "tabular-nums opacity-70", children: counts[key] })
|
|
5859
|
-
]
|
|
6694
|
+
id: "automations",
|
|
6695
|
+
label: "",
|
|
6696
|
+
count: shown.length,
|
|
6697
|
+
countIcon: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Workflow, { className: "size-3.5" }),
|
|
6698
|
+
countPlacement: "leading",
|
|
6699
|
+
presentation: "count",
|
|
6700
|
+
hasActiveFilters: !!q || [...filterStates.values()].some(Boolean)
|
|
5860
6701
|
},
|
|
5861
|
-
|
|
5862
|
-
|
|
5863
|
-
|
|
5864
|
-
|
|
5865
|
-
|
|
5866
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5867
|
-
|
|
6702
|
+
...props.tabs ?? []
|
|
6703
|
+
],
|
|
6704
|
+
activeTabId: props.activeTabId ?? "automations",
|
|
6705
|
+
onTabChange: props.onTabChange ?? (() => {
|
|
6706
|
+
}),
|
|
6707
|
+
firstTabContent: /* @__PURE__ */ jsxRuntime.jsx(
|
|
6708
|
+
chunkMZL67U2E_cjs.FilterInput,
|
|
5868
6709
|
{
|
|
5869
|
-
type: "search",
|
|
5870
6710
|
value: query,
|
|
5871
|
-
onChange:
|
|
5872
|
-
|
|
5873
|
-
|
|
5874
|
-
|
|
5875
|
-
|
|
6711
|
+
onChange: setQuery,
|
|
6712
|
+
fields: ["text"],
|
|
6713
|
+
onFieldsChange: () => {
|
|
6714
|
+
},
|
|
6715
|
+
hideFieldPicker: true,
|
|
6716
|
+
ariaLabel: l.searchLabel,
|
|
6717
|
+
testIds: { input: "workflow-search" },
|
|
6718
|
+
filter: /* @__PURE__ */ jsxRuntime.jsx(
|
|
6719
|
+
chunk2QTT2RZE_cjs.TriStateFilterMenu,
|
|
6720
|
+
{
|
|
6721
|
+
testId: "automations-filter-button",
|
|
6722
|
+
open: filterOpen,
|
|
6723
|
+
onOpenChange: setFilterOpen,
|
|
6724
|
+
filterStates,
|
|
6725
|
+
onFiltersChange: setFilterStates,
|
|
6726
|
+
triggerClassName: "flex h-5 items-center gap-0.5 rounded px-1 text-muted-foreground hover:text-foreground pointer-coarse:h-11! pointer-coarse:min-w-11 pointer-coarse:justify-center",
|
|
6727
|
+
renderChevron: true,
|
|
6728
|
+
disableHoverOpen: true,
|
|
6729
|
+
options: [
|
|
6730
|
+
...!props.automationsOnly ? [
|
|
6731
|
+
{ id: "skills", label: l.filterSkills, count: counts.skills },
|
|
6732
|
+
{
|
|
6733
|
+
id: "workflows",
|
|
6734
|
+
label: l.filterWorkflows,
|
|
6735
|
+
count: counts.workflows
|
|
6736
|
+
}
|
|
6737
|
+
] : [],
|
|
6738
|
+
{ id: "active", label: l.filterActive, count: counts.active },
|
|
6739
|
+
{ id: "paused", label: l.filterPaused, count: counts.paused }
|
|
6740
|
+
]
|
|
6741
|
+
}
|
|
6742
|
+
)
|
|
5876
6743
|
}
|
|
5877
|
-
)
|
|
5878
|
-
|
|
5879
|
-
|
|
5880
|
-
|
|
6744
|
+
),
|
|
6745
|
+
rightContent: header
|
|
6746
|
+
}
|
|
6747
|
+
),
|
|
6748
|
+
props.content ? props.content : workflows.length === 0 && !isLoading ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
5881
6749
|
chunkZW6FPIFC_cjs.EmptyState,
|
|
5882
6750
|
{
|
|
5883
6751
|
icon: lucideReact.Workflow,
|
|
@@ -5886,7 +6754,7 @@ function WorkflowsTable(props) {
|
|
|
5886
6754
|
testId: "workflow-list-empty"
|
|
5887
6755
|
}
|
|
5888
6756
|
) : /* @__PURE__ */ jsxRuntime.jsx("div", { className: "min-h-0 flex-1", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
5889
|
-
|
|
6757
|
+
chunkIA7RTPT3_cjs.GridView,
|
|
5890
6758
|
{
|
|
5891
6759
|
testId: "workflow-grid",
|
|
5892
6760
|
gridId: props.gridId ?? "workflows-grid-v2",
|
|
@@ -5907,10 +6775,10 @@ function WorkflowsTable(props) {
|
|
|
5907
6775
|
gridOptions: GRID_OPTIONS
|
|
5908
6776
|
}
|
|
5909
6777
|
) }),
|
|
5910
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
6778
|
+
!props.content && /* @__PURE__ */ jsxRuntime.jsx(chunkIA7RTPT3_cjs.SelectionBar, { count: selected.length, onClear: clearSelection, children: (isCompact) => /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
5911
6779
|
props.onToggleActiveMany && /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
5912
6780
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5913
|
-
|
|
6781
|
+
chunkIA7RTPT3_cjs.SelectionBarAction,
|
|
5914
6782
|
{
|
|
5915
6783
|
icon: lucideReact.Play,
|
|
5916
6784
|
label: l.makeActive,
|
|
@@ -5924,7 +6792,7 @@ function WorkflowsTable(props) {
|
|
|
5924
6792
|
}
|
|
5925
6793
|
),
|
|
5926
6794
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
5927
|
-
|
|
6795
|
+
chunkIA7RTPT3_cjs.SelectionBarAction,
|
|
5928
6796
|
{
|
|
5929
6797
|
icon: lucideReact.Workflow,
|
|
5930
6798
|
label: l.makePaused,
|
|
@@ -5939,7 +6807,7 @@ function WorkflowsTable(props) {
|
|
|
5939
6807
|
)
|
|
5940
6808
|
] }),
|
|
5941
6809
|
props.onDeleteMany && /* @__PURE__ */ jsxRuntime.jsx(
|
|
5942
|
-
|
|
6810
|
+
chunkIA7RTPT3_cjs.SelectionBarAction,
|
|
5943
6811
|
{
|
|
5944
6812
|
icon: lucideReact.Trash2,
|
|
5945
6813
|
label: l.delete,
|
|
@@ -5958,16 +6826,7 @@ function WorkflowsTable(props) {
|
|
|
5958
6826
|
}
|
|
5959
6827
|
);
|
|
5960
6828
|
}
|
|
5961
|
-
var
|
|
5962
|
-
{ colId: "shared", minWidth: 1060 },
|
|
5963
|
-
{ colId: "last_run", minWidth: 880 }
|
|
5964
|
-
];
|
|
5965
|
-
var GRID_OPTIONS = {
|
|
5966
|
-
suppressClickEdit: true,
|
|
5967
|
-
suppressCellFocus: true,
|
|
5968
|
-
suppressColumnVirtualisation: true,
|
|
5969
|
-
onGridSizeChanged: (event) => applyColumnWidthRules(event.api, event.clientWidth, WIDTH_RULES2)
|
|
5970
|
-
};
|
|
6829
|
+
var GRID_OPTIONS = { suppressClickEdit: true };
|
|
5971
6830
|
var DEFAULT_TASK_ACTIVITY_LABELS = {
|
|
5972
6831
|
title: "Activity",
|
|
5973
6832
|
empty: "Nothing has happened yet.",
|
|
@@ -5997,11 +6856,19 @@ var ICONS = {
|
|
|
5997
6856
|
awaiting_access: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Lock, { className: "size-3.5", "aria-hidden": true }),
|
|
5998
6857
|
access_granted: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.KeyRound, { className: "size-3.5", "aria-hidden": true }),
|
|
5999
6858
|
ready_for_review: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CircleDot, { className: "size-3.5", "aria-hidden": true }),
|
|
6859
|
+
reviewed: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CheckCircle2, { className: "size-3.5", "aria-hidden": true }),
|
|
6000
6860
|
handed_off: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.UserRoundCog, { className: "size-3.5", "aria-hidden": true }),
|
|
6001
6861
|
changes_requested: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.MessageSquareReply, { className: "size-3.5", "aria-hidden": true }),
|
|
6002
6862
|
done: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CheckCircle2, { className: "size-3.5", "aria-hidden": true }),
|
|
6003
6863
|
reopened: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.RotateCcw, { className: "size-3.5", "aria-hidden": true }),
|
|
6004
|
-
failed: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.AlertTriangle, { className: "size-3.5", "aria-hidden": true })
|
|
6864
|
+
failed: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.AlertTriangle, { className: "size-3.5", "aria-hidden": true }),
|
|
6865
|
+
participant_joined: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.UserRoundCog, { className: "size-3.5", "aria-hidden": true }),
|
|
6866
|
+
assistant_responded: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Sparkles, { className: "size-3.5", "aria-hidden": true }),
|
|
6867
|
+
artifact_created: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Sparkles, { className: "size-3.5", "aria-hidden": true }),
|
|
6868
|
+
artifact_edited: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.MessageSquareReply, { className: "size-3.5", "aria-hidden": true }),
|
|
6869
|
+
document_added: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Sparkles, { className: "size-3.5", "aria-hidden": true }),
|
|
6870
|
+
document_removed: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.AlertTriangle, { className: "size-3.5", "aria-hidden": true }),
|
|
6871
|
+
notified: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.UserRoundCog, { className: "size-3.5", "aria-hidden": true })
|
|
6005
6872
|
};
|
|
6006
6873
|
var asString = (v) => typeof v === "string" && v.trim() ? v : null;
|
|
6007
6874
|
function summarizeError(error) {
|
|
@@ -6025,6 +6892,20 @@ function TaskActivityTimeline({
|
|
|
6025
6892
|
const agentId = asString(detail.agent_ext_id);
|
|
6026
6893
|
const agent = agentId ? agentName?.(agentId) : void 0;
|
|
6027
6894
|
switch (e.kind) {
|
|
6895
|
+
case "participant_joined":
|
|
6896
|
+
return { headline: "Joined the conversation" };
|
|
6897
|
+
case "assistant_responded":
|
|
6898
|
+
return { headline: "Responded" };
|
|
6899
|
+
case "artifact_created":
|
|
6900
|
+
return { headline: "Created a document" };
|
|
6901
|
+
case "artifact_edited":
|
|
6902
|
+
return { headline: "Edited a document" };
|
|
6903
|
+
case "document_added":
|
|
6904
|
+
return { headline: "Added a document" };
|
|
6905
|
+
case "document_removed":
|
|
6906
|
+
return { headline: "Removed a document" };
|
|
6907
|
+
case "notified":
|
|
6908
|
+
return { headline: "Sent a notification" };
|
|
6028
6909
|
case "created":
|
|
6029
6910
|
return { headline: detail.from_workflow ? l.createdFromWorkflow : l.created };
|
|
6030
6911
|
case "run_started":
|
|
@@ -6035,6 +6916,8 @@ function TaskActivityTimeline({
|
|
|
6035
6916
|
return { headline: l.accessGranted };
|
|
6036
6917
|
case "ready_for_review":
|
|
6037
6918
|
return { headline: l.readyForReview };
|
|
6919
|
+
case "reviewed":
|
|
6920
|
+
return { headline: "Approved this review stage" };
|
|
6038
6921
|
case "handed_off":
|
|
6039
6922
|
return {
|
|
6040
6923
|
headline: l.handedOff,
|
|
@@ -6046,7 +6929,7 @@ function TaskActivityTimeline({
|
|
|
6046
6929
|
extra: note ? /* @__PURE__ */ jsxRuntime.jsx(Quote, { text: l.sentBackNote(note) }) : void 0
|
|
6047
6930
|
};
|
|
6048
6931
|
case "done":
|
|
6049
|
-
return { headline: l.done };
|
|
6932
|
+
return { headline: l.done, extra: note ? /* @__PURE__ */ jsxRuntime.jsx(Quote, { text: note }) : void 0 };
|
|
6050
6933
|
case "reopened":
|
|
6051
6934
|
return { headline: l.reopened };
|
|
6052
6935
|
case "failed": {
|
|
@@ -6114,39 +6997,189 @@ function TaskActivityTimeline({
|
|
|
6114
6997
|
);
|
|
6115
6998
|
}) });
|
|
6116
6999
|
}
|
|
6117
|
-
function Quote({ text }) {
|
|
6118
|
-
return /* @__PURE__ */ jsxRuntime.jsx("blockquote", { className: "border-l-2 pl-2 text-xs text-muted-foreground whitespace-pre-wrap", children: text });
|
|
7000
|
+
function Quote({ text }) {
|
|
7001
|
+
return /* @__PURE__ */ jsxRuntime.jsx("blockquote", { className: "border-l-2 pl-2 text-xs text-muted-foreground whitespace-pre-wrap", children: text });
|
|
7002
|
+
}
|
|
7003
|
+
function TaskActivityDialog({
|
|
7004
|
+
open,
|
|
7005
|
+
onOpenChange,
|
|
7006
|
+
taskName,
|
|
7007
|
+
events,
|
|
7008
|
+
isLoading,
|
|
7009
|
+
isError,
|
|
7010
|
+
labels,
|
|
7011
|
+
testId,
|
|
7012
|
+
...timeline
|
|
7013
|
+
}) {
|
|
7014
|
+
const l = { ...DEFAULT_TASK_ACTIVITY_LABELS, ...labels };
|
|
7015
|
+
const id = chunkMHVNT4J3_cjs.testIdOr(testId, { testId: "task-activity" });
|
|
7016
|
+
const count = events?.length ?? 0;
|
|
7017
|
+
const scrollToEnd = react.useCallback(
|
|
7018
|
+
(el) => {
|
|
7019
|
+
if (count >= 0) el?.scrollIntoView?.({ block: "end" });
|
|
7020
|
+
},
|
|
7021
|
+
[count]
|
|
7022
|
+
);
|
|
7023
|
+
return /* @__PURE__ */ jsxRuntime.jsx(ui.Dialog, { open, onOpenChange, children: /* @__PURE__ */ jsxRuntime.jsxs(ui.DialogContent, { presentation: "sheet", className: "max-h-[80dvh] sm:max-w-lg", "data-testid": id, children: [
|
|
7024
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogHeader, { children: [
|
|
7025
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DialogTitle, { children: l.title }),
|
|
7026
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DialogDescription, { className: "truncate", children: taskName })
|
|
7027
|
+
] }),
|
|
7028
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "max-h-[55dvh] overflow-y-auto pr-1", "data-testid": `${id}-scroll`, children: [
|
|
7029
|
+
isLoading && !events ? /* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm text-muted-foreground", children: l.loading }) : isError && !events ? /* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm text-destructive", children: l.error }) : count === 0 ? /* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm text-muted-foreground", children: l.empty }) : /* @__PURE__ */ jsxRuntime.jsx(TaskActivityTimeline, { events: events ?? [], labels, testId: id, ...timeline }),
|
|
7030
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { ref: scrollToEnd })
|
|
7031
|
+
] })
|
|
7032
|
+
] }) });
|
|
7033
|
+
}
|
|
7034
|
+
function TaskFlow({
|
|
7035
|
+
items,
|
|
7036
|
+
className
|
|
7037
|
+
}) {
|
|
7038
|
+
const scroll = react.useRef(null);
|
|
7039
|
+
const following = react.useRef(true);
|
|
7040
|
+
const latest = items.at(-1)?.id;
|
|
7041
|
+
react.useLayoutEffect(() => {
|
|
7042
|
+
const el = scroll.current;
|
|
7043
|
+
if (!el) return;
|
|
7044
|
+
const follow = () => {
|
|
7045
|
+
if (following.current) el.scrollLeft = el.scrollWidth;
|
|
7046
|
+
};
|
|
7047
|
+
follow();
|
|
7048
|
+
const resize = new ResizeObserver(follow);
|
|
7049
|
+
resize.observe(el);
|
|
7050
|
+
return () => resize.disconnect();
|
|
7051
|
+
}, [latest]);
|
|
7052
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
7053
|
+
"div",
|
|
7054
|
+
{
|
|
7055
|
+
ref: scroll,
|
|
7056
|
+
className: ui.cn("min-w-0 flex-1 overflow-x-auto overscroll-x-contain", className),
|
|
7057
|
+
"data-testid": "thread-flow",
|
|
7058
|
+
role: "region",
|
|
7059
|
+
"aria-label": "Thread activity",
|
|
7060
|
+
tabIndex: 0,
|
|
7061
|
+
onScroll: (e) => {
|
|
7062
|
+
const el = e.currentTarget;
|
|
7063
|
+
following.current = el.scrollWidth - el.scrollLeft - el.clientWidth < 24;
|
|
7064
|
+
},
|
|
7065
|
+
children: /* @__PURE__ */ jsxRuntime.jsx("ol", { className: "flex w-max min-w-full items-center gap-1", children: items.map((item, i) => {
|
|
7066
|
+
const content = /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
7067
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "shrink-0", children: item.avatar }),
|
|
7068
|
+
/* @__PURE__ */ jsxRuntime.jsxs("span", { className: "min-w-0 text-left", children: [
|
|
7069
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "block max-w-32 truncate text-[11px] leading-tight font-medium", children: item.label }),
|
|
7070
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7071
|
+
"span",
|
|
7072
|
+
{
|
|
7073
|
+
className: "block text-[10px] leading-tight text-muted-foreground",
|
|
7074
|
+
title: item.exactTime,
|
|
7075
|
+
children: item.time
|
|
7076
|
+
}
|
|
7077
|
+
)
|
|
7078
|
+
] })
|
|
7079
|
+
] });
|
|
7080
|
+
const cls = ui.cn(
|
|
7081
|
+
"flex shrink-0 items-center gap-1.5 rounded-md px-1 py-0.5",
|
|
7082
|
+
item.current && "bg-accent text-accent-foreground"
|
|
7083
|
+
);
|
|
7084
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7085
|
+
"li",
|
|
7086
|
+
{
|
|
7087
|
+
className: "flex shrink-0 items-center gap-1",
|
|
7088
|
+
"data-testid": `thread-flow-${item.id}`,
|
|
7089
|
+
children: [
|
|
7090
|
+
i > 0 && /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronRight, { className: "size-3 shrink-0 text-muted-foreground", "aria-hidden": true }),
|
|
7091
|
+
item.onSelect ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
7092
|
+
"button",
|
|
7093
|
+
{
|
|
7094
|
+
className: ui.cn(cls, "hover:bg-muted"),
|
|
7095
|
+
onClick: item.onSelect,
|
|
7096
|
+
title: item.description ?? item.label,
|
|
7097
|
+
children: content
|
|
7098
|
+
}
|
|
7099
|
+
) : item.detail ? /* @__PURE__ */ jsxRuntime.jsxs(ui.Popover, { children: [
|
|
7100
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.PopoverTrigger, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
7101
|
+
"button",
|
|
7102
|
+
{
|
|
7103
|
+
className: ui.cn(cls, "hover:bg-muted"),
|
|
7104
|
+
title: item.description ?? item.label,
|
|
7105
|
+
children: content
|
|
7106
|
+
}
|
|
7107
|
+
) }),
|
|
7108
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.PopoverContent, { className: "max-h-72 overflow-y-auto text-sm whitespace-pre-wrap", children: item.detail })
|
|
7109
|
+
] }) : /* @__PURE__ */ jsxRuntime.jsx("div", { className: cls, title: item.description ?? item.label, children: content })
|
|
7110
|
+
]
|
|
7111
|
+
},
|
|
7112
|
+
item.id
|
|
7113
|
+
);
|
|
7114
|
+
}) })
|
|
7115
|
+
}
|
|
7116
|
+
);
|
|
7117
|
+
}
|
|
7118
|
+
function ThreadActivity({ item, children }) {
|
|
7119
|
+
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex justify-center px-3 py-2", "data-testid": `thread-activity-${item.id}`, children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7120
|
+
"div",
|
|
7121
|
+
{
|
|
7122
|
+
className: "max-w-full text-center text-xs text-muted-foreground",
|
|
7123
|
+
title: item.description,
|
|
7124
|
+
children: [
|
|
7125
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-wrap items-center justify-center gap-1.5", children: [
|
|
7126
|
+
item.avatar,
|
|
7127
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { children: item.label }),
|
|
7128
|
+
/* @__PURE__ */ jsxRuntime.jsx("time", { title: item.exactTime, children: item.time })
|
|
7129
|
+
] }),
|
|
7130
|
+
children,
|
|
7131
|
+
item.detail && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "mt-1 whitespace-pre-wrap break-words text-left", children: item.detail })
|
|
7132
|
+
]
|
|
7133
|
+
}
|
|
7134
|
+
) });
|
|
6119
7135
|
}
|
|
6120
|
-
|
|
6121
|
-
|
|
6122
|
-
|
|
6123
|
-
|
|
6124
|
-
|
|
6125
|
-
|
|
6126
|
-
|
|
6127
|
-
|
|
6128
|
-
|
|
6129
|
-
|
|
6130
|
-
|
|
6131
|
-
|
|
6132
|
-
|
|
6133
|
-
|
|
6134
|
-
|
|
6135
|
-
|
|
6136
|
-
|
|
6137
|
-
|
|
6138
|
-
|
|
6139
|
-
|
|
6140
|
-
|
|
6141
|
-
|
|
6142
|
-
|
|
6143
|
-
|
|
6144
|
-
|
|
6145
|
-
|
|
6146
|
-
|
|
6147
|
-
|
|
6148
|
-
|
|
6149
|
-
|
|
7136
|
+
|
|
7137
|
+
// src/agents/tasks/compact-thread-activity.ts
|
|
7138
|
+
function compactThreadActivity(events) {
|
|
7139
|
+
const result = [];
|
|
7140
|
+
const batches = /* @__PURE__ */ new Map();
|
|
7141
|
+
for (const event of events) {
|
|
7142
|
+
if (event.kind === "notified") {
|
|
7143
|
+
if (["conversation_ready_for_review", "conversation_done"].includes(
|
|
7144
|
+
String(event.detail?.notification_type)
|
|
7145
|
+
))
|
|
7146
|
+
continue;
|
|
7147
|
+
const source = event.detail?.batch_ext_id ?? event.detail?.message_ext_id;
|
|
7148
|
+
const key = typeof source === "string" && source ? `${event.actor_ext_id}:${source}` : event.external_id;
|
|
7149
|
+
let entry = batches.get(key);
|
|
7150
|
+
if (!entry) {
|
|
7151
|
+
entry = { event, label: "Notified 1 user", recipients: [] };
|
|
7152
|
+
batches.set(key, entry);
|
|
7153
|
+
result.push(entry);
|
|
7154
|
+
}
|
|
7155
|
+
if (event.to_ext_id && !entry.recipients.includes(event.to_ext_id))
|
|
7156
|
+
entry.recipients.push(event.to_ext_id);
|
|
7157
|
+
const count = Math.max(1, entry.recipients.length);
|
|
7158
|
+
entry.label = `Notified ${count} ${count === 1 ? "user" : "users"}`;
|
|
7159
|
+
} else if (["artifact_created", "artifact_edited", "document_added", "document_removed"].includes(
|
|
7160
|
+
event.kind
|
|
7161
|
+
)) {
|
|
7162
|
+
const labels = {
|
|
7163
|
+
artifact_created: "Generated",
|
|
7164
|
+
artifact_edited: "Edited document",
|
|
7165
|
+
document_added: "Added document",
|
|
7166
|
+
document_removed: "Removed document"
|
|
7167
|
+
};
|
|
7168
|
+
result.push({ event, label: labels[event.kind], recipients: [] });
|
|
7169
|
+
} else if (["created", "participant_joined", "assistant_responded", "done"].includes(event.kind)) {
|
|
7170
|
+
result.push({
|
|
7171
|
+
event,
|
|
7172
|
+
label: {
|
|
7173
|
+
created: "Started Task",
|
|
7174
|
+
participant_joined: "Followed Up",
|
|
7175
|
+
assistant_responded: "Answered",
|
|
7176
|
+
done: "Marked Done"
|
|
7177
|
+
}[event.kind],
|
|
7178
|
+
recipients: []
|
|
7179
|
+
});
|
|
7180
|
+
}
|
|
7181
|
+
}
|
|
7182
|
+
return result;
|
|
6150
7183
|
}
|
|
6151
7184
|
var DEFAULT_TASK_THREAD_CHIP_LABELS = {
|
|
6152
7185
|
open: "Open thread",
|
|
@@ -6208,105 +7241,127 @@ var DEFAULT_TASK_RUNS_DIALOG_LABELS = {
|
|
|
6208
7241
|
var STATUS_STYLE = {
|
|
6209
7242
|
running: "bg-ai-soft text-ai-ink",
|
|
6210
7243
|
success: "bg-green-bg text-green-text",
|
|
7244
|
+
completed: "bg-green-bg text-green-text",
|
|
6211
7245
|
failed: "bg-red-bg text-red-text"
|
|
6212
7246
|
};
|
|
6213
7247
|
function TaskRunsDialog({
|
|
7248
|
+
inline = false,
|
|
7249
|
+
renderErrorReport,
|
|
7250
|
+
hideHeader = false,
|
|
6214
7251
|
open,
|
|
6215
7252
|
onOpenChange,
|
|
6216
7253
|
taskName,
|
|
6217
|
-
error,
|
|
6218
7254
|
runs,
|
|
6219
7255
|
isLoading,
|
|
6220
7256
|
onOpenRun,
|
|
7257
|
+
onOpenResult,
|
|
6221
7258
|
getRunHref,
|
|
6222
7259
|
testIds,
|
|
6223
7260
|
labels
|
|
6224
7261
|
}) {
|
|
6225
7262
|
const l = { ...DEFAULT_TASK_RUNS_DIALOG_LABELS, ...labels };
|
|
6226
|
-
|
|
6227
|
-
|
|
6228
|
-
|
|
6229
|
-
|
|
6230
|
-
|
|
6231
|
-
|
|
6232
|
-
|
|
6233
|
-
|
|
6234
|
-
|
|
6235
|
-
|
|
6236
|
-
" ",
|
|
6237
|
-
l.title(taskName)
|
|
6238
|
-
] }),
|
|
6239
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.DialogDescription, { children: l.description })
|
|
6240
|
-
] }),
|
|
6241
|
-
error && /* @__PURE__ */ jsxRuntime.jsx("p", { role: "alert", className: "rounded-md bg-red-bg p-3 text-sm text-red-text", children: error }),
|
|
6242
|
-
isLoading ? /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex items-center justify-center gap-2 py-8 text-muted-foreground", children: [
|
|
6243
|
-
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Loader2, { className: "size-4 animate-spin" }),
|
|
6244
|
-
" ",
|
|
6245
|
-
l.loading
|
|
6246
|
-
] }) : runs.length === 0 ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
6247
|
-
"p",
|
|
7263
|
+
const columns = react.useMemo(
|
|
7264
|
+
() => [
|
|
7265
|
+
{
|
|
7266
|
+
colId: "status",
|
|
7267
|
+
field: "status",
|
|
7268
|
+
headerName: "Status",
|
|
7269
|
+
width: 160,
|
|
7270
|
+
minWidth: 140,
|
|
7271
|
+
cellRenderer: ({ data }) => data && /* @__PURE__ */ jsxRuntime.jsx(
|
|
7272
|
+
"span",
|
|
6248
7273
|
{
|
|
6249
|
-
className:
|
|
6250
|
-
|
|
6251
|
-
|
|
7274
|
+
className: ui.cn(
|
|
7275
|
+
"rounded-full px-2 py-0.5 text-xs font-medium capitalize",
|
|
7276
|
+
STATUS_STYLE[data.status] ?? "text-muted-foreground"
|
|
7277
|
+
),
|
|
7278
|
+
children: workflowRunStatusLabel(data.status)
|
|
6252
7279
|
}
|
|
6253
|
-
)
|
|
6254
|
-
|
|
6255
|
-
|
|
6256
|
-
|
|
6257
|
-
|
|
6258
|
-
|
|
6259
|
-
|
|
7280
|
+
)
|
|
7281
|
+
},
|
|
7282
|
+
{ colId: "when", field: "when", headerName: "Run", flex: 2, minWidth: 240 },
|
|
7283
|
+
{
|
|
7284
|
+
colId: "result",
|
|
7285
|
+
headerName: "",
|
|
7286
|
+
width: 280,
|
|
7287
|
+
minWidth: 220,
|
|
7288
|
+
sortable: false,
|
|
7289
|
+
cellRenderer: ({ data: run }) => {
|
|
7290
|
+
if (!run) return null;
|
|
7291
|
+
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex h-full items-center gap-2", children: [
|
|
7292
|
+
run.error && renderErrorReport?.(run),
|
|
7293
|
+
(run.conversationId || run.resultId && onOpenResult) && /* @__PURE__ */ jsxRuntime.jsx(ui.Button, { asChild: true, variant: "ghost", size: "sm", className: "h-7 gap-1.5", children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7294
|
+
chunkOB5F4577_cjs.ActionLink,
|
|
6260
7295
|
{
|
|
6261
|
-
|
|
6262
|
-
|
|
7296
|
+
href: getRunHref?.(run),
|
|
7297
|
+
onSelect: () => {
|
|
7298
|
+
if (run.conversationId) onOpenRun(run.conversationId);
|
|
7299
|
+
else if (run.resultId) onOpenResult?.(run.resultId);
|
|
7300
|
+
onOpenChange(false);
|
|
7301
|
+
},
|
|
7302
|
+
"data-testid": chunkMHVNT4J3_cjs.testIdOr(testIds?.open, { testId: "task-run-open" }),
|
|
6263
7303
|
children: [
|
|
6264
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
6265
|
-
|
|
6266
|
-
|
|
6267
|
-
className: ui.cn(
|
|
6268
|
-
"shrink-0 rounded-full px-2 py-0.5 text-xs font-medium capitalize",
|
|
6269
|
-
STATUS_STYLE[run.status] ?? "bg-background text-muted-foreground"
|
|
6270
|
-
),
|
|
6271
|
-
children: run.status
|
|
6272
|
-
}
|
|
6273
|
-
),
|
|
6274
|
-
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "min-w-0 flex-1", children: [
|
|
6275
|
-
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "truncate text-sm", children: run.when || "\u2014" }),
|
|
6276
|
-
run.error && /* @__PURE__ */ jsxRuntime.jsx("p", { className: "truncate text-xs text-red-text", title: run.error, children: run.error })
|
|
6277
|
-
] }),
|
|
6278
|
-
run.conversationId && /* @__PURE__ */ jsxRuntime.jsx(
|
|
6279
|
-
ui.Button,
|
|
6280
|
-
{
|
|
6281
|
-
asChild: true,
|
|
6282
|
-
variant: "outline",
|
|
6283
|
-
size: "sm",
|
|
6284
|
-
className: "h-7 shrink-0 gap-1.5 pointer-coarse:h-11",
|
|
6285
|
-
children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
6286
|
-
chunkOB5F4577_cjs.ActionLink,
|
|
6287
|
-
{
|
|
6288
|
-
href: getRunHref?.(run),
|
|
6289
|
-
onSelect: () => {
|
|
6290
|
-
onOpenRun(run.conversationId);
|
|
6291
|
-
onOpenChange(false);
|
|
6292
|
-
},
|
|
6293
|
-
"data-testid": chunkMHVNT4J3_cjs.testIdOr(testIds?.open, { testId: "task-run-open" }),
|
|
6294
|
-
children: [
|
|
6295
|
-
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Eye, { size: 13 }),
|
|
6296
|
-
" ",
|
|
6297
|
-
l.open
|
|
6298
|
-
]
|
|
6299
|
-
}
|
|
6300
|
-
)
|
|
6301
|
-
}
|
|
6302
|
-
)
|
|
7304
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.Eye, { size: 13 }),
|
|
7305
|
+
" ",
|
|
7306
|
+
l.open
|
|
6303
7307
|
]
|
|
6304
|
-
}
|
|
6305
|
-
|
|
6306
|
-
|
|
7308
|
+
}
|
|
7309
|
+
) })
|
|
7310
|
+
] });
|
|
7311
|
+
}
|
|
7312
|
+
}
|
|
7313
|
+
],
|
|
7314
|
+
[onOpenRun, onOpenResult, getRunHref, onOpenChange, testIds?.open, l.open, renderErrorReport]
|
|
7315
|
+
);
|
|
7316
|
+
const content = /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
7317
|
+
hideHeader ? null : inline ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
7318
|
+
chunk6DNYPLCD_cjs.TabHeader,
|
|
7319
|
+
{
|
|
7320
|
+
tabs: [
|
|
7321
|
+
{
|
|
7322
|
+
id: "history",
|
|
7323
|
+
label: l.title(taskName),
|
|
7324
|
+
count: runs.length,
|
|
7325
|
+
countIcon: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.History, { size: 14 }),
|
|
7326
|
+
presentation: "count",
|
|
7327
|
+
onClose: () => onOpenChange(false)
|
|
6307
7328
|
}
|
|
6308
|
-
|
|
6309
|
-
|
|
7329
|
+
],
|
|
7330
|
+
activeTabId: "history",
|
|
7331
|
+
onTabChange: () => {
|
|
7332
|
+
}
|
|
7333
|
+
}
|
|
7334
|
+
) : /* @__PURE__ */ jsxRuntime.jsxs(ui.DialogHeader, { children: [
|
|
7335
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogTitle, { className: "flex items-center gap-2", children: [
|
|
7336
|
+
/* @__PURE__ */ jsxRuntime.jsx(lucideReact.History, { size: 16 }),
|
|
7337
|
+
" ",
|
|
7338
|
+
l.title(taskName)
|
|
7339
|
+
] }),
|
|
7340
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DialogDescription, { children: l.description })
|
|
7341
|
+
] }),
|
|
7342
|
+
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "min-h-0 flex-1", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
7343
|
+
chunkIA7RTPT3_cjs.GridView,
|
|
7344
|
+
{
|
|
7345
|
+
testId: chunkMHVNT4J3_cjs.testIdOr(testIds?.list, { testId: "task-runs-list" }),
|
|
7346
|
+
gridId: "workflow-runs",
|
|
7347
|
+
items: runs,
|
|
7348
|
+
columnDefs: columns,
|
|
7349
|
+
getItemId: (run) => run.id,
|
|
7350
|
+
getRowTestId: () => chunkMHVNT4J3_cjs.testIdOr(testIds?.row, { testId: "task-run-row" }),
|
|
7351
|
+
isLoading,
|
|
7352
|
+
loadingMessage: l.loading,
|
|
7353
|
+
emptyState: { title: l.empty },
|
|
7354
|
+
height: "100%"
|
|
7355
|
+
}
|
|
7356
|
+
) })
|
|
7357
|
+
] });
|
|
7358
|
+
return inline ? /* @__PURE__ */ jsxRuntime.jsx("section", { className: "flex min-h-0 flex-1 flex-col", "data-testid": "automation-history", children: content }) : /* @__PURE__ */ jsxRuntime.jsx(ui.Dialog, { open, onOpenChange, children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
7359
|
+
ui.DialogContent,
|
|
7360
|
+
{
|
|
7361
|
+
presentation: "sheet",
|
|
7362
|
+
className: "flex h-[min(32rem,calc(100dvh-2rem))] min-h-0 max-w-3xl flex-col",
|
|
7363
|
+
"data-testid": chunkMHVNT4J3_cjs.testIdOr(testIds?.modal, { testId: "task-runs-modal" }),
|
|
7364
|
+
children: content
|
|
6310
7365
|
}
|
|
6311
7366
|
) });
|
|
6312
7367
|
}
|
|
@@ -6326,7 +7381,7 @@ function TasksToolbar({ count, onNewTask, testIds, labels }) {
|
|
|
6326
7381
|
}
|
|
6327
7382
|
];
|
|
6328
7383
|
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "sticky top-0 z-10 bg-background", "data-slot": "tasks-toolbar", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
6329
|
-
|
|
7384
|
+
chunk6DNYPLCD_cjs.TabHeader,
|
|
6330
7385
|
{
|
|
6331
7386
|
tabs,
|
|
6332
7387
|
activeTabId: "tasks",
|
|
@@ -6362,7 +7417,7 @@ function WorkflowsToolbar({ count, onNewWorkflow, testIds, labels }) {
|
|
|
6362
7417
|
}
|
|
6363
7418
|
];
|
|
6364
7419
|
return /* @__PURE__ */ jsxRuntime.jsx("div", { className: "sticky top-0 z-10 bg-background", "data-slot": "workflows-toolbar", children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
6365
|
-
|
|
7420
|
+
chunk6DNYPLCD_cjs.TabHeader,
|
|
6366
7421
|
{
|
|
6367
7422
|
tabs,
|
|
6368
7423
|
activeTabId: "workflows",
|
|
@@ -6428,7 +7483,7 @@ var DEFAULT_TASK_COMPOSER_LABELS = {
|
|
|
6428
7483
|
dueClear: "Clear date",
|
|
6429
7484
|
parentTask: "Part of",
|
|
6430
7485
|
parentTaskNone: "Nothing (top-level)",
|
|
6431
|
-
visibility: "
|
|
7486
|
+
visibility: "Visibility",
|
|
6432
7487
|
visibilityWorkspace: "Workspace",
|
|
6433
7488
|
visibilityPrivate: "Only me",
|
|
6434
7489
|
assistant: "Task Assistant",
|
|
@@ -6478,8 +7533,8 @@ var DEFAULT_TASK_COMPOSER_LABELS = {
|
|
|
6478
7533
|
empty: "No match.",
|
|
6479
7534
|
cancel: "Cancel",
|
|
6480
7535
|
addTask: "Add task",
|
|
6481
|
-
addAndStart: "
|
|
6482
|
-
addAndSchedule: "
|
|
7536
|
+
addAndStart: "Start now",
|
|
7537
|
+
addAndSchedule: "Schedule",
|
|
6483
7538
|
save: "Save changes",
|
|
6484
7539
|
saving: "Saving\u2026"
|
|
6485
7540
|
};
|
|
@@ -6498,7 +7553,7 @@ function defaultTaskComposerValues(workflows, initial) {
|
|
|
6498
7553
|
afterTaskId: "",
|
|
6499
7554
|
parentTaskId: "",
|
|
6500
7555
|
signoffUserId: "",
|
|
6501
|
-
shared:
|
|
7556
|
+
shared: false,
|
|
6502
7557
|
description: "",
|
|
6503
7558
|
dueAt: "",
|
|
6504
7559
|
agentId: "",
|
|
@@ -6508,7 +7563,6 @@ function defaultTaskComposerValues(workflows, initial) {
|
|
|
6508
7563
|
...initial
|
|
6509
7564
|
};
|
|
6510
7565
|
}
|
|
6511
|
-
var WHEN_ORDER = ["now", "once", "repeat", "event", "task"];
|
|
6512
7566
|
var GLYPH2 = "size-3.5 shrink-0";
|
|
6513
7567
|
function missingWhen(values, runAtPast) {
|
|
6514
7568
|
if (values.when === "now" || values.when === "manual") return null;
|
|
@@ -6522,6 +7576,8 @@ function WorkflowComposer({
|
|
|
6522
7576
|
open,
|
|
6523
7577
|
onOpenChange,
|
|
6524
7578
|
isEdit = false,
|
|
7579
|
+
saveOnly = false,
|
|
7580
|
+
hideRunLater = false,
|
|
6525
7581
|
workflows,
|
|
6526
7582
|
agents,
|
|
6527
7583
|
people,
|
|
@@ -6530,6 +7586,8 @@ function WorkflowComposer({
|
|
|
6530
7586
|
initialValues,
|
|
6531
7587
|
onValuesChange,
|
|
6532
7588
|
timezones = [],
|
|
7589
|
+
eventOptions,
|
|
7590
|
+
eventWorkflowOptions,
|
|
6533
7591
|
goal,
|
|
6534
7592
|
standingAccess,
|
|
6535
7593
|
scopeSource,
|
|
@@ -6551,7 +7609,11 @@ function WorkflowComposer({
|
|
|
6551
7609
|
const l = {
|
|
6552
7610
|
...DEFAULT_TASK_COMPOSER_LABELS,
|
|
6553
7611
|
...labels,
|
|
6554
|
-
whenOptions: {
|
|
7612
|
+
whenOptions: {
|
|
7613
|
+
...DEFAULT_TASK_COMPOSER_LABELS.whenOptions,
|
|
7614
|
+
...labels?.whenOptions,
|
|
7615
|
+
...saveOnly ? { now: "When needed" } : {}
|
|
7616
|
+
},
|
|
6555
7617
|
accessOptions: { ...DEFAULT_TASK_COMPOSER_LABELS.accessOptions, ...labels?.accessOptions }
|
|
6556
7618
|
};
|
|
6557
7619
|
const seed = react.useMemo(
|
|
@@ -6565,12 +7627,15 @@ function WorkflowComposer({
|
|
|
6565
7627
|
seed,
|
|
6566
7628
|
onValuesChange
|
|
6567
7629
|
);
|
|
7630
|
+
const [runOnce, setRunOnce] = react.useState(false);
|
|
7631
|
+
const [automationWhen, setAutomationWhen] = react.useState(seed.when);
|
|
6568
7632
|
const [planOpen, setPlanOpen] = react.useState(false);
|
|
6569
7633
|
const [moreOpen, setMoreOpen] = react.useState(false);
|
|
6570
7634
|
const [agentAutoSet, setAgentAutoSet] = react.useState(false);
|
|
6571
7635
|
react.useEffect(() => {
|
|
6572
7636
|
if (open) {
|
|
6573
7637
|
if (valuesProp === void 0) setValues(seed);
|
|
7638
|
+
setRunOnce(false);
|
|
6574
7639
|
setPlanOpen(false);
|
|
6575
7640
|
setAgentAutoSet(false);
|
|
6576
7641
|
}
|
|
@@ -6599,7 +7664,12 @@ function WorkflowComposer({
|
|
|
6599
7664
|
const derivedName = workflow ? deriveWorkflowName(workflow, values.inputs) : "";
|
|
6600
7665
|
const pickWorkflow = (next) => {
|
|
6601
7666
|
const def = workflows.find((w) => w.id === next);
|
|
6602
|
-
setValues({
|
|
7667
|
+
setValues({
|
|
7668
|
+
...values,
|
|
7669
|
+
workflowId: next,
|
|
7670
|
+
inputs: def ? defaultInputs(def) : {},
|
|
7671
|
+
...def?.documentAction ? { access: "standing" } : {}
|
|
7672
|
+
});
|
|
6603
7673
|
};
|
|
6604
7674
|
const pickWhen = (next) => {
|
|
6605
7675
|
const goesScheduled = next !== "now" && next !== "manual";
|
|
@@ -6623,14 +7693,18 @@ function WorkflowComposer({
|
|
|
6623
7693
|
setAgentAutoSet(false);
|
|
6624
7694
|
set("agentId", agentId);
|
|
6625
7695
|
};
|
|
6626
|
-
const submit = () =>
|
|
6627
|
-
|
|
6628
|
-
|
|
6629
|
-
|
|
6630
|
-
|
|
6631
|
-
|
|
6632
|
-
|
|
6633
|
-
|
|
7696
|
+
const submit = () => {
|
|
7697
|
+
const submitted = {
|
|
7698
|
+
...values,
|
|
7699
|
+
// A scope pick is bound to explicit file ids before anything is sent.
|
|
7700
|
+
inputs: workflow && !workflow.documentAction ? resolveScopeInputs(workflow, values.inputs, scopeSource) : values.inputs,
|
|
7701
|
+
assignee: "agent",
|
|
7702
|
+
notifyOnComplete: true,
|
|
7703
|
+
name: values.name.trim()
|
|
7704
|
+
};
|
|
7705
|
+
if (runOnce) onSubmit(submitted, { runOnce: true });
|
|
7706
|
+
else onSubmit(submitted);
|
|
7707
|
+
};
|
|
6634
7708
|
const pillLabels = { search: l.search, empty: l.empty };
|
|
6635
7709
|
const personOptions = (people ?? []).map((p) => ({
|
|
6636
7710
|
id: p.id,
|
|
@@ -6643,10 +7717,11 @@ function WorkflowComposer({
|
|
|
6643
7717
|
label: t.name,
|
|
6644
7718
|
icon: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CornerDownRight, { className: GLYPH2, "aria-hidden": true })
|
|
6645
7719
|
}));
|
|
6646
|
-
const whenOptions =
|
|
6647
|
-
id:
|
|
6648
|
-
label:
|
|
6649
|
-
|
|
7720
|
+
const whenOptions = [
|
|
7721
|
+
{ id: "manual", label: "Start now" },
|
|
7722
|
+
{ id: "schedule", label: "Schedule" },
|
|
7723
|
+
{ id: "event", label: "Notification" }
|
|
7724
|
+
];
|
|
6650
7725
|
const assistantOptions = agents.map((a) => ({ id: a.id, label: a.label }));
|
|
6651
7726
|
if (values.agentId && !assistantOptions.some((a) => a.id === values.agentId)) {
|
|
6652
7727
|
assistantOptions.push({ id: values.agentId, label: "Assigned agent" });
|
|
@@ -6654,18 +7729,42 @@ function WorkflowComposer({
|
|
|
6654
7729
|
const goalNode = typeof goal === "function" ? goal(values) : goal;
|
|
6655
7730
|
const pickedTemplate = workflows.find((w) => w.id === values.workflowId && !w.generic);
|
|
6656
7731
|
const hint = (key) => l[key];
|
|
6657
|
-
return /* @__PURE__ */ jsxRuntime.jsx(ui.Dialog, { open, onOpenChange, children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7732
|
+
return /* @__PURE__ */ jsxRuntime.jsx(ui.Dialog, { modal: false, open, onOpenChange, children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
6658
7733
|
ui.DialogContent,
|
|
6659
7734
|
{
|
|
6660
|
-
presentation: "
|
|
6661
|
-
|
|
7735
|
+
presentation: "right",
|
|
7736
|
+
hideCloseButton: true,
|
|
7737
|
+
onInteractOutside: (event) => event.preventDefault(),
|
|
7738
|
+
className: "flex flex-col gap-0 overflow-hidden p-0 shadow-lg",
|
|
6662
7739
|
"data-testid": id,
|
|
6663
7740
|
children: [
|
|
6664
|
-
/* @__PURE__ */ jsxRuntime.
|
|
6665
|
-
|
|
6666
|
-
|
|
6667
|
-
|
|
6668
|
-
|
|
7741
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DialogTitle, { className: "sr-only", children: "Automation settings" }),
|
|
7742
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DialogDescription, { className: "sr-only", children: l.descriptionWorkflow }),
|
|
7743
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7744
|
+
chunk6DNYPLCD_cjs.TabHeader,
|
|
7745
|
+
{
|
|
7746
|
+
tabs: [
|
|
7747
|
+
{
|
|
7748
|
+
id: "automation-setup",
|
|
7749
|
+
label: isEdit ? l.titleEditWorkflow : pickedTemplate ? l.titleRunTemplate(pickedTemplate.title) : l.titleNewWorkflow,
|
|
7750
|
+
presentation: "count"
|
|
7751
|
+
},
|
|
7752
|
+
...(saveOnly || isEdit) && !workflow?.documentAction ? [{ id: "start-task", label: "Start task" }] : []
|
|
7753
|
+
],
|
|
7754
|
+
activeTabId: runOnce ? "start-task" : "automation-setup",
|
|
7755
|
+
onTabChange: (tab) => {
|
|
7756
|
+
if (tab === "start-task" && !runOnce) {
|
|
7757
|
+
setAutomationWhen(values.when);
|
|
7758
|
+
set("when", "now");
|
|
7759
|
+
setRunOnce(true);
|
|
7760
|
+
} else if (tab === "automation-setup" && runOnce) {
|
|
7761
|
+
set("when", automationWhen);
|
|
7762
|
+
setRunOnce(false);
|
|
7763
|
+
}
|
|
7764
|
+
},
|
|
7765
|
+
rightContent: /* @__PURE__ */ jsxRuntime.jsx(ui.DialogClose, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "ghost", size: "icon", "aria-label": "Close", children: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.X, { className: "size-4" }) }) })
|
|
7766
|
+
}
|
|
7767
|
+
),
|
|
6669
7768
|
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
6670
7769
|
"form",
|
|
6671
7770
|
{
|
|
@@ -6702,7 +7801,7 @@ function WorkflowComposer({
|
|
|
6702
7801
|
},
|
|
6703
7802
|
"data-testid": `${id}-dropzone`,
|
|
6704
7803
|
children: /* @__PURE__ */ jsxRuntime.jsx(
|
|
6705
|
-
|
|
7804
|
+
chunkWBDK4PIA_cjs.AddFilesFirst,
|
|
6706
7805
|
{
|
|
6707
7806
|
reason: l.addFilesReason,
|
|
6708
7807
|
action: addFilesAction,
|
|
@@ -6755,7 +7854,7 @@ function WorkflowComposer({
|
|
|
6755
7854
|
goalNode
|
|
6756
7855
|
] })
|
|
6757
7856
|
] }),
|
|
6758
|
-
(scheduled || isEdit) && /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
7857
|
+
!runOnce && (scheduled || isEdit) && /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
|
|
6759
7858
|
/* @__PURE__ */ jsxRuntime.jsxs("section", { className: "flex flex-col gap-2", "data-testid": `${id}-when-section`, children: [
|
|
6760
7859
|
/* @__PURE__ */ jsxRuntime.jsx("h3", { className: "text-sm font-medium", children: l.whenHeading }),
|
|
6761
7860
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
@@ -6763,14 +7862,30 @@ function WorkflowComposer({
|
|
|
6763
7862
|
{
|
|
6764
7863
|
icon: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Play, { className: GLYPH2, "aria-hidden": true }),
|
|
6765
7864
|
prefix: l.start,
|
|
6766
|
-
value: values.when,
|
|
7865
|
+
value: values.when === "once" || values.when === "repeat" ? "schedule" : values.when === "task" ? "event" : values.when === "now" ? "manual" : values.when,
|
|
6767
7866
|
options: whenOptions,
|
|
6768
|
-
onChange: (v) => pickWhen(v),
|
|
7867
|
+
onChange: (v) => pickWhen(v === "schedule" ? "once" : v),
|
|
6769
7868
|
labels: pillLabels,
|
|
6770
7869
|
testId: `${id}-when`,
|
|
6771
7870
|
className: "self-start"
|
|
6772
7871
|
}
|
|
6773
7872
|
),
|
|
7873
|
+
(values.when === "once" || values.when === "repeat") && /* @__PURE__ */ jsxRuntime.jsx(
|
|
7874
|
+
PillSelect,
|
|
7875
|
+
{
|
|
7876
|
+
icon: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Play, { className: GLYPH2, "aria-hidden": true }),
|
|
7877
|
+
prefix: "Schedule",
|
|
7878
|
+
value: values.when,
|
|
7879
|
+
options: [
|
|
7880
|
+
{ id: "once", label: "Once" },
|
|
7881
|
+
{ id: "repeat", label: "Repeat" }
|
|
7882
|
+
],
|
|
7883
|
+
onChange: (value) => pickWhen(value),
|
|
7884
|
+
labels: pillLabels,
|
|
7885
|
+
testId: `${id}-schedule-mode`,
|
|
7886
|
+
className: "self-start"
|
|
7887
|
+
}
|
|
7888
|
+
),
|
|
6774
7889
|
values.when === "once" && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col gap-1.5", children: [
|
|
6775
7890
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Label, { htmlFor: "task-composer-runat", className: "sr-only", children: l.runAt }),
|
|
6776
7891
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
@@ -6814,7 +7929,25 @@ function WorkflowComposer({
|
|
|
6814
7929
|
] }),
|
|
6815
7930
|
values.when === "event" && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-col gap-1.5", children: [
|
|
6816
7931
|
/* @__PURE__ */ jsxRuntime.jsx(ui.Label, { htmlFor: "task-composer-event", className: "sr-only", children: l.event }),
|
|
6817
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
7932
|
+
eventOptions ? /* @__PURE__ */ jsxRuntime.jsx(
|
|
7933
|
+
PillSelect,
|
|
7934
|
+
{
|
|
7935
|
+
icon: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Zap, { className: GLYPH2, "aria-hidden": true }),
|
|
7936
|
+
prefix: l.event,
|
|
7937
|
+
value: values.eventKind,
|
|
7938
|
+
options: eventOptions.some((option) => option.id === values.eventKind) || !values.eventKind ? [...eventOptions] : [
|
|
7939
|
+
...eventOptions,
|
|
7940
|
+
{
|
|
7941
|
+
id: values.eventKind,
|
|
7942
|
+
label: values.eventKind.replaceAll("_", " ")
|
|
7943
|
+
}
|
|
7944
|
+
],
|
|
7945
|
+
onChange: (event) => set("eventKind", event),
|
|
7946
|
+
labels: pillLabels,
|
|
7947
|
+
testId: `${id}-event`,
|
|
7948
|
+
className: "self-start"
|
|
7949
|
+
}
|
|
7950
|
+
) : /* @__PURE__ */ jsxRuntime.jsx(
|
|
6818
7951
|
ui.Input,
|
|
6819
7952
|
{
|
|
6820
7953
|
id: "task-composer-event",
|
|
@@ -6827,6 +7960,22 @@ function WorkflowComposer({
|
|
|
6827
7960
|
),
|
|
6828
7961
|
/* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-xs text-muted-foreground", children: l.eventHint })
|
|
6829
7962
|
] }),
|
|
7963
|
+
values.when === "event" && values.eventKind === "workflow_completed" && eventWorkflowOptions && /* @__PURE__ */ jsxRuntime.jsx(
|
|
7964
|
+
PillSelect,
|
|
7965
|
+
{
|
|
7966
|
+
icon: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Zap, { className: GLYPH2, "aria-hidden": true }),
|
|
7967
|
+
prefix: "Automation",
|
|
7968
|
+
value: typeof values.eventFilter?.workflow_ext_id === "string" ? values.eventFilter.workflow_ext_id : "",
|
|
7969
|
+
options: [{ id: "", label: "Any automation" }, ...eventWorkflowOptions],
|
|
7970
|
+
onChange: (id2) => set(
|
|
7971
|
+
"eventFilter",
|
|
7972
|
+
id2 ? { ...values.eventFilter, workflow_ext_id: id2 } : null
|
|
7973
|
+
),
|
|
7974
|
+
labels: pillLabels,
|
|
7975
|
+
testId: `${id}-event-workflow`,
|
|
7976
|
+
className: "self-start"
|
|
7977
|
+
}
|
|
7978
|
+
),
|
|
6830
7979
|
values.when === "task" && /* @__PURE__ */ jsxRuntime.jsx(
|
|
6831
7980
|
PillSelect,
|
|
6832
7981
|
{
|
|
@@ -7021,7 +8170,7 @@ function WorkflowComposer({
|
|
|
7021
8170
|
children: l.cancel
|
|
7022
8171
|
}
|
|
7023
8172
|
),
|
|
7024
|
-
!isEdit && /* @__PURE__ */ jsxRuntime.jsx(
|
|
8173
|
+
!isEdit && !saveOnly && !hideRunLater && /* @__PURE__ */ jsxRuntime.jsx(
|
|
7025
8174
|
ui.Button,
|
|
7026
8175
|
{
|
|
7027
8176
|
type: "button",
|
|
@@ -7041,7 +8190,7 @@ function WorkflowComposer({
|
|
|
7041
8190
|
className: "gap-1.5 pointer-coarse:min-h-11",
|
|
7042
8191
|
children: [
|
|
7043
8192
|
isPending && /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Loader2, { className: "size-4 animate-spin" }),
|
|
7044
|
-
isPending ? l.saving : isEdit ? l.save : scheduled ? l.saveWorkflow : l.runNow
|
|
8193
|
+
isPending ? l.saving : runOnce ? "Start now" : isEdit ? l.save : saveOnly || scheduled ? l.saveWorkflow : l.runNow
|
|
7045
8194
|
]
|
|
7046
8195
|
}
|
|
7047
8196
|
)
|
|
@@ -7053,7 +8202,7 @@ function WorkflowComposer({
|
|
|
7053
8202
|
}
|
|
7054
8203
|
) });
|
|
7055
8204
|
}
|
|
7056
|
-
var
|
|
8205
|
+
var WHEN_ORDER = ["now", "once", "repeat", "event", "task"];
|
|
7057
8206
|
function formatDue2(local) {
|
|
7058
8207
|
const d = new Date(local);
|
|
7059
8208
|
if (Number.isNaN(d.getTime())) return local;
|
|
@@ -7156,7 +8305,7 @@ function WorkTaskComposer({
|
|
|
7156
8305
|
label: t.name,
|
|
7157
8306
|
icon: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.CornerDownRight, { className: GLYPH3, "aria-hidden": true })
|
|
7158
8307
|
}));
|
|
7159
|
-
const whenOptions =
|
|
8308
|
+
const whenOptions = WHEN_ORDER.map((mode) => ({
|
|
7160
8309
|
id: mode,
|
|
7161
8310
|
label: l.whenOptions[mode]
|
|
7162
8311
|
}));
|
|
@@ -7165,8 +8314,8 @@ function WorkTaskComposer({
|
|
|
7165
8314
|
return /* @__PURE__ */ jsxRuntime.jsx(ui.Dialog, { open, onOpenChange, children: /* @__PURE__ */ jsxRuntime.jsxs(
|
|
7166
8315
|
ui.DialogContent,
|
|
7167
8316
|
{
|
|
7168
|
-
presentation: "
|
|
7169
|
-
className: "flex
|
|
8317
|
+
presentation: "right",
|
|
8318
|
+
className: "flex flex-col overflow-hidden p-0",
|
|
7170
8319
|
"data-testid": id,
|
|
7171
8320
|
children: [
|
|
7172
8321
|
/* @__PURE__ */ jsxRuntime.jsxs(chunk2ZTONLT5_cjs.ModalHeader, { children: [
|
|
@@ -7268,6 +8417,7 @@ function WorkTaskComposer({
|
|
|
7268
8417
|
items: { shared: values.shared },
|
|
7269
8418
|
onToggle: (share) => set("shared", share),
|
|
7270
8419
|
label: l.visibility,
|
|
8420
|
+
presentation: "select",
|
|
7271
8421
|
"data-testid": `${id}-visibility`
|
|
7272
8422
|
}
|
|
7273
8423
|
)
|
|
@@ -7521,6 +8671,210 @@ function WorkTaskComposer({
|
|
|
7521
8671
|
function TaskComposer(props) {
|
|
7522
8672
|
return props.kind === "workflow" ? /* @__PURE__ */ jsxRuntime.jsx(WorkflowComposer, { ...props }) : /* @__PURE__ */ jsxRuntime.jsx(WorkTaskComposer, { ...props });
|
|
7523
8673
|
}
|
|
8674
|
+
function TaskReviewDialog(p) {
|
|
8675
|
+
const [action, setAction] = react.useState("forward");
|
|
8676
|
+
const [userId, setUserId] = react.useState("");
|
|
8677
|
+
const [note, setNote] = react.useState("");
|
|
8678
|
+
react.useEffect(() => {
|
|
8679
|
+
if (p.open) {
|
|
8680
|
+
setAction(p.people.length ? "forward" : p.canApprove ? "finish" : "revise");
|
|
8681
|
+
setUserId("");
|
|
8682
|
+
setNote("");
|
|
8683
|
+
}
|
|
8684
|
+
}, [p.open]);
|
|
8685
|
+
const valid = action === "forward" ? p.people.some((person) => person.id === userId) : action === "revise" ? p.canRevise && Boolean(note.trim()) : p.canApprove;
|
|
8686
|
+
return /* @__PURE__ */ jsxRuntime.jsx(ui.Dialog, { open: p.open, onOpenChange: (next) => !p.isPending && p.onOpenChange(next), children: /* @__PURE__ */ jsxRuntime.jsxs(ui.DialogContent, { "data-testid": "task-review-dialog", className: "sm:max-w-lg", children: [
|
|
8687
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.DialogTitle, { children: [
|
|
8688
|
+
"Review: ",
|
|
8689
|
+
p.taskName
|
|
8690
|
+
] }),
|
|
8691
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DialogDescription, { children: p.canApprove ? "Approve your review and send it on, request changes, or finish the task." : "Choose who should review this work next, or ask ARBI for changes." }),
|
|
8692
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "space-y-4 py-2", children: [
|
|
8693
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "space-y-2", children: [
|
|
8694
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Label, { htmlFor: "review-next-step", children: "Next step" }),
|
|
8695
|
+
/* @__PURE__ */ jsxRuntime.jsxs(
|
|
8696
|
+
ui.Select,
|
|
8697
|
+
{
|
|
8698
|
+
value: action,
|
|
8699
|
+
onValueChange: (value) => setAction(value),
|
|
8700
|
+
disabled: p.isPending,
|
|
8701
|
+
children: [
|
|
8702
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.SelectTrigger, { id: "review-next-step", children: /* @__PURE__ */ jsxRuntime.jsx(ui.SelectValue, {}) }),
|
|
8703
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.SelectContent, { children: [
|
|
8704
|
+
p.people.length > 0 && /* @__PURE__ */ jsxRuntime.jsx(ui.SelectItem, { value: "forward", children: p.canApprove ? "Approve and send for review" : "Send for review" }),
|
|
8705
|
+
p.canRevise && /* @__PURE__ */ jsxRuntime.jsx(ui.SelectItem, { value: "revise", children: "Ask ARBI for changes" }),
|
|
8706
|
+
p.canApprove && /* @__PURE__ */ jsxRuntime.jsx(ui.SelectItem, { value: "finish", children: "Approve and finish task" })
|
|
8707
|
+
] })
|
|
8708
|
+
]
|
|
8709
|
+
}
|
|
8710
|
+
)
|
|
8711
|
+
] }),
|
|
8712
|
+
action === "forward" && /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "space-y-2", children: [
|
|
8713
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Label, { htmlFor: "review-recipient", children: "Next reviewer" }),
|
|
8714
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Select, { value: userId, onValueChange: setUserId, disabled: p.isPending, children: [
|
|
8715
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.SelectTrigger, { id: "review-recipient", children: /* @__PURE__ */ jsxRuntime.jsx(ui.SelectValue, { placeholder: "Choose a person" }) }),
|
|
8716
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.SelectContent, { children: p.people.map((person) => /* @__PURE__ */ jsxRuntime.jsx(ui.SelectItem, { value: person.id, children: person.label }, person.id)) })
|
|
8717
|
+
] })
|
|
8718
|
+
] }),
|
|
8719
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "space-y-2", children: [
|
|
8720
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Label, { htmlFor: "review-note", children: action === "revise" ? "What should ARBI change?" : "Review note (optional)" }),
|
|
8721
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8722
|
+
ui.Textarea,
|
|
8723
|
+
{
|
|
8724
|
+
id: "review-note",
|
|
8725
|
+
value: note,
|
|
8726
|
+
onChange: (e) => setNote(e.target.value),
|
|
8727
|
+
disabled: p.isPending,
|
|
8728
|
+
placeholder: action === "revise" ? "Explain what needs changing in the same draft\u2026" : "Explain what you checked and what the next reviewer should focus on\u2026"
|
|
8729
|
+
}
|
|
8730
|
+
)
|
|
8731
|
+
] }),
|
|
8732
|
+
p.error && /* @__PURE__ */ jsxRuntime.jsx("p", { role: "alert", className: "text-sm text-destructive", children: p.error })
|
|
8733
|
+
] }),
|
|
8734
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex justify-end gap-2", children: [
|
|
8735
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "outline", onClick: () => p.onOpenChange(false), disabled: p.isPending, children: "Cancel" }),
|
|
8736
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8737
|
+
ui.Button,
|
|
8738
|
+
{
|
|
8739
|
+
"data-testid": "task-review-submit",
|
|
8740
|
+
disabled: !valid || p.isPending,
|
|
8741
|
+
onClick: () => p.onSubmit({
|
|
8742
|
+
action,
|
|
8743
|
+
userId,
|
|
8744
|
+
note: note.trim(),
|
|
8745
|
+
approveCurrent: p.canApprove && action === "forward"
|
|
8746
|
+
}),
|
|
8747
|
+
children: p.isPending ? "Saving\u2026" : action === "forward" ? p.canApprove ? "Approve and send" : "Send for review" : action === "revise" ? "Send to ARBI" : "Finish task"
|
|
8748
|
+
}
|
|
8749
|
+
)
|
|
8750
|
+
] })
|
|
8751
|
+
] }) });
|
|
8752
|
+
}
|
|
8753
|
+
function ThreadNotifyDialog({
|
|
8754
|
+
open,
|
|
8755
|
+
onOpenChange,
|
|
8756
|
+
people,
|
|
8757
|
+
isShared,
|
|
8758
|
+
onNotify
|
|
8759
|
+
}) {
|
|
8760
|
+
const [selected, setSelected] = react.useState([]);
|
|
8761
|
+
const [query, setQuery] = react.useState("");
|
|
8762
|
+
const [busy, setBusy] = react.useState(false);
|
|
8763
|
+
const [error, setError] = react.useState(null);
|
|
8764
|
+
react.useEffect(() => {
|
|
8765
|
+
if (open) {
|
|
8766
|
+
setSelected([]);
|
|
8767
|
+
setQuery("");
|
|
8768
|
+
setError(null);
|
|
8769
|
+
}
|
|
8770
|
+
}, [open]);
|
|
8771
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
8772
|
+
ui.Dialog,
|
|
8773
|
+
{
|
|
8774
|
+
open,
|
|
8775
|
+
onOpenChange: (value) => {
|
|
8776
|
+
if (!busy) onOpenChange(value);
|
|
8777
|
+
},
|
|
8778
|
+
children: /* @__PURE__ */ jsxRuntime.jsxs(ui.DialogContent, { className: "max-w-sm", "data-testid": "thread-notify-dialog", children: [
|
|
8779
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DialogTitle, { children: "Notify" }),
|
|
8780
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.DialogDescription, { children: isShared ? "Ask someone to follow up in this thread." : "Notifying someone shares this thread with your workspace." }),
|
|
8781
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8782
|
+
ui.Input,
|
|
8783
|
+
{
|
|
8784
|
+
"aria-label": "Find people",
|
|
8785
|
+
placeholder: "Find someone\u2026",
|
|
8786
|
+
value: query,
|
|
8787
|
+
onChange: (event) => setQuery(event.target.value)
|
|
8788
|
+
}
|
|
8789
|
+
),
|
|
8790
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "max-h-64 overflow-y-auto space-y-1", children: [
|
|
8791
|
+
people.filter((person) => person.label.toLowerCase().includes(query.toLowerCase())).map((person) => /* @__PURE__ */ jsxRuntime.jsxs(
|
|
8792
|
+
"label",
|
|
8793
|
+
{
|
|
8794
|
+
className: "flex cursor-pointer items-center gap-2 rounded px-2 py-2 hover:bg-muted",
|
|
8795
|
+
children: [
|
|
8796
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8797
|
+
ui.Checkbox,
|
|
8798
|
+
{
|
|
8799
|
+
disabled: busy,
|
|
8800
|
+
checked: selected.includes(person.id),
|
|
8801
|
+
onCheckedChange: (checked) => setSelected(
|
|
8802
|
+
(old) => checked ? [...old, person.id] : old.filter((id) => id !== person.id)
|
|
8803
|
+
)
|
|
8804
|
+
}
|
|
8805
|
+
),
|
|
8806
|
+
person.label
|
|
8807
|
+
]
|
|
8808
|
+
},
|
|
8809
|
+
person.id
|
|
8810
|
+
)),
|
|
8811
|
+
!people.length && /* @__PURE__ */ jsxRuntime.jsx("p", { className: "text-sm text-muted-foreground", children: "No other workspace members yet." })
|
|
8812
|
+
] }),
|
|
8813
|
+
error && /* @__PURE__ */ jsxRuntime.jsx("p", { role: "alert", className: "text-sm text-destructive", children: error }),
|
|
8814
|
+
/* @__PURE__ */ jsxRuntime.jsx(
|
|
8815
|
+
ui.Button,
|
|
8816
|
+
{
|
|
8817
|
+
disabled: busy || !selected.length,
|
|
8818
|
+
"data-testid": "thread-notify-submit",
|
|
8819
|
+
onClick: async () => {
|
|
8820
|
+
setBusy(true);
|
|
8821
|
+
setError(null);
|
|
8822
|
+
try {
|
|
8823
|
+
await onNotify(selected);
|
|
8824
|
+
onOpenChange(false);
|
|
8825
|
+
} catch (failure) {
|
|
8826
|
+
setError(failure instanceof Error ? failure.message : "Could not notify people");
|
|
8827
|
+
} finally {
|
|
8828
|
+
setBusy(false);
|
|
8829
|
+
}
|
|
8830
|
+
},
|
|
8831
|
+
children: busy ? "Notifying\u2026" : "Notify"
|
|
8832
|
+
}
|
|
8833
|
+
)
|
|
8834
|
+
] })
|
|
8835
|
+
}
|
|
8836
|
+
);
|
|
8837
|
+
}
|
|
8838
|
+
function ConversationTurnSpeaker({
|
|
8839
|
+
role,
|
|
8840
|
+
actor,
|
|
8841
|
+
currentUserId,
|
|
8842
|
+
colorClass,
|
|
8843
|
+
platformName = "ARBI",
|
|
8844
|
+
platformLogoSrc = "/favicon.svg"
|
|
8845
|
+
}) {
|
|
8846
|
+
if (!role) return /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-muted-foreground", children: "\u2014" });
|
|
8847
|
+
if (role === "assistant" && !actor)
|
|
8848
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
8849
|
+
ui.UserEntity,
|
|
8850
|
+
{
|
|
8851
|
+
size: "sm",
|
|
8852
|
+
variant: "pill",
|
|
8853
|
+
interactive: false,
|
|
8854
|
+
picture: platformLogoSrc,
|
|
8855
|
+
avatarImageClassName: "object-contain p-0.5",
|
|
8856
|
+
initials: platformName.charAt(0),
|
|
8857
|
+
displayName: platformName
|
|
8858
|
+
}
|
|
8859
|
+
);
|
|
8860
|
+
if (!actor) return /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-muted-foreground", children: "Unknown participant" });
|
|
8861
|
+
const isMe = actor.external_id === currentUserId;
|
|
8862
|
+
const displayName = isMe ? "You" : [actor.given_name, actor.family_name].filter(Boolean).join(" ");
|
|
8863
|
+
return /* @__PURE__ */ jsxRuntime.jsx(
|
|
8864
|
+
ui.UserEntity,
|
|
8865
|
+
{
|
|
8866
|
+
size: "sm",
|
|
8867
|
+
variant: "pill",
|
|
8868
|
+
interactive: false,
|
|
8869
|
+
isMe,
|
|
8870
|
+
isAgent: actor.external_id.startsWith("agt-"),
|
|
8871
|
+
displayName,
|
|
8872
|
+
initials: `${actor.given_name.charAt(0)}${actor.family_name?.charAt(0) ?? ""}`.toUpperCase(),
|
|
8873
|
+
picture: actor.picture,
|
|
8874
|
+
colorClass
|
|
8875
|
+
}
|
|
8876
|
+
);
|
|
8877
|
+
}
|
|
7524
8878
|
var DEFAULT_TUPLE_ARRAY_FIELD_LABELS = {
|
|
7525
8879
|
addRow: "Add Row",
|
|
7526
8880
|
empty: 'No examples added yet. Click "Add Row" to start.',
|
|
@@ -9145,7 +10499,7 @@ function AgentCreateView({
|
|
|
9145
10499
|
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "font-normal text-muted-foreground", children: l.optional })
|
|
9146
10500
|
] }),
|
|
9147
10501
|
/* @__PURE__ */ jsxRuntime.jsx(
|
|
9148
|
-
|
|
10502
|
+
chunk2QTT2RZE_cjs.MultiSelect,
|
|
9149
10503
|
{
|
|
9150
10504
|
data: workspaces.map((ws) => ({ label: ws.name, value: ws.id })),
|
|
9151
10505
|
value: selectedWorkspaces,
|
|
@@ -9210,6 +10564,8 @@ exports.ConsentPermissionList = ConsentPermissionList;
|
|
|
9210
10564
|
exports.ConsentSection = ConsentSection;
|
|
9211
10565
|
exports.ConsentStrong = ConsentStrong;
|
|
9212
10566
|
exports.ConsentText = ConsentText;
|
|
10567
|
+
exports.ConversationListView = ConversationListView;
|
|
10568
|
+
exports.ConversationTurnSpeaker = ConversationTurnSpeaker;
|
|
9213
10569
|
exports.CopyableUrl = CopyableUrl;
|
|
9214
10570
|
exports.DEFAULT_AGENT_AVATAR_FIELD_LABELS = DEFAULT_AGENT_AVATAR_FIELD_LABELS;
|
|
9215
10571
|
exports.DEFAULT_AGENT_BAR_LABELS = DEFAULT_AGENT_BAR_LABELS;
|
|
@@ -9256,6 +10612,7 @@ exports.DEFAULT_WORKFLOW_LIST_LABELS = DEFAULT_WORKFLOW_LIST_LABELS;
|
|
|
9256
10612
|
exports.DERIVED_NAME_WORDS = DERIVED_NAME_WORDS;
|
|
9257
10613
|
exports.EMPTY_NEW_THREAD = EMPTY_NEW_THREAD;
|
|
9258
10614
|
exports.EMPTY_WORKFLOW_SCOPE = EMPTY_WORKFLOW_SCOPE;
|
|
10615
|
+
exports.EntityChip = EntityChip;
|
|
9259
10616
|
exports.GoalCriteria = GoalCriteria;
|
|
9260
10617
|
exports.MAX_TASK_DEPTH = MAX_TASK_DEPTH;
|
|
9261
10618
|
exports.NewThreadDialog = NewThreadDialog;
|
|
@@ -9296,16 +10653,22 @@ exports.TRIGGER_LABELS = TRIGGER_LABELS;
|
|
|
9296
10653
|
exports.TaskActivityDialog = TaskActivityDialog;
|
|
9297
10654
|
exports.TaskActivityTimeline = TaskActivityTimeline;
|
|
9298
10655
|
exports.TaskComposer = TaskComposer;
|
|
10656
|
+
exports.TaskFlow = TaskFlow;
|
|
10657
|
+
exports.TaskInbox = TaskInbox;
|
|
9299
10658
|
exports.TaskMoveDialog = TaskMoveDialog;
|
|
9300
10659
|
exports.TaskOutputsCell = TaskOutputsCell;
|
|
9301
10660
|
exports.TaskPlan = TaskPlan;
|
|
9302
10661
|
exports.TaskReviewActions = TaskReviewActions;
|
|
10662
|
+
exports.TaskReviewDialog = TaskReviewDialog;
|
|
9303
10663
|
exports.TaskRunsDialog = TaskRunsDialog;
|
|
10664
|
+
exports.TaskStartDialog = TaskStartDialog;
|
|
9304
10665
|
exports.TaskStatusPill = TaskStatusPill;
|
|
9305
10666
|
exports.TaskTable = TaskTable;
|
|
9306
10667
|
exports.TaskThreadChip = TaskThreadChip;
|
|
9307
10668
|
exports.TaskTriggerChip = TaskTriggerChip;
|
|
9308
10669
|
exports.TasksToolbar = TasksToolbar;
|
|
10670
|
+
exports.ThreadActivity = ThreadActivity;
|
|
10671
|
+
exports.ThreadNotifyDialog = ThreadNotifyDialog;
|
|
9309
10672
|
exports.TupleArrayField = TupleArrayField;
|
|
9310
10673
|
exports.UploadTaskItem = UploadTaskItem;
|
|
9311
10674
|
exports.UploadTaskList = UploadTaskList;
|
|
@@ -9324,6 +10687,7 @@ exports.buildLaunch = buildLaunch;
|
|
|
9324
10687
|
exports.buildRRule = buildRRule;
|
|
9325
10688
|
exports.buildTaskRows = buildTaskRows;
|
|
9326
10689
|
exports.buildWorkflowScopeSource = buildWorkflowScopeSource;
|
|
10690
|
+
exports.compactThreadActivity = compactThreadActivity;
|
|
9327
10691
|
exports.composePersona = composePersona;
|
|
9328
10692
|
exports.composeWorkflowPrompt = composeWorkflowPrompt;
|
|
9329
10693
|
exports.composerToTaskQuery = composerToTaskQuery;
|
|
@@ -9340,6 +10704,7 @@ exports.deriveAgentName = deriveAgentName;
|
|
|
9340
10704
|
exports.deriveWorkflowName = deriveWorkflowName;
|
|
9341
10705
|
exports.descendantIds = descendantIds;
|
|
9342
10706
|
exports.describeRRule = describeRRule;
|
|
10707
|
+
exports.filterConversationRows = filterConversationRows;
|
|
9343
10708
|
exports.firstWords = firstWords;
|
|
9344
10709
|
exports.formatElapsed = formatElapsed;
|
|
9345
10710
|
exports.goalProgress = goalProgress;
|
|
@@ -9386,5 +10751,5 @@ exports.workflowTriggerType = workflowTriggerType;
|
|
|
9386
10751
|
exports.workflowWhen = workflowWhen;
|
|
9387
10752
|
exports.workflowsAccepting = workflowsAccepting;
|
|
9388
10753
|
exports.workflowsForHost = workflowsForHost;
|
|
9389
|
-
//# sourceMappingURL=chunk-
|
|
9390
|
-
//# sourceMappingURL=chunk-
|
|
10754
|
+
//# sourceMappingURL=chunk-SEQWI6E4.cjs.map
|
|
10755
|
+
//# sourceMappingURL=chunk-SEQWI6E4.cjs.map
|