From e38212281a5b9ee37bca1383d7a8b6d5dd4dbf89 Mon Sep 17 00:00:00 2001 From: Daniel Han Date: Wed, 18 Mar 2026 08:44:38 -0700 Subject: [PATCH] Fix TypeScript build errors in studio frontend (#4429) - tool-ui-python.tsx: use explicit tuple type instead of `as const` to match the mutable `[BundledTheme, BundledTheme]` expected by Streamdown - chat-adapter.ts: add missing `argsText` field required by ToolCallMessagePart and fix `args` type to use ReadonlyJSONObject --- .../src/components/assistant-ui/tool-ui-python.tsx | 2 +- studio/frontend/src/features/chat/api/chat-adapter.ts | 8 +++++--- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/studio/frontend/src/components/assistant-ui/tool-ui-python.tsx b/studio/frontend/src/components/assistant-ui/tool-ui-python.tsx index 760efc8db4..28468a10ad 100644 --- a/studio/frontend/src/components/assistant-ui/tool-ui-python.tsx +++ b/studio/frontend/src/components/assistant-ui/tool-ui-python.tsx @@ -17,7 +17,7 @@ import { const MAX_DISPLAY = 10_000; const COPY_RESET_MS = 2000; -const SHIKI_THEME = ["github-light", "github-dark"] as const; +const SHIKI_THEME = ["github-light", "github-dark"] as ["github-light", "github-dark"]; function truncate(text: string): string { return text.length <= MAX_DISPLAY diff --git a/studio/frontend/src/features/chat/api/chat-adapter.ts b/studio/frontend/src/features/chat/api/chat-adapter.ts index 0d25db2997..13ba64a5a8 100644 --- a/studio/frontend/src/features/chat/api/chat-adapter.ts +++ b/studio/frontend/src/features/chat/api/chat-adapter.ts @@ -2,7 +2,7 @@ // Copyright 2026-present the Unsloth AI Inc. team. All rights reserved. See /studio/LICENSE.AGPL-3.0 import type { ChatModelAdapter } from "@assistant-ui/react"; -import type { MessageTiming } from "@assistant-ui/core"; +import type { MessageTiming, ToolCallMessagePart } from "@assistant-ui/core"; import { toast } from "sonner"; import { generateAudio, @@ -527,7 +527,7 @@ export function createOpenAIStreamAdapter(): ChatModelAdapter { let reasoningDuration = 0; // Tool call content parts — accumulated and yielded cumulatively. // result is set directly on the tool-call part when tool_end arrives. - const toolCallParts: { type: "tool-call"; toolCallId: string; toolName: string; args: Record; result?: unknown }[] = []; + const toolCallParts: ToolCallMessagePart[] = []; try { const { supportsReasoning, reasoningEnabled } = runtime; @@ -582,11 +582,13 @@ export function createOpenAIStreamAdapter(): ChatModelAdapter { if (toolEvent !== undefined) { if (toolEvent.type === "tool_start") { const id = (toolEvent.tool_call_id as string) || `${toolEvent.tool_name}_${Date.now()}`; + const toolArgs = (toolEvent.arguments ?? {}) as ToolCallMessagePart["args"]; toolCallParts.push({ type: "tool-call" as const, toolCallId: id, toolName: toolEvent.tool_name as string, - args: (toolEvent.arguments as Record) ?? {}, + argsText: JSON.stringify(toolArgs), + args: toolArgs, }); } else if (toolEvent.type === "tool_end") { const id = (toolEvent.tool_call_id as string) ||