UNPKG

@assistant-ui/react

Version:

React components for AI chat.

100 lines (99 loc) 4.08 kB
"use client"; // src/primitives/message/MessageContent.tsx import { memo, useMemo } from "react"; import { useContentPart, useContentPartRuntime, useToolUIs } from "../../context/index.mjs"; import { useMessage, useMessageRuntime } from "../../context/react/MessageContext.mjs"; import { ContentPartRuntimeProvider } from "../../context/providers/ContentPartRuntimeProvider.mjs"; import { ContentPartPrimitiveText } from "../contentPart/ContentPartText.mjs"; import { ContentPartPrimitiveImage } from "../contentPart/ContentPartImage.mjs"; import { ContentPartPrimitiveDisplay } from "../contentPart/ContentPartDisplay.mjs"; import { ContentPartPrimitiveInProgress } from "../contentPart/ContentPartInProgress.mjs"; import { EMPTY_CONTENT } from "../../api/MessageRuntime.mjs"; import { jsx, jsxs } from "react/jsx-runtime"; var ToolUIDisplay = ({ UI, ...props }) => { const Render = useToolUIs((s) => s.getToolUI(props.toolName)) ?? UI; if (!Render) return null; return /* @__PURE__ */ jsx(Render, { ...props }); }; var defaultComponents = { Text: () => /* @__PURE__ */ jsxs("p", { style: { whiteSpace: "pre-line" }, children: [ /* @__PURE__ */ jsx(ContentPartPrimitiveText, {}), /* @__PURE__ */ jsx(ContentPartPrimitiveInProgress, { children: /* @__PURE__ */ jsx("span", { style: { fontFamily: "revert" }, children: " \u25CF" }) }) ] }), Image: () => /* @__PURE__ */ jsx(ContentPartPrimitiveImage, {}), Unstable_Audio: () => null, UI: () => /* @__PURE__ */ jsx(ContentPartPrimitiveDisplay, {}) }; var MessageContentPartComponent = ({ components: { Text = defaultComponents.Text, Empty, Image = defaultComponents.Image, UI = defaultComponents.UI, Unstable_Audio: Audio = defaultComponents.Unstable_Audio, tools: { by_name = {}, Fallback = void 0 } = {} } = {} }) => { const contentPartRuntime = useContentPartRuntime(); const part = useContentPart(); const type = part.type; if (type === "tool-call") { const Tool = by_name[part.toolName] || Fallback; const addResult = (result) => contentPartRuntime.addToolResult(result); return /* @__PURE__ */ jsx(ToolUIDisplay, { ...part, part, UI: Tool, addResult }); } if (part.status.type === "requires-action") throw new Error("Encountered unexpected requires-action status"); switch (type) { case "text": if (part.part === EMPTY_CONTENT && !!Empty) { return /* @__PURE__ */ jsx(Empty, { status: part.status }); } return /* @__PURE__ */ jsx(Text, { ...part, part }); case "image": return /* @__PURE__ */ jsx(Image, { ...part, part }); case "audio": return /* @__PURE__ */ jsx(Audio, { ...part, part }); case "ui": return /* @__PURE__ */ jsx(UI, { ...part, part }); default: const unhandledType = type; throw new Error(`Unknown content part type: ${unhandledType}`); } }; var MessageContentPartImpl = ({ partIndex, components }) => { const messageRuntime = useMessageRuntime(); const runtime = useMemo( () => messageRuntime.getContentPartByIndex(partIndex), [messageRuntime, partIndex] ); return /* @__PURE__ */ jsx(ContentPartRuntimeProvider, { runtime, children: /* @__PURE__ */ jsx(MessageContentPartComponent, { components }) }); }; var MessageContentPart = memo( MessageContentPartImpl, (prev, next) => prev.partIndex === next.partIndex && prev.components?.Text === next.components?.Text && prev.components?.Image === next.components?.Image && prev.components?.Unstable_Audio === next.components?.Unstable_Audio && prev.components?.UI === next.components?.UI && prev.components?.tools === next.components?.tools ); var MessagePrimitiveContent = ({ components }) => { const contentLength = useMessage((s) => s.content.length) || 1; return Array.from({ length: contentLength }, (_, index) => /* @__PURE__ */ jsx(MessageContentPart, { partIndex: index, components }, index)); }; MessagePrimitiveContent.displayName = "MessagePrimitive.Content"; export { MessagePrimitiveContent }; //# sourceMappingURL=MessageContent.mjs.map