@assistant-ui/react 0.7.67 → 0.7.69
Sign up to get free protection for your applications and to get access to all the features.
- package/dist/primitives/index.d.ts +1 -0
- package/dist/primitives/index.d.ts.map +1 -1
- package/dist/primitives/index.js +5 -2
- package/dist/primitives/index.js.map +1 -1
- package/dist/primitives/index.mjs +3 -1
- package/dist/primitives/index.mjs.map +1 -1
- package/dist/primitives/thread/ThreadSuggestion.d.ts +2 -2
- package/dist/primitives/thread/ThreadSuggestion.d.ts.map +1 -1
- package/dist/primitives/thread/ThreadSuggestion.js +0 -1
- package/dist/primitives/thread/ThreadSuggestion.js.map +1 -1
- package/dist/primitives/thread/ThreadSuggestion.mjs +0 -1
- package/dist/primitives/thread/ThreadSuggestion.mjs.map +1 -1
- package/dist/runtimes/external-store/external-message-converter.d.ts +7 -2
- package/dist/runtimes/external-store/external-message-converter.d.ts.map +1 -1
- package/dist/runtimes/external-store/external-message-converter.js +21 -11
- package/dist/runtimes/external-store/external-message-converter.js.map +1 -1
- package/dist/runtimes/external-store/external-message-converter.mjs +21 -11
- package/dist/runtimes/external-store/external-message-converter.mjs.map +1 -1
- package/dist/styles/tailwindcss/thread.css +5 -5
- package/dist/styles/tailwindcss/thread.css.json +5 -5
- package/package.json +3 -3
- package/src/primitives/index.ts +1 -0
- package/src/primitives/thread/ThreadSuggestion.tsx +1 -2
- package/src/runtimes/external-store/external-message-converter.tsx +39 -11
- package/src/styles/tailwindcss/thread.css +5 -5
@@ -11,4 +11,5 @@ export * as ThreadListItemPrimitive from "./threadListItem";
|
|
11
11
|
export { useContentPartDisplay } from "./contentPart/useContentPartDisplay";
|
12
12
|
export { useContentPartImage } from "./contentPart/useContentPartImage";
|
13
13
|
export { useContentPartText } from "./contentPart/useContentPartText";
|
14
|
+
export { useThreadViewportAutoScroll } from "./thread/useThreadViewportAutoScroll";
|
14
15
|
//# sourceMappingURL=index.d.ts.map
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/primitives/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,kBAAkB,MAAM,aAAa,CAAC;AAClD,OAAO,KAAK,uBAAuB,MAAM,kBAAkB,CAAC;AAC5D,OAAO,KAAK,mBAAmB,MAAM,cAAc,CAAC;AACpD,OAAO,KAAK,qBAAqB,MAAM,gBAAgB,CAAC;AACxD,OAAO,KAAK,iBAAiB,MAAM,YAAY,CAAC;AAChD,OAAO,KAAK,oBAAoB,MAAM,eAAe,CAAC;AACtD,OAAO,KAAK,gBAAgB,MAAM,WAAW,CAAC;AAC9C,OAAO,KAAK,eAAe,MAAM,UAAU,CAAC;AAC5C,OAAO,KAAK,mBAAmB,MAAM,cAAc,CAAC;AACpD,OAAO,KAAK,uBAAuB,MAAM,kBAAkB,CAAC;AAE5D,OAAO,EAAE,qBAAqB,EAAE,MAAM,qCAAqC,CAAC;AAC5E,OAAO,EAAE,mBAAmB,EAAE,MAAM,mCAAmC,CAAC;AACxE,OAAO,EAAE,kBAAkB,EAAE,MAAM,kCAAkC,CAAC"}
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/primitives/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,kBAAkB,MAAM,aAAa,CAAC;AAClD,OAAO,KAAK,uBAAuB,MAAM,kBAAkB,CAAC;AAC5D,OAAO,KAAK,mBAAmB,MAAM,cAAc,CAAC;AACpD,OAAO,KAAK,qBAAqB,MAAM,gBAAgB,CAAC;AACxD,OAAO,KAAK,iBAAiB,MAAM,YAAY,CAAC;AAChD,OAAO,KAAK,oBAAoB,MAAM,eAAe,CAAC;AACtD,OAAO,KAAK,gBAAgB,MAAM,WAAW,CAAC;AAC9C,OAAO,KAAK,eAAe,MAAM,UAAU,CAAC;AAC5C,OAAO,KAAK,mBAAmB,MAAM,cAAc,CAAC;AACpD,OAAO,KAAK,uBAAuB,MAAM,kBAAkB,CAAC;AAE5D,OAAO,EAAE,qBAAqB,EAAE,MAAM,qCAAqC,CAAC;AAC5E,OAAO,EAAE,mBAAmB,EAAE,MAAM,mCAAmC,CAAC;AACxE,OAAO,EAAE,kBAAkB,EAAE,MAAM,kCAAkC,CAAC;AACtE,OAAO,EAAE,2BAA2B,EAAE,MAAM,sCAAsC,CAAC"}
|
package/dist/primitives/index.js
CHANGED
@@ -42,7 +42,8 @@ __export(primitives_exports, {
|
|
42
42
|
ThreadPrimitive: () => ThreadPrimitive,
|
43
43
|
useContentPartDisplay: () => import_useContentPartDisplay.useContentPartDisplay,
|
44
44
|
useContentPartImage: () => import_useContentPartImage.useContentPartImage,
|
45
|
-
useContentPartText: () => import_useContentPartText.useContentPartText
|
45
|
+
useContentPartText: () => import_useContentPartText.useContentPartText,
|
46
|
+
useThreadViewportAutoScroll: () => import_useThreadViewportAutoScroll.useThreadViewportAutoScroll
|
46
47
|
});
|
47
48
|
module.exports = __toCommonJS(primitives_exports);
|
48
49
|
var ActionBarPrimitive = __toESM(require("./actionBar/index.js"));
|
@@ -58,6 +59,7 @@ var ThreadListItemPrimitive = __toESM(require("./threadListItem/index.js"));
|
|
58
59
|
var import_useContentPartDisplay = require("./contentPart/useContentPartDisplay.js");
|
59
60
|
var import_useContentPartImage = require("./contentPart/useContentPartImage.js");
|
60
61
|
var import_useContentPartText = require("./contentPart/useContentPartText.js");
|
62
|
+
var import_useThreadViewportAutoScroll = require("./thread/useThreadViewportAutoScroll.js");
|
61
63
|
// Annotate the CommonJS export names for ESM import in node:
|
62
64
|
0 && (module.exports = {
|
63
65
|
ActionBarPrimitive,
|
@@ -72,6 +74,7 @@ var import_useContentPartText = require("./contentPart/useContentPartText.js");
|
|
72
74
|
ThreadPrimitive,
|
73
75
|
useContentPartDisplay,
|
74
76
|
useContentPartImage,
|
75
|
-
useContentPartText
|
77
|
+
useContentPartText,
|
78
|
+
useThreadViewportAutoScroll
|
76
79
|
});
|
77
80
|
//# sourceMappingURL=index.js.map
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../../src/primitives/index.ts"],"sourcesContent":["export * as ActionBarPrimitive from \"./actionBar\";\nexport * as AssistantModalPrimitive from \"./assistantModal\";\nexport * as AttachmentPrimitive from \"./attachment\";\nexport * as BranchPickerPrimitive from \"./branchPicker\";\nexport * as ComposerPrimitive from \"./composer\";\nexport * as ContentPartPrimitive from \"./contentPart\";\nexport * as MessagePrimitive from \"./message\";\nexport * as ThreadPrimitive from \"./thread\";\nexport * as ThreadListPrimitive from \"./threadList\";\nexport * as ThreadListItemPrimitive from \"./threadListItem\";\n\nexport { useContentPartDisplay } from \"./contentPart/useContentPartDisplay\";\nexport { useContentPartImage } from \"./contentPart/useContentPartImage\";\nexport { useContentPartText } from \"./contentPart/useContentPartText\";\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,yBAAoC;AACpC,8BAAyC;AACzC,0BAAqC;AACrC,4BAAuC;AACvC,wBAAmC;AACnC,2BAAsC;AACtC,uBAAkC;AAClC,sBAAiC;AACjC,0BAAqC;AACrC,8BAAyC;AAEzC,mCAAsC;AACtC,iCAAoC;AACpC,gCAAmC;","names":[]}
|
1
|
+
{"version":3,"sources":["../../src/primitives/index.ts"],"sourcesContent":["export * as ActionBarPrimitive from \"./actionBar\";\nexport * as AssistantModalPrimitive from \"./assistantModal\";\nexport * as AttachmentPrimitive from \"./attachment\";\nexport * as BranchPickerPrimitive from \"./branchPicker\";\nexport * as ComposerPrimitive from \"./composer\";\nexport * as ContentPartPrimitive from \"./contentPart\";\nexport * as MessagePrimitive from \"./message\";\nexport * as ThreadPrimitive from \"./thread\";\nexport * as ThreadListPrimitive from \"./threadList\";\nexport * as ThreadListItemPrimitive from \"./threadListItem\";\n\nexport { useContentPartDisplay } from \"./contentPart/useContentPartDisplay\";\nexport { useContentPartImage } from \"./contentPart/useContentPartImage\";\nexport { useContentPartText } from \"./contentPart/useContentPartText\";\nexport { useThreadViewportAutoScroll } from \"./thread/useThreadViewportAutoScroll\";\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,yBAAoC;AACpC,8BAAyC;AACzC,0BAAqC;AACrC,4BAAuC;AACvC,wBAAmC;AACnC,2BAAsC;AACtC,uBAAkC;AAClC,sBAAiC;AACjC,0BAAqC;AACrC,8BAAyC;AAEzC,mCAAsC;AACtC,iCAAoC;AACpC,gCAAmC;AACnC,yCAA4C;","names":[]}
|
@@ -12,6 +12,7 @@ import * as ThreadListItemPrimitive from "./threadListItem/index.mjs";
|
|
12
12
|
import { useContentPartDisplay } from "./contentPart/useContentPartDisplay.mjs";
|
13
13
|
import { useContentPartImage } from "./contentPart/useContentPartImage.mjs";
|
14
14
|
import { useContentPartText } from "./contentPart/useContentPartText.mjs";
|
15
|
+
import { useThreadViewportAutoScroll } from "./thread/useThreadViewportAutoScroll.mjs";
|
15
16
|
export {
|
16
17
|
ActionBarPrimitive,
|
17
18
|
AssistantModalPrimitive,
|
@@ -25,6 +26,7 @@ export {
|
|
25
26
|
ThreadPrimitive,
|
26
27
|
useContentPartDisplay,
|
27
28
|
useContentPartImage,
|
28
|
-
useContentPartText
|
29
|
+
useContentPartText,
|
30
|
+
useThreadViewportAutoScroll
|
29
31
|
};
|
30
32
|
//# sourceMappingURL=index.mjs.map
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../../src/primitives/index.ts"],"sourcesContent":["export * as ActionBarPrimitive from \"./actionBar\";\nexport * as AssistantModalPrimitive from \"./assistantModal\";\nexport * as AttachmentPrimitive from \"./attachment\";\nexport * as BranchPickerPrimitive from \"./branchPicker\";\nexport * as ComposerPrimitive from \"./composer\";\nexport * as ContentPartPrimitive from \"./contentPart\";\nexport * as MessagePrimitive from \"./message\";\nexport * as ThreadPrimitive from \"./thread\";\nexport * as ThreadListPrimitive from \"./threadList\";\nexport * as ThreadListItemPrimitive from \"./threadListItem\";\n\nexport { useContentPartDisplay } from \"./contentPart/useContentPartDisplay\";\nexport { useContentPartImage } from \"./contentPart/useContentPartImage\";\nexport { useContentPartText } from \"./contentPart/useContentPartText\";\n"],"mappings":";AAAA,YAAY,wBAAwB;AACpC,YAAY,6BAA6B;AACzC,YAAY,yBAAyB;AACrC,YAAY,2BAA2B;AACvC,YAAY,uBAAuB;AACnC,YAAY,0BAA0B;AACtC,YAAY,sBAAsB;AAClC,YAAY,qBAAqB;AACjC,YAAY,yBAAyB;AACrC,YAAY,6BAA6B;AAEzC,SAAS,6BAA6B;AACtC,SAAS,2BAA2B;AACpC,SAAS,0BAA0B;","names":[]}
|
1
|
+
{"version":3,"sources":["../../src/primitives/index.ts"],"sourcesContent":["export * as ActionBarPrimitive from \"./actionBar\";\nexport * as AssistantModalPrimitive from \"./assistantModal\";\nexport * as AttachmentPrimitive from \"./attachment\";\nexport * as BranchPickerPrimitive from \"./branchPicker\";\nexport * as ComposerPrimitive from \"./composer\";\nexport * as ContentPartPrimitive from \"./contentPart\";\nexport * as MessagePrimitive from \"./message\";\nexport * as ThreadPrimitive from \"./thread\";\nexport * as ThreadListPrimitive from \"./threadList\";\nexport * as ThreadListItemPrimitive from \"./threadListItem\";\n\nexport { useContentPartDisplay } from \"./contentPart/useContentPartDisplay\";\nexport { useContentPartImage } from \"./contentPart/useContentPartImage\";\nexport { useContentPartText } from \"./contentPart/useContentPartText\";\nexport { useThreadViewportAutoScroll } from \"./thread/useThreadViewportAutoScroll\";\n"],"mappings":";AAAA,YAAY,wBAAwB;AACpC,YAAY,6BAA6B;AACzC,YAAY,yBAAyB;AACrC,YAAY,2BAA2B;AACvC,YAAY,uBAAuB;AACnC,YAAY,0BAA0B;AACtC,YAAY,sBAAsB;AAClC,YAAY,qBAAqB;AACjC,YAAY,yBAAyB;AACrC,YAAY,6BAA6B;AAEzC,SAAS,6BAA6B;AACtC,SAAS,2BAA2B;AACpC,SAAS,0BAA0B;AACnC,SAAS,mCAAmC;","names":[]}
|
@@ -1,7 +1,7 @@
|
|
1
1
|
import { ActionButtonElement, ActionButtonProps } from "../../utils/createActionButton";
|
2
2
|
declare const useThreadSuggestion: ({ prompt, autoSend, }: {
|
3
3
|
prompt: string;
|
4
|
-
method
|
4
|
+
method?: "replace";
|
5
5
|
autoSend?: boolean | undefined;
|
6
6
|
}) => (() => void) | null;
|
7
7
|
export declare namespace ThreadPrimitiveSuggestion {
|
@@ -12,7 +12,7 @@ export declare const ThreadPrimitiveSuggestion: import("react").ForwardRefExotic
|
|
12
12
|
asChild?: boolean;
|
13
13
|
}, "ref"> & {
|
14
14
|
prompt: string;
|
15
|
-
method
|
15
|
+
method?: "replace";
|
16
16
|
autoSend?: boolean | undefined;
|
17
17
|
} & import("react").RefAttributes<HTMLButtonElement>>;
|
18
18
|
export {};
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"ThreadSuggestion.d.ts","sourceRoot":"","sources":["../../../src/primitives/thread/ThreadSuggestion.tsx"],"names":[],"mappings":"AAEA,OAAO,EACL,mBAAmB,EACnB,iBAAiB,EAElB,MAAM,gCAAgC,CAAC;AAKxC,QAAA,MAAM,mBAAmB,0BAGtB;IACD,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,SAAS,CAAC;
|
1
|
+
{"version":3,"file":"ThreadSuggestion.d.ts","sourceRoot":"","sources":["../../../src/primitives/thread/ThreadSuggestion.tsx"],"names":[],"mappings":"AAEA,OAAO,EACL,mBAAmB,EACnB,iBAAiB,EAElB,MAAM,gCAAgC,CAAC;AAKxC,QAAA,MAAM,mBAAmB,0BAGtB;IACD,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,SAAS,CAAC;IACnB,QAAQ,CAAC,EAAE,OAAO,GAAG,SAAS,CAAC;CAChC,wBAcA,CAAC;AAEF,yBAAiB,yBAAyB,CAAC;IACzC,KAAY,OAAO,GAAG,mBAAmB,CAAC;IAC1C,KAAY,KAAK,GAAG,iBAAiB,CAAC,OAAO,mBAAmB,CAAC,CAAC;CACnE;AAED,eAAO,MAAM,yBAAyB;;;YAxB5B,MAAM;aACL,SAAS;eACP,OAAO,GAAG,SAAS;qDA0B/B,CAAC"}
|
@@ -37,7 +37,6 @@ var useThreadSuggestion = ({
|
|
37
37
|
const callback = (0, import_react.useCallback)(() => {
|
38
38
|
if (autoSend && !threadRuntime.getState().isRunning) {
|
39
39
|
threadRuntime.append(prompt);
|
40
|
-
threadRuntime.composer.setText("");
|
41
40
|
} else {
|
42
41
|
threadRuntime.composer.setText(prompt);
|
43
42
|
}
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../../../src/primitives/thread/ThreadSuggestion.tsx"],"sourcesContent":["\"use client\";\n\nimport {\n ActionButtonElement,\n ActionButtonProps,\n createActionButton,\n} from \"../../utils/createActionButton\";\nimport { useCallback } from \"react\";\nimport { useThread } from \"../../context\";\nimport { useThreadRuntime } from \"../../context/react/ThreadContext\";\n\nconst useThreadSuggestion = ({\n prompt,\n autoSend,\n}: {\n prompt: string;\n method
|
1
|
+
{"version":3,"sources":["../../../src/primitives/thread/ThreadSuggestion.tsx"],"sourcesContent":["\"use client\";\n\nimport {\n ActionButtonElement,\n ActionButtonProps,\n createActionButton,\n} from \"../../utils/createActionButton\";\nimport { useCallback } from \"react\";\nimport { useThread } from \"../../context\";\nimport { useThreadRuntime } from \"../../context/react/ThreadContext\";\n\nconst useThreadSuggestion = ({\n prompt,\n autoSend,\n}: {\n prompt: string;\n method?: \"replace\";\n autoSend?: boolean | undefined;\n}) => {\n const threadRuntime = useThreadRuntime();\n\n const disabled = useThread((t) => t.isDisabled);\n const callback = useCallback(() => {\n if (autoSend && !threadRuntime.getState().isRunning) {\n threadRuntime.append(prompt);\n } else {\n threadRuntime.composer.setText(prompt);\n }\n }, [threadRuntime, autoSend, prompt]);\n\n if (disabled) return null;\n return callback;\n};\n\nexport namespace ThreadPrimitiveSuggestion {\n export type Element = ActionButtonElement;\n export type Props = ActionButtonProps<typeof useThreadSuggestion>;\n}\n\nexport const ThreadPrimitiveSuggestion = createActionButton(\n \"ThreadPrimitive.Suggestion\",\n useThreadSuggestion,\n [\"prompt\", \"autoSend\", \"method\"],\n);\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAEA,gCAIO;AACP,mBAA4B;AAC5B,qBAA0B;AAC1B,2BAAiC;AAEjC,IAAM,sBAAsB,CAAC;AAAA,EAC3B;AAAA,EACA;AACF,MAIM;AACJ,QAAM,oBAAgB,uCAAiB;AAEvC,QAAM,eAAW,0BAAU,CAAC,MAAM,EAAE,UAAU;AAC9C,QAAM,eAAW,0BAAY,MAAM;AACjC,QAAI,YAAY,CAAC,cAAc,SAAS,EAAE,WAAW;AACnD,oBAAc,OAAO,MAAM;AAAA,IAC7B,OAAO;AACL,oBAAc,SAAS,QAAQ,MAAM;AAAA,IACvC;AAAA,EACF,GAAG,CAAC,eAAe,UAAU,MAAM,CAAC;AAEpC,MAAI,SAAU,QAAO;AACrB,SAAO;AACT;AAOO,IAAM,gCAA4B;AAAA,EACvC;AAAA,EACA;AAAA,EACA,CAAC,UAAU,YAAY,QAAQ;AACjC;","names":[]}
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../../../src/primitives/thread/ThreadSuggestion.tsx"],"sourcesContent":["\"use client\";\n\nimport {\n ActionButtonElement,\n ActionButtonProps,\n createActionButton,\n} from \"../../utils/createActionButton\";\nimport { useCallback } from \"react\";\nimport { useThread } from \"../../context\";\nimport { useThreadRuntime } from \"../../context/react/ThreadContext\";\n\nconst useThreadSuggestion = ({\n prompt,\n autoSend,\n}: {\n prompt: string;\n method
|
1
|
+
{"version":3,"sources":["../../../src/primitives/thread/ThreadSuggestion.tsx"],"sourcesContent":["\"use client\";\n\nimport {\n ActionButtonElement,\n ActionButtonProps,\n createActionButton,\n} from \"../../utils/createActionButton\";\nimport { useCallback } from \"react\";\nimport { useThread } from \"../../context\";\nimport { useThreadRuntime } from \"../../context/react/ThreadContext\";\n\nconst useThreadSuggestion = ({\n prompt,\n autoSend,\n}: {\n prompt: string;\n method?: \"replace\";\n autoSend?: boolean | undefined;\n}) => {\n const threadRuntime = useThreadRuntime();\n\n const disabled = useThread((t) => t.isDisabled);\n const callback = useCallback(() => {\n if (autoSend && !threadRuntime.getState().isRunning) {\n threadRuntime.append(prompt);\n } else {\n threadRuntime.composer.setText(prompt);\n }\n }, [threadRuntime, autoSend, prompt]);\n\n if (disabled) return null;\n return callback;\n};\n\nexport namespace ThreadPrimitiveSuggestion {\n export type Element = ActionButtonElement;\n export type Props = ActionButtonProps<typeof useThreadSuggestion>;\n}\n\nexport const ThreadPrimitiveSuggestion = createActionButton(\n \"ThreadPrimitive.Suggestion\",\n useThreadSuggestion,\n [\"prompt\", \"autoSend\", \"method\"],\n);\n"],"mappings":";;;AAEA;AAAA,EAGE;AAAA,OACK;AACP,SAAS,mBAAmB;AAC5B,SAAS,iBAAiB;AAC1B,SAAS,wBAAwB;AAEjC,IAAM,sBAAsB,CAAC;AAAA,EAC3B;AAAA,EACA;AACF,MAIM;AACJ,QAAM,gBAAgB,iBAAiB;AAEvC,QAAM,WAAW,UAAU,CAAC,MAAM,EAAE,UAAU;AAC9C,QAAM,WAAW,YAAY,MAAM;AACjC,QAAI,YAAY,CAAC,cAAc,SAAS,EAAE,WAAW;AACnD,oBAAc,OAAO,MAAM;AAAA,IAC7B,OAAO;AACL,oBAAc,SAAS,QAAQ,MAAM;AAAA,IACvC;AAAA,EACF,GAAG,CAAC,eAAe,UAAU,MAAM,CAAC;AAEpC,MAAI,SAAU,QAAO;AACrB,SAAO;AACT;AAOO,IAAM,4BAA4B;AAAA,EACvC;AAAA,EACA;AAAA,EACA,CAAC,UAAU,YAAY,QAAQ;AACjC;","names":[]}
|
@@ -1,6 +1,10 @@
|
|
1
1
|
import { ThreadMessageLike } from "./ThreadMessageLike";
|
2
2
|
export declare namespace useExternalMessageConverter {
|
3
|
-
type Message = ThreadMessageLike
|
3
|
+
type Message = (ThreadMessageLike & {
|
4
|
+
readonly convertConfig?: {
|
5
|
+
readonly joinStrategy?: "concat-content" | "none";
|
6
|
+
};
|
7
|
+
}) | {
|
4
8
|
role: "tool";
|
5
9
|
toolCallId: string;
|
6
10
|
toolName?: string | undefined;
|
@@ -9,9 +13,10 @@ export declare namespace useExternalMessageConverter {
|
|
9
13
|
type Callback<T> = (message: T) => Message | Message[];
|
10
14
|
}
|
11
15
|
export declare const convertExternalMessages: <T extends WeakKey>(messages: T[], callback: useExternalMessageConverter.Callback<T>, isRunning: boolean) => import("../..").ThreadMessage[];
|
12
|
-
export declare const useExternalMessageConverter: <T extends WeakKey>({ callback, messages, isRunning, }: {
|
16
|
+
export declare const useExternalMessageConverter: <T extends WeakKey>({ callback, messages, isRunning, joinStrategy, }: {
|
13
17
|
callback: useExternalMessageConverter.Callback<T>;
|
14
18
|
messages: T[];
|
15
19
|
isRunning: boolean;
|
20
|
+
joinStrategy?: "concat-content" | "none";
|
16
21
|
}) => import("../..").ThreadMessage[];
|
17
22
|
//# sourceMappingURL=external-message-converter.d.ts.map
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"external-message-converter.d.ts","sourceRoot":"","sources":["../../../src/runtimes/external-store/external-message-converter.tsx"],"names":[],"mappings":"AAQA,OAAO,EAAyB,iBAAiB,EAAE,MAAM,qBAAqB,CAAC;AAI/E,yBAAiB,2BAA2B,CAAC;IAC3C,KAAY,OAAO,GACf,iBAAiB,
|
1
|
+
{"version":3,"file":"external-message-converter.d.ts","sourceRoot":"","sources":["../../../src/runtimes/external-store/external-message-converter.tsx"],"names":[],"mappings":"AAQA,OAAO,EAAyB,iBAAiB,EAAE,MAAM,qBAAqB,CAAC;AAI/E,yBAAiB,2BAA2B,CAAC;IAC3C,KAAY,OAAO,GACf,CAAC,iBAAiB,GAAG;QACnB,QAAQ,CAAC,aAAa,CAAC,EAAE;YACvB,QAAQ,CAAC,YAAY,CAAC,EAAE,gBAAgB,GAAG,MAAM,CAAC;SACnD,CAAC;KACH,CAAC,GACF;QACE,IAAI,EAAE,MAAM,CAAC;QACb,UAAU,EAAE,MAAM,CAAC;QACnB,QAAQ,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;QAC9B,MAAM,EAAE,GAAG,CAAC;KACb,CAAC;IAEN,KAAY,QAAQ,CAAC,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,KAAK,OAAO,GAAG,OAAO,EAAE,CAAC;CAC/D;AAqLD,eAAO,MAAM,uBAAuB,GAAI,CAAC,SAAS,OAAO,YAC7C,CAAC,EAAE,YACH,2BAA2B,CAAC,QAAQ,CAAC,CAAC,CAAC,aACtC,OAAO,oCAuBnB,CAAC;AAEF,eAAO,MAAM,2BAA2B,GAAI,CAAC,SAAS,OAAO,oDAK1D;IACD,QAAQ,EAAE,2BAA2B,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC;IAClD,QAAQ,EAAE,CAAC,EAAE,CAAC;IACd,SAAS,EAAE,OAAO,CAAC;IACnB,YAAY,CAAC,EAAE,gBAAgB,GAAG,MAAM,CAAC;CAC1C,oCA0EA,CAAC"}
|
@@ -126,9 +126,10 @@ var joinExternalMessages = (messages) => {
|
|
126
126
|
}
|
127
127
|
return assistantMessage;
|
128
128
|
};
|
129
|
-
var chunkExternalMessages = (callbackResults) => {
|
129
|
+
var chunkExternalMessages = (callbackResults, joinStrategy) => {
|
130
130
|
const results = [];
|
131
131
|
let isAssistant = false;
|
132
|
+
let pendingNone = false;
|
132
133
|
let inputs = [];
|
133
134
|
let outputs = [];
|
134
135
|
const flush = () => {
|
@@ -140,10 +141,12 @@ var chunkExternalMessages = (callbackResults) => {
|
|
140
141
|
}
|
141
142
|
inputs = [];
|
142
143
|
outputs = [];
|
144
|
+
isAssistant = false;
|
145
|
+
pendingNone = false;
|
143
146
|
};
|
144
147
|
for (const callbackResult of callbackResults) {
|
145
148
|
for (const output of callbackResult.outputs) {
|
146
|
-
if (!isAssistant || output.role === "user" || output.role === "system") {
|
149
|
+
if (pendingNone && output.role !== "tool" || !isAssistant || output.role === "user" || output.role === "system") {
|
147
150
|
flush();
|
148
151
|
}
|
149
152
|
isAssistant = output.role === "assistant" || output.role === "tool";
|
@@ -151,6 +154,9 @@ var chunkExternalMessages = (callbackResults) => {
|
|
151
154
|
inputs.push(callbackResult.input);
|
152
155
|
}
|
153
156
|
outputs.push(output);
|
157
|
+
if (output.role === "assistant" && (output.convertConfig?.joinStrategy === "none" || joinStrategy === "none")) {
|
158
|
+
pendingNone = true;
|
159
|
+
}
|
154
160
|
}
|
155
161
|
}
|
156
162
|
flush();
|
@@ -180,7 +186,8 @@ var convertExternalMessages = (messages, callback, isRunning) => {
|
|
180
186
|
var useExternalMessageConverter = ({
|
181
187
|
callback,
|
182
188
|
messages,
|
183
|
-
isRunning
|
189
|
+
isRunning,
|
190
|
+
joinStrategy
|
184
191
|
}) => {
|
185
192
|
const state = (0, import_react.useMemo)(
|
186
193
|
() => ({
|
@@ -203,14 +210,17 @@ var useExternalMessageConverter = ({
|
|
203
210
|
}
|
204
211
|
callbackResults.push(result);
|
205
212
|
}
|
206
|
-
const chunks = chunkExternalMessages(callbackResults).map(
|
207
|
-
|
208
|
-
|
209
|
-
|
210
|
-
|
211
|
-
|
212
|
-
|
213
|
-
|
213
|
+
const chunks = chunkExternalMessages(callbackResults, joinStrategy).map(
|
214
|
+
(m) => {
|
215
|
+
const key = m.outputs[0];
|
216
|
+
if (!key) return m;
|
217
|
+
const cached = state.chunkCache.get(key);
|
218
|
+
if (cached && shallowArrayEqual(cached.outputs, m.outputs))
|
219
|
+
return cached;
|
220
|
+
state.chunkCache.set(key, m);
|
221
|
+
return m;
|
222
|
+
}
|
223
|
+
);
|
214
224
|
const threadMessages = state.converterCache.convertMessages(
|
215
225
|
chunks,
|
216
226
|
(cache, message, idx) => {
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../../../src/runtimes/external-store/external-message-converter.tsx"],"sourcesContent":["\"use client\";\n\nimport { useMemo } from \"react\";\nimport { ThreadMessageConverter } from \"./ThreadMessageConverter\";\nimport {\n getExternalStoreMessages,\n symbolInnerMessage,\n} from \"./getExternalStoreMessage\";\nimport { fromThreadMessageLike, ThreadMessageLike } from \"./ThreadMessageLike\";\nimport { getAutoStatus, isAutoStatus } from \"./auto-status\";\nimport { ToolCallContentPart } from \"../../types\";\n\nexport namespace useExternalMessageConverter {\n export type Message =\n | ThreadMessageLike\n | {\n role: \"tool\";\n toolCallId: string;\n toolName?: string | undefined;\n result: any;\n };\n\n export type Callback<T> = (message: T) => Message | Message[];\n}\n\ntype CallbackResult<T> = {\n input: T;\n outputs: useExternalMessageConverter.Message[];\n};\n\ntype ChunkResult<T> = {\n inputs: T[];\n outputs: useExternalMessageConverter.Message[];\n};\n\ntype Mutable<T> = {\n -readonly [P in keyof T]: T[P];\n};\n\nconst joinExternalMessages = (\n messages: readonly useExternalMessageConverter.Message[],\n): ThreadMessageLike => {\n const assistantMessage: Mutable<Omit<ThreadMessageLike, \"metadata\">> & {\n content: Exclude<ThreadMessageLike[\"content\"][0], string>[];\n metadata?: Mutable<ThreadMessageLike[\"metadata\"]>;\n } = {\n role: \"assistant\",\n content: [],\n };\n for (const output of messages) {\n if (output.role === \"tool\") {\n const toolCallIdx = assistantMessage.content.findIndex(\n (c) => c.type === \"tool-call\" && c.toolCallId === output.toolCallId,\n );\n if (toolCallIdx !== -1) {\n const toolCall = assistantMessage.content[\n toolCallIdx\n ]! as ToolCallContentPart;\n if (output.toolName) {\n if (toolCall.toolName !== output.toolName)\n throw new Error(\n `Tool call name ${output.toolCallId} ${output.toolName} does not match existing tool call ${toolCall.toolName}`,\n );\n }\n assistantMessage.content[toolCallIdx] = {\n ...toolCall,\n ...{\n [symbolInnerMessage]: [\n ...((toolCall as any)[symbolInnerMessage] ?? []),\n output,\n ],\n },\n result: output.result,\n };\n } else {\n throw new Error(\n `Tool call ${output.toolCallId} ${output.toolName} not found in assistant message`,\n );\n }\n } else {\n const role = output.role;\n const content = (\n typeof output.content === \"string\"\n ? [{ type: \"text\" as const, text: output.content }]\n : output.content\n ).map((c) => ({\n ...c,\n ...{ [symbolInnerMessage]: [output] },\n }));\n switch (role) {\n case \"system\":\n case \"user\":\n return {\n ...output,\n content,\n };\n case \"assistant\":\n if (assistantMessage.content.length === 0) {\n assistantMessage.id = output.id;\n assistantMessage.createdAt ??= output.createdAt;\n assistantMessage.status ??= output.status;\n\n if (output.attachments) {\n assistantMessage.attachments = [\n ...(assistantMessage.attachments ?? []),\n ...output.attachments,\n ];\n }\n\n if (output.metadata) {\n assistantMessage.metadata ??= {};\n if (output.metadata.unstable_annotations) {\n assistantMessage.metadata.unstable_annotations = [\n ...(assistantMessage.metadata.unstable_annotations ?? []),\n ...output.metadata.unstable_annotations,\n ];\n }\n if (output.metadata.unstable_data) {\n assistantMessage.metadata.unstable_data = [\n ...(assistantMessage.metadata.unstable_data ?? []),\n ...output.metadata.unstable_data,\n ];\n }\n if (output.metadata.steps) {\n assistantMessage.metadata.steps = [\n ...(assistantMessage.metadata.steps ?? []),\n ...output.metadata.steps,\n ];\n }\n if (output.metadata.custom) {\n assistantMessage.metadata.custom = {\n ...(assistantMessage.metadata.custom ?? {}),\n ...output.metadata.custom,\n };\n }\n }\n // TODO keep this in sync\n }\n\n assistantMessage.content.push(...content);\n break;\n default: {\n const unsupportedRole: never = role;\n throw new Error(`Unknown message role: ${unsupportedRole}`);\n }\n }\n }\n }\n return assistantMessage;\n};\n\nconst chunkExternalMessages = <T,>(callbackResults: CallbackResult<T>[]) => {\n const results: ChunkResult<T>[] = [];\n let isAssistant = false;\n let inputs: T[] = [];\n let outputs: useExternalMessageConverter.Message[] = [];\n\n const flush = () => {\n if (outputs.length) {\n results.push({\n inputs,\n outputs,\n });\n }\n inputs = [];\n outputs = [];\n };\n\n for (const callbackResult of callbackResults) {\n for (const output of callbackResult.outputs) {\n if (!isAssistant || output.role === \"user\" || output.role === \"system\") {\n flush();\n }\n isAssistant = output.role === \"assistant\" || output.role === \"tool\";\n\n if (inputs.at(-1) !== callbackResult.input) {\n inputs.push(callbackResult.input);\n }\n outputs.push(output);\n }\n }\n flush();\n return results;\n};\n\nexport const convertExternalMessages = <T extends WeakKey>(\n messages: T[],\n callback: useExternalMessageConverter.Callback<T>,\n isRunning: boolean,\n) => {\n const callbackResults: CallbackResult<T>[] = [];\n for (const message of messages) {\n const output = callback(message);\n const outputs = Array.isArray(output) ? output : [output];\n const result = { input: message, outputs };\n callbackResults.push(result);\n }\n\n const chunks = chunkExternalMessages(callbackResults);\n\n return chunks.map((message, idx) => {\n const isLast = idx === chunks.length - 1;\n const autoStatus = getAutoStatus(isLast, isRunning);\n const newMessage = fromThreadMessageLike(\n joinExternalMessages(message.outputs),\n idx.toString(),\n autoStatus,\n );\n (newMessage as any)[symbolInnerMessage] = message.inputs;\n return newMessage;\n });\n};\n\nexport const useExternalMessageConverter = <T extends WeakKey>({\n callback,\n messages,\n isRunning,\n}: {\n callback: useExternalMessageConverter.Callback<T>;\n messages: T[];\n isRunning: boolean;\n}) => {\n const state = useMemo(\n () => ({\n callback,\n callbackCache: new WeakMap<T, CallbackResult<T>>(),\n chunkCache: new WeakMap<\n useExternalMessageConverter.Message,\n ChunkResult<T>\n >(),\n converterCache: new ThreadMessageConverter(),\n }),\n [callback],\n );\n\n return useMemo(() => {\n const callbackResults: CallbackResult<T>[] = [];\n for (const message of messages) {\n let result = state.callbackCache.get(message);\n if (!result) {\n const output = state.callback(message);\n const outputs = Array.isArray(output) ? output : [output];\n result = { input: message, outputs };\n state.callbackCache.set(message, result);\n }\n callbackResults.push(result);\n }\n\n const chunks = chunkExternalMessages(callbackResults).map((m) => {\n const key = m.outputs[0];\n if (!key) return m;\n\n const cached = state.chunkCache.get(key);\n if (cached && shallowArrayEqual(cached.outputs, m.outputs)) return cached;\n state.chunkCache.set(key, m);\n return m;\n });\n\n const threadMessages = state.converterCache.convertMessages(\n chunks,\n (cache, message, idx) => {\n const isLast = idx === chunks.length - 1;\n const autoStatus = getAutoStatus(isLast, isRunning);\n\n if (\n cache &&\n (cache.role !== \"assistant\" ||\n !isAutoStatus(cache.status) ||\n cache.status === autoStatus)\n ) {\n const inputs = getExternalStoreMessages<T>(cache);\n if (shallowArrayEqual(inputs, message.inputs)) {\n return cache;\n }\n }\n\n const newMessage = fromThreadMessageLike(\n joinExternalMessages(message.outputs),\n idx.toString(),\n autoStatus,\n );\n (newMessage as any)[symbolInnerMessage] = message.inputs;\n return newMessage;\n },\n );\n\n (threadMessages as unknown as { [symbolInnerMessage]: T[] })[\n symbolInnerMessage\n ] = messages;\n\n return threadMessages;\n }, [state, messages, isRunning]);\n};\n\nconst shallowArrayEqual = (a: unknown[], b: unknown[]) => {\n if (a.length !== b.length) return false;\n for (let i = 0; i < a.length; i++) {\n if (a[i] !== b[i]) return false;\n }\n return true;\n};\n"],"mappings":"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","names":[]}
|
1
|
+
{"version":3,"sources":["../../../src/runtimes/external-store/external-message-converter.tsx"],"sourcesContent":["\"use client\";\n\nimport { useMemo } from \"react\";\nimport { ThreadMessageConverter } from \"./ThreadMessageConverter\";\nimport {\n getExternalStoreMessages,\n symbolInnerMessage,\n} from \"./getExternalStoreMessage\";\nimport { fromThreadMessageLike, ThreadMessageLike } from \"./ThreadMessageLike\";\nimport { getAutoStatus, isAutoStatus } from \"./auto-status\";\nimport { ToolCallContentPart } from \"../../types\";\n\nexport namespace useExternalMessageConverter {\n export type Message =\n | (ThreadMessageLike & {\n readonly convertConfig?: {\n readonly joinStrategy?: \"concat-content\" | \"none\";\n };\n })\n | {\n role: \"tool\";\n toolCallId: string;\n toolName?: string | undefined;\n result: any;\n };\n\n export type Callback<T> = (message: T) => Message | Message[];\n}\n\ntype CallbackResult<T> = {\n input: T;\n outputs: useExternalMessageConverter.Message[];\n};\n\ntype ChunkResult<T> = {\n inputs: T[];\n outputs: useExternalMessageConverter.Message[];\n};\n\ntype Mutable<T> = {\n -readonly [P in keyof T]: T[P];\n};\n\nconst joinExternalMessages = (\n messages: readonly useExternalMessageConverter.Message[],\n): ThreadMessageLike => {\n const assistantMessage: Mutable<Omit<ThreadMessageLike, \"metadata\">> & {\n content: Exclude<ThreadMessageLike[\"content\"][0], string>[];\n metadata?: Mutable<ThreadMessageLike[\"metadata\"]>;\n } = {\n role: \"assistant\",\n content: [],\n };\n for (const output of messages) {\n if (output.role === \"tool\") {\n const toolCallIdx = assistantMessage.content.findIndex(\n (c) => c.type === \"tool-call\" && c.toolCallId === output.toolCallId,\n );\n if (toolCallIdx !== -1) {\n const toolCall = assistantMessage.content[\n toolCallIdx\n ]! as ToolCallContentPart;\n if (output.toolName) {\n if (toolCall.toolName !== output.toolName)\n throw new Error(\n `Tool call name ${output.toolCallId} ${output.toolName} does not match existing tool call ${toolCall.toolName}`,\n );\n }\n assistantMessage.content[toolCallIdx] = {\n ...toolCall,\n ...{\n [symbolInnerMessage]: [\n ...((toolCall as any)[symbolInnerMessage] ?? []),\n output,\n ],\n },\n result: output.result,\n };\n } else {\n throw new Error(\n `Tool call ${output.toolCallId} ${output.toolName} not found in assistant message`,\n );\n }\n } else {\n const role = output.role;\n const content = (\n typeof output.content === \"string\"\n ? [{ type: \"text\" as const, text: output.content }]\n : output.content\n ).map((c) => ({\n ...c,\n ...{ [symbolInnerMessage]: [output] },\n }));\n switch (role) {\n case \"system\":\n case \"user\":\n return {\n ...output,\n content,\n };\n case \"assistant\":\n if (assistantMessage.content.length === 0) {\n assistantMessage.id = output.id;\n assistantMessage.createdAt ??= output.createdAt;\n assistantMessage.status ??= output.status;\n\n if (output.attachments) {\n assistantMessage.attachments = [\n ...(assistantMessage.attachments ?? []),\n ...output.attachments,\n ];\n }\n\n if (output.metadata) {\n assistantMessage.metadata ??= {};\n if (output.metadata.unstable_annotations) {\n assistantMessage.metadata.unstable_annotations = [\n ...(assistantMessage.metadata.unstable_annotations ?? []),\n ...output.metadata.unstable_annotations,\n ];\n }\n if (output.metadata.unstable_data) {\n assistantMessage.metadata.unstable_data = [\n ...(assistantMessage.metadata.unstable_data ?? []),\n ...output.metadata.unstable_data,\n ];\n }\n if (output.metadata.steps) {\n assistantMessage.metadata.steps = [\n ...(assistantMessage.metadata.steps ?? []),\n ...output.metadata.steps,\n ];\n }\n if (output.metadata.custom) {\n assistantMessage.metadata.custom = {\n ...(assistantMessage.metadata.custom ?? {}),\n ...output.metadata.custom,\n };\n }\n }\n // TODO keep this in sync\n }\n\n assistantMessage.content.push(...content);\n break;\n default: {\n const unsupportedRole: never = role;\n throw new Error(`Unknown message role: ${unsupportedRole}`);\n }\n }\n }\n }\n return assistantMessage;\n};\n\nconst chunkExternalMessages = <T,>(\n callbackResults: CallbackResult<T>[],\n joinStrategy?: \"concat-content\" | \"none\",\n) => {\n const results: ChunkResult<T>[] = [];\n let isAssistant = false;\n let pendingNone = false; // true if the previous assistant message had joinStrategy \"none\"\n let inputs: T[] = [];\n let outputs: useExternalMessageConverter.Message[] = [];\n\n const flush = () => {\n if (outputs.length) {\n results.push({\n inputs,\n outputs,\n });\n }\n inputs = [];\n outputs = [];\n isAssistant = false;\n pendingNone = false;\n };\n\n for (const callbackResult of callbackResults) {\n for (const output of callbackResult.outputs) {\n if (\n (pendingNone && output.role !== \"tool\") ||\n !isAssistant ||\n output.role === \"user\" ||\n output.role === \"system\"\n ) {\n flush();\n }\n isAssistant = output.role === \"assistant\" || output.role === \"tool\";\n\n if (inputs.at(-1) !== callbackResult.input) {\n inputs.push(callbackResult.input);\n }\n outputs.push(output);\n\n if (\n output.role === \"assistant\" &&\n (output.convertConfig?.joinStrategy === \"none\" ||\n joinStrategy === \"none\")\n ) {\n pendingNone = true;\n }\n }\n }\n flush();\n return results;\n};\n\nexport const convertExternalMessages = <T extends WeakKey>(\n messages: T[],\n callback: useExternalMessageConverter.Callback<T>,\n isRunning: boolean,\n) => {\n const callbackResults: CallbackResult<T>[] = [];\n for (const message of messages) {\n const output = callback(message);\n const outputs = Array.isArray(output) ? output : [output];\n const result = { input: message, outputs };\n callbackResults.push(result);\n }\n\n const chunks = chunkExternalMessages(callbackResults);\n\n return chunks.map((message, idx) => {\n const isLast = idx === chunks.length - 1;\n const autoStatus = getAutoStatus(isLast, isRunning);\n const newMessage = fromThreadMessageLike(\n joinExternalMessages(message.outputs),\n idx.toString(),\n autoStatus,\n );\n (newMessage as any)[symbolInnerMessage] = message.inputs;\n return newMessage;\n });\n};\n\nexport const useExternalMessageConverter = <T extends WeakKey>({\n callback,\n messages,\n isRunning,\n joinStrategy,\n}: {\n callback: useExternalMessageConverter.Callback<T>;\n messages: T[];\n isRunning: boolean;\n joinStrategy?: \"concat-content\" | \"none\";\n}) => {\n const state = useMemo(\n () => ({\n callback,\n callbackCache: new WeakMap<T, CallbackResult<T>>(),\n chunkCache: new WeakMap<\n useExternalMessageConverter.Message,\n ChunkResult<T>\n >(),\n converterCache: new ThreadMessageConverter(),\n }),\n [callback],\n );\n\n return useMemo(() => {\n const callbackResults: CallbackResult<T>[] = [];\n for (const message of messages) {\n let result = state.callbackCache.get(message);\n if (!result) {\n const output = state.callback(message);\n const outputs = Array.isArray(output) ? output : [output];\n result = { input: message, outputs };\n state.callbackCache.set(message, result);\n }\n callbackResults.push(result);\n }\n\n const chunks = chunkExternalMessages(callbackResults, joinStrategy).map(\n (m) => {\n const key = m.outputs[0];\n if (!key) return m;\n\n const cached = state.chunkCache.get(key);\n if (cached && shallowArrayEqual(cached.outputs, m.outputs))\n return cached;\n state.chunkCache.set(key, m);\n return m;\n },\n );\n\n const threadMessages = state.converterCache.convertMessages(\n chunks,\n (cache, message, idx) => {\n const isLast = idx === chunks.length - 1;\n const autoStatus = getAutoStatus(isLast, isRunning);\n\n if (\n cache &&\n (cache.role !== \"assistant\" ||\n !isAutoStatus(cache.status) ||\n cache.status === autoStatus)\n ) {\n const inputs = getExternalStoreMessages<T>(cache);\n if (shallowArrayEqual(inputs, message.inputs)) {\n return cache;\n }\n }\n\n const newMessage = fromThreadMessageLike(\n joinExternalMessages(message.outputs),\n idx.toString(),\n autoStatus,\n );\n (newMessage as any)[symbolInnerMessage] = message.inputs;\n return newMessage;\n },\n );\n\n (threadMessages as unknown as { [symbolInnerMessage]: T[] })[\n symbolInnerMessage\n ] = messages;\n\n return threadMessages;\n }, [state, messages, isRunning]);\n};\n\nconst shallowArrayEqual = (a: unknown[], b: unknown[]) => {\n if (a.length !== b.length) return false;\n for (let i = 0; i < a.length; i++) {\n if (a[i] !== b[i]) return false;\n }\n return true;\n};\n"],"mappings":"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","names":[]}
|
@@ -105,9 +105,10 @@ var joinExternalMessages = (messages) => {
|
|
105
105
|
}
|
106
106
|
return assistantMessage;
|
107
107
|
};
|
108
|
-
var chunkExternalMessages = (callbackResults) => {
|
108
|
+
var chunkExternalMessages = (callbackResults, joinStrategy) => {
|
109
109
|
const results = [];
|
110
110
|
let isAssistant = false;
|
111
|
+
let pendingNone = false;
|
111
112
|
let inputs = [];
|
112
113
|
let outputs = [];
|
113
114
|
const flush = () => {
|
@@ -119,10 +120,12 @@ var chunkExternalMessages = (callbackResults) => {
|
|
119
120
|
}
|
120
121
|
inputs = [];
|
121
122
|
outputs = [];
|
123
|
+
isAssistant = false;
|
124
|
+
pendingNone = false;
|
122
125
|
};
|
123
126
|
for (const callbackResult of callbackResults) {
|
124
127
|
for (const output of callbackResult.outputs) {
|
125
|
-
if (!isAssistant || output.role === "user" || output.role === "system") {
|
128
|
+
if (pendingNone && output.role !== "tool" || !isAssistant || output.role === "user" || output.role === "system") {
|
126
129
|
flush();
|
127
130
|
}
|
128
131
|
isAssistant = output.role === "assistant" || output.role === "tool";
|
@@ -130,6 +133,9 @@ var chunkExternalMessages = (callbackResults) => {
|
|
130
133
|
inputs.push(callbackResult.input);
|
131
134
|
}
|
132
135
|
outputs.push(output);
|
136
|
+
if (output.role === "assistant" && (output.convertConfig?.joinStrategy === "none" || joinStrategy === "none")) {
|
137
|
+
pendingNone = true;
|
138
|
+
}
|
133
139
|
}
|
134
140
|
}
|
135
141
|
flush();
|
@@ -159,7 +165,8 @@ var convertExternalMessages = (messages, callback, isRunning) => {
|
|
159
165
|
var useExternalMessageConverter = ({
|
160
166
|
callback,
|
161
167
|
messages,
|
162
|
-
isRunning
|
168
|
+
isRunning,
|
169
|
+
joinStrategy
|
163
170
|
}) => {
|
164
171
|
const state = useMemo(
|
165
172
|
() => ({
|
@@ -182,14 +189,17 @@ var useExternalMessageConverter = ({
|
|
182
189
|
}
|
183
190
|
callbackResults.push(result);
|
184
191
|
}
|
185
|
-
const chunks = chunkExternalMessages(callbackResults).map(
|
186
|
-
|
187
|
-
|
188
|
-
|
189
|
-
|
190
|
-
|
191
|
-
|
192
|
-
|
192
|
+
const chunks = chunkExternalMessages(callbackResults, joinStrategy).map(
|
193
|
+
(m) => {
|
194
|
+
const key = m.outputs[0];
|
195
|
+
if (!key) return m;
|
196
|
+
const cached = state.chunkCache.get(key);
|
197
|
+
if (cached && shallowArrayEqual(cached.outputs, m.outputs))
|
198
|
+
return cached;
|
199
|
+
state.chunkCache.set(key, m);
|
200
|
+
return m;
|
201
|
+
}
|
202
|
+
);
|
193
203
|
const threadMessages = state.converterCache.convertMessages(
|
194
204
|
chunks,
|
195
205
|
(cache, message, idx) => {
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"sources":["../../../src/runtimes/external-store/external-message-converter.tsx"],"sourcesContent":["\"use client\";\n\nimport { useMemo } from \"react\";\nimport { ThreadMessageConverter } from \"./ThreadMessageConverter\";\nimport {\n getExternalStoreMessages,\n symbolInnerMessage,\n} from \"./getExternalStoreMessage\";\nimport { fromThreadMessageLike, ThreadMessageLike } from \"./ThreadMessageLike\";\nimport { getAutoStatus, isAutoStatus } from \"./auto-status\";\nimport { ToolCallContentPart } from \"../../types\";\n\nexport namespace useExternalMessageConverter {\n export type Message =\n | ThreadMessageLike\n | {\n role: \"tool\";\n toolCallId: string;\n toolName?: string | undefined;\n result: any;\n };\n\n export type Callback<T> = (message: T) => Message | Message[];\n}\n\ntype CallbackResult<T> = {\n input: T;\n outputs: useExternalMessageConverter.Message[];\n};\n\ntype ChunkResult<T> = {\n inputs: T[];\n outputs: useExternalMessageConverter.Message[];\n};\n\ntype Mutable<T> = {\n -readonly [P in keyof T]: T[P];\n};\n\nconst joinExternalMessages = (\n messages: readonly useExternalMessageConverter.Message[],\n): ThreadMessageLike => {\n const assistantMessage: Mutable<Omit<ThreadMessageLike, \"metadata\">> & {\n content: Exclude<ThreadMessageLike[\"content\"][0], string>[];\n metadata?: Mutable<ThreadMessageLike[\"metadata\"]>;\n } = {\n role: \"assistant\",\n content: [],\n };\n for (const output of messages) {\n if (output.role === \"tool\") {\n const toolCallIdx = assistantMessage.content.findIndex(\n (c) => c.type === \"tool-call\" && c.toolCallId === output.toolCallId,\n );\n if (toolCallIdx !== -1) {\n const toolCall = assistantMessage.content[\n toolCallIdx\n ]! as ToolCallContentPart;\n if (output.toolName) {\n if (toolCall.toolName !== output.toolName)\n throw new Error(\n `Tool call name ${output.toolCallId} ${output.toolName} does not match existing tool call ${toolCall.toolName}`,\n );\n }\n assistantMessage.content[toolCallIdx] = {\n ...toolCall,\n ...{\n [symbolInnerMessage]: [\n ...((toolCall as any)[symbolInnerMessage] ?? []),\n output,\n ],\n },\n result: output.result,\n };\n } else {\n throw new Error(\n `Tool call ${output.toolCallId} ${output.toolName} not found in assistant message`,\n );\n }\n } else {\n const role = output.role;\n const content = (\n typeof output.content === \"string\"\n ? [{ type: \"text\" as const, text: output.content }]\n : output.content\n ).map((c) => ({\n ...c,\n ...{ [symbolInnerMessage]: [output] },\n }));\n switch (role) {\n case \"system\":\n case \"user\":\n return {\n ...output,\n content,\n };\n case \"assistant\":\n if (assistantMessage.content.length === 0) {\n assistantMessage.id = output.id;\n assistantMessage.createdAt ??= output.createdAt;\n assistantMessage.status ??= output.status;\n\n if (output.attachments) {\n assistantMessage.attachments = [\n ...(assistantMessage.attachments ?? []),\n ...output.attachments,\n ];\n }\n\n if (output.metadata) {\n assistantMessage.metadata ??= {};\n if (output.metadata.unstable_annotations) {\n assistantMessage.metadata.unstable_annotations = [\n ...(assistantMessage.metadata.unstable_annotations ?? []),\n ...output.metadata.unstable_annotations,\n ];\n }\n if (output.metadata.unstable_data) {\n assistantMessage.metadata.unstable_data = [\n ...(assistantMessage.metadata.unstable_data ?? []),\n ...output.metadata.unstable_data,\n ];\n }\n if (output.metadata.steps) {\n assistantMessage.metadata.steps = [\n ...(assistantMessage.metadata.steps ?? []),\n ...output.metadata.steps,\n ];\n }\n if (output.metadata.custom) {\n assistantMessage.metadata.custom = {\n ...(assistantMessage.metadata.custom ?? {}),\n ...output.metadata.custom,\n };\n }\n }\n // TODO keep this in sync\n }\n\n assistantMessage.content.push(...content);\n break;\n default: {\n const unsupportedRole: never = role;\n throw new Error(`Unknown message role: ${unsupportedRole}`);\n }\n }\n }\n }\n return assistantMessage;\n};\n\nconst chunkExternalMessages = <T,>(callbackResults: CallbackResult<T>[]) => {\n const results: ChunkResult<T>[] = [];\n let isAssistant = false;\n let inputs: T[] = [];\n let outputs: useExternalMessageConverter.Message[] = [];\n\n const flush = () => {\n if (outputs.length) {\n results.push({\n inputs,\n outputs,\n });\n }\n inputs = [];\n outputs = [];\n };\n\n for (const callbackResult of callbackResults) {\n for (const output of callbackResult.outputs) {\n if (!isAssistant || output.role === \"user\" || output.role === \"system\") {\n flush();\n }\n isAssistant = output.role === \"assistant\" || output.role === \"tool\";\n\n if (inputs.at(-1) !== callbackResult.input) {\n inputs.push(callbackResult.input);\n }\n outputs.push(output);\n }\n }\n flush();\n return results;\n};\n\nexport const convertExternalMessages = <T extends WeakKey>(\n messages: T[],\n callback: useExternalMessageConverter.Callback<T>,\n isRunning: boolean,\n) => {\n const callbackResults: CallbackResult<T>[] = [];\n for (const message of messages) {\n const output = callback(message);\n const outputs = Array.isArray(output) ? output : [output];\n const result = { input: message, outputs };\n callbackResults.push(result);\n }\n\n const chunks = chunkExternalMessages(callbackResults);\n\n return chunks.map((message, idx) => {\n const isLast = idx === chunks.length - 1;\n const autoStatus = getAutoStatus(isLast, isRunning);\n const newMessage = fromThreadMessageLike(\n joinExternalMessages(message.outputs),\n idx.toString(),\n autoStatus,\n );\n (newMessage as any)[symbolInnerMessage] = message.inputs;\n return newMessage;\n });\n};\n\nexport const useExternalMessageConverter = <T extends WeakKey>({\n callback,\n messages,\n isRunning,\n}: {\n callback: useExternalMessageConverter.Callback<T>;\n messages: T[];\n isRunning: boolean;\n}) => {\n const state = useMemo(\n () => ({\n callback,\n callbackCache: new WeakMap<T, CallbackResult<T>>(),\n chunkCache: new WeakMap<\n useExternalMessageConverter.Message,\n ChunkResult<T>\n >(),\n converterCache: new ThreadMessageConverter(),\n }),\n [callback],\n );\n\n return useMemo(() => {\n const callbackResults: CallbackResult<T>[] = [];\n for (const message of messages) {\n let result = state.callbackCache.get(message);\n if (!result) {\n const output = state.callback(message);\n const outputs = Array.isArray(output) ? output : [output];\n result = { input: message, outputs };\n state.callbackCache.set(message, result);\n }\n callbackResults.push(result);\n }\n\n const chunks = chunkExternalMessages(callbackResults).map((m) => {\n const key = m.outputs[0];\n if (!key) return m;\n\n const cached = state.chunkCache.get(key);\n if (cached && shallowArrayEqual(cached.outputs, m.outputs)) return cached;\n state.chunkCache.set(key, m);\n return m;\n });\n\n const threadMessages = state.converterCache.convertMessages(\n chunks,\n (cache, message, idx) => {\n const isLast = idx === chunks.length - 1;\n const autoStatus = getAutoStatus(isLast, isRunning);\n\n if (\n cache &&\n (cache.role !== \"assistant\" ||\n !isAutoStatus(cache.status) ||\n cache.status === autoStatus)\n ) {\n const inputs = getExternalStoreMessages<T>(cache);\n if (shallowArrayEqual(inputs, message.inputs)) {\n return cache;\n }\n }\n\n const newMessage = fromThreadMessageLike(\n joinExternalMessages(message.outputs),\n idx.toString(),\n autoStatus,\n );\n (newMessage as any)[symbolInnerMessage] = message.inputs;\n return newMessage;\n },\n );\n\n (threadMessages as unknown as { [symbolInnerMessage]: T[] })[\n symbolInnerMessage\n ] = messages;\n\n return threadMessages;\n }, [state, messages, isRunning]);\n};\n\nconst shallowArrayEqual = (a: unknown[], b: unknown[]) => {\n if (a.length !== b.length) return false;\n for (let i = 0; i < a.length; i++) {\n if (a[i] !== b[i]) return false;\n }\n return true;\n};\n"],"mappings":"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","names":[]}
|
1
|
+
{"version":3,"sources":["../../../src/runtimes/external-store/external-message-converter.tsx"],"sourcesContent":["\"use client\";\n\nimport { useMemo } from \"react\";\nimport { ThreadMessageConverter } from \"./ThreadMessageConverter\";\nimport {\n getExternalStoreMessages,\n symbolInnerMessage,\n} from \"./getExternalStoreMessage\";\nimport { fromThreadMessageLike, ThreadMessageLike } from \"./ThreadMessageLike\";\nimport { getAutoStatus, isAutoStatus } from \"./auto-status\";\nimport { ToolCallContentPart } from \"../../types\";\n\nexport namespace useExternalMessageConverter {\n export type Message =\n | (ThreadMessageLike & {\n readonly convertConfig?: {\n readonly joinStrategy?: \"concat-content\" | \"none\";\n };\n })\n | {\n role: \"tool\";\n toolCallId: string;\n toolName?: string | undefined;\n result: any;\n };\n\n export type Callback<T> = (message: T) => Message | Message[];\n}\n\ntype CallbackResult<T> = {\n input: T;\n outputs: useExternalMessageConverter.Message[];\n};\n\ntype ChunkResult<T> = {\n inputs: T[];\n outputs: useExternalMessageConverter.Message[];\n};\n\ntype Mutable<T> = {\n -readonly [P in keyof T]: T[P];\n};\n\nconst joinExternalMessages = (\n messages: readonly useExternalMessageConverter.Message[],\n): ThreadMessageLike => {\n const assistantMessage: Mutable<Omit<ThreadMessageLike, \"metadata\">> & {\n content: Exclude<ThreadMessageLike[\"content\"][0], string>[];\n metadata?: Mutable<ThreadMessageLike[\"metadata\"]>;\n } = {\n role: \"assistant\",\n content: [],\n };\n for (const output of messages) {\n if (output.role === \"tool\") {\n const toolCallIdx = assistantMessage.content.findIndex(\n (c) => c.type === \"tool-call\" && c.toolCallId === output.toolCallId,\n );\n if (toolCallIdx !== -1) {\n const toolCall = assistantMessage.content[\n toolCallIdx\n ]! as ToolCallContentPart;\n if (output.toolName) {\n if (toolCall.toolName !== output.toolName)\n throw new Error(\n `Tool call name ${output.toolCallId} ${output.toolName} does not match existing tool call ${toolCall.toolName}`,\n );\n }\n assistantMessage.content[toolCallIdx] = {\n ...toolCall,\n ...{\n [symbolInnerMessage]: [\n ...((toolCall as any)[symbolInnerMessage] ?? []),\n output,\n ],\n },\n result: output.result,\n };\n } else {\n throw new Error(\n `Tool call ${output.toolCallId} ${output.toolName} not found in assistant message`,\n );\n }\n } else {\n const role = output.role;\n const content = (\n typeof output.content === \"string\"\n ? [{ type: \"text\" as const, text: output.content }]\n : output.content\n ).map((c) => ({\n ...c,\n ...{ [symbolInnerMessage]: [output] },\n }));\n switch (role) {\n case \"system\":\n case \"user\":\n return {\n ...output,\n content,\n };\n case \"assistant\":\n if (assistantMessage.content.length === 0) {\n assistantMessage.id = output.id;\n assistantMessage.createdAt ??= output.createdAt;\n assistantMessage.status ??= output.status;\n\n if (output.attachments) {\n assistantMessage.attachments = [\n ...(assistantMessage.attachments ?? []),\n ...output.attachments,\n ];\n }\n\n if (output.metadata) {\n assistantMessage.metadata ??= {};\n if (output.metadata.unstable_annotations) {\n assistantMessage.metadata.unstable_annotations = [\n ...(assistantMessage.metadata.unstable_annotations ?? []),\n ...output.metadata.unstable_annotations,\n ];\n }\n if (output.metadata.unstable_data) {\n assistantMessage.metadata.unstable_data = [\n ...(assistantMessage.metadata.unstable_data ?? []),\n ...output.metadata.unstable_data,\n ];\n }\n if (output.metadata.steps) {\n assistantMessage.metadata.steps = [\n ...(assistantMessage.metadata.steps ?? []),\n ...output.metadata.steps,\n ];\n }\n if (output.metadata.custom) {\n assistantMessage.metadata.custom = {\n ...(assistantMessage.metadata.custom ?? {}),\n ...output.metadata.custom,\n };\n }\n }\n // TODO keep this in sync\n }\n\n assistantMessage.content.push(...content);\n break;\n default: {\n const unsupportedRole: never = role;\n throw new Error(`Unknown message role: ${unsupportedRole}`);\n }\n }\n }\n }\n return assistantMessage;\n};\n\nconst chunkExternalMessages = <T,>(\n callbackResults: CallbackResult<T>[],\n joinStrategy?: \"concat-content\" | \"none\",\n) => {\n const results: ChunkResult<T>[] = [];\n let isAssistant = false;\n let pendingNone = false; // true if the previous assistant message had joinStrategy \"none\"\n let inputs: T[] = [];\n let outputs: useExternalMessageConverter.Message[] = [];\n\n const flush = () => {\n if (outputs.length) {\n results.push({\n inputs,\n outputs,\n });\n }\n inputs = [];\n outputs = [];\n isAssistant = false;\n pendingNone = false;\n };\n\n for (const callbackResult of callbackResults) {\n for (const output of callbackResult.outputs) {\n if (\n (pendingNone && output.role !== \"tool\") ||\n !isAssistant ||\n output.role === \"user\" ||\n output.role === \"system\"\n ) {\n flush();\n }\n isAssistant = output.role === \"assistant\" || output.role === \"tool\";\n\n if (inputs.at(-1) !== callbackResult.input) {\n inputs.push(callbackResult.input);\n }\n outputs.push(output);\n\n if (\n output.role === \"assistant\" &&\n (output.convertConfig?.joinStrategy === \"none\" ||\n joinStrategy === \"none\")\n ) {\n pendingNone = true;\n }\n }\n }\n flush();\n return results;\n};\n\nexport const convertExternalMessages = <T extends WeakKey>(\n messages: T[],\n callback: useExternalMessageConverter.Callback<T>,\n isRunning: boolean,\n) => {\n const callbackResults: CallbackResult<T>[] = [];\n for (const message of messages) {\n const output = callback(message);\n const outputs = Array.isArray(output) ? output : [output];\n const result = { input: message, outputs };\n callbackResults.push(result);\n }\n\n const chunks = chunkExternalMessages(callbackResults);\n\n return chunks.map((message, idx) => {\n const isLast = idx === chunks.length - 1;\n const autoStatus = getAutoStatus(isLast, isRunning);\n const newMessage = fromThreadMessageLike(\n joinExternalMessages(message.outputs),\n idx.toString(),\n autoStatus,\n );\n (newMessage as any)[symbolInnerMessage] = message.inputs;\n return newMessage;\n });\n};\n\nexport const useExternalMessageConverter = <T extends WeakKey>({\n callback,\n messages,\n isRunning,\n joinStrategy,\n}: {\n callback: useExternalMessageConverter.Callback<T>;\n messages: T[];\n isRunning: boolean;\n joinStrategy?: \"concat-content\" | \"none\";\n}) => {\n const state = useMemo(\n () => ({\n callback,\n callbackCache: new WeakMap<T, CallbackResult<T>>(),\n chunkCache: new WeakMap<\n useExternalMessageConverter.Message,\n ChunkResult<T>\n >(),\n converterCache: new ThreadMessageConverter(),\n }),\n [callback],\n );\n\n return useMemo(() => {\n const callbackResults: CallbackResult<T>[] = [];\n for (const message of messages) {\n let result = state.callbackCache.get(message);\n if (!result) {\n const output = state.callback(message);\n const outputs = Array.isArray(output) ? output : [output];\n result = { input: message, outputs };\n state.callbackCache.set(message, result);\n }\n callbackResults.push(result);\n }\n\n const chunks = chunkExternalMessages(callbackResults, joinStrategy).map(\n (m) => {\n const key = m.outputs[0];\n if (!key) return m;\n\n const cached = state.chunkCache.get(key);\n if (cached && shallowArrayEqual(cached.outputs, m.outputs))\n return cached;\n state.chunkCache.set(key, m);\n return m;\n },\n );\n\n const threadMessages = state.converterCache.convertMessages(\n chunks,\n (cache, message, idx) => {\n const isLast = idx === chunks.length - 1;\n const autoStatus = getAutoStatus(isLast, isRunning);\n\n if (\n cache &&\n (cache.role !== \"assistant\" ||\n !isAutoStatus(cache.status) ||\n cache.status === autoStatus)\n ) {\n const inputs = getExternalStoreMessages<T>(cache);\n if (shallowArrayEqual(inputs, message.inputs)) {\n return cache;\n }\n }\n\n const newMessage = fromThreadMessageLike(\n joinExternalMessages(message.outputs),\n idx.toString(),\n autoStatus,\n );\n (newMessage as any)[symbolInnerMessage] = message.inputs;\n return newMessage;\n },\n );\n\n (threadMessages as unknown as { [symbolInnerMessage]: T[] })[\n symbolInnerMessage\n ] = messages;\n\n return threadMessages;\n }, [state, messages, isRunning]);\n};\n\nconst shallowArrayEqual = (a: unknown[], b: unknown[]) => {\n if (a.length !== b.length) return false;\n for (let i = 0; i < a.length; i++) {\n if (a[i] !== b[i]) return false;\n }\n return true;\n};\n"],"mappings":";;;AAEA,SAAS,eAAe;AACxB,SAAS,8BAA8B;AACvC;AAAA,EACE;AAAA,EACA;AAAA,OACK;AACP,SAAS,6BAAgD;AACzD,SAAS,eAAe,oBAAoB;AAkC5C,IAAM,uBAAuB,CAC3B,aACsB;AACtB,QAAM,mBAGF;AAAA,IACF,MAAM;AAAA,IACN,SAAS,CAAC;AAAA,EACZ;AACA,aAAW,UAAU,UAAU;AAC7B,QAAI,OAAO,SAAS,QAAQ;AAC1B,YAAM,cAAc,iBAAiB,QAAQ;AAAA,QAC3C,CAAC,MAAM,EAAE,SAAS,eAAe,EAAE,eAAe,OAAO;AAAA,MAC3D;AACA,UAAI,gBAAgB,IAAI;AACtB,cAAM,WAAW,iBAAiB,QAChC,WACF;AACA,YAAI,OAAO,UAAU;AACnB,cAAI,SAAS,aAAa,OAAO;AAC/B,kBAAM,IAAI;AAAA,cACR,kBAAkB,OAAO,UAAU,IAAI,OAAO,QAAQ,sCAAsC,SAAS,QAAQ;AAAA,YAC/G;AAAA,QACJ;AACA,yBAAiB,QAAQ,WAAW,IAAI;AAAA,UACtC,GAAG;AAAA,UACH,GAAG;AAAA,YACD,CAAC,kBAAkB,GAAG;AAAA,cACpB,GAAK,SAAiB,kBAAkB,KAAK,CAAC;AAAA,cAC9C;AAAA,YACF;AAAA,UACF;AAAA,UACA,QAAQ,OAAO;AAAA,QACjB;AAAA,MACF,OAAO;AACL,cAAM,IAAI;AAAA,UACR,aAAa,OAAO,UAAU,IAAI,OAAO,QAAQ;AAAA,QACnD;AAAA,MACF;AAAA,IACF,OAAO;AACL,YAAM,OAAO,OAAO;AACpB,YAAM,WACJ,OAAO,OAAO,YAAY,WACtB,CAAC,EAAE,MAAM,QAAiB,MAAM,OAAO,QAAQ,CAAC,IAChD,OAAO,SACX,IAAI,CAAC,OAAO;AAAA,QACZ,GAAG;AAAA,QACH,GAAG,EAAE,CAAC,kBAAkB,GAAG,CAAC,MAAM,EAAE;AAAA,MACtC,EAAE;AACF,cAAQ,MAAM;AAAA,QACZ,KAAK;AAAA,QACL,KAAK;AACH,iBAAO;AAAA,YACL,GAAG;AAAA,YACH;AAAA,UACF;AAAA,QACF,KAAK;AACH,cAAI,iBAAiB,QAAQ,WAAW,GAAG;AACzC,6BAAiB,KAAK,OAAO;AAC7B,6BAAiB,cAAc,OAAO;AACtC,6BAAiB,WAAW,OAAO;AAEnC,gBAAI,OAAO,aAAa;AACtB,+BAAiB,cAAc;AAAA,gBAC7B,GAAI,iBAAiB,eAAe,CAAC;AAAA,gBACrC,GAAG,OAAO;AAAA,cACZ;AAAA,YACF;AAEA,gBAAI,OAAO,UAAU;AACnB,+BAAiB,aAAa,CAAC;AAC/B,kBAAI,OAAO,SAAS,sBAAsB;AACxC,iCAAiB,SAAS,uBAAuB;AAAA,kBAC/C,GAAI,iBAAiB,SAAS,wBAAwB,CAAC;AAAA,kBACvD,GAAG,OAAO,SAAS;AAAA,gBACrB;AAAA,cACF;AACA,kBAAI,OAAO,SAAS,eAAe;AACjC,iCAAiB,SAAS,gBAAgB;AAAA,kBACxC,GAAI,iBAAiB,SAAS,iBAAiB,CAAC;AAAA,kBAChD,GAAG,OAAO,SAAS;AAAA,gBACrB;AAAA,cACF;AACA,kBAAI,OAAO,SAAS,OAAO;AACzB,iCAAiB,SAAS,QAAQ;AAAA,kBAChC,GAAI,iBAAiB,SAAS,SAAS,CAAC;AAAA,kBACxC,GAAG,OAAO,SAAS;AAAA,gBACrB;AAAA,cACF;AACA,kBAAI,OAAO,SAAS,QAAQ;AAC1B,iCAAiB,SAAS,SAAS;AAAA,kBACjC,GAAI,iBAAiB,SAAS,UAAU,CAAC;AAAA,kBACzC,GAAG,OAAO,SAAS;AAAA,gBACrB;AAAA,cACF;AAAA,YACF;AAAA,UAEF;AAEA,2BAAiB,QAAQ,KAAK,GAAG,OAAO;AACxC;AAAA,QACF,SAAS;AACP,gBAAM,kBAAyB;AAC/B,gBAAM,IAAI,MAAM,yBAAyB,eAAe,EAAE;AAAA,QAC5D;AAAA,MACF;AAAA,IACF;AAAA,EACF;AACA,SAAO;AACT;AAEA,IAAM,wBAAwB,CAC5B,iBACA,iBACG;AACH,QAAM,UAA4B,CAAC;AACnC,MAAI,cAAc;AAClB,MAAI,cAAc;AAClB,MAAI,SAAc,CAAC;AACnB,MAAI,UAAiD,CAAC;AAEtD,QAAM,QAAQ,MAAM;AAClB,QAAI,QAAQ,QAAQ;AAClB,cAAQ,KAAK;AAAA,QACX;AAAA,QACA;AAAA,MACF,CAAC;AAAA,IACH;AACA,aAAS,CAAC;AACV,cAAU,CAAC;AACX,kBAAc;AACd,kBAAc;AAAA,EAChB;AAEA,aAAW,kBAAkB,iBAAiB;AAC5C,eAAW,UAAU,eAAe,SAAS;AAC3C,UACG,eAAe,OAAO,SAAS,UAChC,CAAC,eACD,OAAO,SAAS,UAChB,OAAO,SAAS,UAChB;AACA,cAAM;AAAA,MACR;AACA,oBAAc,OAAO,SAAS,eAAe,OAAO,SAAS;AAE7D,UAAI,OAAO,GAAG,EAAE,MAAM,eAAe,OAAO;AAC1C,eAAO,KAAK,eAAe,KAAK;AAAA,MAClC;AACA,cAAQ,KAAK,MAAM;AAEnB,UACE,OAAO,SAAS,gBACf,OAAO,eAAe,iBAAiB,UACtC,iBAAiB,SACnB;AACA,sBAAc;AAAA,MAChB;AAAA,IACF;AAAA,EACF;AACA,QAAM;AACN,SAAO;AACT;AAEO,IAAM,0BAA0B,CACrC,UACA,UACA,cACG;AACH,QAAM,kBAAuC,CAAC;AAC9C,aAAW,WAAW,UAAU;AAC9B,UAAM,SAAS,SAAS,OAAO;AAC/B,UAAM,UAAU,MAAM,QAAQ,MAAM,IAAI,SAAS,CAAC,MAAM;AACxD,UAAM,SAAS,EAAE,OAAO,SAAS,QAAQ;AACzC,oBAAgB,KAAK,MAAM;AAAA,EAC7B;AAEA,QAAM,SAAS,sBAAsB,eAAe;AAEpD,SAAO,OAAO,IAAI,CAAC,SAAS,QAAQ;AAClC,UAAM,SAAS,QAAQ,OAAO,SAAS;AACvC,UAAM,aAAa,cAAc,QAAQ,SAAS;AAClD,UAAM,aAAa;AAAA,MACjB,qBAAqB,QAAQ,OAAO;AAAA,MACpC,IAAI,SAAS;AAAA,MACb;AAAA,IACF;AACA,IAAC,WAAmB,kBAAkB,IAAI,QAAQ;AAClD,WAAO;AAAA,EACT,CAAC;AACH;AAEO,IAAM,8BAA8B,CAAoB;AAAA,EAC7D;AAAA,EACA;AAAA,EACA;AAAA,EACA;AACF,MAKM;AACJ,QAAM,QAAQ;AAAA,IACZ,OAAO;AAAA,MACL;AAAA,MACA,eAAe,oBAAI,QAA8B;AAAA,MACjD,YAAY,oBAAI,QAGd;AAAA,MACF,gBAAgB,IAAI,uBAAuB;AAAA,IAC7C;AAAA,IACA,CAAC,QAAQ;AAAA,EACX;AAEA,SAAO,QAAQ,MAAM;AACnB,UAAM,kBAAuC,CAAC;AAC9C,eAAW,WAAW,UAAU;AAC9B,UAAI,SAAS,MAAM,cAAc,IAAI,OAAO;AAC5C,UAAI,CAAC,QAAQ;AACX,cAAM,SAAS,MAAM,SAAS,OAAO;AACrC,cAAM,UAAU,MAAM,QAAQ,MAAM,IAAI,SAAS,CAAC,MAAM;AACxD,iBAAS,EAAE,OAAO,SAAS,QAAQ;AACnC,cAAM,cAAc,IAAI,SAAS,MAAM;AAAA,MACzC;AACA,sBAAgB,KAAK,MAAM;AAAA,IAC7B;AAEA,UAAM,SAAS,sBAAsB,iBAAiB,YAAY,EAAE;AAAA,MAClE,CAAC,MAAM;AACL,cAAM,MAAM,EAAE,QAAQ,CAAC;AACvB,YAAI,CAAC,IAAK,QAAO;AAEjB,cAAM,SAAS,MAAM,WAAW,IAAI,GAAG;AACvC,YAAI,UAAU,kBAAkB,OAAO,SAAS,EAAE,OAAO;AACvD,iBAAO;AACT,cAAM,WAAW,IAAI,KAAK,CAAC;AAC3B,eAAO;AAAA,MACT;AAAA,IACF;AAEA,UAAM,iBAAiB,MAAM,eAAe;AAAA,MAC1C;AAAA,MACA,CAAC,OAAO,SAAS,QAAQ;AACvB,cAAM,SAAS,QAAQ,OAAO,SAAS;AACvC,cAAM,aAAa,cAAc,QAAQ,SAAS;AAElD,YACE,UACC,MAAM,SAAS,eACd,CAAC,aAAa,MAAM,MAAM,KAC1B,MAAM,WAAW,aACnB;AACA,gBAAM,SAAS,yBAA4B,KAAK;AAChD,cAAI,kBAAkB,QAAQ,QAAQ,MAAM,GAAG;AAC7C,mBAAO;AAAA,UACT;AAAA,QACF;AAEA,cAAM,aAAa;AAAA,UACjB,qBAAqB,QAAQ,OAAO;AAAA,UACpC,IAAI,SAAS;AAAA,UACb;AAAA,QACF;AACA,QAAC,WAAmB,kBAAkB,IAAI,QAAQ;AAClD,eAAO;AAAA,MACT;AAAA,IACF;AAEA,IAAC,eACC,kBACF,IAAI;AAEJ,WAAO;AAAA,EACT,GAAG,CAAC,OAAO,UAAU,SAAS,CAAC;AACjC;AAEA,IAAM,oBAAoB,CAAC,GAAc,MAAiB;AACxD,MAAI,EAAE,WAAW,EAAE,OAAQ,QAAO;AAClC,WAAS,IAAI,GAAG,IAAI,EAAE,QAAQ,KAAK;AACjC,QAAI,EAAE,CAAC,MAAM,EAAE,CAAC,EAAG,QAAO;AAAA,EAC5B;AACA,SAAO;AACT;","names":[]}
|
@@ -9,7 +9,7 @@
|
|
9
9
|
}
|
10
10
|
|
11
11
|
.aui-thread-viewport-footer {
|
12
|
-
@apply max-w-aui-thread sticky bottom-0 mt-3 flex w-full flex-col items-center justify-end rounded-t-lg bg-inherit pb-4;
|
12
|
+
@apply max-w-[var(--aui-thread-max-width)] sticky bottom-0 mt-3 flex w-full flex-col items-center justify-end rounded-t-lg bg-inherit pb-4;
|
13
13
|
}
|
14
14
|
|
15
15
|
.aui-thread-scroll-to-bottom {
|
@@ -27,7 +27,7 @@
|
|
27
27
|
/* thread welcome */
|
28
28
|
|
29
29
|
.aui-thread-welcome-root {
|
30
|
-
@apply max-w-aui-thread flex w-full flex-grow flex-col;
|
30
|
+
@apply max-w-[var(--aui-thread-max-width)] flex w-full flex-grow flex-col;
|
31
31
|
}
|
32
32
|
|
33
33
|
.aui-thread-welcome-center {
|
@@ -108,7 +108,7 @@
|
|
108
108
|
|
109
109
|
.aui-user-message-root {
|
110
110
|
@apply grid auto-rows-auto grid-cols-[minmax(72px,1fr)_auto] gap-y-2 [&>*]:col-start-2;
|
111
|
-
@apply max-w-aui-thread w-full py-4;
|
111
|
+
@apply max-w-[var(--aui-thread-max-width)] w-full py-4;
|
112
112
|
}
|
113
113
|
|
114
114
|
:where(.aui-user-message-root) > .aui-user-action-bar-root {
|
@@ -146,7 +146,7 @@
|
|
146
146
|
/* edit composer */
|
147
147
|
|
148
148
|
.aui-edit-composer-root {
|
149
|
-
@apply bg-aui-muted max-w-aui-thread my-4 flex w-full flex-col gap-2 rounded-xl;
|
149
|
+
@apply bg-aui-muted max-w-[var(--aui-thread-max-width)] my-4 flex w-full flex-col gap-2 rounded-xl;
|
150
150
|
}
|
151
151
|
|
152
152
|
.aui-edit-composer-input {
|
@@ -161,7 +161,7 @@
|
|
161
161
|
|
162
162
|
.aui-assistant-message-root {
|
163
163
|
@apply grid grid-cols-[auto_auto_1fr] grid-rows-[auto_1fr];
|
164
|
-
@apply max-w-aui-thread relative w-full py-4;
|
164
|
+
@apply max-w-[var(--aui-thread-max-width)] relative w-full py-4;
|
165
165
|
}
|
166
166
|
|
167
167
|
:where(.aui-assistant-message-root) > .aui-avatar-root {
|
@@ -7,7 +7,7 @@
|
|
7
7
|
"@apply bg-aui-background flex h-full flex-col items-center overflow-y-scroll scroll-smooth px-4 pt-8": {}
|
8
8
|
},
|
9
9
|
".aui-thread-viewport-footer": {
|
10
|
-
"@apply max-w-aui-thread sticky bottom-0 mt-3 flex w-full flex-col items-center justify-end rounded-t-lg bg-inherit pb-4": {}
|
10
|
+
"@apply max-w-[var(--aui-thread-max-width)] sticky bottom-0 mt-3 flex w-full flex-col items-center justify-end rounded-t-lg bg-inherit pb-4": {}
|
11
11
|
},
|
12
12
|
".aui-thread-scroll-to-bottom": {
|
13
13
|
"@apply absolute -top-8 rounded-full disabled:invisible": {}
|
@@ -19,7 +19,7 @@
|
|
19
19
|
"@apply bg-aui-background hover:bg-aui-muted/80 rounded-full border px-3 py-1 text-sm transition-colors ease-in": {}
|
20
20
|
},
|
21
21
|
".aui-thread-welcome-root": {
|
22
|
-
"@apply max-w-aui-thread flex w-full flex-grow flex-col": {}
|
22
|
+
"@apply max-w-[var(--aui-thread-max-width)] flex w-full flex-grow flex-col": {}
|
23
23
|
},
|
24
24
|
".aui-thread-welcome-center": {
|
25
25
|
"@apply flex w-full flex-grow flex-col items-center justify-center": {}
|
@@ -74,7 +74,7 @@
|
|
74
74
|
},
|
75
75
|
".aui-user-message-root": {
|
76
76
|
"@apply grid auto-rows-auto grid-cols-[minmax(72px,1fr)_auto] gap-y-2 [&>*]:col-start-2": {},
|
77
|
-
"@apply max-w-aui-thread w-full py-4": {}
|
77
|
+
"@apply max-w-[var(--aui-thread-max-width)] w-full py-4": {}
|
78
78
|
},
|
79
79
|
":where(.aui-user-message-root) > .aui-user-action-bar-root": {
|
80
80
|
"@apply col-start-1 row-start-2 mr-3 mt-2.5": {}
|
@@ -100,7 +100,7 @@
|
|
100
100
|
"@apply flex flex-col items-end": {}
|
101
101
|
},
|
102
102
|
".aui-edit-composer-root": {
|
103
|
-
"@apply bg-aui-muted max-w-aui-thread my-4 flex w-full flex-col gap-2 rounded-xl": {}
|
103
|
+
"@apply bg-aui-muted max-w-[var(--aui-thread-max-width)] my-4 flex w-full flex-col gap-2 rounded-xl": {}
|
104
104
|
},
|
105
105
|
".aui-edit-composer-input": {
|
106
106
|
"@apply text-aui-foreground flex h-8 w-full resize-none bg-transparent p-4 pb-0 outline-none": {}
|
@@ -110,7 +110,7 @@
|
|
110
110
|
},
|
111
111
|
".aui-assistant-message-root": {
|
112
112
|
"@apply grid grid-cols-[auto_auto_1fr] grid-rows-[auto_1fr]": {},
|
113
|
-
"@apply max-w-aui-thread relative w-full py-4": {}
|
113
|
+
"@apply max-w-[var(--aui-thread-max-width)] relative w-full py-4": {}
|
114
114
|
},
|
115
115
|
":where(.aui-assistant-message-root) > .aui-avatar-root": {
|
116
116
|
"@apply col-start-1 row-span-full row-start-1 mr-4": {}
|
package/package.json
CHANGED
@@ -29,7 +29,7 @@
|
|
29
29
|
"conversational-ui",
|
30
30
|
"conversational-ai"
|
31
31
|
],
|
32
|
-
"version": "0.7.
|
32
|
+
"version": "0.7.69",
|
33
33
|
"license": "MIT",
|
34
34
|
"exports": {
|
35
35
|
".": {
|
@@ -118,8 +118,8 @@
|
|
118
118
|
"tailwindcss-animate": "^1.0.7",
|
119
119
|
"tsx": "^4.19.2",
|
120
120
|
"@assistant-ui/tailwindcss-transformer": "0.1.0",
|
121
|
-
"@assistant-ui/
|
122
|
-
"@assistant-ui/
|
121
|
+
"@assistant-ui/tsconfig": "0.0.0",
|
122
|
+
"@assistant-ui/tsbuildutils": "^0.0.1"
|
123
123
|
},
|
124
124
|
"publishConfig": {
|
125
125
|
"access": "public",
|
package/src/primitives/index.ts
CHANGED
@@ -12,3 +12,4 @@ export * as ThreadListItemPrimitive from "./threadListItem";
|
|
12
12
|
export { useContentPartDisplay } from "./contentPart/useContentPartDisplay";
|
13
13
|
export { useContentPartImage } from "./contentPart/useContentPartImage";
|
14
14
|
export { useContentPartText } from "./contentPart/useContentPartText";
|
15
|
+
export { useThreadViewportAutoScroll } from "./thread/useThreadViewportAutoScroll";
|
@@ -14,7 +14,7 @@ const useThreadSuggestion = ({
|
|
14
14
|
autoSend,
|
15
15
|
}: {
|
16
16
|
prompt: string;
|
17
|
-
method
|
17
|
+
method?: "replace";
|
18
18
|
autoSend?: boolean | undefined;
|
19
19
|
}) => {
|
20
20
|
const threadRuntime = useThreadRuntime();
|
@@ -23,7 +23,6 @@ const useThreadSuggestion = ({
|
|
23
23
|
const callback = useCallback(() => {
|
24
24
|
if (autoSend && !threadRuntime.getState().isRunning) {
|
25
25
|
threadRuntime.append(prompt);
|
26
|
-
threadRuntime.composer.setText("");
|
27
26
|
} else {
|
28
27
|
threadRuntime.composer.setText(prompt);
|
29
28
|
}
|
@@ -12,7 +12,11 @@ import { ToolCallContentPart } from "../../types";
|
|
12
12
|
|
13
13
|
export namespace useExternalMessageConverter {
|
14
14
|
export type Message =
|
15
|
-
| ThreadMessageLike
|
15
|
+
| (ThreadMessageLike & {
|
16
|
+
readonly convertConfig?: {
|
17
|
+
readonly joinStrategy?: "concat-content" | "none";
|
18
|
+
};
|
19
|
+
})
|
16
20
|
| {
|
17
21
|
role: "tool";
|
18
22
|
toolCallId: string;
|
@@ -149,9 +153,13 @@ const joinExternalMessages = (
|
|
149
153
|
return assistantMessage;
|
150
154
|
};
|
151
155
|
|
152
|
-
const chunkExternalMessages = <T,>(
|
156
|
+
const chunkExternalMessages = <T,>(
|
157
|
+
callbackResults: CallbackResult<T>[],
|
158
|
+
joinStrategy?: "concat-content" | "none",
|
159
|
+
) => {
|
153
160
|
const results: ChunkResult<T>[] = [];
|
154
161
|
let isAssistant = false;
|
162
|
+
let pendingNone = false; // true if the previous assistant message had joinStrategy "none"
|
155
163
|
let inputs: T[] = [];
|
156
164
|
let outputs: useExternalMessageConverter.Message[] = [];
|
157
165
|
|
@@ -164,11 +172,18 @@ const chunkExternalMessages = <T,>(callbackResults: CallbackResult<T>[]) => {
|
|
164
172
|
}
|
165
173
|
inputs = [];
|
166
174
|
outputs = [];
|
175
|
+
isAssistant = false;
|
176
|
+
pendingNone = false;
|
167
177
|
};
|
168
178
|
|
169
179
|
for (const callbackResult of callbackResults) {
|
170
180
|
for (const output of callbackResult.outputs) {
|
171
|
-
if (
|
181
|
+
if (
|
182
|
+
(pendingNone && output.role !== "tool") ||
|
183
|
+
!isAssistant ||
|
184
|
+
output.role === "user" ||
|
185
|
+
output.role === "system"
|
186
|
+
) {
|
172
187
|
flush();
|
173
188
|
}
|
174
189
|
isAssistant = output.role === "assistant" || output.role === "tool";
|
@@ -177,6 +192,14 @@ const chunkExternalMessages = <T,>(callbackResults: CallbackResult<T>[]) => {
|
|
177
192
|
inputs.push(callbackResult.input);
|
178
193
|
}
|
179
194
|
outputs.push(output);
|
195
|
+
|
196
|
+
if (
|
197
|
+
output.role === "assistant" &&
|
198
|
+
(output.convertConfig?.joinStrategy === "none" ||
|
199
|
+
joinStrategy === "none")
|
200
|
+
) {
|
201
|
+
pendingNone = true;
|
202
|
+
}
|
180
203
|
}
|
181
204
|
}
|
182
205
|
flush();
|
@@ -215,10 +238,12 @@ export const useExternalMessageConverter = <T extends WeakKey>({
|
|
215
238
|
callback,
|
216
239
|
messages,
|
217
240
|
isRunning,
|
241
|
+
joinStrategy,
|
218
242
|
}: {
|
219
243
|
callback: useExternalMessageConverter.Callback<T>;
|
220
244
|
messages: T[];
|
221
245
|
isRunning: boolean;
|
246
|
+
joinStrategy?: "concat-content" | "none";
|
222
247
|
}) => {
|
223
248
|
const state = useMemo(
|
224
249
|
() => ({
|
@@ -246,15 +271,18 @@ export const useExternalMessageConverter = <T extends WeakKey>({
|
|
246
271
|
callbackResults.push(result);
|
247
272
|
}
|
248
273
|
|
249
|
-
const chunks = chunkExternalMessages(callbackResults).map(
|
250
|
-
|
251
|
-
|
274
|
+
const chunks = chunkExternalMessages(callbackResults, joinStrategy).map(
|
275
|
+
(m) => {
|
276
|
+
const key = m.outputs[0];
|
277
|
+
if (!key) return m;
|
252
278
|
|
253
|
-
|
254
|
-
|
255
|
-
|
256
|
-
|
257
|
-
|
279
|
+
const cached = state.chunkCache.get(key);
|
280
|
+
if (cached && shallowArrayEqual(cached.outputs, m.outputs))
|
281
|
+
return cached;
|
282
|
+
state.chunkCache.set(key, m);
|
283
|
+
return m;
|
284
|
+
},
|
285
|
+
);
|
258
286
|
|
259
287
|
const threadMessages = state.converterCache.convertMessages(
|
260
288
|
chunks,
|
@@ -9,7 +9,7 @@
|
|
9
9
|
}
|
10
10
|
|
11
11
|
.aui-thread-viewport-footer {
|
12
|
-
@apply max-w-aui-thread sticky bottom-0 mt-3 flex w-full flex-col items-center justify-end rounded-t-lg bg-inherit pb-4;
|
12
|
+
@apply max-w-[var(--aui-thread-max-width)] sticky bottom-0 mt-3 flex w-full flex-col items-center justify-end rounded-t-lg bg-inherit pb-4;
|
13
13
|
}
|
14
14
|
|
15
15
|
.aui-thread-scroll-to-bottom {
|
@@ -27,7 +27,7 @@
|
|
27
27
|
/* thread welcome */
|
28
28
|
|
29
29
|
.aui-thread-welcome-root {
|
30
|
-
@apply max-w-aui-thread flex w-full flex-grow flex-col;
|
30
|
+
@apply max-w-[var(--aui-thread-max-width)] flex w-full flex-grow flex-col;
|
31
31
|
}
|
32
32
|
|
33
33
|
.aui-thread-welcome-center {
|
@@ -108,7 +108,7 @@
|
|
108
108
|
|
109
109
|
.aui-user-message-root {
|
110
110
|
@apply grid auto-rows-auto grid-cols-[minmax(72px,1fr)_auto] gap-y-2 [&>*]:col-start-2;
|
111
|
-
@apply max-w-aui-thread w-full py-4;
|
111
|
+
@apply max-w-[var(--aui-thread-max-width)] w-full py-4;
|
112
112
|
}
|
113
113
|
|
114
114
|
:where(.aui-user-message-root) > .aui-user-action-bar-root {
|
@@ -146,7 +146,7 @@
|
|
146
146
|
/* edit composer */
|
147
147
|
|
148
148
|
.aui-edit-composer-root {
|
149
|
-
@apply bg-aui-muted max-w-aui-thread my-4 flex w-full flex-col gap-2 rounded-xl;
|
149
|
+
@apply bg-aui-muted max-w-[var(--aui-thread-max-width)] my-4 flex w-full flex-col gap-2 rounded-xl;
|
150
150
|
}
|
151
151
|
|
152
152
|
.aui-edit-composer-input {
|
@@ -161,7 +161,7 @@
|
|
161
161
|
|
162
162
|
.aui-assistant-message-root {
|
163
163
|
@apply grid grid-cols-[auto_auto_1fr] grid-rows-[auto_1fr];
|
164
|
-
@apply max-w-aui-thread relative w-full py-4;
|
164
|
+
@apply max-w-[var(--aui-thread-max-width)] relative w-full py-4;
|
165
165
|
}
|
166
166
|
|
167
167
|
:where(.aui-assistant-message-root) > .aui-avatar-root {
|