@arbidocs/blocks 0.4.86 → 0.4.88

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (99) hide show
  1. package/dist/activity/NotificationRelevanceControls.d.ts +47 -0
  2. package/dist/activity/WorkspaceActivityList.d.ts +34 -0
  3. package/dist/activity/index.d.ts +3 -0
  4. package/dist/activity/workspace-activity.d.ts +46 -0
  5. package/dist/agents/index.cjs +290 -286
  6. package/dist/agents/index.js +5 -5
  7. package/dist/agents/tasks/TaskActivityTimeline.d.ts +5 -0
  8. package/dist/agents/tasks/index.d.ts +1 -1
  9. package/dist/{chunk-2EI7NCUA.cjs → chunk-2CFW2ELM.cjs} +8 -2
  10. package/dist/chunk-2CFW2ELM.cjs.map +1 -0
  11. package/dist/{chunk-7YUFMNFW.cjs → chunk-2ZDFVRGV.cjs} +5 -13
  12. package/dist/chunk-2ZDFVRGV.cjs.map +1 -0
  13. package/dist/{chunk-RZUMQM7W.cjs → chunk-5XZU64E2.cjs} +190 -2
  14. package/dist/chunk-5XZU64E2.cjs.map +1 -0
  15. package/dist/{chunk-R26OHONI.js → chunk-6S5FLMWG.js} +83 -72
  16. package/dist/chunk-6S5FLMWG.js.map +1 -0
  17. package/dist/chunk-6XS5IJ5R.cjs +43 -0
  18. package/dist/chunk-6XS5IJ5R.cjs.map +1 -0
  19. package/dist/chunk-BX62HJZU.js +41 -0
  20. package/dist/chunk-BX62HJZU.js.map +1 -0
  21. package/dist/{chunk-IHYVK6F7.cjs → chunk-FNEL2BYV.cjs} +49 -235
  22. package/dist/chunk-FNEL2BYV.cjs.map +1 -0
  23. package/dist/{chunk-AFSOUS5X.cjs → chunk-N26CXGXC.cjs} +83 -72
  24. package/dist/chunk-N26CXGXC.cjs.map +1 -0
  25. package/dist/{chunk-X23U6QEJ.js → chunk-NXWKMKZY.js} +581 -217
  26. package/dist/chunk-NXWKMKZY.js.map +1 -0
  27. package/dist/{chunk-WRSBM6QN.cjs → chunk-UCAYNE44.cjs} +587 -214
  28. package/dist/chunk-UCAYNE44.cjs.map +1 -0
  29. package/dist/{chunk-A24C6BNA.js → chunk-UDLMLU6T.js} +3 -3
  30. package/dist/{chunk-A24C6BNA.js.map → chunk-UDLMLU6T.js.map} +1 -1
  31. package/dist/{chunk-S2NFD4QV.js → chunk-UZV27QLC.js} +8 -192
  32. package/dist/chunk-UZV27QLC.js.map +1 -0
  33. package/dist/{chunk-OPA2Y6YZ.js → chunk-W2R7YVFM.js} +5 -13
  34. package/dist/chunk-W2R7YVFM.js.map +1 -0
  35. package/dist/{chunk-TZR36PPP.cjs → chunk-YFPIJUV3.cjs} +5 -5
  36. package/dist/{chunk-TZR36PPP.cjs.map → chunk-YFPIJUV3.cjs.map} +1 -1
  37. package/dist/{chunk-KHY4PYU7.js → chunk-YX466FWL.js} +189 -4
  38. package/dist/chunk-YX466FWL.js.map +1 -0
  39. package/dist/{chunk-YU2KUMGE.js → chunk-ZX2VPMBJ.js} +8 -2
  40. package/dist/chunk-ZX2VPMBJ.js.map +1 -0
  41. package/dist/connect/docx.cjs +6 -6
  42. package/dist/connect/docx.js +4 -4
  43. package/dist/connect/index.cjs +118 -26
  44. package/dist/connect/index.cjs.map +1 -1
  45. package/dist/connect/index.d.ts +2 -0
  46. package/dist/connect/index.js +98 -9
  47. package/dist/connect/index.js.map +1 -1
  48. package/dist/connection/ConnectedNotificationRelevance.d.ts +16 -0
  49. package/dist/connection/ConnectedWorkspaceActivity.d.ts +11 -0
  50. package/dist/docx/NativeDocxEditor.d.ts +4 -2
  51. package/dist/docx/StreamedWordArtifact.d.ts +9 -6
  52. package/dist/docx/index.cjs +15 -15
  53. package/dist/docx/index.js +3 -3
  54. package/dist/facts/index.cjs +6 -6
  55. package/dist/facts/index.js +3 -3
  56. package/dist/files/index.cjs +3 -22
  57. package/dist/files/index.cjs.map +1 -1
  58. package/dist/files/index.js +3 -21
  59. package/dist/files/index.js.map +1 -1
  60. package/dist/files/views/TagFormParts.d.ts +0 -8
  61. package/dist/files/views/index.d.ts +1 -1
  62. package/dist/home/index.cjs +1 -1
  63. package/dist/home/index.js +1 -1
  64. package/dist/index.cjs +563 -431
  65. package/dist/index.cjs.map +1 -1
  66. package/dist/index.d.ts +1 -0
  67. package/dist/index.js +113 -22
  68. package/dist/index.js.map +1 -1
  69. package/dist/settings/index.cjs +3 -3
  70. package/dist/settings/index.js +1 -1
  71. package/dist/shell/FilterInput.d.ts +3 -1
  72. package/dist/shell/index.cjs +5 -5
  73. package/dist/shell/index.js +2 -2
  74. package/dist/studio/index.cjs +1 -1
  75. package/dist/studio/index.js +1 -1
  76. package/dist/tags/TagDetail.d.ts +14 -2
  77. package/dist/tags/TagTable.d.ts +20 -11
  78. package/dist/tags/TagsNav.d.ts +28 -4
  79. package/dist/tags/index.d.ts +1 -1
  80. package/dist/tags/tagTableModel.d.ts +10 -2
  81. package/dist/workflow-canvas/index.cjs +48 -48
  82. package/dist/workflow-canvas/index.js +5 -5
  83. package/package.json +4 -4
  84. package/dist/chunk-2EI7NCUA.cjs.map +0 -1
  85. package/dist/chunk-7YUFMNFW.cjs.map +0 -1
  86. package/dist/chunk-AFSOUS5X.cjs.map +0 -1
  87. package/dist/chunk-AINNADMT.cjs +0 -62
  88. package/dist/chunk-AINNADMT.cjs.map +0 -1
  89. package/dist/chunk-FT5FFXSJ.js +0 -60
  90. package/dist/chunk-FT5FFXSJ.js.map +0 -1
  91. package/dist/chunk-IHYVK6F7.cjs.map +0 -1
  92. package/dist/chunk-KHY4PYU7.js.map +0 -1
  93. package/dist/chunk-OPA2Y6YZ.js.map +0 -1
  94. package/dist/chunk-R26OHONI.js.map +0 -1
  95. package/dist/chunk-RZUMQM7W.cjs.map +0 -1
  96. package/dist/chunk-S2NFD4QV.js.map +0 -1
  97. package/dist/chunk-WRSBM6QN.cjs.map +0 -1
  98. package/dist/chunk-X23U6QEJ.js.map +0 -1
  99. package/dist/chunk-YU2KUMGE.js.map +0 -1
@@ -1,12 +1,292 @@
1
1
  "use client";
2
2
  'use strict';
3
3
 
4
- var react = require('react');
4
+ var chunk5XZU64E2_cjs = require('./chunk-5XZU64E2.cjs');
5
5
  var lucideReact = require('lucide-react');
6
6
  var ui = require('@arbidocs/react/ui');
7
7
  var jsxRuntime = require('react/jsx-runtime');
8
+ var react = require('react');
8
9
  var fflate = require('fflate');
9
10
 
11
+ // src/activity/workspace-activity.ts
12
+ function workspaceActivityTarget(item) {
13
+ switch (item.source) {
14
+ case "thread":
15
+ case "message":
16
+ return item.conversation_ext_id ? {
17
+ kind: "thread",
18
+ conversationId: item.conversation_ext_id,
19
+ ...item.message_ext_id ? { messageId: item.message_ext_id } : {}
20
+ } : null;
21
+ case "document":
22
+ if (!item.document_ext_id) return null;
23
+ return item.kind !== "document_uploaded" && item.version ? { kind: "document", documentId: item.document_ext_id, version: item.version } : { kind: "document", documentId: item.document_ext_id };
24
+ case "workflow":
25
+ return item.workflow_ext_id ? {
26
+ kind: "workflow",
27
+ workflowId: item.workflow_ext_id,
28
+ ...item.conversation_ext_id ? { conversationId: item.conversation_ext_id } : {}
29
+ } : null;
30
+ default:
31
+ return null;
32
+ }
33
+ }
34
+ var quoted = (name, fallback) => name ? `\u201C${name}\u201D` : fallback;
35
+ function workspaceActivityHeadline(item) {
36
+ const thread = quoted(item.conversation_title, "a thread");
37
+ const document = quoted(item.document_name, "a document");
38
+ switch (item.kind) {
39
+ case "message_posted":
40
+ return `Posted in ${thread}`;
41
+ case "document_uploaded":
42
+ return `Uploaded ${document}`;
43
+ case "document_version":
44
+ return item.version ? `Saved version ${item.version} of ${document}` : `Saved a new version of ${document}`;
45
+ case "document_signed":
46
+ return `Signed ${document}`;
47
+ case "workflow_run": {
48
+ const run2 = `Ran ${quoted(item.workflow_name, "a workflow")}`;
49
+ return item.status ? `${run2} (${item.status.replace(/_/g, " ")})` : run2;
50
+ }
51
+ default: {
52
+ const headline = chunk5XZU64E2_cjs.taskActivityHeadline(
53
+ { kind: item.kind, detail: item.detail },
54
+ chunk5XZU64E2_cjs.DEFAULT_TASK_ACTIVITY_LABELS
55
+ );
56
+ return `${headline} in ${thread}`;
57
+ }
58
+ }
59
+ }
60
+ var DEFAULT_WORKSPACE_ACTIVITY_LABELS = {
61
+ empty: "Nothing has happened in this workspace yet.",
62
+ loading: "Loading activity\u2026",
63
+ error: "Could not load the activity.",
64
+ loadMore: "Show older",
65
+ loadingMore: "Loading\u2026",
66
+ retry: "Retry",
67
+ system: "ARBI"
68
+ };
69
+ var ICONS = {
70
+ thread: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Activity, { className: "size-4", "aria-hidden": true }),
71
+ message: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.MessageSquare, { className: "size-4", "aria-hidden": true }),
72
+ document: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.FileText, { className: "size-4", "aria-hidden": true }),
73
+ workflow: /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Workflow, { className: "size-4", "aria-hidden": true })
74
+ };
75
+ var localTime = (iso) => new Date(iso).toLocaleString();
76
+ function WorkspaceActivityList({
77
+ items,
78
+ isLoading,
79
+ isError,
80
+ hasMore,
81
+ isLoadingMore,
82
+ onLoadMore,
83
+ onRetry,
84
+ onOpen,
85
+ nameOf,
86
+ formatTime = localTime,
87
+ labels,
88
+ className,
89
+ testId = "workspace-activity"
90
+ }) {
91
+ const l = { ...DEFAULT_WORKSPACE_ACTIVITY_LABELS, ...labels };
92
+ if (isLoading)
93
+ return /* @__PURE__ */ jsxRuntime.jsx("p", { className: ui.cn("p-3 text-sm text-muted-foreground", className), "data-testid": testId, children: l.loading });
94
+ if (isError && items.length === 0)
95
+ return /* @__PURE__ */ jsxRuntime.jsxs(
96
+ "div",
97
+ {
98
+ className: ui.cn("flex items-center gap-2 p-3 text-sm text-muted-foreground", className),
99
+ "data-testid": testId,
100
+ children: [
101
+ /* @__PURE__ */ jsxRuntime.jsx("span", { role: "alert", children: l.error }),
102
+ onRetry && /* @__PURE__ */ jsxRuntime.jsx(ui.Button, { size: "sm", variant: "ghost", onClick: onRetry, children: l.retry })
103
+ ]
104
+ }
105
+ );
106
+ if (items.length === 0)
107
+ return /* @__PURE__ */ jsxRuntime.jsx("p", { className: ui.cn("p-3 text-sm text-muted-foreground", className), "data-testid": testId, children: l.empty });
108
+ return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cn("flex flex-col", className), "data-testid": testId, children: [
109
+ /* @__PURE__ */ jsxRuntime.jsx("ul", { className: "divide-y divide-border", "data-testid": `${testId}-list`, children: items.map((item) => {
110
+ const target = workspaceActivityTarget(item);
111
+ const actor = item.actor_ext_id ? nameOf?.(item.actor_ext_id) ?? null : l.system;
112
+ const body = /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
113
+ /* @__PURE__ */ jsxRuntime.jsx("span", { className: "mt-0.5 shrink-0 text-muted-foreground", children: ICONS[item.source] }),
114
+ /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "min-w-0 flex-1 text-sm", children: [
115
+ actor && /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "font-medium", children: [
116
+ actor,
117
+ " "
118
+ ] }),
119
+ /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-muted-foreground", children: workspaceActivityHeadline(item) })
120
+ ] }),
121
+ /* @__PURE__ */ jsxRuntime.jsx(
122
+ "time",
123
+ {
124
+ dateTime: item.created_at,
125
+ className: "shrink-0 text-xs tabular-nums text-muted-foreground",
126
+ children: formatTime(item.created_at)
127
+ }
128
+ )
129
+ ] });
130
+ return /* @__PURE__ */ jsxRuntime.jsx(
131
+ "li",
132
+ {
133
+ "data-testid": `${testId}-item-${item.external_id}`,
134
+ "data-kind": item.kind,
135
+ children: target && onOpen ? /* @__PURE__ */ jsxRuntime.jsx(
136
+ "button",
137
+ {
138
+ type: "button",
139
+ className: "flex w-full items-start gap-3 px-3 py-2 text-left hover:bg-accent focus-visible:bg-accent focus-visible:outline-none",
140
+ onClick: () => onOpen(target, item),
141
+ children: body
142
+ }
143
+ ) : /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex items-start gap-3 px-3 py-2", children: body })
144
+ },
145
+ item.external_id
146
+ );
147
+ }) }),
148
+ hasMore && onLoadMore && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex justify-center p-2", children: /* @__PURE__ */ jsxRuntime.jsx(
149
+ ui.Button,
150
+ {
151
+ size: "sm",
152
+ variant: "ghost",
153
+ disabled: isLoadingMore,
154
+ onClick: onLoadMore,
155
+ "data-testid": `${testId}-load-more`,
156
+ children: isLoadingMore ? l.loadingMore : l.loadMore
157
+ }
158
+ ) })
159
+ ] });
160
+ }
161
+ var DEFAULT_WORKSPACE_NOTIFICATION_MENU_LABELS = {
162
+ trigger: "Workspace notifications",
163
+ heading: "Notify me about",
164
+ default: "What involves me",
165
+ defaultHint: "Mentions, assignments and replies to my threads",
166
+ following: "Everything",
167
+ followingHint: "Follow every thread, upload and run",
168
+ muted: "Nothing",
169
+ mutedHint: "Mute the workspace, mentions included",
170
+ activity: "Workspace activity"
171
+ };
172
+ var LEVEL_ICON = { default: lucideReact.Bell, following: lucideReact.BellRing, muted: lucideReact.BellOff };
173
+ function WorkspaceNotificationMenu({
174
+ level,
175
+ onLevelChange,
176
+ disabled,
177
+ onOpenActivity,
178
+ labels,
179
+ className,
180
+ testId = "workspace-notification-menu"
181
+ }) {
182
+ const l = { ...DEFAULT_WORKSPACE_NOTIFICATION_MENU_LABELS, ...labels };
183
+ const Icon = LEVEL_ICON[level];
184
+ const options = [
185
+ { value: "default", title: l.default, hint: l.defaultHint },
186
+ { value: "following", title: l.following, hint: l.followingHint },
187
+ { value: "muted", title: l.muted, hint: l.mutedHint }
188
+ ];
189
+ return /* @__PURE__ */ jsxRuntime.jsxs(ui.DropdownMenu, { children: [
190
+ /* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxRuntime.jsx(
191
+ ui.Button,
192
+ {
193
+ size: "icon",
194
+ variant: "ghost",
195
+ className: ui.cn("size-7 shrink-0 pointer-coarse:size-11", className),
196
+ "aria-label": l.trigger,
197
+ title: l.trigger,
198
+ "data-testid": testId,
199
+ "data-level": level,
200
+ children: /* @__PURE__ */ jsxRuntime.jsx(Icon, { className: ui.cn("size-4", level === "muted" && "text-muted-foreground") })
201
+ }
202
+ ) }),
203
+ /* @__PURE__ */ jsxRuntime.jsxs(ui.DropdownMenuContent, { align: "end", className: "w-72", children: [
204
+ /* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuLabel, { children: l.heading }),
205
+ /* @__PURE__ */ jsxRuntime.jsx(
206
+ ui.DropdownMenuRadioGroup,
207
+ {
208
+ value: level,
209
+ onValueChange: (value) => {
210
+ if (value !== level) onLevelChange(value);
211
+ },
212
+ children: options.map((option) => /* @__PURE__ */ jsxRuntime.jsx(
213
+ ui.DropdownMenuRadioItem,
214
+ {
215
+ value: option.value,
216
+ disabled,
217
+ "data-testid": `${testId}-${option.value}`,
218
+ children: /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "flex flex-col", children: [
219
+ /* @__PURE__ */ jsxRuntime.jsx("span", { children: option.title }),
220
+ /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-xs text-muted-foreground", children: option.hint })
221
+ ] })
222
+ },
223
+ option.value
224
+ ))
225
+ }
226
+ ),
227
+ onOpenActivity && /* @__PURE__ */ jsxRuntime.jsxs(jsxRuntime.Fragment, { children: [
228
+ /* @__PURE__ */ jsxRuntime.jsx(ui.DropdownMenuSeparator, {}),
229
+ /* @__PURE__ */ jsxRuntime.jsxs(ui.DropdownMenuItem, { onSelect: onOpenActivity, "data-testid": `${testId}-activity`, children: [
230
+ /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Activity, { className: "mr-2 size-4", "aria-hidden": true }),
231
+ l.activity
232
+ ] })
233
+ ] })
234
+ ] })
235
+ ] });
236
+ }
237
+ var DEFAULT_THREAD_FOLLOW_LABELS = {
238
+ follow: "Follow thread",
239
+ unfollow: "Unfollow thread"
240
+ };
241
+ function ThreadFollowMenuItem({
242
+ following,
243
+ onFollowingChange,
244
+ disabled,
245
+ labels,
246
+ testId = "thread-follow-item"
247
+ }) {
248
+ const l = { ...DEFAULT_THREAD_FOLLOW_LABELS, ...labels };
249
+ const Icon = following ? lucideReact.BellOff : lucideReact.BellRing;
250
+ return /* @__PURE__ */ jsxRuntime.jsxs(
251
+ ui.DropdownMenuItem,
252
+ {
253
+ disabled,
254
+ onSelect: () => onFollowingChange(!following),
255
+ "data-testid": testId,
256
+ "data-following": following,
257
+ children: [
258
+ /* @__PURE__ */ jsxRuntime.jsx(Icon, { className: "mr-2 size-4", "aria-hidden": true }),
259
+ following ? l.unfollow : l.follow
260
+ ]
261
+ }
262
+ );
263
+ }
264
+ function ThreadFollowButton({
265
+ following,
266
+ onFollowingChange,
267
+ disabled,
268
+ labels,
269
+ testId = "thread-follow-button"
270
+ }) {
271
+ const l = { ...DEFAULT_THREAD_FOLLOW_LABELS, ...labels };
272
+ const label = following ? l.unfollow : l.follow;
273
+ return /* @__PURE__ */ jsxRuntime.jsx(
274
+ ui.Button,
275
+ {
276
+ size: "icon",
277
+ variant: "ghost",
278
+ className: "size-8 shrink-0",
279
+ "aria-label": label,
280
+ "aria-pressed": following,
281
+ title: label,
282
+ disabled,
283
+ onClick: () => onFollowingChange(!following),
284
+ "data-testid": testId,
285
+ children: following ? /* @__PURE__ */ jsxRuntime.jsx(lucideReact.BellRing, { className: "size-4 text-primary" }) : /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Bell, { className: "size-4" })
286
+ }
287
+ );
288
+ }
289
+
10
290
  // src/tags/tagTableModel.ts
11
291
  var NO_LINKS = {
12
292
  docs: [],
@@ -22,10 +302,16 @@ var isGap = (row) => {
22
302
  const l = rowLinks(row);
23
303
  return l.doc_count + l.fact_count + l.thread_count === 0;
24
304
  };
305
+ function linkedTagIds(value) {
306
+ if (typeof value === "string") return value ? [value] : [];
307
+ return Array.isArray(value) ? value.filter((id) => typeof id === "string") : [];
308
+ }
25
309
  function cellText(value, column, nameOf) {
26
310
  if (value === void 0 || value === null || value === "") return "";
27
311
  if (column.type === "checkbox") return value ? "Yes" : "No";
28
312
  if (column.type === "person" && typeof value === "string") return nameOf?.(value) ?? value;
313
+ if (column.type === "tag")
314
+ return linkedTagIds(value).map((id) => nameOf?.(id) ?? id).join(", ");
29
315
  if (Array.isArray(value)) return value.map(String).join(", ");
30
316
  return String(value);
31
317
  }
@@ -96,7 +382,8 @@ var DEFAULT_TAG_COLUMNS_EDITOR_LABELS = {
96
382
  document: "Document",
97
383
  relation: "Relation",
98
384
  lookup: "Lookup",
99
- rollup: "Rollup"
385
+ rollup: "Rollup",
386
+ tag: "Link to tags"
100
387
  }
101
388
  };
102
389
  var TYPES = ["text", "number", "date", "checkbox", "select", "person"];
@@ -110,7 +397,7 @@ var toWrite = (d) => ({
110
397
  ...d.id ? { id: d.id } : {},
111
398
  name: d.name.trim(),
112
399
  type: d.type,
113
- options: d.type === "select" ? d.options.split(",").map((o) => o.trim()).filter(Boolean) : null
400
+ options: d.type === "tag" ? d.options.split(",").map((o) => o.trim()).filter(Boolean) : d.type === "select" ? d.options.split(",").map((o) => o.trim()).filter(Boolean) : null
114
401
  });
115
402
  function TagColumnsEditor({
116
403
  columns,
@@ -273,7 +560,7 @@ function TagColumnsEditor({
273
560
  }
274
561
  var DEFAULT_TAG_TABLE_LABELS = {
275
562
  row: "Item",
276
- evidence: "Evidence",
563
+ evidence: "Tagged items",
277
564
  documents: "{count} documents",
278
565
  facts: "{count} facts",
279
566
  threads: "{count} threads",
@@ -282,9 +569,6 @@ var DEFAULT_TAG_TABLE_LABELS = {
282
569
  thread: "1 thread",
283
570
  untitledThread: "Untitled thread",
284
571
  more: "+{count} more",
285
- gap: "No evidence",
286
- gapsOnly: "Show gaps only",
287
- gapCount: "{count} without evidence",
288
572
  addRow: "Add row",
289
573
  addRowPlaceholder: "Name of the new row",
290
574
  add: "Add",
@@ -298,25 +582,41 @@ var DEFAULT_TAG_TABLE_LABELS = {
298
582
  yes: "Yes",
299
583
  editColumns: "Columns"
300
584
  };
301
- var ROW_LABEL_WIDTH = "w-[18rem] min-w-[12rem] max-w-[18rem]";
585
+ var ROW_LABEL_WIDTH = "w-[11rem]";
586
+ var EVIDENCE_WIDTH = "w-[14rem]";
302
587
  var ROW_LABEL = "line-clamp-3 whitespace-normal break-words";
303
588
  function TagTableCell({
304
589
  row,
305
590
  column,
306
591
  people,
592
+ tags,
593
+ onOpenTag,
307
594
  onChange,
308
595
  l,
309
596
  testId
310
597
  }) {
311
598
  const value = cellValue(row, column);
312
- const nameOf = (id) => people?.find((p) => p.value === id)?.label;
599
+ const nameOf = (id) => (column.type === "tag" ? tags : people)?.find((p) => p.value === id)?.label;
313
600
  const shown = cellText(value, column, nameOf);
314
601
  const [draft, setDraft] = react.useState(shown);
315
602
  react.useEffect(() => setDraft(cellText(value, column)), [value, column]);
316
603
  const set = (next) => void onChange?.(row.external_id, column.id, next);
604
+ if (column.type === "tag")
605
+ return /* @__PURE__ */ jsxRuntime.jsx(
606
+ TagLinkCell,
607
+ {
608
+ row,
609
+ column,
610
+ tags,
611
+ onOpenTag,
612
+ onChange: onChange ? set : void 0,
613
+ l,
614
+ testId
615
+ }
616
+ );
317
617
  if (!onChange)
318
618
  return /* @__PURE__ */ jsxRuntime.jsx("span", { className: "block truncate", title: shown, "data-testid": testId, children: shown || /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-muted-foreground", children: l.choose }) });
319
- const field = "h-8 w-full min-w-24 rounded-md border border-transparent bg-transparent px-1.5 text-sm hover:border-input focus:border-input focus:bg-background focus:outline-none";
619
+ const field = "h-8 w-full min-w-0 rounded-md border border-transparent bg-transparent px-1.5 text-sm hover:border-input focus:border-input focus:bg-background focus:outline-none";
320
620
  switch (column.type) {
321
621
  case "checkbox":
322
622
  return /* @__PURE__ */ jsxRuntime.jsx(
@@ -334,7 +634,7 @@ function TagTableCell({
334
634
  return /* @__PURE__ */ jsxRuntime.jsxs(
335
635
  "select",
336
636
  {
337
- className: ui.cn(field, "min-w-32 pr-6"),
637
+ className: ui.cn(field, "pr-6"),
338
638
  value: typeof value === "string" ? value : "",
339
639
  onChange: (e) => set(e.target.value || null),
340
640
  "aria-label": `${row.name}: ${column.name}`,
@@ -354,7 +654,7 @@ function TagTableCell({
354
654
  return /* @__PURE__ */ jsxRuntime.jsx(
355
655
  "input",
356
656
  {
357
- className: ui.cn(field, "min-w-32 pr-6"),
657
+ className: ui.cn(field, "pr-6"),
358
658
  type: column.type === "number" ? "number" : column.type === "date" ? "date" : "text",
359
659
  value: column.type === "date" ? draft.slice(0, 10) : draft,
360
660
  onChange: (e) => setDraft(e.target.value),
@@ -370,6 +670,95 @@ function TagTableCell({
370
670
  }
371
671
  }
372
672
  }
673
+ function TagLinkCell({
674
+ row,
675
+ column,
676
+ tags,
677
+ onOpenTag,
678
+ onChange,
679
+ l,
680
+ testId
681
+ }) {
682
+ const ids = linkedTagIds(cellValue(row, column));
683
+ const kinds = column.options ?? [];
684
+ const options = (tags ?? []).filter(
685
+ (t) => t.value !== row.external_id && (kinds.length === 0 || kinds.includes(t.kind))
686
+ );
687
+ const label = (id) => tags?.find((t) => t.value === id)?.label ?? id;
688
+ const chips = ids.map(
689
+ (id) => onOpenTag ? /* @__PURE__ */ jsxRuntime.jsx(
690
+ "button",
691
+ {
692
+ type: "button",
693
+ onClick: () => onOpenTag(id),
694
+ className: "inline-flex min-w-0 max-w-full items-center truncate rounded-md border border-border px-1.5 py-0.5 text-xs hover:border-primary/40 hover:text-primary",
695
+ "data-testid": `${testId}-link-${id}`,
696
+ children: label(id)
697
+ },
698
+ id
699
+ ) : /* @__PURE__ */ jsxRuntime.jsx(
700
+ "span",
701
+ {
702
+ className: "inline-flex min-w-0 max-w-full truncate rounded-md border border-border px-1.5 py-0.5 text-xs",
703
+ "data-testid": `${testId}-link-${id}`,
704
+ children: label(id)
705
+ },
706
+ id
707
+ )
708
+ );
709
+ if (!onChange)
710
+ return /* @__PURE__ */ jsxRuntime.jsx("span", { className: "flex min-w-0 flex-wrap gap-1", "data-testid": testId, children: chips.length ? chips : /* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-muted-foreground", children: l.choose }) });
711
+ const current = ids[0];
712
+ return (
713
+ // Wraps: in a narrow column the name breaks between words and the picker moves below it.
714
+ /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "flex min-w-0 flex-wrap items-center gap-x-1 py-1", children: [
715
+ current && (onOpenTag ? /* @__PURE__ */ jsxRuntime.jsxs(
716
+ "button",
717
+ {
718
+ type: "button",
719
+ onClick: () => onOpenTag(current),
720
+ className: "max-w-full rounded px-1 text-left text-sm break-words hover:text-primary hover:underline focus-visible:ring-2 focus-visible:ring-ring",
721
+ "aria-label": `Open ${label(current)}`,
722
+ title: `Open ${label(current)}`,
723
+ "data-testid": `${testId}-open`,
724
+ children: [
725
+ label(current),
726
+ /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ArrowUpRight, { className: "ml-0.5 inline size-3.5 align-[-2px] text-muted-foreground" })
727
+ ]
728
+ }
729
+ ) : /* @__PURE__ */ jsxRuntime.jsx("span", { className: "max-w-full px-1 text-sm break-words", children: label(current) })),
730
+ /* @__PURE__ */ jsxRuntime.jsxs(
731
+ "span",
732
+ {
733
+ className: ui.cn(
734
+ "relative inline-flex h-6 shrink-0 items-center rounded text-muted-foreground hover:bg-muted hover:text-foreground focus-within:ring-2 focus-within:ring-ring",
735
+ current ? "w-6 justify-center" : "min-w-0 flex-1 gap-1 px-1 text-sm"
736
+ ),
737
+ title: current ? `${column.name}: ${label(current)}` : void 0,
738
+ children: [
739
+ !current && /* @__PURE__ */ jsxRuntime.jsx("span", { className: "truncate", children: l.choose }),
740
+ /* @__PURE__ */ jsxRuntime.jsx(lucideReact.ChevronDown, { className: "size-3.5 shrink-0" }),
741
+ /* @__PURE__ */ jsxRuntime.jsxs(
742
+ "select",
743
+ {
744
+ className: "absolute inset-0 h-full w-full cursor-pointer opacity-0",
745
+ value: current ?? "",
746
+ onChange: (e) => onChange(e.target.value ? [e.target.value] : null),
747
+ "aria-label": `${row.name}: ${column.name}`,
748
+ "data-testid": testId,
749
+ children: [
750
+ /* @__PURE__ */ jsxRuntime.jsx("option", { value: "", children: l.choose }),
751
+ options.map((t) => /* @__PURE__ */ jsxRuntime.jsx("option", { value: t.value, children: t.label }, t.value)),
752
+ current && !options.some((t) => t.value === current) && /* @__PURE__ */ jsxRuntime.jsx("option", { value: current, children: label(current) })
753
+ ]
754
+ }
755
+ )
756
+ ]
757
+ }
758
+ )
759
+ ] })
760
+ );
761
+ }
373
762
  var countText = (count2, one, many) => count2 === 1 ? one : count2 ? many.replace("{count}", String(count2)) : null;
374
763
  function Evidence({
375
764
  row,
@@ -380,27 +769,15 @@ function Evidence({
380
769
  onOpenRow,
381
770
  testId
382
771
  }) {
383
- if (isGap(row))
384
- return /* @__PURE__ */ jsxRuntime.jsxs(
385
- "span",
386
- {
387
- className: "inline-flex items-center gap-1 rounded-full bg-amber-500/15 px-2 py-0.5 text-xs font-medium text-amber-700 dark:text-amber-300",
388
- "data-testid": `${testId}-gap`,
389
- children: [
390
- /* @__PURE__ */ jsxRuntime.jsx(lucideReact.AlertTriangle, { className: "size-3" }),
391
- " ",
392
- l.gap
393
- ]
394
- }
395
- );
772
+ if (isGap(row)) return null;
396
773
  const links = rowLinks(row);
397
774
  const docs = links.docs ?? [];
398
775
  const facts = links.facts ?? [];
399
776
  const threads = links.threads ?? [];
400
777
  const more = links.doc_count - docs.length + (links.fact_count - facts.length) + (links.thread_count - threads.length);
401
- const chip = "inline-flex max-w-44 items-center gap-1 truncate rounded-md border border-border px-1.5 py-0.5 text-xs hover:border-primary/40 hover:text-primary disabled:hover:border-border disabled:hover:text-inherit";
402
- return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-wrap items-center gap-1", "data-testid": testId, children: [
403
- /* @__PURE__ */ jsxRuntime.jsx("span", { className: "mr-1 text-xs text-muted-foreground", children: [
778
+ const chip = "inline-flex min-w-0 max-w-full items-center gap-1 truncate rounded-md border border-border px-1.5 py-0.5 text-xs hover:border-primary/40 hover:text-primary disabled:hover:border-border disabled:hover:text-inherit";
779
+ return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex min-w-0 flex-wrap items-center gap-1", "data-testid": testId, children: [
780
+ /* @__PURE__ */ jsxRuntime.jsx("span", { className: "mr-1 w-full text-xs text-muted-foreground", children: [
404
781
  countText(links.doc_count, l.document, l.documents),
405
782
  countText(links.fact_count, l.fact, l.facts),
406
783
  countText(links.thread_count, l.thread, l.threads)
@@ -478,6 +855,8 @@ function TagTable({
478
855
  onExport,
479
856
  onDownload,
480
857
  people,
858
+ tags,
859
+ onOpenTag,
481
860
  actions,
482
861
  labels,
483
862
  className,
@@ -487,12 +866,9 @@ function TagTable({
487
866
  const columns = react.useMemo(() => table?.columns ?? [], [table]);
488
867
  const rows = table?.rows ?? [];
489
868
  const [editingColumns, setEditingColumns] = react.useState(false);
490
- const gaps = rows.filter(isGap).length;
491
- const [gapsOnly, setGapsOnly] = react.useState(false);
492
869
  const [name, setName] = react.useState("");
493
870
  const [adding, setAdding] = react.useState(false);
494
871
  const [exporting, setExporting] = react.useState(false);
495
- const shown = gapsOnly ? rows.filter(isGap) : rows;
496
872
  const add = async () => {
497
873
  const n = name.trim();
498
874
  if (!n || !onAddRow) return;
@@ -505,76 +881,58 @@ function TagTable({
505
881
  }
506
882
  };
507
883
  return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cn("space-y-3", className), "data-testid": testId, children: [
508
- /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex flex-wrap items-center gap-2", children: [
509
- gaps > 0 && /* @__PURE__ */ jsxRuntime.jsxs("label", { className: "flex items-center gap-2 text-sm", children: [
510
- /* @__PURE__ */ jsxRuntime.jsx(
511
- ui.Checkbox,
512
- {
513
- checked: gapsOnly,
514
- onCheckedChange: (v) => setGapsOnly(v === true),
515
- "data-testid": `${testId}-gaps-only`
516
- }
517
- ),
518
- l.gapsOnly,
519
- /* @__PURE__ */ jsxRuntime.jsxs("span", { className: "text-xs text-amber-700 dark:text-amber-300", children: [
520
- "(",
521
- l.gapCount.replace("{count}", String(gaps)),
522
- ")"
523
- ] })
524
- ] }),
525
- /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "ml-auto flex flex-wrap items-center gap-2", children: [
526
- actions,
527
- onChangeColumns && /* @__PURE__ */ jsxRuntime.jsxs(
528
- ui.Button,
529
- {
530
- variant: "outline",
531
- size: "sm",
532
- "aria-pressed": editingColumns,
533
- onClick: () => setEditingColumns((v) => !v),
534
- "data-testid": `${testId}-edit-columns`,
535
- children: [
536
- /* @__PURE__ */ jsxRuntime.jsx(lucideReact.SlidersHorizontal, { className: "size-4" }),
537
- l.editColumns
538
- ]
539
- }
540
- ),
541
- onDownload && /* @__PURE__ */ jsxRuntime.jsxs(
542
- ui.Button,
543
- {
544
- variant: "outline",
545
- size: "sm",
546
- disabled: rows.length === 0,
547
- onClick: () => void onDownload(),
548
- "data-testid": `${testId}-download`,
549
- children: [
550
- /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Download, { className: "size-4" }),
551
- l.download
552
- ]
553
- }
554
- ),
555
- onExport && /* @__PURE__ */ jsxRuntime.jsxs(
556
- ui.Button,
557
- {
558
- variant: "outline",
559
- size: "sm",
560
- disabled: exporting || rows.length === 0,
561
- onClick: async () => {
562
- setExporting(true);
563
- try {
564
- await onExport();
565
- } finally {
566
- setExporting(false);
567
- }
568
- },
569
- "data-testid": `${testId}-export`,
570
- children: [
571
- exporting ? /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Loader2, { className: "size-4 animate-spin" }) : /* @__PURE__ */ jsxRuntime.jsx(lucideReact.FileDown, { className: "size-4" }),
572
- exporting ? l.exporting : l.export
573
- ]
574
- }
575
- )
576
- ] })
577
- ] }),
884
+ /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex flex-wrap items-center gap-2", children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "ml-auto flex flex-wrap items-center gap-2", children: [
885
+ actions,
886
+ onChangeColumns && /* @__PURE__ */ jsxRuntime.jsxs(
887
+ ui.Button,
888
+ {
889
+ variant: "outline",
890
+ size: "sm",
891
+ "aria-pressed": editingColumns,
892
+ onClick: () => setEditingColumns((v) => !v),
893
+ "data-testid": `${testId}-edit-columns`,
894
+ children: [
895
+ /* @__PURE__ */ jsxRuntime.jsx(lucideReact.SlidersHorizontal, { className: "size-4" }),
896
+ l.editColumns
897
+ ]
898
+ }
899
+ ),
900
+ onDownload && /* @__PURE__ */ jsxRuntime.jsxs(
901
+ ui.Button,
902
+ {
903
+ variant: "outline",
904
+ size: "sm",
905
+ disabled: rows.length === 0,
906
+ onClick: () => void onDownload(),
907
+ "data-testid": `${testId}-download`,
908
+ children: [
909
+ /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Download, { className: "size-4" }),
910
+ l.download
911
+ ]
912
+ }
913
+ ),
914
+ onExport && /* @__PURE__ */ jsxRuntime.jsxs(
915
+ ui.Button,
916
+ {
917
+ variant: "outline",
918
+ size: "sm",
919
+ disabled: exporting || rows.length === 0,
920
+ onClick: async () => {
921
+ setExporting(true);
922
+ try {
923
+ await onExport();
924
+ } finally {
925
+ setExporting(false);
926
+ }
927
+ },
928
+ "data-testid": `${testId}-export`,
929
+ children: [
930
+ exporting ? /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Loader2, { className: "size-4 animate-spin" }) : /* @__PURE__ */ jsxRuntime.jsx(lucideReact.FileDown, { className: "size-4" }),
931
+ exporting ? l.exporting : l.export
932
+ ]
933
+ }
934
+ )
935
+ ] }) }),
578
936
  editingColumns && onChangeColumns && /* @__PURE__ */ jsxRuntime.jsx(
579
937
  TagColumnsEditor,
580
938
  {
@@ -588,116 +946,6 @@ function TagTable({
588
946
  testId: `${testId}-columns`
589
947
  }
590
948
  ),
591
- isLoading ? /* @__PURE__ */ jsxRuntime.jsxs("p", { className: "flex items-center gap-2 text-sm text-muted-foreground", children: [
592
- /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Loader2, { className: "size-4 animate-spin" }),
593
- " ",
594
- l.loading
595
- ] }) : /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "overflow-x-auto rounded-lg border border-border", children: [
596
- /* @__PURE__ */ jsxRuntime.jsxs("table", { className: "w-full border-collapse text-sm", "data-testid": `${testId}-table`, children: [
597
- /* @__PURE__ */ jsxRuntime.jsx("thead", { className: "bg-muted/40", children: /* @__PURE__ */ jsxRuntime.jsxs("tr", { children: [
598
- /* @__PURE__ */ jsxRuntime.jsx(
599
- "th",
600
- {
601
- className: ui.cn(
602
- ROW_LABEL_WIDTH,
603
- "sticky left-0 z-10 bg-muted/40 px-3 py-2 text-left font-medium"
604
- ),
605
- children: l.row
606
- }
607
- ),
608
- columns.map((c) => /* @__PURE__ */ jsxRuntime.jsx(
609
- "th",
610
- {
611
- className: "px-3 py-2 text-left font-medium",
612
- "data-testid": `${testId}-column-${c.id}`,
613
- children: c.name
614
- },
615
- c.id
616
- )),
617
- /* @__PURE__ */ jsxRuntime.jsx("th", { className: "px-3 py-2 text-left font-medium", children: l.evidence })
618
- ] }) }),
619
- /* @__PURE__ */ jsxRuntime.jsxs("tbody", { children: [
620
- shown.map((row) => {
621
- const id = row.external_id;
622
- const gap = isGap(row);
623
- return /* @__PURE__ */ jsxRuntime.jsxs(
624
- "tr",
625
- {
626
- className: ui.cn("border-t border-border align-top", gap && "bg-amber-500/5"),
627
- "data-gap": gap || void 0,
628
- "data-testid": `${testId}-row-${id}`,
629
- children: [
630
- /* @__PURE__ */ jsxRuntime.jsx(
631
- "th",
632
- {
633
- scope: "row",
634
- className: ui.cn(
635
- ROW_LABEL_WIDTH,
636
- "sticky left-0 z-10 px-3 py-2 text-left font-medium",
637
- gap ? "bg-amber-50 dark:bg-amber-950" : "bg-background",
638
- gap && "border-l-2 border-l-amber-500"
639
- ),
640
- children: onOpenRow ? /* @__PURE__ */ jsxRuntime.jsx(
641
- "button",
642
- {
643
- type: "button",
644
- className: ui.cn(ROW_LABEL, "text-left hover:text-primary hover:underline"),
645
- title: row.name,
646
- onClick: () => onOpenRow(id),
647
- "data-testid": `${testId}-row-${id}-label`,
648
- children: row.name
649
- }
650
- ) : /* @__PURE__ */ jsxRuntime.jsx(
651
- "span",
652
- {
653
- className: ROW_LABEL,
654
- title: row.name,
655
- "data-testid": `${testId}-row-${id}-label`,
656
- children: row.name
657
- }
658
- )
659
- }
660
- ),
661
- columns.map((c) => /* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-1.5 py-1", children: /* @__PURE__ */ jsxRuntime.jsx(
662
- TagTableCell,
663
- {
664
- row,
665
- column: c,
666
- people,
667
- onChange: onChangeValue,
668
- l,
669
- testId: `${testId}-cell-${id}-${c.id}`
670
- }
671
- ) }, c.id)),
672
- /* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-3 py-2", children: /* @__PURE__ */ jsxRuntime.jsx(
673
- Evidence,
674
- {
675
- row,
676
- l,
677
- onOpenDocument,
678
- onOpenFact,
679
- onOpenThread,
680
- onOpenRow,
681
- testId: `${testId}-evidence-${id}`
682
- }
683
- ) })
684
- ]
685
- },
686
- id
687
- );
688
- }),
689
- shown.length === 0 && /* @__PURE__ */ jsxRuntime.jsx("tr", { children: /* @__PURE__ */ jsxRuntime.jsx(
690
- "td",
691
- {
692
- colSpan: columns.length + 2,
693
- className: "px-3 py-6 text-center text-sm text-muted-foreground",
694
- children: l.empty
695
- }
696
- ) })
697
- ] })
698
- ] }),
699
- columns.length === 0 && rows.length > 0 && /* @__PURE__ */ jsxRuntime.jsx("p", { className: "border-t border-border px-3 py-2 text-xs text-muted-foreground", children: l.noColumns })
700
- ] }),
701
949
  onAddRow && /* @__PURE__ */ jsxRuntime.jsxs(
702
950
  "form",
703
951
  {
@@ -734,7 +982,123 @@ function TagTable({
734
982
  )
735
983
  ]
736
984
  }
737
- )
985
+ ),
986
+ isLoading ? /* @__PURE__ */ jsxRuntime.jsxs("p", { className: "flex items-center gap-2 text-sm text-muted-foreground", children: [
987
+ /* @__PURE__ */ jsxRuntime.jsx(lucideReact.Loader2, { className: "size-4 animate-spin" }),
988
+ " ",
989
+ l.loading
990
+ ] }) : /* @__PURE__ */ jsxRuntime.jsxs("div", { className: "overflow-x-auto rounded-lg border border-border", children: [
991
+ /* @__PURE__ */ jsxRuntime.jsxs(
992
+ "table",
993
+ {
994
+ className: "w-full min-w-[36rem] table-fixed border-collapse text-sm",
995
+ "data-testid": `${testId}-table`,
996
+ children: [
997
+ /* @__PURE__ */ jsxRuntime.jsx("thead", { className: "bg-muted/40", children: /* @__PURE__ */ jsxRuntime.jsxs("tr", { children: [
998
+ /* @__PURE__ */ jsxRuntime.jsx(
999
+ "th",
1000
+ {
1001
+ className: ui.cn(
1002
+ ROW_LABEL_WIDTH,
1003
+ "sticky left-0 z-10 bg-muted/40 px-3 py-2 text-left font-medium"
1004
+ ),
1005
+ children: l.row
1006
+ }
1007
+ ),
1008
+ columns.map((c) => /* @__PURE__ */ jsxRuntime.jsx(
1009
+ "th",
1010
+ {
1011
+ className: "truncate px-3 py-2 text-left font-medium",
1012
+ title: c.name,
1013
+ "data-testid": `${testId}-column-${c.id}`,
1014
+ children: c.name
1015
+ },
1016
+ c.id
1017
+ )),
1018
+ /* @__PURE__ */ jsxRuntime.jsx("th", { className: ui.cn(EVIDENCE_WIDTH, "px-3 py-2 text-left font-medium"), children: l.evidence })
1019
+ ] }) }),
1020
+ /* @__PURE__ */ jsxRuntime.jsxs("tbody", { children: [
1021
+ rows.map((row) => {
1022
+ const id = row.external_id;
1023
+ return /* @__PURE__ */ jsxRuntime.jsxs(
1024
+ "tr",
1025
+ {
1026
+ className: "border-t border-border align-top",
1027
+ "data-testid": `${testId}-row-${id}`,
1028
+ children: [
1029
+ /* @__PURE__ */ jsxRuntime.jsx(
1030
+ "th",
1031
+ {
1032
+ scope: "row",
1033
+ className: ui.cn(
1034
+ ROW_LABEL_WIDTH,
1035
+ "sticky left-0 z-10 bg-background px-3 py-2 text-left font-medium"
1036
+ ),
1037
+ children: onOpenRow ? /* @__PURE__ */ jsxRuntime.jsx(
1038
+ "button",
1039
+ {
1040
+ type: "button",
1041
+ className: ui.cn(ROW_LABEL, "text-left hover:text-primary hover:underline"),
1042
+ title: row.name,
1043
+ onClick: () => onOpenRow(id),
1044
+ "data-testid": `${testId}-row-${id}-label`,
1045
+ children: row.name
1046
+ }
1047
+ ) : /* @__PURE__ */ jsxRuntime.jsx(
1048
+ "span",
1049
+ {
1050
+ className: ROW_LABEL,
1051
+ title: row.name,
1052
+ "data-testid": `${testId}-row-${id}-label`,
1053
+ children: row.name
1054
+ }
1055
+ )
1056
+ }
1057
+ ),
1058
+ columns.map((c) => /* @__PURE__ */ jsxRuntime.jsx("td", { className: "px-1.5 py-1", children: /* @__PURE__ */ jsxRuntime.jsx(
1059
+ TagTableCell,
1060
+ {
1061
+ row,
1062
+ column: c,
1063
+ people,
1064
+ tags,
1065
+ onOpenTag,
1066
+ onChange: onChangeValue,
1067
+ l,
1068
+ testId: `${testId}-cell-${id}-${c.id}`
1069
+ }
1070
+ ) }, c.id)),
1071
+ /* @__PURE__ */ jsxRuntime.jsx("td", { className: "min-w-0 px-3 py-2", children: /* @__PURE__ */ jsxRuntime.jsx(
1072
+ Evidence,
1073
+ {
1074
+ row,
1075
+ l,
1076
+ onOpenDocument,
1077
+ onOpenFact,
1078
+ onOpenThread,
1079
+ onOpenRow,
1080
+ testId: `${testId}-evidence-${id}`
1081
+ }
1082
+ ) })
1083
+ ]
1084
+ },
1085
+ id
1086
+ );
1087
+ }),
1088
+ rows.length === 0 && /* @__PURE__ */ jsxRuntime.jsx("tr", { children: /* @__PURE__ */ jsxRuntime.jsx(
1089
+ "td",
1090
+ {
1091
+ colSpan: columns.length + 2,
1092
+ className: "px-3 py-6 text-center text-sm text-muted-foreground",
1093
+ children: l.empty
1094
+ }
1095
+ ) })
1096
+ ] })
1097
+ ]
1098
+ }
1099
+ ),
1100
+ columns.length === 0 && rows.length > 0 && /* @__PURE__ */ jsxRuntime.jsx("p", { className: "border-t border-border px-3 py-2 text-xs text-muted-foreground", children: l.noColumns })
1101
+ ] })
738
1102
  ] });
739
1103
  }
740
1104
  var DOCX_MIME_TYPE = "application/vnd.openxmlformats-officedocument.wordprocessingml.document";
@@ -880,11 +1244,18 @@ function tagTableDocx(table, options) {
880
1244
  exports.DEFAULT_TAG_COLUMNS_EDITOR_LABELS = DEFAULT_TAG_COLUMNS_EDITOR_LABELS;
881
1245
  exports.DEFAULT_TAG_TABLE_DOCX_LABELS = DEFAULT_TAG_TABLE_DOCX_LABELS;
882
1246
  exports.DEFAULT_TAG_TABLE_LABELS = DEFAULT_TAG_TABLE_LABELS;
1247
+ exports.DEFAULT_THREAD_FOLLOW_LABELS = DEFAULT_THREAD_FOLLOW_LABELS;
1248
+ exports.DEFAULT_WORKSPACE_ACTIVITY_LABELS = DEFAULT_WORKSPACE_ACTIVITY_LABELS;
1249
+ exports.DEFAULT_WORKSPACE_NOTIFICATION_MENU_LABELS = DEFAULT_WORKSPACE_NOTIFICATION_MENU_LABELS;
883
1250
  exports.DOCX_MIME_TYPE = DOCX_MIME_TYPE;
884
1251
  exports.TAG_TABLE_DOCX_LANDSCAPE_AFTER = TAG_TABLE_DOCX_LANDSCAPE_AFTER;
885
1252
  exports.TagColumnsEditor = TagColumnsEditor;
886
1253
  exports.TagTable = TagTable;
887
1254
  exports.TagTableCell = TagTableCell;
1255
+ exports.ThreadFollowButton = ThreadFollowButton;
1256
+ exports.ThreadFollowMenuItem = ThreadFollowMenuItem;
1257
+ exports.WorkspaceActivityList = WorkspaceActivityList;
1258
+ exports.WorkspaceNotificationMenu = WorkspaceNotificationMenu;
888
1259
  exports.cellText = cellText;
889
1260
  exports.cellValue = cellValue;
890
1261
  exports.fieldWrites = fieldWrites;
@@ -894,5 +1265,7 @@ exports.rowLinks = rowLinks;
894
1265
  exports.tagTableDocumentXml = tagTableDocumentXml;
895
1266
  exports.tagTableDocx = tagTableDocx;
896
1267
  exports.tagTableMarkdown = tagTableMarkdown;
897
- //# sourceMappingURL=chunk-WRSBM6QN.cjs.map
898
- //# sourceMappingURL=chunk-WRSBM6QN.cjs.map
1268
+ exports.workspaceActivityHeadline = workspaceActivityHeadline;
1269
+ exports.workspaceActivityTarget = workspaceActivityTarget;
1270
+ //# sourceMappingURL=chunk-UCAYNE44.cjs.map
1271
+ //# sourceMappingURL=chunk-UCAYNE44.cjs.map