@burdenoff/fe-libs 2026.904.28 → 2026.905.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.
@@ -76,6 +76,26 @@ export interface AssistantProductCapabilities {
76
76
  output: number;
77
77
  };
78
78
  }) => Promise<void>;
79
+ /**
80
+ * Where the assistant's files land in the workspace file library.
81
+ *
82
+ * ★★ Irreducible, and unusually load-bearing: these are real paths holding
83
+ * real uploads. A wrong value does not fail loudly — it quietly starts a
84
+ * SECOND folder beside the first, so yesterday's attachments are still there
85
+ * and no longer reachable from the panel.
86
+ *
87
+ * Shared code cannot derive it. HealthyBowl's is `/HealthyBowl/AI Assistant/…`
88
+ * — capitalised as a display name — while its product id is `healthybowl`;
89
+ * deriving from the id would rename the folder and orphan everything in it.
90
+ *
91
+ * Omitted, it falls back to `/<product>/AI Assistant/…`, which is correct for
92
+ * a product that has never stored anything and wrong only for one that
93
+ * already has files elsewhere. That product knows, and says so here.
94
+ */
95
+ storageFolders?: {
96
+ attachments: string;
97
+ artifacts: string;
98
+ };
79
99
  }
80
100
  export interface AssistantProductValue extends AssistantProductCapabilities {
81
101
  /**
@@ -93,7 +113,7 @@ export interface AssistantProductProviderProps extends AssistantProductCapabilit
93
113
  * Mount once, above the assistant. Everything below can ask what product it is
94
114
  * running inside and what that product offers.
95
115
  */
96
- export declare function AssistantProductProvider({ product, modes, describeCurrentPage, gatherPageContext, buildPrompt, reportTokenUsage, children, }: AssistantProductProviderProps): import("react/jsx-runtime").JSX.Element;
116
+ export declare function AssistantProductProvider({ product, modes, describeCurrentPage, gatherPageContext, buildPrompt, reportTokenUsage, storageFolders, children, }: AssistantProductProviderProps): import("react/jsx-runtime").JSX.Element;
97
117
  /** The product in force, or null when no provider is mounted. */
98
118
  export declare function useAssistantProductOrNull(): AssistantProductValue | null;
99
119
  /**
@@ -115,4 +135,16 @@ export declare function useAssistantProduct(): AssistantProductValue;
115
135
  * `undefined` there renders an empty panel rather than a usable one.
116
136
  */
117
137
  export declare function resolveModeConfig(modes: readonly AssistantModeConfig[], mode: string | undefined): AssistantModeConfig | undefined;
138
+ /**
139
+ * Where this product's assistant files belong, with its override applied.
140
+ *
141
+ * ★ ONE resolver, used by BOTH call sites — the attachment upload and the
142
+ * artifact save button. Two independent copies of this default is exactly how
143
+ * the two folders drift apart, and a file written to the wrong one is invisible
144
+ * rather than missing.
145
+ */
146
+ export declare function useAssistantStorageFolders(): {
147
+ attachments: string;
148
+ artifacts: string;
149
+ };
118
150
  //# sourceMappingURL=product.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"product.d.ts","sourceRoot":"","sources":["../../../src/shared/assistant/product.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAsC,KAAK,SAAS,EAAE,MAAM,OAAO,CAAC;AAE3E,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,gBAAgB,CAAC;AAC1D,OAAO,KAAK,EAAE,aAAa,EAAE,WAAW,EAAE,MAAM,SAAS,CAAC;AAE1D;;;;;;;;;;;;;;;;;;;GAmBG;AACH,MAAM,WAAW,4BAA4B;IAC3C;;;;;;OAMG;IACH,KAAK,EAAE,SAAS,mBAAmB,EAAE,CAAC;IACtC;;;;;;;;OAQG;IACH,mBAAmB,CAAC,EAAE,MAAM,MAAM,GAAG,IAAI,CAAC;IAC1C;;;;;;;OAOG;IACH,iBAAiB,CAAC,EAAE,MAAM,WAAW,CAAC;IACtC;;;;;;;OAOG;IACH,WAAW,CAAC,EAAE,CACZ,IAAI,EAAE,aAAa,EACnB,OAAO,EAAE,MAAM,EACf,YAAY,CAAC,EAAE,MAAM,EACrB,gBAAgB,CAAC,EAAE,OAAO,EAC1B,QAAQ,CAAC,EAAE,OAAO,KACf,MAAM,CAAC;IACZ;;;;;;;OAOG;IACH,gBAAgB,CAAC,EAAE,CAAC,KAAK,EAAE;QACzB,WAAW,EAAE,MAAM,CAAC;QACpB,SAAS,EAAE,MAAM,CAAC;QAClB,SAAS,CAAC,EAAE,MAAM,CAAC;QACnB,KAAK,CAAC,EAAE,MAAM,CAAC;QACf,MAAM,EAAE;YAAE,KAAK,EAAE,MAAM,CAAC;YAAC,MAAM,EAAE,MAAM,CAAA;SAAE,CAAC;KAC3C,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;CACrB;AAED,MAAM,WAAW,qBAAsB,SAAQ,4BAA4B;IACzE;;;;OAIG;IACH,OAAO,EAAE,MAAM,CAAC;CACjB;AAID,MAAM,WAAW,6BAA8B,SAAQ,4BAA4B;IACjF,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,SAAS,CAAC;CACrB;AAED;;;GAGG;AACH,wBAAgB,wBAAwB,CAAC,EACvC,OAAO,EACP,KAAK,EACL,mBAAmB,EACnB,iBAAiB,EACjB,WAAW,EACX,gBAAgB,EAChB,QAAQ,GACT,EAAE,6BAA6B,2CAe/B;AAED,iEAAiE;AACjE,wBAAgB,yBAAyB,IAAI,qBAAqB,GAAG,IAAI,CAExE;AAID;;;;;;;;GAQG;AACH,wBAAgB,mBAAmB,IAAI,qBAAqB,CAE3D;AAED;;;;;;;GAOG;AACH,wBAAgB,iBAAiB,CAC/B,KAAK,EAAE,SAAS,mBAAmB,EAAE,EACrC,IAAI,EAAE,MAAM,GAAG,SAAS,GACvB,mBAAmB,GAAG,SAAS,CAEjC"}
1
+ {"version":3,"file":"product.d.ts","sourceRoot":"","sources":["../../../src/shared/assistant/product.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAsC,KAAK,SAAS,EAAE,MAAM,OAAO,CAAC;AAE3E,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,gBAAgB,CAAC;AAC1D,OAAO,KAAK,EAAE,aAAa,EAAE,WAAW,EAAE,MAAM,SAAS,CAAC;AAE1D;;;;;;;;;;;;;;;;;;;GAmBG;AACH,MAAM,WAAW,4BAA4B;IAC3C;;;;;;OAMG;IACH,KAAK,EAAE,SAAS,mBAAmB,EAAE,CAAC;IACtC;;;;;;;;OAQG;IACH,mBAAmB,CAAC,EAAE,MAAM,MAAM,GAAG,IAAI,CAAC;IAC1C;;;;;;;OAOG;IACH,iBAAiB,CAAC,EAAE,MAAM,WAAW,CAAC;IACtC;;;;;;;OAOG;IACH,WAAW,CAAC,EAAE,CACZ,IAAI,EAAE,aAAa,EACnB,OAAO,EAAE,MAAM,EACf,YAAY,CAAC,EAAE,MAAM,EACrB,gBAAgB,CAAC,EAAE,OAAO,EAC1B,QAAQ,CAAC,EAAE,OAAO,KACf,MAAM,CAAC;IACZ;;;;;;;OAOG;IACH,gBAAgB,CAAC,EAAE,CAAC,KAAK,EAAE;QACzB,WAAW,EAAE,MAAM,CAAC;QACpB,SAAS,EAAE,MAAM,CAAC;QAClB,SAAS,CAAC,EAAE,MAAM,CAAC;QACnB,KAAK,CAAC,EAAE,MAAM,CAAC;QACf,MAAM,EAAE;YAAE,KAAK,EAAE,MAAM,CAAC;YAAC,MAAM,EAAE,MAAM,CAAA;SAAE,CAAC;KAC3C,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IACpB;;;;;;;;;;;;;;;OAeG;IACH,cAAc,CAAC,EAAE;QAAE,WAAW,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,CAAA;KAAE,CAAC;CAC7D;AAED,MAAM,WAAW,qBAAsB,SAAQ,4BAA4B;IACzE;;;;OAIG;IACH,OAAO,EAAE,MAAM,CAAC;CACjB;AAID,MAAM,WAAW,6BAA8B,SAAQ,4BAA4B;IACjF,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,SAAS,CAAC;CACrB;AAED;;;GAGG;AACH,wBAAgB,wBAAwB,CAAC,EACvC,OAAO,EACP,KAAK,EACL,mBAAmB,EACnB,iBAAiB,EACjB,WAAW,EACX,gBAAgB,EAChB,cAAc,EACd,QAAQ,GACT,EAAE,6BAA6B,2CAwB/B;AAED,iEAAiE;AACjE,wBAAgB,yBAAyB,IAAI,qBAAqB,GAAG,IAAI,CAExE;AAID;;;;;;;;GAQG;AACH,wBAAgB,mBAAmB,IAAI,qBAAqB,CAE3D;AAED;;;;;;;GAOG;AACH,wBAAgB,iBAAiB,CAC/B,KAAK,EAAE,SAAS,mBAAmB,EAAE,EACrC,IAAI,EAAE,MAAM,GAAG,SAAS,GACvB,mBAAmB,GAAG,SAAS,CAEjC;AAED;;;;;;;GAOG;AACH,wBAAgB,0BAA0B,IAAI;IAC5C,WAAW,EAAE,MAAM,CAAC;IACpB,SAAS,EAAE,MAAM,CAAC;CACnB,CAYA"}
@@ -2,25 +2,27 @@ import { createContext as e, useContext as t, useMemo as n } from "react";
2
2
  import { jsx as r } from "react/jsx-runtime";
3
3
  //#region src/shared/assistant/product.tsx
4
4
  var i = e(null);
5
- function a({ product: e, modes: t, describeCurrentPage: a, gatherPageContext: o, buildPrompt: s, reportTokenUsage: c, children: l }) {
6
- let u = n(() => ({
5
+ function a({ product: e, modes: t, describeCurrentPage: a, gatherPageContext: o, buildPrompt: s, reportTokenUsage: c, storageFolders: l, children: u }) {
6
+ let d = n(() => ({
7
7
  product: e,
8
8
  modes: t,
9
9
  describeCurrentPage: a,
10
10
  gatherPageContext: o,
11
11
  buildPrompt: s,
12
- reportTokenUsage: c
12
+ reportTokenUsage: c,
13
+ storageFolders: l
13
14
  }), [
14
15
  e,
15
16
  t,
16
17
  a,
17
18
  o,
18
19
  s,
19
- c
20
+ c,
21
+ l
20
22
  ]);
21
23
  return /* @__PURE__ */ r(i.Provider, {
22
- value: u,
23
- children: l
24
+ value: d,
25
+ children: u
24
26
  });
25
27
  }
26
28
  function o() {
@@ -36,5 +38,16 @@ function c() {
36
38
  function l(e, t) {
37
39
  return e.find((e) => e.id === t) ?? e[0];
38
40
  }
41
+ function u() {
42
+ let { product: e, storageFolders: t } = c();
43
+ return n(() => {
44
+ if (t) return t;
45
+ let n = e ? `/${e}` : "";
46
+ return {
47
+ attachments: `${n}/AI Assistant/Attachments`,
48
+ artifacts: `${n}/AI Assistant/Artifacts`
49
+ };
50
+ }, [e, t]);
51
+ }
39
52
  //#endregion
40
- export { a as AssistantProductProvider, l as resolveModeConfig, c as useAssistantProduct, o as useAssistantProductOrNull };
53
+ export { a as AssistantProductProvider, l as resolveModeConfig, c as useAssistantProduct, o as useAssistantProductOrNull, u as useAssistantStorageFolders };
@@ -1 +1 @@
1
- {"version":3,"file":"AssistantHeader.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/ui/AssistantHeader.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,EAAE,EAAE,MAAM,OAAO,CAAC;AAKhC,UAAU,KAAK;IACb,qEAAqE;IACrE;;;;;;;OAOG;IACH,YAAY,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,iBAAiB,EAAE,MAAM,IAAI,CAAC;IAC9B,aAAa,EAAE,MAAM,IAAI,CAAC;IAC1B,gFAAgF;IAChF,WAAW,EAAE,OAAO,CAAC;IACrB,OAAO,EAAE,MAAM,IAAI,CAAC;IACpB,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,YAAY,CAAC,EAAE,MAAM,IAAI,CAAC;CAC3B;AAED;;;;;;;;;GASG;AACH,eAAO,MAAM,eAAe,EAAE,EAAE,CAAC,KAAK,CAgGrC,CAAC"}
1
+ {"version":3,"file":"AssistantHeader.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/ui/AssistantHeader.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,EAAE,EAAE,MAAM,OAAO,CAAC;AAKhC,UAAU,KAAK;IACb,qEAAqE;IACrE;;;;;;;OAOG;IACH,YAAY,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,iBAAiB,EAAE,MAAM,IAAI,CAAC;IAC9B,aAAa,EAAE,MAAM,IAAI,CAAC;IAC1B,gFAAgF;IAChF,WAAW,EAAE,OAAO,CAAC;IACrB,OAAO,EAAE,MAAM,IAAI,CAAC;IACpB,MAAM,CAAC,EAAE,OAAO,CAAC;IACjB,YAAY,CAAC,EAAE,MAAM,IAAI,CAAC;CAC3B;AAED;;;;;;;;;GASG;AACH,eAAO,MAAM,eAAe,EAAE,EAAE,CAAC,KAAK,CAmHrC,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"AssistantMessageItem.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/ui/AssistantMessageItem.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAqB,KAAK,EAAE,EAAE,MAAM,OAAO,CAAC;AAoBnD,OAAO,KAAK,EAGV,OAAO,EACR,MAAM,iBAAiB,CAAC;AAIzB,UAAU,KAAK;IACb,OAAO,EAAE,OAAO,CAAC;IACjB,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,4EAA4E;IAC5E,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB;;;;OAIG;IACH,eAAe,CAAC,EAAE,OAAO,CAAC;IAC1B,iEAAiE;IACjE,OAAO,CAAC,EAAE,MAAM,IAAI,CAAC;CACtB;AAyCD,eAAO,MAAM,oBAAoB,EAAE,EAAE,CAAC,KAAK,CA0R1C,CAAC"}
1
+ {"version":3,"file":"AssistantMessageItem.d.ts","sourceRoot":"","sources":["../../../../src/shared/assistant/ui/AssistantMessageItem.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAqB,KAAK,EAAE,EAAE,MAAM,OAAO,CAAC;AAqBnD,OAAO,KAAK,EAGV,OAAO,EACR,MAAM,iBAAiB,CAAC;AAIzB,UAAU,KAAK;IACb,OAAO,EAAE,OAAO,CAAC;IACjB,WAAW,CAAC,EAAE,OAAO,CAAC;IACtB,4EAA4E;IAC5E,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB;;;;OAIG;IACH,eAAe,CAAC,EAAE,OAAO,CAAC;IAC1B,iEAAiE;IACjE,OAAO,CAAC,EAAE,MAAM,IAAI,CAAC;CACtB;AAyCD,eAAO,MAAM,oBAAoB,EAAE,EAAE,CAAC,KAAK,CA4R1C,CAAC"}
@@ -1,180 +1,181 @@
1
1
  import { useAuthToken as e } from "../../providers/shell/AuthTokenProvider.js";
2
2
  import "../../../shared-providers-shell.js";
3
3
  import { downloadAssistantArtifact as t } from "../api.js";
4
- import { useAssistantTr as n } from "../i18n.js";
5
- import { AssistantToolActivity as r, parseToolActivity as i } from "./AssistantToolActivity.js";
6
- import { useAssistantSpeech as a } from "./AssistantSpeechProvider.js";
7
- import { copyToClipboard as o } from "../clipboard.js";
8
- import { AssistantMarkdownRenderer as s } from "./AssistantMarkdownRenderer.js";
9
- import { AssistantMessageAttachments as c } from "./AssistantMessageAttachments.js";
10
- import { AssistantPendingWriteCard as l } from "./AssistantPendingWriteCard.js";
11
- import { AssistantSpeakButton as u } from "./AssistantSpeakButton.js";
12
- import { SaveToFilesButton as d } from "../../../storage/SaveToFilesButton.js";
4
+ import { useAssistantStorageFolders as n } from "../product.js";
5
+ import { useAssistantTr as r } from "../i18n.js";
6
+ import { AssistantToolActivity as i, parseToolActivity as a } from "./AssistantToolActivity.js";
7
+ import { useAssistantSpeech as o } from "./AssistantSpeechProvider.js";
8
+ import { copyToClipboard as s } from "../clipboard.js";
9
+ import { AssistantMarkdownRenderer as c } from "./AssistantMarkdownRenderer.js";
10
+ import { AssistantMessageAttachments as l } from "./AssistantMessageAttachments.js";
11
+ import { AssistantPendingWriteCard as u } from "./AssistantPendingWriteCard.js";
12
+ import { AssistantSpeakButton as d } from "./AssistantSpeakButton.js";
13
+ import { SaveToFilesButton as f } from "../../../storage/SaveToFilesButton.js";
13
14
  import "../../../storage/index.js";
14
- import { useMemo as f, useState as p } from "react";
15
- import { Check as m, Copy as h, RotateCcw as g, Sparkles as _ } from "lucide-react";
16
- import { Fragment as v, jsx as y, jsxs as b } from "react/jsx-runtime";
15
+ import { useMemo as p, useState as m } from "react";
16
+ import { Check as h, Copy as g, RotateCcw as _, Sparkles as v } from "lucide-react";
17
+ import { Fragment as y, jsx as b, jsxs as x } from "react/jsx-runtime";
17
18
  //#region src/shared/assistant/ui/AssistantMessageItem.tsx
18
- function x(e) {
19
+ function S(e) {
19
20
  return e.role === "assistant" ? e.metadata : void 0;
20
21
  }
21
- function S(e) {
22
+ function C(e) {
22
23
  return e?.artifacts ?? [];
23
24
  }
24
- function C(e) {
25
+ function w(e) {
25
26
  return window.atob(e);
26
27
  }
27
- function w(e, t, n) {
28
- let r = C(e), i = new Uint8Array(r.length);
28
+ function T(e, t, n) {
29
+ let r = w(e), i = new Uint8Array(r.length);
29
30
  for (let e = 0; e < r.length; e += 1) i[e] = r.charCodeAt(e);
30
31
  let a = new Blob([i], { type: n }), o = URL.createObjectURL(a), s = document.createElement("a");
31
32
  s.href = o, s.download = t, document.body.appendChild(s), s.click(), document.body.removeChild(s), URL.revokeObjectURL(o);
32
33
  }
33
- var T = ({ message: C, isStreaming: T, isFailed: E, isLastAssistant: D, onRetry: O }) => {
34
- let k = n(), { getAccessToken: A, getWorkspaceToken: j } = e(), M = a(), [N, P] = p(null), [F, I] = p(!1), L = C.role === "user", R = f(() => x(C), [C]), z = f(() => S(R), [R]), { steps: B, text: V } = f(() => L ? {
34
+ var E = ({ message: w, isStreaming: E, isFailed: D, isLastAssistant: O, onRetry: k }) => {
35
+ let A = r(), j = n(), { getAccessToken: M, getWorkspaceToken: N } = e(), P = o(), [F, I] = m(null), [L, R] = m(!1), z = w.role === "user", B = p(() => S(w), [w]), V = p(() => C(B), [B]), { steps: H, text: U } = p(() => z ? {
35
36
  steps: [],
36
- text: C.content
37
- } : i(C.content), [L, C.content]), H = () => {
38
- o(V || C.content).then((e) => {
39
- e && (I(!0), setTimeout(() => I(!1), 2e3));
37
+ text: w.content
38
+ } : a(w.content), [z, w.content]), W = () => {
39
+ s(U || w.content).then((e) => {
40
+ e && (R(!0), setTimeout(() => R(!1), 2e3));
40
41
  });
41
- }, U = async (e) => {
42
- if (!R?.sandboxId || !R.sessionId) return;
42
+ }, G = async (e) => {
43
+ if (!B?.sandboxId || !B.sessionId) return;
43
44
  let n = new URLSearchParams(window.location.search).get("workspace") ?? "";
44
45
  if (n) {
45
- P(e.path);
46
+ I(e.path);
46
47
  try {
47
- let r = await t(R.sandboxId, n, R.sessionId, e.path, {
48
- accessToken: A(),
49
- workspaceToken: j()
48
+ let r = await t(B.sandboxId, n, B.sessionId, e.path, {
49
+ accessToken: M(),
50
+ workspaceToken: N()
50
51
  });
51
- w(r.contentBase64, r.filename, r.mimeType);
52
+ T(r.contentBase64, r.filename, r.mimeType);
52
53
  } finally {
53
- P(null);
54
+ I(null);
54
55
  }
55
56
  }
56
- }, W = new Date(C.timestamp).toLocaleTimeString([], {
57
+ }, K = new Date(w.timestamp).toLocaleTimeString([], {
57
58
  hour: "2-digit",
58
59
  minute: "2-digit"
59
60
  });
60
- if (C.role === "system") return /* @__PURE__ */ y("div", {
61
+ if (w.role === "system") return /* @__PURE__ */ b("div", {
61
62
  className: "flex justify-center px-2 py-1",
62
63
  "data-testid": "assistant-message-system",
63
- children: /* @__PURE__ */ y("p", {
64
+ children: /* @__PURE__ */ b("p", {
64
65
  className: "max-w-[90%] whitespace-pre-wrap break-words rounded-lg border border-border-subtle bg-bg-sunken/60 px-3 py-2 text-center text-xs leading-relaxed text-text-muted",
65
- children: C.content
66
+ children: w.content
66
67
  })
67
68
  });
68
- if (L) {
69
- let e = C.metadata?.attachments ?? [];
70
- return /* @__PURE__ */ y("div", {
69
+ if (z) {
70
+ let e = w.metadata?.attachments ?? [];
71
+ return /* @__PURE__ */ b("div", {
71
72
  className: "flex justify-end",
72
73
  "data-testid": "assistant-message-user",
73
- children: /* @__PURE__ */ b("div", {
74
+ children: /* @__PURE__ */ x("div", {
74
75
  className: "max-w-[85%]",
75
76
  children: [
76
- C.content && /* @__PURE__ */ y("div", {
77
+ w.content && /* @__PURE__ */ b("div", {
77
78
  className: "rounded-2xl rounded-br-md bg-action-primary-bg/12 px-3.5 py-2.5 text-[15px] leading-relaxed text-text-primary",
78
- children: /* @__PURE__ */ y("p", {
79
+ children: /* @__PURE__ */ b("p", {
79
80
  className: "whitespace-pre-wrap",
80
- children: C.content
81
+ children: w.content
81
82
  })
82
83
  }),
83
- /* @__PURE__ */ y(c, { attachments: e }),
84
- /* @__PURE__ */ y("div", {
84
+ /* @__PURE__ */ b(l, { attachments: e }),
85
+ /* @__PURE__ */ b("div", {
85
86
  className: "mt-1 pr-1 text-right text-[10px] text-text-muted",
86
- children: W
87
+ children: K
87
88
  })
88
89
  ]
89
90
  })
90
91
  });
91
92
  }
92
- return /* @__PURE__ */ b("div", {
93
+ return /* @__PURE__ */ x("div", {
93
94
  className: "flex gap-2.5",
94
95
  "data-testid": "assistant-message-assistant",
95
- children: [/* @__PURE__ */ y("div", {
96
+ children: [/* @__PURE__ */ b("div", {
96
97
  className: "mt-0.5 flex size-6 flex-shrink-0 items-center justify-center rounded-full bg-gradient-to-br from-action-primary-bg/25 to-action-primary-bg/5 text-action-primary-bg",
97
- children: /* @__PURE__ */ y(_, { className: "size-3.5" })
98
- }), /* @__PURE__ */ b("div", {
98
+ children: /* @__PURE__ */ b(v, { className: "size-3.5" })
99
+ }), /* @__PURE__ */ x("div", {
99
100
  className: "min-w-0 flex-1",
100
101
  children: [
101
- B.length > 0 && /* @__PURE__ */ y(r, { steps: B }),
102
- R?.pendingWrite ? /* @__PURE__ */ y(l, { pendingWrite: R.pendingWrite }) : null,
103
- V && /* @__PURE__ */ y("div", {
102
+ H.length > 0 && /* @__PURE__ */ b(i, { steps: H }),
103
+ B?.pendingWrite ? /* @__PURE__ */ b(u, { pendingWrite: B.pendingWrite }) : null,
104
+ U && /* @__PURE__ */ b("div", {
104
105
  className: "text-[15px] leading-relaxed text-text-primary",
105
- children: /* @__PURE__ */ y(s, { content: V })
106
+ children: /* @__PURE__ */ b(c, { content: U })
106
107
  }),
107
- T && /* @__PURE__ */ y("span", {
108
+ E && /* @__PURE__ */ b("span", {
108
109
  "aria-hidden": "true",
109
110
  className: "ml-0.5 inline-block h-4 w-1.5 rounded-sm bg-text-secondary align-middle motion-safe:animate-pulse"
110
111
  }),
111
- z.length > 0 && R?.sandboxId && R.sessionId && /* @__PURE__ */ b("div", {
112
+ V.length > 0 && B?.sandboxId && B.sessionId && /* @__PURE__ */ x("div", {
112
113
  className: "mt-3 space-y-2 border-t border-border-subtle pt-2",
113
- children: [/* @__PURE__ */ y("p", {
114
+ children: [/* @__PURE__ */ b("p", {
114
115
  className: "text-[10px] font-medium uppercase tracking-wide text-text-muted",
115
- children: k("message.downloads", "Downloads")
116
- }), /* @__PURE__ */ y("div", {
116
+ children: A("message.downloads", "Downloads")
117
+ }), /* @__PURE__ */ b("div", {
117
118
  className: "flex flex-wrap gap-2",
118
- children: z.map((e) => {
119
+ children: V.map((e) => {
119
120
  let t = `${e.name}${e.type === "directory" ? ".tar.gz" : ""}`;
120
- return /* @__PURE__ */ y(d, {
121
+ return /* @__PURE__ */ b(f, {
121
122
  label: t,
122
- disabled: N === e.path,
123
+ disabled: F === e.path,
123
124
  testId: `assistant-artifact-${e.name}`,
124
125
  source: {
125
126
  kind: "sandbox-artifact",
126
- sandboxId: R.sandboxId,
127
- sessionId: R.sessionId,
127
+ sandboxId: B.sandboxId,
128
+ sessionId: B.sessionId,
128
129
  path: e.path,
129
130
  filename: t
130
131
  },
131
- defaultFolderPath: "/HealthyBowl/AI Assistant/Artifacts",
132
- onDownload: () => U(e)
132
+ defaultFolderPath: j.artifacts,
133
+ onDownload: () => G(e)
133
134
  }, e.path);
134
135
  })
135
136
  })]
136
137
  }),
137
- !T && (V || E || D) && /* @__PURE__ */ b("div", {
138
+ !E && (U || D || O) && /* @__PURE__ */ x("div", {
138
139
  className: "mt-1.5 flex items-center gap-1",
139
140
  children: [
140
- V && /* @__PURE__ */ y("button", {
141
+ U && /* @__PURE__ */ b("button", {
141
142
  type: "button",
142
- onClick: H,
143
+ onClick: W,
143
144
  className: "flex items-center gap-1 rounded-md px-1.5 py-1 text-[11px] text-text-muted transition-colors hover:bg-bg-elevated hover:text-text-secondary",
144
- "aria-label": k("message.copy", "Copy message"),
145
+ "aria-label": A("message.copy", "Copy message"),
145
146
  "data-testid": "assistant-message-copy",
146
- children: F ? /* @__PURE__ */ b(v, { children: [/* @__PURE__ */ y(m, { className: "size-3 text-status-success-text" }), /* @__PURE__ */ y("span", { children: k("message.copied", "Copied") })] }) : /* @__PURE__ */ b(v, { children: [/* @__PURE__ */ y(h, { className: "size-3" }), /* @__PURE__ */ y("span", { children: k("message.copy", "Copy") })] })
147
+ children: L ? /* @__PURE__ */ x(y, { children: [/* @__PURE__ */ b(h, { className: "size-3 text-status-success-text" }), /* @__PURE__ */ b("span", { children: A("message.copied", "Copied") })] }) : /* @__PURE__ */ x(y, { children: [/* @__PURE__ */ b(g, { className: "size-3" }), /* @__PURE__ */ b("span", { children: A("message.copy", "Copy") })] })
147
148
  }),
148
- V && M.isSupported && (() => {
149
- let e = M.blockedFor(C.id) ?? M.disabledReason, t = !!e && !!D, n = t ? `speak-reason-${C.id}` : void 0;
150
- return /* @__PURE__ */ b(v, { children: [/* @__PURE__ */ y(u, {
151
- isSpeaking: M.isSpeaking(C.id),
149
+ U && P.isSupported && (() => {
150
+ let e = P.blockedFor(w.id) ?? P.disabledReason, t = !!e && !!O, n = t ? `speak-reason-${w.id}` : void 0;
151
+ return /* @__PURE__ */ x(y, { children: [/* @__PURE__ */ b(d, {
152
+ isSpeaking: P.isSpeaking(w.id),
152
153
  disabled: e !== null,
153
154
  disabledReason: e,
154
155
  describedById: n,
155
- onClick: () => M.toggle(C.id, V, R?.lang)
156
- }), t && /* @__PURE__ */ y("span", {
156
+ onClick: () => P.toggle(w.id, U, B?.lang)
157
+ }), t && /* @__PURE__ */ b("span", {
157
158
  id: n,
158
159
  className: "text-[11px] text-text-muted",
159
160
  "data-testid": "assistant-speak-reason",
160
161
  children: e
161
162
  })] });
162
163
  })(),
163
- (E || D) && O && /* @__PURE__ */ b("button", {
164
+ (D || O) && k && /* @__PURE__ */ x("button", {
164
165
  type: "button",
165
- onClick: O,
166
- className: `flex items-center gap-1 rounded-md px-1.5 py-1 text-[11px] transition-colors hover:bg-bg-elevated ${E ? "text-status-error-text" : "text-text-muted hover:text-text-secondary"}`,
167
- "aria-label": k("message.retry", "Retry"),
166
+ onClick: k,
167
+ className: `flex items-center gap-1 rounded-md px-1.5 py-1 text-[11px] transition-colors hover:bg-bg-elevated ${D ? "text-status-error-text" : "text-text-muted hover:text-text-secondary"}`,
168
+ "aria-label": A("message.retry", "Retry"),
168
169
  "data-testid": "assistant-message-retry",
169
- children: [/* @__PURE__ */ y(g, { className: "size-3" }), /* @__PURE__ */ y("span", { children: k("message.retry", "Retry") })]
170
+ children: [/* @__PURE__ */ b(_, { className: "size-3" }), /* @__PURE__ */ b("span", { children: A("message.retry", "Retry") })]
170
171
  })
171
172
  ]
172
173
  }),
173
- /* @__PURE__ */ b("div", {
174
+ /* @__PURE__ */ x("div", {
174
175
  className: "mt-1 text-[10px] text-text-muted",
175
- children: [W, C.tokens && /* @__PURE__ */ b("span", {
176
+ children: [K, w.tokens && /* @__PURE__ */ x("span", {
176
177
  className: "ml-2",
177
- children: [C.tokens.input + C.tokens.output, " tokens"]
178
+ children: [w.tokens.input + w.tokens.output, " tokens"]
178
179
  })]
179
180
  })
180
181
  ]
@@ -182,4 +183,4 @@ var T = ({ message: C, isStreaming: T, isFailed: E, isLastAssistant: D, onRetry:
182
183
  });
183
184
  };
184
185
  //#endregion
185
- export { T as AssistantMessageItem };
186
+ export { E as AssistantMessageItem };
@@ -1 +1 @@
1
- {"version":3,"file":"useAssistantAttachments.d.ts","sourceRoot":"","sources":["../../../src/shared/assistant/useAssistantAttachments.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AAOH,OAAO,EAYL,KAAK,mBAAmB,EACxB,KAAK,mBAAmB,EACxB,KAAK,qBAAqB,EAC3B,MAAM,eAAe,CAAC;AAmJvB,MAAM,WAAW,6BAA6B;IAC5C,yEAAyE;IACzE,cAAc,EAAE,MAAM,CAAC;IACvB,WAAW,EAAE,mBAAmB,EAAE,CAAC;IACnC,qEAAqE;IACrE,MAAM,EAAE,OAAO,CAAC;IAChB;;;;;OAKG;IACH,WAAW,EAAE,qBAAqB,GAAG,IAAI,CAAC;IAC1C,6DAA6D;IAC7D,SAAS,EAAE,mBAAmB,GAAG,IAAI,CAAC;IACtC,QAAQ,EAAE,CAAC,KAAK,EAAE,QAAQ,GAAG,IAAI,EAAE,GAAG,IAAI,GAAG,SAAS,KAAK,IAAI,CAAC;IAChE,MAAM,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,IAAI,CAAC;IAC7B,gFAAgF;IAChF,KAAK,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,IAAI,CAAC;IAC5B,KAAK,EAAE,MAAM,IAAI,CAAC;IAClB,cAAc,EAAE,MAAM,IAAI,CAAC;IAC3B,UAAU,EAAE,OAAO,CAAC;CACrB;AAED,wBAAgB,uBAAuB,IAAI,6BAA6B,CAiQvE"}
1
+ {"version":3,"file":"useAssistantAttachments.d.ts","sourceRoot":"","sources":["../../../src/shared/assistant/useAssistantAttachments.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AAOH,OAAO,EAYL,KAAK,mBAAmB,EACxB,KAAK,mBAAmB,EACxB,KAAK,qBAAqB,EAC3B,MAAM,eAAe,CAAC;AAkJvB,MAAM,WAAW,6BAA6B;IAC5C,yEAAyE;IACzE,cAAc,EAAE,MAAM,CAAC;IACvB,WAAW,EAAE,mBAAmB,EAAE,CAAC;IACnC,qEAAqE;IACrE,MAAM,EAAE,OAAO,CAAC;IAChB;;;;;OAKG;IACH,WAAW,EAAE,qBAAqB,GAAG,IAAI,CAAC;IAC1C,6DAA6D;IAC7D,SAAS,EAAE,mBAAmB,GAAG,IAAI,CAAC;IACtC,QAAQ,EAAE,CAAC,KAAK,EAAE,QAAQ,GAAG,IAAI,EAAE,GAAG,IAAI,GAAG,SAAS,KAAK,IAAI,CAAC;IAChE,MAAM,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,IAAI,CAAC;IAC7B,gFAAgF;IAChF,KAAK,EAAE,CAAC,EAAE,EAAE,MAAM,KAAK,IAAI,CAAC;IAC5B,KAAK,EAAE,MAAM,IAAI,CAAC;IAClB,cAAc,EAAE,MAAM,IAAI,CAAC;IAC3B,UAAU,EAAE,OAAO,CAAC;CACrB;AAED,wBAAgB,uBAAuB,IAAI,6BAA6B,CAqQvE"}
@@ -1,15 +1,16 @@
1
1
  import { graphqlFetch as e } from "../graphql/fetch.js";
2
2
  import "../../shared-graphql.js";
3
3
  import { downscaleImage as t } from "../utils/imageDownscale.js";
4
- import { useAssistantTr as n } from "./i18n.js";
5
- import { AttachmentRejectedError as r, INLINE_IMAGE_QUALITY as i, MAX_INLINE_CHARS_PER_FILE as a, classifyAttachment as o, detectDocumentFormat as s, getAttachmentSendBlocker as c, truncateForInline as l, validateFile as u } from "./attachments.js";
6
- import { getWorkspaceId as d } from "./context.js";
7
- import { useSaveToFiles as f } from "../../storage/useSaveToFiles.js";
4
+ import { useAssistantStorageFolders as n } from "./product.js";
5
+ import { useAssistantTr as r } from "./i18n.js";
6
+ import { AttachmentRejectedError as i, INLINE_IMAGE_QUALITY as a, MAX_INLINE_CHARS_PER_FILE as o, classifyAttachment as s, detectDocumentFormat as c, getAttachmentSendBlocker as l, truncateForInline as u, validateFile as d } from "./attachments.js";
7
+ import { getWorkspaceId as f } from "./context.js";
8
+ import { useSaveToFiles as p } from "../../storage/useSaveToFiles.js";
8
9
  import "../../storage/index.js";
9
- import { extractDocumentText as p } from "./documentExtract.js";
10
- import { useCallback as m, useEffect as h, useRef as g, useState as _ } from "react";
10
+ import { extractDocumentText as m } from "./documentExtract.js";
11
+ import { useCallback as h, useEffect as g, useRef as _, useState as v } from "react";
11
12
  //#region src/shared/assistant/useAssistantAttachments.ts
12
- var v = "/HealthyBowl/AI Assistant/Attachments", y = "\n query AssistantAttachmentUrl($id: ID!) {\n getFileDownloadUrl(id: $id)\n }\n";
13
+ var y = "\n query AssistantAttachmentUrl($id: ID!) {\n getFileDownloadUrl(id: $id)\n }\n";
13
14
  async function b(t, n) {
14
15
  if (!t || !n) return null;
15
16
  try {
@@ -30,53 +31,53 @@ function S() {
30
31
  return x += 1, `att-${Date.now()}-${x}`;
31
32
  }
32
33
  async function C(e) {
33
- let n = o(e.type, e.name), c = {
34
+ let n = s(e.type, e.name), r = {
34
35
  id: S(),
35
36
  status: "pending"
36
37
  };
37
38
  if (n === "image") {
38
- let a = await t(e, {
39
+ let o = await t(e, {
39
40
  encodeFallback: !1,
40
41
  inline: {
41
42
  maxDim: 768,
42
- quality: i
43
+ quality: a
43
44
  }
44
45
  });
45
- if (!a.downscaled && a.blob.size > 10485760) throw new r("unsupported-image");
46
+ if (!o.downscaled && o.blob.size > 10485760) throw new i("unsupported-image");
46
47
  return {
47
48
  attachment: {
48
- ...c,
49
- filename: a.filename,
50
- mimeType: a.mimeType,
51
- size: a.blob.size,
49
+ ...r,
50
+ filename: o.filename,
51
+ mimeType: o.mimeType,
52
+ size: o.blob.size,
52
53
  kind: n,
53
- previewUrl: a.dataUrl || void 0,
54
- inlineDataUrl: a.inlineDataUrl
54
+ previewUrl: o.dataUrl || void 0,
55
+ inlineDataUrl: o.inlineDataUrl
55
56
  },
56
- blob: a.blob
57
+ blob: o.blob
57
58
  };
58
59
  }
59
60
  if (n === "text") {
60
- let { text: t, truncated: r } = l(await e.text(), a);
61
+ let { text: t, truncated: i } = u(await e.text(), o);
61
62
  return {
62
63
  attachment: {
63
- ...c,
64
+ ...r,
64
65
  filename: e.name,
65
66
  mimeType: e.type || "text/plain",
66
67
  size: e.size,
67
68
  kind: n,
68
69
  textContent: t,
69
- textTruncated: r
70
+ textTruncated: i
70
71
  },
71
72
  blob: e
72
73
  };
73
74
  }
74
- let u = s(e.type, e.name);
75
- if (u) {
76
- let t = await p(e, u);
75
+ let l = c(e.type, e.name);
76
+ if (l) {
77
+ let t = await m(e, l);
77
78
  return {
78
79
  attachment: {
79
- ...c,
80
+ ...r,
80
81
  filename: e.name,
81
82
  mimeType: e.type || "application/octet-stream",
82
83
  size: e.size,
@@ -91,7 +92,7 @@ async function C(e) {
91
92
  }
92
93
  return {
93
94
  attachment: {
94
- ...c,
95
+ ...r,
95
96
  filename: e.name,
96
97
  mimeType: e.type || "application/octet-stream",
97
98
  size: e.size,
@@ -101,27 +102,27 @@ async function C(e) {
101
102
  };
102
103
  }
103
104
  function w() {
104
- let e = n(), { save: t } = f(), [i, a] = _([]), [o, s] = _(null), l = g(Promise.resolve()), [p, y] = _(0), x = g(0), S = g(/* @__PURE__ */ new Map()), w = g(/* @__PURE__ */ new Set()), T = g(0), E = g(!0);
105
- h(() => () => {
106
- E.current = !1;
105
+ let e = r(), t = n(), { save: a } = p(), [o, s] = v([]), [c, u] = v(null), m = _(Promise.resolve()), [y, x] = v(0), S = _(0), w = _(/* @__PURE__ */ new Map()), T = _(/* @__PURE__ */ new Set()), E = _(0), D = _(!0);
106
+ g(() => () => {
107
+ D.current = !1;
107
108
  }, []);
108
- let D = g([]);
109
- h(() => {
110
- D.current = i;
111
- }, [i]);
112
- let O = m((e, t) => {
113
- E.current && a((n) => n.map((n) => n.id === e ? {
109
+ let O = _([]);
110
+ g(() => {
111
+ O.current = o;
112
+ }, [o]);
113
+ let k = h((e, t) => {
114
+ D.current && s((n) => n.map((n) => n.id === e ? {
114
115
  ...n,
115
116
  ...t
116
117
  } : n));
117
- }, []), k = m(async ({ attachment: n, blob: r }) => {
118
- if (!w.current.has(n.id)) {
119
- O(n.id, {
118
+ }, []), A = h(async ({ attachment: n, blob: r }) => {
119
+ if (!T.current.has(n.id)) {
120
+ k(n.id, {
120
121
  status: "uploading",
121
122
  progressNote: void 0
122
123
  });
123
124
  try {
124
- let i = await t({
125
+ let i = await a({
125
126
  source: {
126
127
  kind: "blob",
127
128
  filename: n.filename,
@@ -132,9 +133,9 @@ function w() {
132
133
  mimeType: n.mimeType
133
134
  })
134
135
  },
135
- folderPath: v,
136
+ folderPath: t.attachments,
136
137
  onRetry: (t) => {
137
- w.current.has(n.id) || O(n.id, { progressNote: t.kind === "cold-start" ? e("attachments.waking", "File service is starting up — retry {{attempt}} of {{max}}", {
138
+ T.current.has(n.id) || k(n.id, { progressNote: t.kind === "cold-start" ? e("attachments.waking", "File service is starting up — retry {{attempt}} of {{max}}", {
138
139
  attempt: String(t.attempt),
139
140
  max: String(t.maxAttempts)
140
141
  }) : e("attachments.retrying", "Retrying {{attempt}} of {{max}}", {
@@ -143,25 +144,25 @@ function w() {
143
144
  }) });
144
145
  }
145
146
  });
146
- if (w.current.has(n.id)) return;
147
- let a = i?.id ? await b(i.id, d()) : null;
148
- if (w.current.has(n.id)) return;
149
- O(n.id, {
147
+ if (T.current.has(n.id)) return;
148
+ let o = i?.id ? await b(i.id, f()) : null;
149
+ if (T.current.has(n.id)) return;
150
+ k(n.id, {
150
151
  status: "ready",
151
152
  fileId: i?.id,
152
- downloadUrl: a ?? void 0,
153
+ downloadUrl: o ?? void 0,
153
154
  progressNote: void 0
154
155
  });
155
156
  } catch (e) {
156
- if (w.current.has(n.id)) return;
157
+ if (T.current.has(n.id)) return;
157
158
  if (n.kind === "text" || n.textContent) {
158
- O(n.id, {
159
+ k(n.id, {
159
160
  status: "ready",
160
161
  progressNote: void 0
161
162
  });
162
163
  return;
163
164
  }
164
- O(n.id, {
165
+ k(n.id, {
165
166
  status: "error",
166
167
  error: e instanceof Error ? e.message : "Upload failed",
167
168
  progressNote: void 0
@@ -169,53 +170,53 @@ function w() {
169
170
  }
170
171
  }
171
172
  }, [
172
- O,
173
- t,
173
+ k,
174
+ a,
174
175
  e
175
- ]), A = m((e) => {
176
+ ]), j = h((e) => {
176
177
  if (!e) return;
177
178
  let t = Array.from(e);
178
179
  if (t.length === 0) return;
179
- s(null);
180
+ u(null);
180
181
  let n = [];
181
182
  for (let e of t) {
182
- let t = u(e, T.current);
183
+ let t = d(e, E.current);
183
184
  if (t) {
184
- s(t);
185
+ u(t);
185
186
  continue;
186
187
  }
187
- n.push(e), T.current += 1;
188
+ n.push(e), E.current += 1;
188
189
  }
189
190
  if (n.length !== 0) {
190
- y((e) => e + n.length);
191
+ x((e) => e + n.length);
191
192
  for (let e of n) {
192
- let t = x.current;
193
- l.current = l.current.then(async () => {
193
+ let t = S.current;
194
+ m.current = m.current.then(async () => {
194
195
  let n = null;
195
196
  try {
196
197
  n = await C(e);
197
198
  } catch (e) {
198
- T.current = Math.max(0, T.current - 1), E.current && s(e instanceof r ? e.reason : "unreadable");
199
+ E.current = Math.max(0, E.current - 1), D.current && u(e instanceof i ? e.reason : "unreadable");
199
200
  }
200
- if (!E.current || (y((e) => Math.max(0, e - 1)), !n)) return;
201
- if (t !== x.current) {
202
- T.current = Math.max(0, T.current - 1);
201
+ if (!D.current || (x((e) => Math.max(0, e - 1)), !n)) return;
202
+ if (t !== S.current) {
203
+ E.current = Math.max(0, E.current - 1);
203
204
  return;
204
205
  }
205
- let i = n;
206
- S.current.set(i.attachment.id, i.blob), a((e) => [...e, i.attachment]), await k(i);
206
+ let r = n;
207
+ w.current.set(r.attachment.id, r.blob), s((e) => [...e, r.attachment]), await A(r);
207
208
  });
208
209
  }
209
210
  }
210
- }, [k]), j = m((e) => {
211
- w.current.add(e), S.current.delete(e), T.current = Math.max(0, T.current - 1), a((t) => t.filter((t) => t.id !== e));
212
- }, []), M = m((e) => {
213
- let t = D.current.find((t) => t.id === e), n = S.current.get(e);
214
- !t || t.status !== "error" || !n || (w.current.delete(e), O(e, {
211
+ }, [A]), M = h((e) => {
212
+ T.current.add(e), w.current.delete(e), E.current = Math.max(0, E.current - 1), s((t) => t.filter((t) => t.id !== e));
213
+ }, []), N = h((e) => {
214
+ let t = O.current.find((t) => t.id === e), n = w.current.get(e);
215
+ !t || t.status !== "error" || !n || (T.current.delete(e), k(e, {
215
216
  status: "pending",
216
217
  error: void 0,
217
218
  progressNote: void 0
218
- }), l.current = l.current.then(() => k({
219
+ }), m.current = m.current.then(() => A({
219
220
  attachment: {
220
221
  ...t,
221
222
  status: "pending",
@@ -223,21 +224,21 @@ function w() {
223
224
  },
224
225
  blob: n
225
226
  })));
226
- }, [O, k]), N = m(() => {
227
- x.current += 1, T.current = 0, D.current.forEach((e) => w.current.add(e.id)), S.current.clear(), a([]);
228
- }, []), P = c(p, i);
227
+ }, [k, A]), P = h(() => {
228
+ S.current += 1, E.current = 0, O.current.forEach((e) => T.current.add(e.id)), w.current.clear(), s([]);
229
+ }, []), F = l(y, o);
229
230
  return {
230
- attachments: i,
231
- isBusy: P === "in-flight",
232
- preparingCount: p,
233
- sendBlocker: P,
234
- rejection: o,
235
- addFiles: A,
236
- remove: j,
237
- retry: M,
238
- clear: N,
239
- clearRejection: m(() => s(null), []),
240
- canAddMore: T.current < 5
231
+ attachments: o,
232
+ isBusy: F === "in-flight",
233
+ preparingCount: y,
234
+ sendBlocker: F,
235
+ rejection: c,
236
+ addFiles: j,
237
+ remove: M,
238
+ retry: N,
239
+ clear: P,
240
+ clearRejection: h(() => u(null), []),
241
+ canAddMore: E.current < 5
241
242
  };
242
243
  }
243
244
  //#endregion
@@ -27,65 +27,65 @@ import { toCaptionText as jt } from "./shared/assistant/voice/captionText.js";
27
27
  import { ASSISTANT_LANGUAGES as Mt, DEFAULT_SPEECH_RATE as Nt, findAssistantLanguage as Pt, resolveAssistantLanguage as Ft } from "./shared/assistant/voice/languages.js";
28
28
  import { replyFollowsInput as It, resolveLanguagePair as Lt } from "./shared/assistant/voice/languagePair.js";
29
29
  import { findPendingWrite as Rt, parseConfirmationRefusal as zt } from "./shared/assistant/pendingWrite.js";
30
- import { AssistantProductProvider as Bt, resolveModeConfig as Vt, useAssistantProduct as Ht, useAssistantProductOrNull as Ut } from "./shared/assistant/product.js";
31
- import { AssistantI18nProvider as Wt, assistantTranslationKey as Gt, useAssistantI18nNamespace as Kt, useAssistantTr as qt } from "./shared/assistant/i18n.js";
32
- import { SPOKEN_LABEL_LANGUAGES as Jt, speechLabelsFor as Yt } from "./shared/assistant/voice/speechLabels.js";
33
- import { detectScriptLocale as Xt, resolveSpeechLocale as Zt } from "./shared/assistant/voice/replyLanguage.js";
34
- import { IDLE_PLAYBACK as Qt, isSpeakingMessage as $t, requiresCancel as en, speechPlaybackReducer as tn } from "./shared/assistant/voice/speechPlayback.js";
35
- import { MAX_INLINE_IMAGE_BASE64_BYTES as nn, MAX_REQUEST_BODY_BYTES as rn } from "./shared/assistant/gatewayLimits.js";
36
- import { BOILERPLATE_PAGE_SHARE as an, MAX_BOILERPLATE_LINE_CHARS as on, MAX_EXTRACTED_CHARS as sn, MAX_PDF_PAGES_SCANNED as cn, MIN_PAGE_TEXT_CHARS as ln, MIN_TEXT_PAGE_SHARE as un, columnLetterToIndex as dn, decodeXmlEntities as fn, docxXmlToText as pn, fitPdfPages as mn, formatPageRanges as hn, isMostlyImagePages as gn, joinSheets as _n, pageMarker as vn, parseSharedStrings as yn, parseWorkbookSheets as bn, pdfTextItemsToPage as xn, sheetXmlToRows as Sn, summarisePageText as Cn, truncatePagesForInline as wn } from "./shared/assistant/documentText.js";
37
- import { ATTACHMENT_ACCEPT as Tn, AttachmentRejectedError as En, INLINE_IMAGE_MAX_DIM as Dn, INLINE_IMAGE_QUALITY as On, MAX_ATTACHMENTS as kn, MAX_FILE_BYTES as An, MAX_INLINE_CHARS_PER_FILE as jn, MAX_INLINE_CHARS_TOTAL as Mn, MAX_INLINE_IMAGE_BASE64_CHARS as Nn, MAX_INLINE_IMAGE_PARTS as Pn, MAX_INLINE_TURN_BODY_BYTES as Fn, MAX_TURN_BODY_BYTES as In, PROMPT_ENVELOPE_RESERVE_BYTES as Ln, TURN_BODY_HEADROOM_BYTES as Rn, buildAttachmentPromptBlock as zn, buildPromptParts as Bn, buildPromptWithAttachments as Vn, classifyAttachment as Hn, countInlineImageCandidates as Un, countInlinedImageParts as Wn, detectDocumentFormat as Gn, estimateTurnBodyBytes as Kn, formatBytes as qn, getAttachmentSendBlocker as Jn, getExtension as Yn, getSendableAttachments as Xn, hasAttachmentWorkInFlight as Zn, parseDataUrl as Qn, toMessageAttachment as $n, truncateForInline as er, validateFile as tr } from "./shared/assistant/attachments.js";
38
- import { useAssistantStore as nr } from "./shared/assistant/store.js";
39
- import { isTurnInFlight as rr } from "./shared/assistant/turnState.js";
40
- import { AssistantToolActivity as ir, parseToolActivity as ar } from "./shared/assistant/ui/AssistantToolActivity.js";
41
- import { AssistantSpeechProvider as or, useAssistantSpeech as sr } from "./shared/assistant/ui/AssistantSpeechProvider.js";
42
- import { useVoiceSession as cr } from "./shared/assistant/ui/useVoiceSession.js";
43
- import { copyToClipboard as lr } from "./shared/assistant/clipboard.js";
44
- import { getActorId as ur, getOrganizationId as dr, getWorkspaceId as fr } from "./shared/assistant/context.js";
45
- import { ATTACHMENT_SOURCES as pr, availableAttachmentSources as mr, deviceHasCamera as hr } from "./shared/assistant/attachmentSources.js";
46
- import { SANDBOX_READY_TTL_MS as gr, createReadinessTracker as _r, isRecentlyVerified as vr } from "./shared/assistant/sandboxReadiness.js";
47
- import { AssistantAutoSpeakToggle as yr } from "./shared/assistant/ui/AssistantAutoSpeakToggle.js";
48
- import { AssistantMarkdownImage as br, imageHostLabel as xr, isRemoteImageSrc as Sr } from "./shared/assistant/ui/AssistantMarkdownImage.js";
49
- import { AssistantMarkdownRenderer as Cr, assistantUrlTransform as wr } from "./shared/assistant/ui/AssistantMarkdownRenderer.js";
50
- import { AssistantMessageAttachments as Tr } from "./shared/assistant/ui/AssistantMessageAttachments.js";
51
- import { AssistantPendingWriteCard as Er } from "./shared/assistant/ui/AssistantPendingWriteCard.js";
52
- import { AssistantReplyLanguageSelector as Dr } from "./shared/assistant/ui/AssistantReplyLanguageSelector.js";
53
- import { AssistantSpeakButton as Or } from "./shared/assistant/ui/AssistantSpeakButton.js";
54
- import { AssistantSpokenTurnsNotice as kr } from "./shared/assistant/ui/AssistantSpokenTurnsNotice.js";
55
- import { AssistantAttachmentButton as Ar } from "./shared/assistant/ui/composer/AssistantAttachmentButton.js";
56
- import { AssistantAttachmentChips as jr } from "./shared/assistant/ui/composer/AssistantAttachmentChips.js";
57
- import { AssistantLanguageSelector as Mr, FOLLOW_APP_LOCALE as Nr } from "./shared/assistant/ui/composer/AssistantLanguageSelector.js";
58
- import { ASSISTANT_MODE_META as Pr, AssistantModeSelector as Fr, nextModeIndex as Ir } from "./shared/assistant/ui/composer/AssistantModeSelector.js";
59
- import { AssistantVoiceButton as Lr } from "./shared/assistant/ui/composer/AssistantVoiceButton.js";
60
- import { AUTO_VOICE as Rr, AssistantVoiceSelector as zr } from "./shared/assistant/ui/composer/AssistantVoiceSelector.js";
61
- import { AssistantVoiceOrb as Br } from "./shared/assistant/ui/voice/AssistantVoiceOrb.js";
62
- import { AssistantVoiceSessionButton as Vr } from "./shared/assistant/ui/voice/AssistantVoiceSessionButton.js";
63
- import { VoiceCaption as Hr } from "./shared/assistant/ui/voice/VoiceCaption.js";
64
- import { VoiceConversationView as Ur } from "./shared/assistant/ui/voice/VoiceConversationView.js";
65
- import { VoiceWaveform as Wr } from "./shared/assistant/ui/voice/VoiceWaveform.js";
66
- import { VoiceMiniController as Gr } from "./shared/assistant/ui/voice/VoiceMiniController.js";
67
- import { VoiceStage as Kr } from "./shared/assistant/ui/voice/VoiceStage.js";
68
- import { VoiceTranscriptDrawer as qr } from "./shared/assistant/ui/voice/VoiceTranscriptDrawer.js";
69
- import { downloadFile as Jr, exportConversation as Yr } from "./shared/assistant/exportConversation.js";
70
- import { AssistantMoreMenu as Xr } from "./shared/assistant/ui/AssistantMoreMenu.js";
71
- import { AssistantHeader as Zr } from "./shared/assistant/ui/AssistantHeader.js";
72
- import { AssistantConversationList as Qr } from "./shared/assistant/ui/AssistantConversationList.js";
73
- import { AssistantEmptyState as $r } from "./shared/assistant/ui/AssistantEmptyState.js";
74
- import { AssistantMessageItem as ei } from "./shared/assistant/ui/AssistantMessageItem.js";
75
- import { AssistantMessageList as ti } from "./shared/assistant/ui/AssistantMessageList.js";
76
- import { AssistantVoiceSession as ni } from "./shared/assistant/ui/voice/AssistantVoiceSession.js";
77
- import { useAssistantApiAccess as ri } from "./shared/assistant/useAssistantApiAccess.js";
78
- import { useConversationTurns as ii } from "./shared/assistant/useConversationTurns.js";
79
- import { isMultimodalBodyRejection as ai, isRecoverableAssistantError as oi } from "./shared/assistant/transportErrors.js";
80
- import { aiCreditsUpdatedEventName as si, dispatchAssistantQuotaExhausted as ci, notifyAiCreditsUpdated as li } from "./shared/assistant/aiCredits.js";
81
- import { useWorkspaceWriteAccess as ui } from "./shared/assistant/useWorkspaceWriteAccess.js";
82
- import { extractDocumentText as di } from "./shared/assistant/documentExtract.js";
83
- import { useAssistantAttachments as fi } from "./shared/assistant/useAssistantAttachments.js";
84
- import { AssistantComposer as pi } from "./shared/assistant/ui/composer/AssistantComposer.js";
85
- import { isProdRuntime as mi } from "./shared/assistant/env.js";
86
- import { useAssistantHeartbeat as hi } from "./shared/assistant/useAssistantHeartbeat.js";
87
- import { useAssistantKeyboardShortcuts as gi } from "./shared/assistant/useAssistantKeyboardShortcuts.js";
88
- import { AssistantApiCallsConsentDialog as _i } from "./shared/assistant/ui/AssistantApiCallsConsentDialog.js";
89
- import { AssistantChatArea as vi } from "./shared/assistant/ui/AssistantChatArea.js";
90
- import { AIAssistantPanel as yi } from "./shared/assistant/ui/AIAssistantPanel.js";
91
- export { yi as AIAssistantPanel, h as ASSISTANT_API_AUTH_STRATEGY, Mt as ASSISTANT_LANGUAGES, Pr as ASSISTANT_MODE_META, Tn as ATTACHMENT_ACCEPT, pr as ATTACHMENT_SOURCES, Rr as AUTO_VOICE, _i as AssistantApiCallsConsentDialog, Ar as AssistantAttachmentButton, jr as AssistantAttachmentChips, yr as AssistantAutoSpeakToggle, vi as AssistantChatArea, pi as AssistantComposer, Qr as AssistantConversationList, $r as AssistantEmptyState, Zr as AssistantHeader, Wt as AssistantI18nProvider, Mr as AssistantLanguageSelector, br as AssistantMarkdownImage, Cr as AssistantMarkdownRenderer, Tr as AssistantMessageAttachments, ei as AssistantMessageItem, ti as AssistantMessageList, Fr as AssistantModeSelector, Xr as AssistantMoreMenu, Er as AssistantPendingWriteCard, Bt as AssistantProductProvider, Dr as AssistantReplyLanguageSelector, G as AssistantRuntimeManager, Or as AssistantSpeakButton, or as AssistantSpeechProvider, kr as AssistantSpokenTurnsNotice, ir as AssistantToolActivity, Lr as AssistantVoiceButton, Br as AssistantVoiceOrb, zr as AssistantVoiceSelector, ni as AssistantVoiceSession, Vr as AssistantVoiceSessionButton, En as AttachmentRejectedError, an as BOILERPLATE_PAGE_SHARE, o as CHECK_AI_CREDITS, s as CREATE_SANDBOX, pt as DEFAULT_SPEAKABLE_LABELS, Nt as DEFAULT_SPEECH_RATE, Be as ENDPOINT_GRACE_MS, c as EXTEND_SANDBOX_TTL, Nr as FOLLOW_APP_LOCALE, l as GET_ACTIVE_SANDBOXES, u as GET_SANDBOX, ge as HOSTED_TTS_MAX_CHARS, fe as HOSTED_TTS_TIER, pe as HOSTED_VOICES, Qt as IDLE_PLAYBACK, Ve as INITIAL_SESSION, Dn as INLINE_IMAGE_MAX_DIM, On as INLINE_IMAGE_QUALITY, He as INTERRUPT_MAX_MS, Ue as INTERRUPT_MIN_MS, kn as MAX_ATTACHMENTS, on as MAX_BOILERPLATE_LINE_CHARS, sn as MAX_EXTRACTED_CHARS, An as MAX_FILE_BYTES, jn as MAX_INLINE_CHARS_PER_FILE, Mn as MAX_INLINE_CHARS_TOTAL, nn as MAX_INLINE_IMAGE_BASE64_BYTES, Nn as MAX_INLINE_IMAGE_BASE64_CHARS, Pn as MAX_INLINE_IMAGE_PARTS, Fn as MAX_INLINE_TURN_BODY_BYTES, cn as MAX_PDF_PAGES_SCANNED, rn as MAX_REQUEST_BODY_BYTES, mt as MAX_SPEAKABLE_CHARS, ht as MAX_SPOKEN_TABLE_ROWS, In as MAX_TURN_BODY_BYTES, ln as MIN_PAGE_TEXT_CHARS, un as MIN_TEXT_PAGE_SHARE, Tt as POLL_FAST_MS, Et as POLL_FAST_UNTIL_MS, Dt as POLL_SLOW_MS, Ot as POLL_STEADY_MS, kt as POLL_STEADY_UNTIL_MS, Ct as PREVIEW_LANGUAGES, Ln as PROMPT_ENVELOPE_RESERVE_BYTES, d as PROXY_SANDBOX_REQUEST, f as REPORT_AI_TOKEN_USAGE, gr as SANDBOX_READY_TTL_MS, We as SILENCE_SUBMIT_MS, _e as SPEAKING_RATE_MAX, ve as SPEAKING_RATE_MAX_STREAMING, ye as SPEAKING_RATE_MAX_SYNC, be as SPEAKING_RATE_MIN, gt as SPEECH_CHUNK_CHARS, _t as SPEECH_CHUNK_CJK_CHARS, Qe as SPEECH_LANG, Jt as SPOKEN_LABEL_LANGUAGES, p as STOP_ASSISTANT_SANDBOX, Rn as TURN_BODY_HEADROOM_BYTES, $e as VOICE_LIST_TIMEOUT_MS, Hr as VoiceCaption, Ur as VoiceConversationView, Gr as VoiceMiniController, Kr as VoiceStage, qr as VoiceTranscriptDrawer, Wr as VoiceWaveform, m as WAIT_FOR_SANDBOX_RUNNING, si as aiCreditsUpdatedEventName, Gt as assistantTranslationKey, wr as assistantUrlTransform, mr as availableAttachmentSources, xe as base64ToBytes, de as browserSpeechEngine, T as buildAssistantSandboxEnv, zn as buildAttachmentPromptBlock, ut as buildContinuedFromVoiceNote, K as buildProgress, Bn as buildPromptParts, E as buildPromptRequestBody, Vn as buildPromptWithAttachments, Se as buildRequest, i as buildSandboxContextInput, dt as buildVoiceTranscriptMarkdown, ie as chatTurns, D as checkAssistantAiCredits, vt as chunkForSpeech, Hn as classifyAttachment, Ce as classifyHttpFailure, t as classifyQuotaError, dn as columnLetterToIndex, ke as configureSpeechEngine, yt as containsCjk, lr as copyToClipboard, Un as countInlineImageCandidates, Wn as countInlinedImageParts, O as createAssistantSandbox, k as createAssistantSession, De as createHostedTtsEngine, _r as createReadinessTracker, Oe as createRoutingSpeechEngine, ne as createSandboxAssistantTransport, Ae as createSpeechEngines, we as decodeAudioResponse, fn as decodeXmlEntities, Gn as detectDocumentFormat, Xt as detectScriptLocale, hr as deviceHasCamera, ci as dispatchAssistantQuotaExhausted, pn as docxXmlToText, A as downloadAssistantArtifact, Jr as downloadFile, Kn as estimateTurnBodyBytes, a as executeSandboxGraphQL, Yr as exportConversation, j as extendAssistantSandboxTTL, di as extractDocumentText, Pt as findAssistantLanguage, M as findExistingSandbox, Rt as findPendingWrite, mn as fitPdfPages, qn as formatBytes, hn as formatPageRanges, ur as getActorId, N as getAssistantArtifacts, q as getAssistantMedia, P as getAssistantMessages, F as getAssistantSession, I as getAssistantStreamAccess, J as getAssistantText, Jn as getAttachmentSendBlocker, x as getCapability, Yn as getExtension, g as getImageForMode, _ as getImageTagForMode, dr as getOrganizationId, Y as getRawMessageCreatedAt, v as getResourcesForMode, y as getSandboxImageRegistry, Xn as getSendableAttachments, je as getSpeechEngine, X as getToolProgress, fr as getWorkspaceId, ae as groupBySession, oe as groupConsecutiveBySession, Zn as hasAttachmentWorkInFlight, me as hostedLocaleFor, he as hostedSupportsLanguage, xr as imageHostLabel, Ge as isCapturing, Ke as isEcho, gn as isMostlyImagePages, ai as isMultimodalBodyRejection, mi as isProdRuntime, n as isQuotaExhaustedError, Z as isReapedSandboxConnectionError, vr as isRecentlyVerified, Q as isRecoverable, oi as isRecoverableAssistantError, Sr as isRemoteImageSrc, $t as isSpeakingMessage, et as isSpeechBlocked, qe as isSubmittable, rr as isTurnInFlight, S as isUnknownFieldError, se as isVoiceTurn, _n as joinSheets, tt as languageDisplayName, $ as mapSessionToHistory, C as markSupported, w as markUnsupported, ee as mergeMessagesById, Pe as micIsInterrupt, L as modeRequiresConfirmWrites, Ir as nextModeIndex, nt as normalizeLangTag, li as notifyAiCreditsUpdated, Je as orbMode, vn as pageMarker, zt as parseConfirmationRefusal, Qn as parseDataUrl, yn as parseSharedStrings, ar as parseToolActivity, bn as parseWorkbookSheets, xn as pdfTextItemsToPage, Ye as planReplyConsumption, At as pollDelayMs, rt as primaryLanguageSubtag, r as quotaExhaustedEventName, Me as readSpeechEngineConfig, It as replyFollowsInput, R as reportAssistantAiTokenUsage, en as requiresCancel, Ne as resetSpeechEngine, Ft as resolveAssistantLanguage, Lt as resolveLanguagePair, Vt as resolveModeConfig, b as resolveSandboxAssistantMode, Zt as resolveSpeechLocale, te as sanitize, z as selectExistingAssistantSandbox, it as selectVoiceForLocale, B as sendAssistantPromptAsync, V as sendHeartbeat, Sn as sheetXmlToRows, Te as shouldDisableEngine, Fe as showsAssistantCaption, Ie as showsUserCaption, bt as speakableEmail, at as speechGate, Yt as speechLabelsFor, ot as speechLangForLocale, tn as speechPlaybackReducer, Ee as splitForVendor, xt as splitTableRow, Xe as spokenSoFar, H as stopReapedAssistantSandbox, Cn as summarisePageText, jt as toCaptionText, $n as toMessageAttachment, St as toSpeakableText, er as truncateForInline, wn as truncatePagesForInline, ri as useAssistantApiAccess, fi as useAssistantAttachments, hi as useAssistantHeartbeat, Kt as useAssistantI18nNamespace, gi as useAssistantKeyboardShortcuts, Ht as useAssistantProduct, Ut as useAssistantProductOrNull, sr as useAssistantSpeech, nr as useAssistantStore, qt as useAssistantTr, ii as useConversationTurns, re as useSandboxAssistantTransport, e as useVoiceInput, cr as useVoiceSession, ui as useWorkspaceWriteAccess, tr as validateFile, st as voiceAvailability, ce as voiceMarker, wt as voicePreviewText, ct as voiceQualityRank, le as voiceSessionIdOf, Ze as voiceSessionReducer, Le as voiceStageState, ft as voiceTranscriptFilename, ue as voiceTurnsOnly, lt as voicesForLocale, U as waitForAssistantServiceReady, W as waitForSandboxRunning, Re as waveformIsActive, ze as waveformIsSettled };
30
+ import { AssistantProductProvider as Bt, resolveModeConfig as Vt, useAssistantProduct as Ht, useAssistantProductOrNull as Ut, useAssistantStorageFolders as Wt } from "./shared/assistant/product.js";
31
+ import { AssistantI18nProvider as Gt, assistantTranslationKey as Kt, useAssistantI18nNamespace as qt, useAssistantTr as Jt } from "./shared/assistant/i18n.js";
32
+ import { SPOKEN_LABEL_LANGUAGES as Yt, speechLabelsFor as Xt } from "./shared/assistant/voice/speechLabels.js";
33
+ import { detectScriptLocale as Zt, resolveSpeechLocale as Qt } from "./shared/assistant/voice/replyLanguage.js";
34
+ import { IDLE_PLAYBACK as $t, isSpeakingMessage as en, requiresCancel as tn, speechPlaybackReducer as nn } from "./shared/assistant/voice/speechPlayback.js";
35
+ import { MAX_INLINE_IMAGE_BASE64_BYTES as rn, MAX_REQUEST_BODY_BYTES as an } from "./shared/assistant/gatewayLimits.js";
36
+ import { BOILERPLATE_PAGE_SHARE as on, MAX_BOILERPLATE_LINE_CHARS as sn, MAX_EXTRACTED_CHARS as cn, MAX_PDF_PAGES_SCANNED as ln, MIN_PAGE_TEXT_CHARS as un, MIN_TEXT_PAGE_SHARE as dn, columnLetterToIndex as fn, decodeXmlEntities as pn, docxXmlToText as mn, fitPdfPages as hn, formatPageRanges as gn, isMostlyImagePages as _n, joinSheets as vn, pageMarker as yn, parseSharedStrings as bn, parseWorkbookSheets as xn, pdfTextItemsToPage as Sn, sheetXmlToRows as Cn, summarisePageText as wn, truncatePagesForInline as Tn } from "./shared/assistant/documentText.js";
37
+ import { ATTACHMENT_ACCEPT as En, AttachmentRejectedError as Dn, INLINE_IMAGE_MAX_DIM as On, INLINE_IMAGE_QUALITY as kn, MAX_ATTACHMENTS as An, MAX_FILE_BYTES as jn, MAX_INLINE_CHARS_PER_FILE as Mn, MAX_INLINE_CHARS_TOTAL as Nn, MAX_INLINE_IMAGE_BASE64_CHARS as Pn, MAX_INLINE_IMAGE_PARTS as Fn, MAX_INLINE_TURN_BODY_BYTES as In, MAX_TURN_BODY_BYTES as Ln, PROMPT_ENVELOPE_RESERVE_BYTES as Rn, TURN_BODY_HEADROOM_BYTES as zn, buildAttachmentPromptBlock as Bn, buildPromptParts as Vn, buildPromptWithAttachments as Hn, classifyAttachment as Un, countInlineImageCandidates as Wn, countInlinedImageParts as Gn, detectDocumentFormat as Kn, estimateTurnBodyBytes as qn, formatBytes as Jn, getAttachmentSendBlocker as Yn, getExtension as Xn, getSendableAttachments as Zn, hasAttachmentWorkInFlight as Qn, parseDataUrl as $n, toMessageAttachment as er, truncateForInline as tr, validateFile as nr } from "./shared/assistant/attachments.js";
38
+ import { useAssistantStore as rr } from "./shared/assistant/store.js";
39
+ import { isTurnInFlight as ir } from "./shared/assistant/turnState.js";
40
+ import { AssistantToolActivity as ar, parseToolActivity as or } from "./shared/assistant/ui/AssistantToolActivity.js";
41
+ import { AssistantSpeechProvider as sr, useAssistantSpeech as cr } from "./shared/assistant/ui/AssistantSpeechProvider.js";
42
+ import { useVoiceSession as lr } from "./shared/assistant/ui/useVoiceSession.js";
43
+ import { copyToClipboard as ur } from "./shared/assistant/clipboard.js";
44
+ import { getActorId as dr, getOrganizationId as fr, getWorkspaceId as pr } from "./shared/assistant/context.js";
45
+ import { ATTACHMENT_SOURCES as mr, availableAttachmentSources as hr, deviceHasCamera as gr } from "./shared/assistant/attachmentSources.js";
46
+ import { SANDBOX_READY_TTL_MS as _r, createReadinessTracker as vr, isRecentlyVerified as yr } from "./shared/assistant/sandboxReadiness.js";
47
+ import { AssistantAutoSpeakToggle as br } from "./shared/assistant/ui/AssistantAutoSpeakToggle.js";
48
+ import { AssistantMarkdownImage as xr, imageHostLabel as Sr, isRemoteImageSrc as Cr } from "./shared/assistant/ui/AssistantMarkdownImage.js";
49
+ import { AssistantMarkdownRenderer as wr, assistantUrlTransform as Tr } from "./shared/assistant/ui/AssistantMarkdownRenderer.js";
50
+ import { AssistantMessageAttachments as Er } from "./shared/assistant/ui/AssistantMessageAttachments.js";
51
+ import { AssistantPendingWriteCard as Dr } from "./shared/assistant/ui/AssistantPendingWriteCard.js";
52
+ import { AssistantReplyLanguageSelector as Or } from "./shared/assistant/ui/AssistantReplyLanguageSelector.js";
53
+ import { AssistantSpeakButton as kr } from "./shared/assistant/ui/AssistantSpeakButton.js";
54
+ import { AssistantSpokenTurnsNotice as Ar } from "./shared/assistant/ui/AssistantSpokenTurnsNotice.js";
55
+ import { AssistantAttachmentButton as jr } from "./shared/assistant/ui/composer/AssistantAttachmentButton.js";
56
+ import { AssistantAttachmentChips as Mr } from "./shared/assistant/ui/composer/AssistantAttachmentChips.js";
57
+ import { AssistantLanguageSelector as Nr, FOLLOW_APP_LOCALE as Pr } from "./shared/assistant/ui/composer/AssistantLanguageSelector.js";
58
+ import { ASSISTANT_MODE_META as Fr, AssistantModeSelector as Ir, nextModeIndex as Lr } from "./shared/assistant/ui/composer/AssistantModeSelector.js";
59
+ import { AssistantVoiceButton as Rr } from "./shared/assistant/ui/composer/AssistantVoiceButton.js";
60
+ import { AUTO_VOICE as zr, AssistantVoiceSelector as Br } from "./shared/assistant/ui/composer/AssistantVoiceSelector.js";
61
+ import { AssistantVoiceOrb as Vr } from "./shared/assistant/ui/voice/AssistantVoiceOrb.js";
62
+ import { AssistantVoiceSessionButton as Hr } from "./shared/assistant/ui/voice/AssistantVoiceSessionButton.js";
63
+ import { VoiceCaption as Ur } from "./shared/assistant/ui/voice/VoiceCaption.js";
64
+ import { VoiceConversationView as Wr } from "./shared/assistant/ui/voice/VoiceConversationView.js";
65
+ import { VoiceWaveform as Gr } from "./shared/assistant/ui/voice/VoiceWaveform.js";
66
+ import { VoiceMiniController as Kr } from "./shared/assistant/ui/voice/VoiceMiniController.js";
67
+ import { VoiceStage as qr } from "./shared/assistant/ui/voice/VoiceStage.js";
68
+ import { VoiceTranscriptDrawer as Jr } from "./shared/assistant/ui/voice/VoiceTranscriptDrawer.js";
69
+ import { downloadFile as Yr, exportConversation as Xr } from "./shared/assistant/exportConversation.js";
70
+ import { AssistantMoreMenu as Zr } from "./shared/assistant/ui/AssistantMoreMenu.js";
71
+ import { AssistantHeader as Qr } from "./shared/assistant/ui/AssistantHeader.js";
72
+ import { AssistantConversationList as $r } from "./shared/assistant/ui/AssistantConversationList.js";
73
+ import { AssistantEmptyState as ei } from "./shared/assistant/ui/AssistantEmptyState.js";
74
+ import { AssistantMessageItem as ti } from "./shared/assistant/ui/AssistantMessageItem.js";
75
+ import { AssistantMessageList as ni } from "./shared/assistant/ui/AssistantMessageList.js";
76
+ import { AssistantVoiceSession as ri } from "./shared/assistant/ui/voice/AssistantVoiceSession.js";
77
+ import { useAssistantApiAccess as ii } from "./shared/assistant/useAssistantApiAccess.js";
78
+ import { useConversationTurns as ai } from "./shared/assistant/useConversationTurns.js";
79
+ import { isMultimodalBodyRejection as oi, isRecoverableAssistantError as si } from "./shared/assistant/transportErrors.js";
80
+ import { aiCreditsUpdatedEventName as ci, dispatchAssistantQuotaExhausted as li, notifyAiCreditsUpdated as ui } from "./shared/assistant/aiCredits.js";
81
+ import { useWorkspaceWriteAccess as di } from "./shared/assistant/useWorkspaceWriteAccess.js";
82
+ import { extractDocumentText as fi } from "./shared/assistant/documentExtract.js";
83
+ import { useAssistantAttachments as pi } from "./shared/assistant/useAssistantAttachments.js";
84
+ import { AssistantComposer as mi } from "./shared/assistant/ui/composer/AssistantComposer.js";
85
+ import { isProdRuntime as hi } from "./shared/assistant/env.js";
86
+ import { useAssistantHeartbeat as gi } from "./shared/assistant/useAssistantHeartbeat.js";
87
+ import { useAssistantKeyboardShortcuts as _i } from "./shared/assistant/useAssistantKeyboardShortcuts.js";
88
+ import { AssistantApiCallsConsentDialog as vi } from "./shared/assistant/ui/AssistantApiCallsConsentDialog.js";
89
+ import { AssistantChatArea as yi } from "./shared/assistant/ui/AssistantChatArea.js";
90
+ import { AIAssistantPanel as bi } from "./shared/assistant/ui/AIAssistantPanel.js";
91
+ export { bi as AIAssistantPanel, h as ASSISTANT_API_AUTH_STRATEGY, Mt as ASSISTANT_LANGUAGES, Fr as ASSISTANT_MODE_META, En as ATTACHMENT_ACCEPT, mr as ATTACHMENT_SOURCES, zr as AUTO_VOICE, vi as AssistantApiCallsConsentDialog, jr as AssistantAttachmentButton, Mr as AssistantAttachmentChips, br as AssistantAutoSpeakToggle, yi as AssistantChatArea, mi as AssistantComposer, $r as AssistantConversationList, ei as AssistantEmptyState, Qr as AssistantHeader, Gt as AssistantI18nProvider, Nr as AssistantLanguageSelector, xr as AssistantMarkdownImage, wr as AssistantMarkdownRenderer, Er as AssistantMessageAttachments, ti as AssistantMessageItem, ni as AssistantMessageList, Ir as AssistantModeSelector, Zr as AssistantMoreMenu, Dr as AssistantPendingWriteCard, Bt as AssistantProductProvider, Or as AssistantReplyLanguageSelector, G as AssistantRuntimeManager, kr as AssistantSpeakButton, sr as AssistantSpeechProvider, Ar as AssistantSpokenTurnsNotice, ar as AssistantToolActivity, Rr as AssistantVoiceButton, Vr as AssistantVoiceOrb, Br as AssistantVoiceSelector, ri as AssistantVoiceSession, Hr as AssistantVoiceSessionButton, Dn as AttachmentRejectedError, on as BOILERPLATE_PAGE_SHARE, o as CHECK_AI_CREDITS, s as CREATE_SANDBOX, pt as DEFAULT_SPEAKABLE_LABELS, Nt as DEFAULT_SPEECH_RATE, Be as ENDPOINT_GRACE_MS, c as EXTEND_SANDBOX_TTL, Pr as FOLLOW_APP_LOCALE, l as GET_ACTIVE_SANDBOXES, u as GET_SANDBOX, ge as HOSTED_TTS_MAX_CHARS, fe as HOSTED_TTS_TIER, pe as HOSTED_VOICES, $t as IDLE_PLAYBACK, Ve as INITIAL_SESSION, On as INLINE_IMAGE_MAX_DIM, kn as INLINE_IMAGE_QUALITY, He as INTERRUPT_MAX_MS, Ue as INTERRUPT_MIN_MS, An as MAX_ATTACHMENTS, sn as MAX_BOILERPLATE_LINE_CHARS, cn as MAX_EXTRACTED_CHARS, jn as MAX_FILE_BYTES, Mn as MAX_INLINE_CHARS_PER_FILE, Nn as MAX_INLINE_CHARS_TOTAL, rn as MAX_INLINE_IMAGE_BASE64_BYTES, Pn as MAX_INLINE_IMAGE_BASE64_CHARS, Fn as MAX_INLINE_IMAGE_PARTS, In as MAX_INLINE_TURN_BODY_BYTES, ln as MAX_PDF_PAGES_SCANNED, an as MAX_REQUEST_BODY_BYTES, mt as MAX_SPEAKABLE_CHARS, ht as MAX_SPOKEN_TABLE_ROWS, Ln as MAX_TURN_BODY_BYTES, un as MIN_PAGE_TEXT_CHARS, dn as MIN_TEXT_PAGE_SHARE, Tt as POLL_FAST_MS, Et as POLL_FAST_UNTIL_MS, Dt as POLL_SLOW_MS, Ot as POLL_STEADY_MS, kt as POLL_STEADY_UNTIL_MS, Ct as PREVIEW_LANGUAGES, Rn as PROMPT_ENVELOPE_RESERVE_BYTES, d as PROXY_SANDBOX_REQUEST, f as REPORT_AI_TOKEN_USAGE, _r as SANDBOX_READY_TTL_MS, We as SILENCE_SUBMIT_MS, _e as SPEAKING_RATE_MAX, ve as SPEAKING_RATE_MAX_STREAMING, ye as SPEAKING_RATE_MAX_SYNC, be as SPEAKING_RATE_MIN, gt as SPEECH_CHUNK_CHARS, _t as SPEECH_CHUNK_CJK_CHARS, Qe as SPEECH_LANG, Yt as SPOKEN_LABEL_LANGUAGES, p as STOP_ASSISTANT_SANDBOX, zn as TURN_BODY_HEADROOM_BYTES, $e as VOICE_LIST_TIMEOUT_MS, Ur as VoiceCaption, Wr as VoiceConversationView, Kr as VoiceMiniController, qr as VoiceStage, Jr as VoiceTranscriptDrawer, Gr as VoiceWaveform, m as WAIT_FOR_SANDBOX_RUNNING, ci as aiCreditsUpdatedEventName, Kt as assistantTranslationKey, Tr as assistantUrlTransform, hr as availableAttachmentSources, xe as base64ToBytes, de as browserSpeechEngine, T as buildAssistantSandboxEnv, Bn as buildAttachmentPromptBlock, ut as buildContinuedFromVoiceNote, K as buildProgress, Vn as buildPromptParts, E as buildPromptRequestBody, Hn as buildPromptWithAttachments, Se as buildRequest, i as buildSandboxContextInput, dt as buildVoiceTranscriptMarkdown, ie as chatTurns, D as checkAssistantAiCredits, vt as chunkForSpeech, Un as classifyAttachment, Ce as classifyHttpFailure, t as classifyQuotaError, fn as columnLetterToIndex, ke as configureSpeechEngine, yt as containsCjk, ur as copyToClipboard, Wn as countInlineImageCandidates, Gn as countInlinedImageParts, O as createAssistantSandbox, k as createAssistantSession, De as createHostedTtsEngine, vr as createReadinessTracker, Oe as createRoutingSpeechEngine, ne as createSandboxAssistantTransport, Ae as createSpeechEngines, we as decodeAudioResponse, pn as decodeXmlEntities, Kn as detectDocumentFormat, Zt as detectScriptLocale, gr as deviceHasCamera, li as dispatchAssistantQuotaExhausted, mn as docxXmlToText, A as downloadAssistantArtifact, Yr as downloadFile, qn as estimateTurnBodyBytes, a as executeSandboxGraphQL, Xr as exportConversation, j as extendAssistantSandboxTTL, fi as extractDocumentText, Pt as findAssistantLanguage, M as findExistingSandbox, Rt as findPendingWrite, hn as fitPdfPages, Jn as formatBytes, gn as formatPageRanges, dr as getActorId, N as getAssistantArtifacts, q as getAssistantMedia, P as getAssistantMessages, F as getAssistantSession, I as getAssistantStreamAccess, J as getAssistantText, Yn as getAttachmentSendBlocker, x as getCapability, Xn as getExtension, g as getImageForMode, _ as getImageTagForMode, fr as getOrganizationId, Y as getRawMessageCreatedAt, v as getResourcesForMode, y as getSandboxImageRegistry, Zn as getSendableAttachments, je as getSpeechEngine, X as getToolProgress, pr as getWorkspaceId, ae as groupBySession, oe as groupConsecutiveBySession, Qn as hasAttachmentWorkInFlight, me as hostedLocaleFor, he as hostedSupportsLanguage, Sr as imageHostLabel, Ge as isCapturing, Ke as isEcho, _n as isMostlyImagePages, oi as isMultimodalBodyRejection, hi as isProdRuntime, n as isQuotaExhaustedError, Z as isReapedSandboxConnectionError, yr as isRecentlyVerified, Q as isRecoverable, si as isRecoverableAssistantError, Cr as isRemoteImageSrc, en as isSpeakingMessage, et as isSpeechBlocked, qe as isSubmittable, ir as isTurnInFlight, S as isUnknownFieldError, se as isVoiceTurn, vn as joinSheets, tt as languageDisplayName, $ as mapSessionToHistory, C as markSupported, w as markUnsupported, ee as mergeMessagesById, Pe as micIsInterrupt, L as modeRequiresConfirmWrites, Lr as nextModeIndex, nt as normalizeLangTag, ui as notifyAiCreditsUpdated, Je as orbMode, yn as pageMarker, zt as parseConfirmationRefusal, $n as parseDataUrl, bn as parseSharedStrings, or as parseToolActivity, xn as parseWorkbookSheets, Sn as pdfTextItemsToPage, Ye as planReplyConsumption, At as pollDelayMs, rt as primaryLanguageSubtag, r as quotaExhaustedEventName, Me as readSpeechEngineConfig, It as replyFollowsInput, R as reportAssistantAiTokenUsage, tn as requiresCancel, Ne as resetSpeechEngine, Ft as resolveAssistantLanguage, Lt as resolveLanguagePair, Vt as resolveModeConfig, b as resolveSandboxAssistantMode, Qt as resolveSpeechLocale, te as sanitize, z as selectExistingAssistantSandbox, it as selectVoiceForLocale, B as sendAssistantPromptAsync, V as sendHeartbeat, Cn as sheetXmlToRows, Te as shouldDisableEngine, Fe as showsAssistantCaption, Ie as showsUserCaption, bt as speakableEmail, at as speechGate, Xt as speechLabelsFor, ot as speechLangForLocale, nn as speechPlaybackReducer, Ee as splitForVendor, xt as splitTableRow, Xe as spokenSoFar, H as stopReapedAssistantSandbox, wn as summarisePageText, jt as toCaptionText, er as toMessageAttachment, St as toSpeakableText, tr as truncateForInline, Tn as truncatePagesForInline, ii as useAssistantApiAccess, pi as useAssistantAttachments, gi as useAssistantHeartbeat, qt as useAssistantI18nNamespace, _i as useAssistantKeyboardShortcuts, Ht as useAssistantProduct, Ut as useAssistantProductOrNull, cr as useAssistantSpeech, Wt as useAssistantStorageFolders, rr as useAssistantStore, Jt as useAssistantTr, ai as useConversationTurns, re as useSandboxAssistantTransport, e as useVoiceInput, lr as useVoiceSession, di as useWorkspaceWriteAccess, nr as validateFile, st as voiceAvailability, ce as voiceMarker, wt as voicePreviewText, ct as voiceQualityRank, le as voiceSessionIdOf, Ze as voiceSessionReducer, Le as voiceStageState, ft as voiceTranscriptFilename, ue as voiceTurnsOnly, lt as voicesForLocale, U as waitForAssistantServiceReady, W as waitForSandboxRunning, Re as waveformIsActive, ze as waveformIsSettled };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@burdenoff/fe-libs",
3
- "version": "2026.904.28",
3
+ "version": "2026.905.1",
4
4
  "description": "Burdenoff frontend primitives and domain libraries",
5
5
  "type": "module",
6
6
  "bin": {