@arbidocs/react 0.3.185 → 0.4.1

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 (41) hide show
  1. package/dist/{chunk-YJAYST7S.js → chunk-3CLGHHME.js} +880 -240
  2. package/dist/chunk-3CLGHHME.js.map +1 -0
  3. package/dist/chunk-6ALMBER7.js +176 -0
  4. package/dist/chunk-6ALMBER7.js.map +1 -0
  5. package/dist/chunk-BXP6S34V.cjs +284 -0
  6. package/dist/chunk-BXP6S34V.cjs.map +1 -0
  7. package/dist/chunk-EJ2BMHYK.js +272 -0
  8. package/dist/chunk-EJ2BMHYK.js.map +1 -0
  9. package/dist/{chunk-IZPXHVPJ.cjs → chunk-OU2QLIKS.cjs} +969 -344
  10. package/dist/chunk-OU2QLIKS.cjs.map +1 -0
  11. package/dist/chunk-RZQACYNQ.cjs +218 -0
  12. package/dist/chunk-RZQACYNQ.cjs.map +1 -0
  13. package/dist/{index-4WwLZsQO.d.cts → index-CcbVSNSP.d.cts} +40 -2
  14. package/dist/{index-4WwLZsQO.d.ts → index-CcbVSNSP.d.ts} +40 -2
  15. package/dist/index.cjs +589 -1070
  16. package/dist/index.cjs.map +1 -1
  17. package/dist/index.d.cts +11 -155
  18. package/dist/index.d.ts +11 -155
  19. package/dist/index.js +223 -725
  20. package/dist/index.js.map +1 -1
  21. package/dist/shell/index.cjs +13 -4
  22. package/dist/shell/index.d.cts +1 -1
  23. package/dist/shell/index.d.ts +1 -1
  24. package/dist/shell/index.js +2 -1
  25. package/dist/ui/index.cjs +211 -190
  26. package/dist/ui/index.d.cts +204 -3
  27. package/dist/ui/index.d.ts +204 -3
  28. package/dist/ui/index.js +2 -1
  29. package/dist/viewers/index.cjs +327 -76
  30. package/dist/viewers/index.cjs.map +1 -1
  31. package/dist/viewers/index.d.cts +90 -4
  32. package/dist/viewers/index.d.ts +90 -4
  33. package/dist/viewers/index.js +316 -78
  34. package/dist/viewers/index.js.map +1 -1
  35. package/package.json +4 -3
  36. package/dist/chunk-3MLQUKT4.cjs +0 -97
  37. package/dist/chunk-3MLQUKT4.cjs.map +0 -1
  38. package/dist/chunk-IZPXHVPJ.cjs.map +0 -1
  39. package/dist/chunk-J3XEKOV5.js +0 -87
  40. package/dist/chunk-J3XEKOV5.js.map +0 -1
  41. package/dist/chunk-YJAYST7S.js.map +0 -1
package/dist/index.js CHANGED
@@ -1,20 +1,23 @@
1
- import { useNotify, selectUnread, DEFAULT_NOTIFY_TONE } from './chunk-J3XEKOV5.js';
2
- export { DEFAULT_NOTIFY_TONE, Toaster, notify, seedNotifications, selectUnread, toast, useNotify } from './chunk-J3XEKOV5.js';
3
- import { cn, Popover, PopoverTrigger, PopoverContent, AiMarkdown, Card, Button, Badge, TagEntity, MarkdownRenderer, Input, FILE_TYPE_COLORS, getEntityIcon, DropdownMenu, DropdownMenuTrigger, DropdownMenuContent, DropdownMenuItem, ScrollArea, UserEntity, getEntityColorStyles, AgentBadge, Textarea, Slider, Dialog, DialogContent, DialogHeader, DialogTitle, DialogFooter, Avatar, AvatarImage, AvatarFallback, DropdownMenuLabel, DropdownMenuSeparator, DocumentEntity, Checkbox, useAudioRecorder, MicWaveformIndicator, IconToggle, classifyMediaError, formatElapsed, VidIcon, AudIcon, ImgIcon, EmlIcon, PdfIcon } from './chunk-YJAYST7S.js';
4
- export { AgentBadge, AiMarkdown, ArbiBotHeadIcon, AudIcon, Avatar, AvatarFallback, AvatarImage, BASE_COLORS, Badge, Button, Card, CardContent, CardDescription, CardFooter, CardHeader, CardTitle, Checkbox, Collapsible, CollapsibleContent, CollapsibleTrigger, Command, CommandDialog, CommandEmpty, CommandGroup, CommandInput, CommandItem, CommandList, CommandSeparator, CommandShortcut, Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogOverlay, DialogPortal, DialogTitle, DialogTrigger, DictateProvider, DocumentEntity, DropdownMenu, DropdownMenuCheckboxItem, DropdownMenuContent, DropdownMenuGroup, DropdownMenuItem, DropdownMenuLabel, DropdownMenuPortal, DropdownMenuRadioGroup, DropdownMenuRadioItem, DropdownMenuSeparator, DropdownMenuShortcut, DropdownMenuSub, DropdownMenuSubContent, DropdownMenuSubTrigger, DropdownMenuTrigger, ENTITY_MAPPINGS, EmlIcon, EntityIcon, EntityPill, FILE_TYPE_COLORS, HoverCard, HoverCardContent, HoverCardTrigger, IconToggle, ImgIcon, InlineMicButton, Input, Label, MarkdownRenderer, MarkdownStreamingContext, MicRecordingOverlay, MicWaveformIndicator, NEUTRAL_GRAY, PLACEHOLDER_COLOR, PdfIcon, Popover, PopoverAnchor, PopoverContent, PopoverTrigger, PresenceLabel, Progress, ProjectEntity, RadioGroup, RadioGroupItem, RagDot, ScrollArea, ScrollBar, Select, SelectContent, SelectGroup, SelectItem, SelectLabel, SelectScrollDownButton, SelectScrollUpButton, SelectSeparator, SelectTrigger, SelectValue, Separator, Slider, StatusPill, Switch, TAG_TYPE_ICONS, TAG_TYPE_LABELS, Table, TableBody, TableCaption, TableCell, TableFooter, TableHead, TableHeader, TableRow, Tabs, TabsContent, TabsList, TabsTrigger, TagEntity, Textarea, Toggle, ToggleGroup, ToggleGroupItem, Tooltip, TooltipContent, TooltipProvider, TooltipTrigger, UserEntity, VISIBILITY_ICONS, VidIcon, VisibilityIcon, badgeVariants, buttonVariants, cardVariants, cn, configureEntityRegistry, configureRagLabels, configureStatusRegistry, formatElapsed, getDocIcon, getEntityColor, getEntityColorStyles, getEntityIcon, getEntityLabel, getStatusVariant, getTagTypeIcon, getTagTypeLabel, getWorkspaceColor, markdownBaseComponents, splitMarkdownBlocks, toggleVariants, useAudioRecorder } from './chunk-YJAYST7S.js';
1
+ import { formatRelativeTime } from './chunk-EJ2BMHYK.js';
2
+ export { DEFAULT_NOTIFY_TONE, NotificationBell, Toaster, formatRelativeTime, notify, seedNotifications, selectUnread, toast, useNotify } from './chunk-EJ2BMHYK.js';
3
+ import { MarkMenu, AiMarkdown, Card, Button, Badge, TagEntity, MarkdownRenderer, Input, FILE_TYPE_COLORS, getEntityIcon, UserEntity, getEntityColorStyles, AgentBadge, Textarea, Slider, Dialog, DialogContent, DialogHeader, DialogTitle, DialogFooter, DocumentEntity, DocumentCard, useAudioRecorder, MicWaveformIndicator, IconToggle, classifyMediaError, formatElapsed, PassageCard } from './chunk-3CLGHHME.js';
4
+ export { AgentBadge, AiMarkdown, ArbiBotHeadIcon, AudIcon, Avatar, AvatarFallback, AvatarImage, BASE_COLORS, Badge, Button, Card, CardContent, CardDescription, CardFooter, CardHeader, CardTitle, Checkbox, Collapsible, CollapsibleContent, CollapsibleTrigger, Command, CommandDialog, CommandEmpty, CommandGroup, CommandInput, CommandItem, CommandList, CommandSeparator, CommandShortcut, Dialog, DialogClose, DialogContent, DialogDescription, DialogFooter, DialogHeader, DialogOverlay, DialogPortal, DialogTitle, DialogTrigger, DictateProvider, DocumentCard, DocumentEntity, ENTITY_MAPPINGS, EmlIcon, EntityIcon, EntityPill, FILE_TYPE_COLORS, HoverCard, HoverCardContent, HoverCardTrigger, IconToggle, ImgIcon, InlineMicButton, Input, Label, MarkMenu, MarkdownRenderer, MarkdownStreamingContext, MicRecordingOverlay, MicWaveformIndicator, NEUTRAL_GRAY, PLACEHOLDER_COLOR, PassageCard, PdfIcon, Popover, PopoverAnchor, PopoverContent, PopoverTrigger, PresenceLabel, Progress, ProjectEntity, RadioGroup, RadioGroupItem, RagDot, RelevanceDot, Select, SelectContent, SelectGroup, SelectItem, SelectLabel, SelectScrollDownButton, SelectScrollUpButton, SelectSeparator, SelectTrigger, SelectValue, Separator, Slider, StatusPill, Switch, TAG_TYPE_ICONS, TAG_TYPE_LABELS, Table, TableBody, TableCaption, TableCell, TableFooter, TableHead, TableHeader, TableRow, Tabs, TabsContent, TabsList, TabsTrigger, TagEntity, Textarea, Toggle, ToggleGroup, ToggleGroupItem, Tooltip, TooltipContent, TooltipProvider, TooltipTrigger, UserEntity, UserMenu, VISIBILITY_ICONS, VidIcon, VisibilityIcon, badgeVariants, buttonVariants, cardVariants, configureEntityRegistry, configureRagLabels, configureStatusRegistry, formatElapsed, getDocIcon, getEntityColor, getEntityColorStyles, getEntityIcon, getEntityLabel, getStatusVariant, getTagTypeIcon, getTagTypeLabel, getWorkspaceColor, markdownBaseComponents, splitMarkdownBlocks, toggleVariants, useAudioRecorder } from './chunk-3CLGHHME.js';
5
+ import { cn, ScrollArea, DropdownMenu, DropdownMenuTrigger, DropdownMenuContent, DropdownMenuItem, DropdownMenuSeparator } from './chunk-6ALMBER7.js';
6
+ export { DropdownMenu, DropdownMenuCheckboxItem, DropdownMenuContent, DropdownMenuGroup, DropdownMenuItem, DropdownMenuLabel, DropdownMenuPortal, DropdownMenuRadioGroup, DropdownMenuRadioItem, DropdownMenuSeparator, DropdownMenuShortcut, DropdownMenuSub, DropdownMenuSubContent, DropdownMenuSubTrigger, DropdownMenuTrigger, ScrollArea, ScrollBar, cn } from './chunk-6ALMBER7.js';
5
7
  import { useArbi, ArbiProvider, AudioViewer, ImageViewer, VideoViewer } from './chunk-JKO3NR5L.js';
6
8
  export { ArbiProvider, useArbi } from './chunk-JKO3NR5L.js';
7
- import React, { memo, useState, createContext, useMemo, useCallback, useRef, useContext, useEffect, useId, Fragment as Fragment$1 } from 'react';
9
+ import React, { memo, useState, createContext, useMemo, useCallback, useEffect, useRef, useLayoutEffect, useContext, useId, Fragment as Fragment$1 } from 'react';
8
10
  import { useQuery, useMutation, useQueries, QueryClient, QueryClientProvider, useQueryClient } from '@tanstack/react-query';
9
11
  import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
10
12
  import { connectWithReconnect, resolveCitations, summarizeCitations } from '@arbidocs/sdk/browser';
11
13
  export { Arbi, ArbiError } from '@arbidocs/sdk/browser';
12
- import { Link, Trash2, CheckCheck, Check, Loader2, AlertTriangle, ShieldCheck, Copy, Sparkles, FileText, GitCompareArrows, Download, Image as Image$1, Search, CornerDownLeft, X, ArrowLeft, Send, Tags, Crown, Info, Activity, Gauge, Gift, PartyPopper, UserCheck, MessageCircleMore, FileX2, FileCheck2, Pencil, FolderPlus, SquareArrowOutUpRight, Bell, BellOff, XCircle, CheckCircle2, MessagesSquare, ArrowRight, ChevronDown, LogOut, MoreHorizontal, SquarePen, Mic, Pause, Play, Square, RotateCcw, Camera, Circle, FileX, SkipForward, CheckCircle } from 'lucide-react';
14
+ import { Link, Trash2, CheckCheck, Check, Loader2, AlertTriangle, ShieldCheck, Copy, Sparkles, FileText, GitCompareArrows, Download, Image as Image$1, Search, CornerDownLeft, X, ArrowLeft, Send, Tags, Crown, Info, Activity, Gauge, Gift, PartyPopper, UserCheck, MessageCircleMore, FileX2, FileCheck2, Pencil, FolderPlus, SquareArrowOutUpRight, MessagesSquare, ArrowRight, MoreHorizontal, SquarePen, Mic, Pause, Play, Square, RotateCcw, Camera, Circle } from 'lucide-react';
13
15
  import { isMessageType } from '@arbidocs/client';
14
16
  export { isMessageType } from '@arbidocs/client';
15
17
  import { create } from 'zustand';
16
18
  import { diffWords } from 'diff';
17
19
  import { AnimatePresence, motion } from 'framer-motion';
20
+ import { createPortal } from 'react-dom';
18
21
  import ReactMarkdown from 'react-markdown';
19
22
  import Cropper from 'react-easy-crop';
20
23
  import { AgGridReact } from 'ag-grid-react';
@@ -1440,8 +1443,8 @@ var ChatBubble = memo(function ChatBubble2({
1440
1443
  isSent ? "justify-end" : "justify-start"
1441
1444
  ),
1442
1445
  children: [
1443
- senderName && /* @__PURE__ */ jsx("span", { className: "text-[11px] font-medium leading-none opacity-90", children: senderName }),
1444
- /* @__PURE__ */ jsx("span", { className: "text-[11px] leading-none opacity-70", children: formatTimestamp(timestamp) }),
1446
+ senderName && /* @__PURE__ */ jsx("span", { className: "text-xs font-medium leading-none opacity-90", children: senderName }),
1447
+ /* @__PURE__ */ jsx("span", { className: "text-xs leading-none opacity-70", children: formatTimestamp(timestamp) }),
1445
1448
  isSent && (read ? /* @__PURE__ */ jsx(CheckCheck, { className: "w-3.5 h-3.5 flex-shrink-0 opacity-80" }) : /* @__PURE__ */ jsx(Check, { className: "w-3.5 h-3.5 flex-shrink-0 opacity-60" }))
1446
1449
  ]
1447
1450
  }
@@ -2192,7 +2195,7 @@ function DocSearch({
2192
2195
  "p.",
2193
2196
  r.page
2194
2197
  ] }),
2195
- r.score != null && /* @__PURE__ */ jsxs("span", { className: "ml-auto text-[10px] text-muted-foreground", children: [
2198
+ r.score != null && /* @__PURE__ */ jsxs("span", { className: "ml-auto text-xs text-muted-foreground", children: [
2196
2199
  "score ",
2197
2200
  r.score.toFixed(2)
2198
2201
  ] })
@@ -2385,79 +2388,6 @@ function DocumentReview({
2385
2388
  }
2386
2389
  );
2387
2390
  }
2388
- var TIERS = [
2389
- { min: 0.7, tone: "bg-emerald-500", label: "High relevance" },
2390
- { min: 0.4, tone: "bg-amber-500", label: "Medium relevance" },
2391
- { min: -Infinity, tone: "bg-muted-foreground/40", label: "Low relevance" }
2392
- ];
2393
- function RelevanceDot({ score }) {
2394
- if (score == null) return null;
2395
- const tier = TIERS.find((t) => score >= t.min) ?? TIERS[TIERS.length - 1];
2396
- return /* @__PURE__ */ jsx(
2397
- "span",
2398
- {
2399
- role: "img",
2400
- "aria-label": tier.label,
2401
- title: `${tier.label} (${score.toFixed(2)})`,
2402
- className: cn("size-1.5 shrink-0 rounded-full", tier.tone),
2403
- "data-testid": "passage-relevance"
2404
- }
2405
- );
2406
- }
2407
- function PassageCard({
2408
- header,
2409
- score,
2410
- headerRight,
2411
- active,
2412
- onClick,
2413
- footer,
2414
- className,
2415
- children,
2416
- "data-testid": testId
2417
- }) {
2418
- const body = /* @__PURE__ */ jsxs(Fragment, { children: [
2419
- /* @__PURE__ */ jsxs("div", { className: "mb-1.5 flex items-center gap-2", children: [
2420
- header,
2421
- (score != null || headerRight) && /* @__PURE__ */ jsxs("div", { className: "ml-auto flex shrink-0 items-center gap-2", children: [
2422
- /* @__PURE__ */ jsx(RelevanceDot, { score }),
2423
- headerRight
2424
- ] })
2425
- ] }),
2426
- /* @__PURE__ */ jsx("div", { className: "[&_mark]:rounded-sm [&_mark]:bg-ai-accent/20 [&_mark]:px-0.5 [&_mark]:font-medium [&_mark]:text-foreground", children })
2427
- ] });
2428
- return /* @__PURE__ */ jsxs(
2429
- "div",
2430
- {
2431
- className: cn(
2432
- "group rounded-lg border border-border bg-card p-3 text-left transition-colors",
2433
- onClick && "hover:border-ai-accent/40 focus-within:ring-2 focus-within:ring-ai-accent/40",
2434
- active && "border-ai-accent/60 ring-1 ring-ai-accent/30",
2435
- className
2436
- ),
2437
- children: [
2438
- onClick ? /* @__PURE__ */ jsx(
2439
- "div",
2440
- {
2441
- role: "button",
2442
- tabIndex: 0,
2443
- onClick,
2444
- onKeyDown: (e) => {
2445
- if (e.key === "Enter" || e.key === " ") {
2446
- e.preventDefault();
2447
- onClick(e);
2448
- }
2449
- },
2450
- "aria-current": active || void 0,
2451
- "data-testid": testId,
2452
- className: "cursor-pointer focus:outline-none",
2453
- children: body
2454
- }
2455
- ) : /* @__PURE__ */ jsx("div", { "aria-current": active || void 0, "data-testid": testId, children: body }),
2456
- footer
2457
- ]
2458
- }
2459
- );
2460
- }
2461
2391
  function queryTerms(query) {
2462
2392
  const terms = /* @__PURE__ */ new Set();
2463
2393
  for (const phrase of query.match(/"([^"]+)"/g) ?? []) {
@@ -2749,7 +2679,8 @@ var CitationRendererComponent = ({
2749
2679
  onActivateChunk,
2750
2680
  useCitationState,
2751
2681
  onCloseCitation,
2752
- onDismissCitation
2682
+ onDismissCitation,
2683
+ notify: notify2
2753
2684
  }) => {
2754
2685
  const chunkMap = useMemo(() => {
2755
2686
  const map = /* @__PURE__ */ new Map();
@@ -2801,6 +2732,7 @@ var CitationRendererComponent = ({
2801
2732
  useCitationState,
2802
2733
  onCloseCitation,
2803
2734
  onDismissCitation,
2735
+ notify: notify2,
2804
2736
  children
2805
2737
  },
2806
2738
  citationKey
@@ -2818,7 +2750,8 @@ var CitationRendererComponent = ({
2818
2750
  ExternalLink,
2819
2751
  useCitationState,
2820
2752
  onCloseCitation,
2821
- onDismissCitation
2753
+ onDismissCitation,
2754
+ notify2
2822
2755
  ]);
2823
2756
  return /* @__PURE__ */ jsx("div", { className: cn("citation-container", className), "data-testid": "citation-renderer", children: renderMarkdown({ components: markdownComponents, isStreaming, children: content }) });
2824
2757
  };
@@ -2832,28 +2765,51 @@ var CitationPopover = ({
2832
2765
  useCitationState,
2833
2766
  onCloseCitation,
2834
2767
  onDismissCitation,
2768
+ notify: notify2,
2835
2769
  children
2836
2770
  }) => {
2837
2771
  const { activeCitationKey, viewingPassageId, isOnConversationPage } = useCitationState();
2838
2772
  const isActive = activeCitationKey === `${messageId}-${citationNum}`;
2839
2773
  const open = isActive && isOnConversationPage;
2840
- const chatContainer = useMemo(
2841
- () => document.querySelector('main[data-testid^="conversation-"]'),
2842
- []
2843
- );
2774
+ useEffect(() => {
2775
+ if (isActive && !isOnConversationPage) onDismissCitation();
2776
+ }, [isActive, isOnConversationPage, onDismissCitation]);
2844
2777
  const triggerRef = useRef(null);
2845
- const [alignOffset, setAlignOffset] = useState(0);
2778
+ const dialogRef = useRef(null);
2779
+ const restoreFocusRef = useRef(false);
2780
+ const dismiss = useCallback(() => {
2781
+ restoreFocusRef.current = true;
2782
+ onDismissCitation();
2783
+ }, [onDismissCitation]);
2784
+ useEffect(() => {
2785
+ if (!open) return;
2786
+ dialogRef.current?.focus({ preventScroll: true });
2787
+ return () => {
2788
+ if (!restoreFocusRef.current) return;
2789
+ restoreFocusRef.current = false;
2790
+ triggerRef.current?.focus({ preventScroll: true });
2791
+ };
2792
+ }, [open]);
2793
+ useEffect(() => {
2794
+ if (!open) return;
2795
+ const onKeyDown = (e) => {
2796
+ if (e.key === "Escape") dismiss();
2797
+ };
2798
+ document.addEventListener("keydown", onKeyDown);
2799
+ return () => document.removeEventListener("keydown", onKeyDown);
2800
+ }, [open, dismiss]);
2801
+ const [dock, setDock] = useState({ left: 0, top: 0, width: 0 });
2802
+ useLayoutEffect(() => {
2803
+ if (!open) return;
2804
+ const edge = (document.querySelector('[data-testid="message-input-container"]') ?? document.querySelector('main[data-testid^="conversation-"]') ?? document.body).getBoundingClientRect();
2805
+ setDock({ left: edge.left, top: edge.top, width: edge.width });
2806
+ }, [open]);
2846
2807
  const handleOpen = useCallback(() => {
2847
- if (triggerRef.current && chatContainer) {
2848
- const triggerLeft = triggerRef.current.getBoundingClientRect().left;
2849
- const chatLeft = chatContainer.getBoundingClientRect().left;
2850
- setAlignOffset(-(triggerLeft - chatLeft));
2851
- }
2852
2808
  onOpen();
2853
2809
  if (chunks.length > 0) {
2854
2810
  onChunkClick(chunks[0]);
2855
2811
  }
2856
- }, [onOpen, onChunkClick, chunks, chatContainer]);
2812
+ }, [onOpen, onChunkClick, chunks]);
2857
2813
  const byDoc = useMemo(() => {
2858
2814
  const map = /* @__PURE__ */ new Map();
2859
2815
  chunks.forEach((chunk) => {
@@ -2864,151 +2820,185 @@ var CitationPopover = ({
2864
2820
  });
2865
2821
  return Array.from(map.entries()).map(([docId, val]) => ({ docId, ...val }));
2866
2822
  }, [chunks]);
2867
- return /* @__PURE__ */ jsxs(
2868
- Popover,
2823
+ const first = chunks[0];
2824
+ const firstText = first ? first.content.replace(/\n+/g, " ").trim() : "";
2825
+ const firstTitle = first ? first.metadata.doc_title ?? first.metadata.doc_ext_id ?? "" : "";
2826
+ const firstPage = first?.metadata.page_number;
2827
+ const copyCitation = useCallback(async () => {
2828
+ const source = [firstTitle, firstPage != null ? `p.${firstPage}` : null].filter(Boolean).join(", ");
2829
+ try {
2830
+ await navigator.clipboard.writeText(source ? `\u201C${firstText}\u201D (${source})` : firstText);
2831
+ notify2?.("Citation copied", "success");
2832
+ } catch {
2833
+ notify2?.("Could not copy the citation", "error");
2834
+ }
2835
+ }, [firstText, firstTitle, firstPage, notify2]);
2836
+ const items = isStreaming || chunks.length === 0 ? [] : [
2869
2837
  {
2870
- open,
2871
- onOpenChange: (next) => {
2872
- if (isStreaming) return;
2873
- if (next) {
2874
- handleOpen();
2875
- } else {
2876
- onCloseCitation();
2877
- }
2878
- },
2879
- children: [
2880
- /* @__PURE__ */ jsx(PopoverTrigger, { asChild: true, children: /* @__PURE__ */ jsx(
2881
- CitationLink,
2882
- {
2883
- ref: triggerRef,
2884
- citationNum,
2885
- isActive,
2886
- isStreaming,
2887
- children
2888
- }
2889
- ) }),
2890
- /* @__PURE__ */ jsxs(
2891
- PopoverContent,
2892
- {
2893
- className: "z-[42] w-[min(var(--radix-popover-content-available-width),48rem)] min-w-0 p-0 max-h-[75vh] overflow-y-auto border-2 border-border shadow-xl",
2894
- align: "start",
2895
- alignOffset,
2896
- side: "bottom",
2897
- sideOffset: 6,
2898
- avoidCollisions: true,
2899
- container: chatContainer,
2900
- collisionBoundary: chatContainer,
2901
- collisionPadding: { top: 8, bottom: 8, left: 8, right: 8 },
2902
- "data-testid": `citation-popover-${citationNum}`,
2903
- onInteractOutside: (e) => e.preventDefault(),
2904
- onEscapeKeyDown: (e) => e.preventDefault(),
2905
- onCloseAutoFocus: (e) => e.preventDefault(),
2906
- children: [
2907
- /* @__PURE__ */ jsxs("div", { className: "px-3 py-2 border-b border-border sticky top-0 bg-popover z-10 flex items-center justify-between gap-2", children: [
2908
- /* @__PURE__ */ jsxs("span", { className: "text-xs font-semibold text-muted-foreground tracking-wide", children: [
2909
- "Citation ",
2910
- citationNum,
2911
- " (",
2912
- chunks.length,
2913
- " passage",
2914
- chunks.length !== 1 ? "s" : "",
2915
- ")"
2838
+ id: "open",
2839
+ label: "Open in viewer",
2840
+ primary: true,
2841
+ onSelect: handleOpen,
2842
+ testId: `citation-open-${citationNum}`
2843
+ },
2844
+ {
2845
+ id: "copy",
2846
+ label: "Copy citation",
2847
+ onSelect: () => void copyCitation(),
2848
+ testId: `citation-copy-${citationNum}`
2849
+ }
2850
+ ];
2851
+ const preview = first ? /* @__PURE__ */ jsxs("div", { className: "max-w-xs", "data-testid": `citation-preview-${citationNum}`, children: [
2852
+ /* @__PURE__ */ jsx("span", { className: "block text-xs font-medium text-foreground", children: firstTitle }),
2853
+ firstPage != null && /* @__PURE__ */ jsxs("span", { className: "block text-xs text-muted-foreground", children: [
2854
+ "Page ",
2855
+ firstPage
2856
+ ] }),
2857
+ /* @__PURE__ */ jsx("span", { className: "mt-1 line-clamp-4 block text-xs italic text-muted-foreground", children: /* @__PURE__ */ jsx(ReactMarkdown, { components: INLINE_MD_COMPONENTS, children: firstText }) }),
2858
+ chunks.length > 1 && /* @__PURE__ */ jsxs("span", { className: "mt-1 block text-xs text-muted-foreground", children: [
2859
+ "+",
2860
+ chunks.length - 1,
2861
+ " more passage",
2862
+ chunks.length > 2 ? "s" : ""
2863
+ ] })
2864
+ ] }) : void 0;
2865
+ return /* @__PURE__ */ jsxs(Fragment, { children: [
2866
+ /* @__PURE__ */ jsx(
2867
+ CitationLink,
2868
+ {
2869
+ triggerRef,
2870
+ citationNum,
2871
+ isActive,
2872
+ isStreaming,
2873
+ items,
2874
+ preview,
2875
+ children
2876
+ }
2877
+ ),
2878
+ open && createPortal(
2879
+ /* @__PURE__ */ jsx(
2880
+ "div",
2881
+ {
2882
+ className: "pointer-events-none fixed z-[42] flex justify-center px-2",
2883
+ style: {
2884
+ left: dock.left,
2885
+ width: dock.width,
2886
+ bottom: window.innerHeight - dock.top + 8
2887
+ },
2888
+ children: /* @__PURE__ */ jsxs(
2889
+ "div",
2890
+ {
2891
+ ref: dialogRef,
2892
+ role: "dialog",
2893
+ tabIndex: -1,
2894
+ "aria-label": `Citation ${citationNum}`,
2895
+ className: "pointer-events-auto z-[42] max-h-[45vh] outline-none w-[min(100%,48rem)] min-w-0 overflow-y-auto rounded-md border border-border bg-popover p-0 text-popover-foreground shadow-xl",
2896
+ "data-testid": `citation-popover-${citationNum}`,
2897
+ children: [
2898
+ /* @__PURE__ */ jsxs("div", { className: "px-3 py-2 pointer-coarse:py-0 border-b border-border sticky top-0 bg-popover z-10 flex items-center justify-between gap-2", children: [
2899
+ /* @__PURE__ */ jsxs("span", { className: "text-xs font-semibold text-muted-foreground tracking-wide", children: [
2900
+ "Citation ",
2901
+ citationNum,
2902
+ " (",
2903
+ chunks.length,
2904
+ " passage",
2905
+ chunks.length !== 1 ? "s" : "",
2906
+ ")"
2907
+ ] }),
2908
+ /* @__PURE__ */ jsx(
2909
+ "button",
2910
+ {
2911
+ onClick: dismiss,
2912
+ className: "-m-1.5 flex shrink-0 items-center justify-center rounded p-1.5 text-muted-foreground transition-colors hover:bg-muted hover:text-foreground pointer-coarse:m-0 pointer-coarse:size-11 pointer-coarse:p-0",
2913
+ "aria-label": "Close",
2914
+ "data-testid": `citation-popover-close-${citationNum}`,
2915
+ children: /* @__PURE__ */ jsx(
2916
+ "svg",
2917
+ {
2918
+ width: "14",
2919
+ height: "14",
2920
+ viewBox: "0 0 12 12",
2921
+ fill: "none",
2922
+ xmlns: "http://www.w3.org/2000/svg",
2923
+ children: /* @__PURE__ */ jsx(
2924
+ "path",
2925
+ {
2926
+ d: "M1 1L11 11M11 1L1 11",
2927
+ stroke: "currentColor",
2928
+ strokeWidth: "1.5",
2929
+ strokeLinecap: "round"
2930
+ }
2931
+ )
2932
+ }
2933
+ )
2934
+ }
2935
+ )
2916
2936
  ] }),
2917
- /* @__PURE__ */ jsx(
2918
- "button",
2919
- {
2920
- onClick: onDismissCitation,
2921
- className: "-m-1.5 flex shrink-0 items-center justify-center rounded p-1.5 text-muted-foreground transition-colors hover:bg-muted hover:text-foreground",
2922
- "aria-label": "Close",
2923
- "data-testid": `citation-popover-close-${citationNum}`,
2924
- children: /* @__PURE__ */ jsx(
2925
- "svg",
2926
- {
2927
- width: "14",
2928
- height: "14",
2929
- viewBox: "0 0 12 12",
2930
- fill: "none",
2931
- xmlns: "http://www.w3.org/2000/svg",
2932
- children: /* @__PURE__ */ jsx(
2933
- "path",
2934
- {
2935
- d: "M1 1L11 11M11 1L1 11",
2936
- stroke: "currentColor",
2937
- strokeWidth: "1.5",
2938
- strokeLinecap: "round"
2939
- }
2940
- )
2941
- }
2942
- )
2943
- }
2944
- )
2945
- ] }),
2946
- (() => {
2947
- let idx = 0;
2948
- return byDoc.map(({ docId, title, chunks: docChunks }) => /* @__PURE__ */ jsxs("div", { className: "px-3 py-2 border-b border-border last:border-0", children: [
2949
- /* @__PURE__ */ jsx("p", { className: "text-xs font-medium text-primary mb-1 truncate", title, children: title }),
2937
+ byDoc.map(({ docId, title, chunks: docChunks }) => /* @__PURE__ */ jsxs("div", { className: "px-3 py-2 border-b border-border last:border-0", children: [
2938
+ /* @__PURE__ */ jsx("p", { className: "text-sm font-semibold text-foreground mb-1 truncate", title, children: title }),
2950
2939
  docChunks.map((chunk) => {
2951
- idx++;
2952
2940
  const isSelected = viewingPassageId === chunk.metadata.chunk_ext_id;
2953
- return /* @__PURE__ */ jsxs(
2941
+ return /* @__PURE__ */ jsx(
2954
2942
  "button",
2955
2943
  {
2956
2944
  "data-testid": `citation-chunk-${chunk.metadata.chunk_ext_id}`,
2957
2945
  onClick: () => onChunkClick(chunk),
2958
2946
  className: cn(
2959
- "w-full text-left text-xs rounded px-2 py-1.5 transition-colors flex items-start gap-2 mb-1 last:mb-0",
2960
- isSelected ? "bg-yellow-100 dark:bg-yellow-900/30 text-yellow-900 dark:text-yellow-100" : "text-muted-foreground hover:text-primary hover:bg-muted"
2947
+ "w-full text-left text-sm rounded-md px-2 py-1.5 pointer-coarse:min-h-11 pointer-coarse:py-3 transition-colors flex items-start gap-2 mb-1 last:mb-0",
2948
+ isSelected ? "bg-ai-soft text-foreground ring-1 ring-ai-accent/40" : "text-muted-foreground hover:text-primary hover:bg-muted"
2961
2949
  ),
2962
- children: [
2963
- /* @__PURE__ */ jsxs("span", { className: "shrink-0 text-[10px] font-mono bg-muted text-muted-foreground rounded px-1 py-0.5 mt-0.5", children: [
2964
- idx,
2965
- "."
2966
- ] }),
2967
- chunk.metadata.page_number != null && /* @__PURE__ */ jsxs("span", { className: "shrink-0 text-[10px] font-mono bg-muted text-muted-foreground rounded-full px-1.5 py-0.5 mt-0.5", children: [
2968
- "p.",
2950
+ children: /* @__PURE__ */ jsxs("span", { className: "min-w-0 flex-1", children: [
2951
+ chunk.metadata.page_number != null && /* @__PURE__ */ jsxs("span", { className: "block text-xs text-muted-foreground", children: [
2952
+ "Page ",
2969
2953
  chunk.metadata.page_number
2970
2954
  ] }),
2971
- /* @__PURE__ */ jsxs("span", { className: "min-w-0 flex-1 overflow-hidden whitespace-nowrap text-ellipsis block", children: [
2972
- /* @__PURE__ */ jsx("span", { children: "(\u201C" }),
2973
- " ",
2974
- /* @__PURE__ */ jsx(ReactMarkdown, { components: INLINE_MD_COMPONENTS, children: chunk.content.replace(/\n+/g, " ").trim() }),
2975
- " ",
2976
- /* @__PURE__ */ jsx("span", { children: "\u201D)" })
2977
- ] })
2978
- ]
2955
+ /* @__PURE__ */ jsx("span", { className: "line-clamp-3 italic", children: /* @__PURE__ */ jsx(ReactMarkdown, { components: INLINE_MD_COMPONENTS, children: chunk.content.replace(/\n+/g, " ").trim() }) })
2956
+ ] })
2979
2957
  },
2980
2958
  chunk.metadata.chunk_ext_id
2981
2959
  );
2982
2960
  })
2983
- ] }, docId));
2984
- })()
2985
- ]
2986
- }
2987
- )
2988
- ]
2989
- }
2990
- );
2991
- };
2992
- var CitationLink = React.forwardRef(
2993
- ({ citationNum, isActive, isStreaming, children, ...props }, ref) => /* @__PURE__ */ jsxs(
2994
- "span",
2995
- {
2996
- ref,
2997
- className: cn(
2998
- "cited-text transition-colors px-0.5 rounded inline-block",
2999
- isStreaming ? "cursor-default" : "cursor-pointer",
3000
- isActive ? "bg-yellow-100 dark:bg-yellow-900/30 hover:bg-yellow-200 dark:hover:bg-yellow-900/40" : "hover:bg-yellow-50 dark:hover:bg-yellow-900/20"
2961
+ ] }, docId))
2962
+ ]
2963
+ }
2964
+ )
2965
+ }
3001
2966
  ),
3002
- "data-testid": `citation-link-${citationNum}`,
3003
- ...props,
3004
- children: [
3005
- children,
3006
- /* @__PURE__ */ jsx("sup", { className: "relative -top-2", children: /* @__PURE__ */ jsx("span", { className: "inline-flex items-center justify-center min-w-4 h-4 px-1 text-[10px] border border-muted bg-muted text-primary rounded font-normal cursor-pointer antialiased tabular-nums font-heading", children: citationNum }) })
3007
- ]
3008
- }
3009
- )
2967
+ document.body
2968
+ )
2969
+ ] });
2970
+ };
2971
+ var CitationLink = ({
2972
+ citationNum,
2973
+ isActive,
2974
+ isStreaming,
2975
+ items,
2976
+ preview,
2977
+ triggerRef,
2978
+ children
2979
+ }) => /* @__PURE__ */ jsxs(
2980
+ MarkMenu,
2981
+ {
2982
+ triggerRef,
2983
+ items,
2984
+ preview: isStreaming ? void 0 : preview,
2985
+ menuLabel: `Citation ${citationNum}`,
2986
+ testId: `citation-link-${citationNum}`,
2987
+ tabIndex: isStreaming ? -1 : 0,
2988
+ "data-mark-kind": "citation",
2989
+ className: cn(
2990
+ "cited-text relative rounded-sm px-0.5 transition-colors",
2991
+ // 44px touch hit area without changing the text layout.
2992
+ "pointer-coarse:after:absolute pointer-coarse:after:content-[''] pointer-coarse:after:-inset-x-3 pointer-coarse:after:-inset-y-4",
2993
+ isStreaming ? "cursor-default" : "cursor-pointer",
2994
+ isActive ? "bg-ai-soft text-foreground" : "bg-ai-soft/30 hover:bg-ai-soft/70"
2995
+ ),
2996
+ children: [
2997
+ children,
2998
+ /* @__PURE__ */ jsx("sup", { className: "ml-px align-super text-[0.7em] font-semibold leading-none tabular-nums text-ai-ink", children: citationNum })
2999
+ ]
3000
+ }
3010
3001
  );
3011
- CitationLink.displayName = "CitationLink";
3012
3002
  var CitationRenderer = React.memo(CitationRendererComponent);
3013
3003
  var DocIcon = ({ size = 16, className = "" }) => {
3014
3004
  return /* @__PURE__ */ jsxs(
@@ -3796,178 +3786,6 @@ function userDisplayName(user) {
3796
3786
  function isAgentUser(user) {
3797
3787
  return user.external_id.startsWith("agt-");
3798
3788
  }
3799
- var RELATIVE = new Intl.RelativeTimeFormat(void 0, { numeric: "auto" });
3800
- var DIVISIONS = [
3801
- { amount: 60, unit: "seconds" },
3802
- { amount: 60, unit: "minutes" },
3803
- { amount: 24, unit: "hours" },
3804
- { amount: 7, unit: "days" },
3805
- { amount: 4.34524, unit: "weeks" },
3806
- { amount: 12, unit: "months" },
3807
- { amount: Number.POSITIVE_INFINITY, unit: "years" }
3808
- ];
3809
- function formatRelativeTime(iso) {
3810
- const then = Date.parse(iso);
3811
- if (Number.isNaN(then)) return "";
3812
- let duration = (then - Date.now()) / 1e3;
3813
- if (Math.abs(duration) < 45) return "just now";
3814
- for (const division of DIVISIONS) {
3815
- if (Math.abs(duration) < division.amount) {
3816
- return RELATIVE.format(Math.round(duration), division.unit);
3817
- }
3818
- duration /= division.amount;
3819
- }
3820
- return "";
3821
- }
3822
- var GLYPH = {
3823
- success: CheckCircle2,
3824
- error: XCircle,
3825
- warning: AlertTriangle,
3826
- info: Info
3827
- };
3828
- function NotificationBell({
3829
- onNavigate,
3830
- onMarkRead,
3831
- onMarkAllRead,
3832
- muted = false,
3833
- onToggleMute,
3834
- toneClassNames,
3835
- emptyText = "You're all caught up.",
3836
- onViewAll,
3837
- viewAllLabel = "View all",
3838
- testId = "notifications"
3839
- }) {
3840
- const notifications = useNotify((s) => s.notifications);
3841
- const unread = useNotify(selectUnread);
3842
- const markAllRead = useNotify((s) => s.markAllRead);
3843
- const markRead = useNotify((s) => s.markRead);
3844
- const tone = (v) => toneClassNames?.[v] ?? DEFAULT_NOTIFY_TONE[v];
3845
- const visible = notifications.filter((n) => !n.ambient);
3846
- return /* @__PURE__ */ jsxs(DropdownMenu, { children: [
3847
- /* @__PURE__ */ jsx(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxs(
3848
- "button",
3849
- {
3850
- className: "relative flex size-9 items-center justify-center rounded-md text-muted-foreground transition-colors hover:bg-accent hover:text-foreground",
3851
- "data-testid": testId,
3852
- "aria-label": `Notifications${unread ? ` (${unread} unread)` : ""}`,
3853
- children: [
3854
- /* @__PURE__ */ jsx(Bell, { className: "size-5" }),
3855
- unread > 0 && /* @__PURE__ */ jsx(
3856
- "span",
3857
- {
3858
- className: "absolute -right-0.5 -top-0.5 flex min-w-4 items-center justify-center rounded-full bg-secondary px-1 text-[10px] font-semibold leading-4 text-secondary-foreground",
3859
- "data-testid": `${testId}-badge`,
3860
- children: unread > 9 ? "9+" : unread
3861
- }
3862
- )
3863
- ]
3864
- }
3865
- ) }),
3866
- /* @__PURE__ */ jsxs(
3867
- DropdownMenuContent,
3868
- {
3869
- align: "end",
3870
- sideOffset: 8,
3871
- collisionPadding: 12,
3872
- className: "w-[360px] rounded-lg border-border/60 p-0 shadow-lg",
3873
- "data-testid": `${testId}-panel`,
3874
- children: [
3875
- /* @__PURE__ */ jsxs("div", { className: "flex items-center justify-between gap-3 border-b border-border px-3.5 py-2.5", children: [
3876
- /* @__PURE__ */ jsx("p", { className: "text-sm font-semibold text-foreground", children: "Notifications" }),
3877
- /* @__PURE__ */ jsxs("div", { className: "flex items-center gap-3", children: [
3878
- unread > 0 && /* @__PURE__ */ jsxs(
3879
- "button",
3880
- {
3881
- onClick: () => {
3882
- markAllRead();
3883
- onMarkAllRead?.();
3884
- },
3885
- className: "flex items-center gap-1 text-xs font-medium text-primary transition-colors hover:opacity-80",
3886
- "data-testid": `${testId}-mark-all`,
3887
- children: [
3888
- /* @__PURE__ */ jsx(CheckCheck, { className: "size-3.5" }),
3889
- " Mark all read"
3890
- ]
3891
- }
3892
- ),
3893
- onToggleMute && /* @__PURE__ */ jsx(
3894
- "button",
3895
- {
3896
- onClick: onToggleMute,
3897
- "aria-pressed": muted,
3898
- title: muted ? "Unmute notifications" : "Mute notifications",
3899
- "aria-label": muted ? "Unmute notifications" : "Mute notifications",
3900
- className: cn(
3901
- "flex size-6 items-center justify-center rounded-md transition-colors hover:bg-accent",
3902
- muted ? "text-foreground" : "text-muted-foreground hover:text-foreground"
3903
- ),
3904
- "data-testid": `${testId}-mute`,
3905
- children: /* @__PURE__ */ jsx(BellOff, { className: "size-3.5" })
3906
- }
3907
- ),
3908
- /* @__PURE__ */ jsx(
3909
- DropdownMenuItem,
3910
- {
3911
- className: "flex size-6 items-center justify-center rounded-md p-0 text-muted-foreground transition-colors hover:bg-accent hover:text-foreground focus:bg-accent",
3912
- "aria-label": "Close notifications",
3913
- "data-testid": `${testId}-close`,
3914
- children: /* @__PURE__ */ jsx(X, { className: "size-3.5" })
3915
- }
3916
- )
3917
- ] })
3918
- ] }),
3919
- muted && /* @__PURE__ */ jsx(
3920
- "p",
3921
- {
3922
- className: "border-b border-border/60 bg-amber-500/10 px-3.5 py-1.5 text-[11px] text-muted-foreground",
3923
- "data-testid": `${testId}-muted-note`,
3924
- children: "Toasts are muted \u2014 everything still lands here."
3925
- }
3926
- ),
3927
- visible.length === 0 ? /* @__PURE__ */ jsx("div", { className: "px-3.5 py-10 text-center text-sm text-muted-foreground", children: emptyText }) : /* @__PURE__ */ jsx(ScrollArea, { className: "max-h-[380px]", children: /* @__PURE__ */ jsx("ul", { "data-testid": `${testId}-list`, children: visible.map((n) => {
3928
- const Glyph = GLYPH[n.variant];
3929
- return /* @__PURE__ */ jsx("li", { children: /* @__PURE__ */ jsxs(
3930
- "button",
3931
- {
3932
- onClick: () => {
3933
- markRead(n.id);
3934
- if (!n.read) onMarkRead?.(n.id);
3935
- if (n.onSelect) n.onSelect();
3936
- else if (n.href) onNavigate?.(n.href);
3937
- },
3938
- className: cn(
3939
- "flex w-full items-start gap-3 border-b border-border/60 px-3.5 py-3 text-left transition-colors hover:bg-accent",
3940
- !n.read && "bg-accent/40"
3941
- ),
3942
- "data-testid": `${testId}-item`,
3943
- children: [
3944
- /* @__PURE__ */ jsx(Glyph, { className: cn("mt-0.5 size-4 shrink-0", tone(n.variant)) }),
3945
- /* @__PURE__ */ jsxs("div", { className: "min-w-0 flex-1", children: [
3946
- /* @__PURE__ */ jsx("p", { className: "text-sm font-medium leading-snug text-foreground", children: n.title }),
3947
- n.description && /* @__PURE__ */ jsx("p", { className: "mt-0.5 line-clamp-2 text-xs leading-relaxed text-muted-foreground", children: n.description }),
3948
- /* @__PURE__ */ jsx("p", { className: "mt-1 text-[11px] text-muted-foreground/80", children: formatRelativeTime(new Date(n.ts).toISOString()) })
3949
- ] }),
3950
- !n.read && /* @__PURE__ */ jsx("span", { className: "mt-1.5 size-2 shrink-0 rounded-full bg-primary" })
3951
- ]
3952
- }
3953
- ) }, n.id);
3954
- }) }) }),
3955
- onViewAll && // A real menu item, not a bare button: selecting it must CLOSE the
3956
- // dropdown on its way to the full surface.
3957
- /* @__PURE__ */ jsx(
3958
- DropdownMenuItem,
3959
- {
3960
- onClick: onViewAll,
3961
- className: "justify-center rounded-none border-t border-border px-3.5 py-2.5 text-xs font-medium text-primary focus:text-primary",
3962
- "data-testid": `${testId}-view-all`,
3963
- children: viewAllLabel
3964
- }
3965
- )
3966
- ]
3967
- }
3968
- )
3969
- ] });
3970
- }
3971
3789
  var DM_QUERY_KEY = ["arbi", "directMessages"];
3972
3790
  var CONTACTS_QUERY_KEY = ["arbi", "contacts"];
3973
3791
  function mergeContacts(threads, contacts) {
@@ -4166,7 +3984,7 @@ function ConversationList({
4166
3984
  Badge,
4167
3985
  {
4168
3986
  variant: "outline",
4169
- className: "shrink-0 rounded-full px-2 py-0 text-[10px] font-medium text-muted-foreground",
3987
+ className: "shrink-0 rounded-full px-2 py-0 text-xs font-medium text-muted-foreground",
4170
3988
  children: c.statusLabel
4171
3989
  }
4172
3990
  ) : unreadCount > 0 ? (
@@ -4178,7 +3996,7 @@ function ConversationList({
4178
3996
  {
4179
3997
  variant: "accent",
4180
3998
  className: cn(
4181
- "min-w-[1.125rem] justify-center rounded-full px-1 py-0 text-[10px] font-medium leading-[1.125rem] shadow-none",
3999
+ "min-w-[1.125rem] justify-center rounded-full px-1 py-0 text-xs font-medium leading-[1.125rem] shadow-none",
4182
4000
  classNames?.unreadBadge
4183
4001
  ),
4184
4002
  children: unreadCount
@@ -4210,7 +4028,7 @@ function ConversationList({
4210
4028
  children: c.subtitle ?? preview
4211
4029
  }
4212
4030
  ),
4213
- /* @__PURE__ */ jsx("span", { className: "shrink-0 text-[11px] text-muted-foreground", children: lastMessage ? formatRelativeTime(lastMessage.createdAt) : "" })
4031
+ /* @__PURE__ */ jsx("span", { className: "shrink-0 text-xs text-muted-foreground", children: lastMessage ? formatRelativeTime(lastMessage.createdAt) : "" })
4214
4032
  ] })
4215
4033
  ] })
4216
4034
  ] });
@@ -4225,7 +4043,7 @@ function ConversationList({
4225
4043
  newSection && /* @__PURE__ */ jsx(
4226
4044
  "p",
4227
4045
  {
4228
- className: "bg-muted/40 px-4 py-1.5 text-[11px] font-medium uppercase tracking-wide text-muted-foreground",
4046
+ className: "bg-muted/40 px-4 py-1.5 text-xs font-medium uppercase tracking-wide text-muted-foreground",
4229
4047
  "data-testid": "arbi-dm-section",
4230
4048
  children: c.sectionLabel
4231
4049
  }
@@ -4550,7 +4368,7 @@ function ImageCropper({
4550
4368
  }
4551
4369
  ) }),
4552
4370
  aspectOptions && aspectOptions.length > 1 ? /* @__PURE__ */ jsxs("div", { className: "flex flex-wrap items-center gap-1", "data-testid": "image-cropper-aspects", children: [
4553
- /* @__PURE__ */ jsx("span", { className: "mr-1 text-[11px] font-semibold uppercase tracking-wider text-muted-foreground", children: "Ratio" }),
4371
+ /* @__PURE__ */ jsx("span", { className: "mr-1 text-xs font-semibold uppercase tracking-wider text-muted-foreground", children: "Ratio" }),
4554
4372
  aspectOptions.map((opt) => {
4555
4373
  const on = opt.value === activeAspect;
4556
4374
  return /* @__PURE__ */ jsx(
@@ -4570,7 +4388,7 @@ function ImageCropper({
4570
4388
  })
4571
4389
  ] }) : null,
4572
4390
  /* @__PURE__ */ jsxs("div", { className: "space-y-1.5", children: [
4573
- /* @__PURE__ */ jsx("label", { className: "text-[11px] font-semibold uppercase tracking-wider text-muted-foreground", children: "Zoom" }),
4391
+ /* @__PURE__ */ jsx("label", { className: "text-xs font-semibold uppercase tracking-wider text-muted-foreground", children: "Zoom" }),
4574
4392
  /* @__PURE__ */ jsx(
4575
4393
  Slider,
4576
4394
  {
@@ -4761,7 +4579,7 @@ function CommandPalette({
4761
4579
  "data-testid": `${testId}-input`
4762
4580
  }
4763
4581
  ),
4764
- /* @__PURE__ */ jsx("kbd", { className: "hidden rounded border border-border px-1.5 py-0.5 text-[10px] text-muted-foreground sm:inline", children: "\u2318K" })
4582
+ /* @__PURE__ */ jsx("kbd", { className: "hidden rounded border border-border px-1.5 py-0.5 text-xs text-muted-foreground sm:inline", children: "\u2318K" })
4765
4583
  ] }),
4766
4584
  /* @__PURE__ */ jsxs("div", { className: "max-h-[60vh] overflow-y-auto p-2", children: [
4767
4585
  query.trim() && !showingAnswer && /* @__PURE__ */ jsxs(
@@ -4820,7 +4638,7 @@ function CommandPalette({
4820
4638
  ) })
4821
4639
  ] }),
4822
4640
  !showingAnswer && /* @__PURE__ */ jsxs(Fragment, { children: [
4823
- /* @__PURE__ */ jsx("p", { className: "px-3 pb-1 pt-2 text-[10px] font-semibold uppercase tracking-wide text-muted-foreground", children: query.trim() ? "Jump to" : "Go to" }),
4641
+ /* @__PURE__ */ jsx("p", { className: "px-3 pb-1 pt-2 text-xs font-semibold uppercase tracking-wide text-muted-foreground", children: query.trim() ? "Jump to" : "Go to" }),
4824
4642
  navMatches.length === 0 && /* @__PURE__ */ jsx("p", { className: "px-3 py-2 text-sm text-muted-foreground", children: "No pages match \u2014 press Enter to ask AI." }),
4825
4643
  navMatches.map((item) => /* @__PURE__ */ jsxs(
4826
4644
  "button",
@@ -4841,7 +4659,7 @@ function CommandPalette({
4841
4659
  item.id
4842
4660
  )),
4843
4661
  searchable && query.trim().length >= 2 && /* @__PURE__ */ jsxs(Fragment, { children: [
4844
- /* @__PURE__ */ jsx("p", { className: "px-3 pb-1 pt-3 text-[10px] font-semibold uppercase tracking-wide text-muted-foreground", children: "Documents" }),
4662
+ /* @__PURE__ */ jsx("p", { className: "px-3 pb-1 pt-3 text-xs font-semibold uppercase tracking-wide text-muted-foreground", children: "Documents" }),
4845
4663
  searchStatus === "done" && docHits.length === 0 && /* @__PURE__ */ jsx("p", { className: "px-3 py-2 text-sm text-muted-foreground", children: "No passages matched." }),
4846
4664
  docHits.map((hit, i) => /* @__PURE__ */ jsxs(
4847
4665
  "button",
@@ -4905,114 +4723,6 @@ function CommandPaletteProvider({
4905
4723
  /* @__PURE__ */ jsx(CommandPalette, { open: isOpen, onOpenChange: setIsOpen, ...paletteProps })
4906
4724
  ] });
4907
4725
  }
4908
- function nameInitials(name) {
4909
- const parts = name.trim().split(/\s+/).filter(Boolean);
4910
- if (!parts.length) return "?";
4911
- return parts.slice(0, 2).map((p) => p[0]?.toUpperCase() ?? "").join("");
4912
- }
4913
- var STATUS_DOT = {
4914
- online: "bg-emerald-500",
4915
- busy: "bg-amber-500",
4916
- offline: "bg-destructive"
4917
- };
4918
- function UserMenu({
4919
- user,
4920
- status,
4921
- items = [],
4922
- onLogout,
4923
- logoutLabel = "Sign out",
4924
- align = "end",
4925
- classNames,
4926
- testId = "user-menu",
4927
- logoutTestId
4928
- }) {
4929
- return /* @__PURE__ */ jsxs(DropdownMenu, { children: [
4930
- /* @__PURE__ */ jsx(DropdownMenuTrigger, { asChild: true, children: /* @__PURE__ */ jsxs(
4931
- "button",
4932
- {
4933
- className: cn(
4934
- "flex items-center gap-2 rounded-md px-1.5 py-1 transition-colors hover:bg-accent",
4935
- classNames?.trigger
4936
- ),
4937
- "data-testid": testId,
4938
- children: [
4939
- /* @__PURE__ */ jsxs("span", { className: "relative", children: [
4940
- /* @__PURE__ */ jsxs(Avatar, { className: "size-8", children: [
4941
- user.picture ? /* @__PURE__ */ jsx(AvatarImage, { src: user.picture, alt: user.name }) : null,
4942
- /* @__PURE__ */ jsx(
4943
- AvatarFallback,
4944
- {
4945
- className: cn("bg-primary text-primary-foreground", classNames?.fallback),
4946
- children: nameInitials(user.name)
4947
- }
4948
- )
4949
- ] }),
4950
- status && /* @__PURE__ */ jsx(
4951
- "span",
4952
- {
4953
- className: cn(
4954
- "absolute -bottom-0.5 -right-0.5 size-2.5 rounded-full border-2 border-background",
4955
- STATUS_DOT[status.tone]
4956
- ),
4957
- title: status.detail ? `${status.label} \xB7 ${status.detail}` : status.label,
4958
- "data-testid": status.testId ? `${status.testId}-dot` : void 0
4959
- }
4960
- )
4961
- ] }),
4962
- /* @__PURE__ */ jsx(ChevronDown, { className: "size-4 text-muted-foreground" })
4963
- ]
4964
- }
4965
- ) }),
4966
- /* @__PURE__ */ jsxs(
4967
- DropdownMenuContent,
4968
- {
4969
- align,
4970
- sideOffset: 8,
4971
- collisionPadding: 12,
4972
- className: "w-56 rounded-lg border-border/60 shadow-lg",
4973
- "data-testid": "user-menu-panel",
4974
- children: [
4975
- /* @__PURE__ */ jsxs(DropdownMenuLabel, { className: "relative pr-8", children: [
4976
- /* @__PURE__ */ jsx(
4977
- DropdownMenuItem,
4978
- {
4979
- className: "absolute right-1 top-1 flex size-6 items-center justify-center rounded-md p-0 text-muted-foreground transition-colors hover:bg-accent hover:text-foreground focus:bg-accent",
4980
- "aria-label": "Close account menu",
4981
- "data-testid": "user-menu-close",
4982
- children: /* @__PURE__ */ jsx(X, { className: "size-3.5" })
4983
- }
4984
- ),
4985
- /* @__PURE__ */ jsx("div", { className: "font-medium text-foreground", children: user.name }),
4986
- user.email && /* @__PURE__ */ jsx("div", { className: "text-xs font-normal text-muted-foreground", children: user.email }),
4987
- status && /* @__PURE__ */ jsxs(
4988
- "div",
4989
- {
4990
- className: "mt-1 text-xs font-normal text-muted-foreground",
4991
- "data-testid": status.testId,
4992
- children: [
4993
- /* @__PURE__ */ jsxs("span", { className: "flex items-center gap-1.5", children: [
4994
- /* @__PURE__ */ jsx("span", { className: cn("size-2 shrink-0 rounded-full", STATUS_DOT[status.tone]) }),
4995
- status.label
4996
- ] }),
4997
- status.detail && /* @__PURE__ */ jsx("div", { className: "mt-0.5 truncate pl-3.5 text-[10px] leading-tight text-muted-foreground/70", children: status.detail })
4998
- ]
4999
- }
5000
- )
5001
- ] }),
5002
- /* @__PURE__ */ jsx(DropdownMenuSeparator, {}),
5003
- items.map((item) => /* @__PURE__ */ jsxs(DropdownMenuItem, { onClick: item.onSelect, "data-testid": item.testId, children: [
5004
- item.icon && /* @__PURE__ */ jsx(item.icon, { className: "size-4" }),
5005
- item.label
5006
- ] }, item.label)),
5007
- /* @__PURE__ */ jsxs(DropdownMenuItem, { onClick: onLogout, "data-testid": logoutTestId ?? `${testId}-logout`, children: [
5008
- /* @__PURE__ */ jsx(LogOut, { className: "size-4" }),
5009
- logoutLabel
5010
- ] })
5011
- ]
5012
- }
5013
- )
5014
- ] });
5015
- }
5016
4726
  var useArbiUiStore = create((set) => ({
5017
4727
  selectedDocIds: [],
5018
4728
  setSelectedDocIds: (ids) => set({ selectedDocIds: ids }),
@@ -5223,218 +4933,6 @@ function DocumentTable({
5223
4933
  }
5224
4934
  ) });
5225
4935
  }
5226
- var ACTIVE_STATUSES = /* @__PURE__ */ new Set([
5227
- "queued",
5228
- "processing",
5229
- "parsing",
5230
- "encrypting",
5231
- "indexing",
5232
- "analysing"
5233
- ]);
5234
- var TERMINAL_STATUSES2 = /* @__PURE__ */ new Set(["completed", "failed", "skipped", "empty", "low-content"]);
5235
- var STATUS_LABEL = {
5236
- queued: "Queued",
5237
- processing: "Processing",
5238
- parsing: "Parsing",
5239
- encrypting: "Encrypting",
5240
- indexing: "Indexing",
5241
- analysing: "Analysing"
5242
- };
5243
- var IMAGE_EXTENSIONS = /* @__PURE__ */ new Set(["jpg", "jpeg", "png", "gif", "bmp", "tiff", "tif", "webp"]);
5244
- var VIDEO_EXTENSIONS = /* @__PURE__ */ new Set(["mp4", "mpeg", "mpg", "webm", "mov", "avi", "mkv"]);
5245
- var AUDIO_EXTENSIONS = /* @__PURE__ */ new Set(["mp3", "wav", "m4a", "aac", "ogg", "flac"]);
5246
- var EMAIL_EXTENSIONS = /* @__PURE__ */ new Set(["eml", "msg"]);
5247
- function fileIcon(fileName, size) {
5248
- const ext = fileName?.split(".").pop()?.toLowerCase();
5249
- if (ext && VIDEO_EXTENSIONS.has(ext)) return /* @__PURE__ */ jsx(VidIcon, { size });
5250
- if (ext && AUDIO_EXTENSIONS.has(ext)) return /* @__PURE__ */ jsx(AudIcon, { size });
5251
- if (ext && IMAGE_EXTENSIONS.has(ext)) return /* @__PURE__ */ jsx(ImgIcon, { size });
5252
- if (ext && EMAIL_EXTENSIONS.has(ext)) return /* @__PURE__ */ jsx(EmlIcon, { size });
5253
- return /* @__PURE__ */ jsx(PdfIcon, { size });
5254
- }
5255
- function RenameField({
5256
- seed,
5257
- onCommit,
5258
- onCancel,
5259
- testId
5260
- }) {
5261
- const done = React.useRef(false);
5262
- const commit = (value) => {
5263
- if (done.current) return;
5264
- done.current = true;
5265
- const trimmed = value.trim();
5266
- if (trimmed && trimmed !== seed) onCommit(trimmed);
5267
- else onCancel();
5268
- };
5269
- return /* @__PURE__ */ jsx(
5270
- "input",
5271
- {
5272
- autoFocus: true,
5273
- defaultValue: seed,
5274
- "data-testid": testId,
5275
- onFocus: (e) => e.currentTarget.select(),
5276
- onClick: (e) => e.stopPropagation(),
5277
- onKeyDown: (e) => {
5278
- if (e.key === "Enter") {
5279
- e.preventDefault();
5280
- commit(e.currentTarget.value);
5281
- } else if (e.key === "Escape") {
5282
- e.preventDefault();
5283
- done.current = true;
5284
- onCancel();
5285
- }
5286
- },
5287
- onBlur: (e) => commit(e.currentTarget.value),
5288
- className: "w-full rounded border border-primary bg-background px-1 py-0.5 text-xs text-foreground outline-none"
5289
- }
5290
- );
5291
- }
5292
- function StatusMarker({ status, testId }) {
5293
- let icon = null;
5294
- let title = "";
5295
- switch (status) {
5296
- case "completed":
5297
- icon = /* @__PURE__ */ jsx(CheckCircle, { className: "size-4 text-success", strokeWidth: 2.75 });
5298
- title = "Ready";
5299
- break;
5300
- case "failed":
5301
- icon = /* @__PURE__ */ jsx(XCircle, { className: "size-4 text-destructive", strokeWidth: 2.75 });
5302
- title = "Failed";
5303
- break;
5304
- case "skipped":
5305
- icon = /* @__PURE__ */ jsx(SkipForward, { className: "size-4 text-muted-foreground", strokeWidth: 2.75 });
5306
- title = "Skipped";
5307
- break;
5308
- case "empty":
5309
- icon = /* @__PURE__ */ jsx(FileX, { className: "size-4 text-warning", strokeWidth: 2.75 });
5310
- title = "Empty \u2014 no extractable content";
5311
- break;
5312
- case "low-content":
5313
- icon = /* @__PURE__ */ jsx(AlertTriangle, { className: "size-4 text-warning", strokeWidth: 2.75 });
5314
- title = "Low content \u2014 minimal extractable content";
5315
- break;
5316
- default:
5317
- return null;
5318
- }
5319
- return /* @__PURE__ */ jsx(
5320
- "span",
5321
- {
5322
- title,
5323
- "data-testid": testId,
5324
- className: "flex size-6 items-center justify-center rounded-full bg-background shadow-sm",
5325
- children: icon
5326
- }
5327
- );
5328
- }
5329
- function DocumentCard({
5330
- doc,
5331
- thumbnailUrl,
5332
- status,
5333
- selected = false,
5334
- onToggleSelect,
5335
- viewing = false,
5336
- onOpen,
5337
- actions,
5338
- renaming = false,
5339
- onCommitRename,
5340
- onCancelRename,
5341
- tooltipContent,
5342
- marker,
5343
- testId = "document-card",
5344
- className
5345
- }) {
5346
- const normalised = (status ?? "").toLowerCase();
5347
- const isProcessing = ACTIVE_STATUSES.has(normalised);
5348
- const showStatusMarker = !isProcessing && TERMINAL_STATUSES2.has(normalised);
5349
- const [thumbFailed, setThumbFailed] = React.useState(false);
5350
- const [thumbLandscape, setThumbLandscape] = React.useState(false);
5351
- const showThumbnail = !!thumbnailUrl && !thumbFailed && !isProcessing;
5352
- return /* @__PURE__ */ jsxs(
5353
- "div",
5354
- {
5355
- "data-testid": testId,
5356
- className: cn(
5357
- // Square corners and a portrait-page aspect (height = 1.3 × width), so a
5358
- // cover-page thumbnail reads edge-to-edge.
5359
- "group relative aspect-[10/13] select-none overflow-hidden border bg-muted/20 transition",
5360
- selected ? "border-primary bg-primary/10" : "border-border shadow-sm hover:border-border/80 hover:bg-muted/50",
5361
- className
5362
- ),
5363
- children: [
5364
- showThumbnail ? /* @__PURE__ */ jsx(
5365
- "img",
5366
- {
5367
- src: thumbnailUrl,
5368
- alt: "",
5369
- loading: "lazy",
5370
- draggable: false,
5371
- onError: () => setThumbFailed(true),
5372
- onLoad: (e) => setThumbLandscape(e.currentTarget.naturalWidth > e.currentTarget.naturalHeight),
5373
- className: cn(
5374
- "absolute inset-0 size-full bg-white",
5375
- thumbLandscape ? "object-contain" : "object-cover object-top"
5376
- )
5377
- }
5378
- ) : /* @__PURE__ */ jsx("div", { className: "absolute inset-0 flex items-center justify-center text-muted-foreground", children: fileIcon(doc.file_name, 44) }),
5379
- isProcessing && /* @__PURE__ */ jsxs(
5380
- "div",
5381
- {
5382
- "data-testid": `${testId}-processing`,
5383
- className: "absolute inset-0 z-10 flex flex-col items-center justify-center gap-1.5 bg-background/80 px-3",
5384
- children: [
5385
- /* @__PURE__ */ jsx("div", { className: "h-1.5 w-full overflow-hidden rounded-sm bg-muted", children: /* @__PURE__ */ jsx("div", { className: "h-full w-1/3 animate-pulse rounded-sm bg-primary" }) }),
5386
- /* @__PURE__ */ jsx("span", { className: "text-xs font-medium text-primary", children: STATUS_LABEL[normalised] ?? normalised })
5387
- ]
5388
- }
5389
- ),
5390
- onToggleSelect && /* @__PURE__ */ jsx(
5391
- Checkbox,
5392
- {
5393
- checked: selected,
5394
- onCheckedChange: () => onToggleSelect(),
5395
- onClick: (e) => e.stopPropagation(),
5396
- "aria-label": selected ? "Deselect" : "Select",
5397
- "data-testid": `${testId}-select`,
5398
- className: cn(
5399
- "absolute left-1.5 top-1.5 z-20 size-6 rounded-none border-muted-foreground/60 bg-background shadow-sm transition",
5400
- selected ? "opacity-100" : "opacity-40 group-hover:opacity-100"
5401
- )
5402
- }
5403
- ),
5404
- actions && /* @__PURE__ */ jsx("div", { className: "absolute right-1.5 top-1.5 z-20", children: actions }),
5405
- /* @__PURE__ */ jsxs("div", { className: "absolute inset-x-1.5 bottom-1.5 z-20 flex flex-col gap-1", children: [
5406
- (marker || showStatusMarker) && /* @__PURE__ */ jsxs("div", { className: "flex items-center", children: [
5407
- marker,
5408
- showStatusMarker && /* @__PURE__ */ jsx("div", { className: "ml-auto flex", children: /* @__PURE__ */ jsx(StatusMarker, { status: normalised, testId: `${testId}-status` }) })
5409
- ] }),
5410
- renaming ? /* @__PURE__ */ jsx(
5411
- RenameField,
5412
- {
5413
- seed: doc.doc_metadata?.title || doc.file_name || "",
5414
- onCommit: (name) => onCommitRename?.(name),
5415
- onCancel: () => onCancelRename?.(),
5416
- testId: `${testId}-rename-input`
5417
- }
5418
- ) : /* @__PURE__ */ jsx(
5419
- DocumentEntity,
5420
- {
5421
- doc,
5422
- fullWidth: true,
5423
- viewing,
5424
- tooltipContent,
5425
- labelClassName: "font-semibold",
5426
- className: "w-full min-w-0 max-w-full bg-background/90 backdrop-blur-sm",
5427
- onClick: (e) => {
5428
- e.stopPropagation();
5429
- onOpen?.();
5430
- }
5431
- }
5432
- )
5433
- ] })
5434
- ]
5435
- }
5436
- );
5437
- }
5438
4936
  function DocumentCardMenu({
5439
4937
  docId,
5440
4938
  fileName,
@@ -5531,7 +5029,7 @@ function TileTooltip({ title, labels }) {
5531
5029
  labels.length > 0 && /* @__PURE__ */ jsx("div", { className: "flex flex-wrap gap-1 border-t border-border/60 pt-1.5", children: labels.map((label) => /* @__PURE__ */ jsx(
5532
5030
  "span",
5533
5031
  {
5534
- className: "rounded bg-muted px-1.5 py-0.5 text-[10px] font-medium text-foreground/80",
5032
+ className: "rounded bg-muted px-1.5 py-0.5 text-xs font-medium text-foreground/80",
5535
5033
  children: label
5536
5034
  },
5537
5035
  label
@@ -6214,6 +5712,6 @@ function hasVideoTrack(blob) {
6214
5712
  });
6215
5713
  }
6216
5714
 
6217
- export { ActivityFeed, AiActionCard, AiAnswer, AppleIcon, ArbiBotIcon, ArbiChat, ArbiChatPanel, ArbiIcon, ArbiWebSocketProvider, ArtifactCanvas, ChatBubble, CitationRenderer, ClaudeIcon, CommandPalette, CommandPaletteProvider, ConversationList, DEFAULT_ASPECT_OPTIONS, DateSeparator, DirectMessages, DmAvatar, DmComposer, DocIcon, DocQaPanel, DocSearch, DocumentCard, DocumentCardMenu, DocumentGallery, DocumentReview, DocumentTable, DraftTitleControls, FileIcon, FireworksIcon, GeminiIcon, GitHubIcon, GoogleIcon, HtmlIcon, ImageCropModal, ImageCropper, LinkedInIcon, MessageArtifactCard, MessageBubble2 as MessageBubble, MessageThread, NotificationBell, OpenAIIcon, PassageCard, PhotoCapture, ProviderIcon, RUN_WINDOW_MS, RelevanceDot, SemanticSearch, TxtIcon, TypingIndicator, UserMenu, VideoCapture, VoiceNoteRecorder, XlsIcon, annotateThread, arbiQueryKeys, captureFrameAsBlob, cropImage, dayKey, describeActivity, formatRelativeTime, getNotificationTypeMeta, getWorkspaceActionText, getWorkspaceSentPhrase, hasVideoTrack, isWorkspaceNotificationType, parseActivityContent, redlineStats, textToArtifact, toRedlineMarkdown, useActivity, useAgents, useAiTask, useArbiConnected, useArbiDocumentSync, useArbiUiStore, useArbiWebSocket, useArbiWsContext, useArbiWsMessage, useArbiWsStatus, useArbiWsStore, useArbiWsTask, useArbiWsTasks, useAssistantQuery, useCameraStream, useCommandPalette, useConfigs, useConversations, useDeleteAgents, useDirectMessages, useDocuments, useFacts, useHealth, useParsedDocument, useProjectInvoices, useProjectUsage, useProjects, useProjectsUsage, useSemanticSearch, useSessions, useTags, useTasks, useThumbnails, useUserUsageToday, useVideoRecorder, useWorkspaceDocs, useWorkspaces, userDisplayName, userInitials };
5715
+ export { ActivityFeed, AiActionCard, AiAnswer, AppleIcon, ArbiBotIcon, ArbiChat, ArbiChatPanel, ArbiIcon, ArbiWebSocketProvider, ArtifactCanvas, ChatBubble, CitationRenderer, ClaudeIcon, CommandPalette, CommandPaletteProvider, ConversationList, DEFAULT_ASPECT_OPTIONS, DateSeparator, DirectMessages, DmAvatar, DmComposer, DocIcon, DocQaPanel, DocSearch, DocumentCardMenu, DocumentGallery, DocumentReview, DocumentTable, DraftTitleControls, FileIcon, FireworksIcon, GeminiIcon, GitHubIcon, GoogleIcon, HtmlIcon, ImageCropModal, ImageCropper, LinkedInIcon, MessageArtifactCard, MessageBubble2 as MessageBubble, MessageThread, OpenAIIcon, PhotoCapture, ProviderIcon, RUN_WINDOW_MS, SemanticSearch, TxtIcon, TypingIndicator, VideoCapture, VoiceNoteRecorder, XlsIcon, annotateThread, arbiQueryKeys, captureFrameAsBlob, cropImage, dayKey, describeActivity, getNotificationTypeMeta, getWorkspaceActionText, getWorkspaceSentPhrase, hasVideoTrack, isWorkspaceNotificationType, parseActivityContent, redlineStats, textToArtifact, toRedlineMarkdown, useActivity, useAgents, useAiTask, useArbiConnected, useArbiDocumentSync, useArbiUiStore, useArbiWebSocket, useArbiWsContext, useArbiWsMessage, useArbiWsStatus, useArbiWsStore, useArbiWsTask, useArbiWsTasks, useAssistantQuery, useCameraStream, useCommandPalette, useConfigs, useConversations, useDeleteAgents, useDirectMessages, useDocuments, useFacts, useHealth, useParsedDocument, useProjectInvoices, useProjectUsage, useProjects, useProjectsUsage, useSemanticSearch, useSessions, useTags, useTasks, useThumbnails, useUserUsageToday, useVideoRecorder, useWorkspaceDocs, useWorkspaces, userDisplayName, userInitials };
6218
5716
  //# sourceMappingURL=index.js.map
6219
5717
  //# sourceMappingURL=index.js.map