import { Braces } from "lucide-react";
import { useState } from "react";
import { useCapabilityTools } from "~/api/mcp.ts";
import { DetailSection, DetailSheet } from "~/components/console/detail-sheet.tsx";
import { ErrorState, LoadingState } from "~/components/console/empty-state.tsx";
import { JsonView } from "~/components/console/json-view.tsx";
import { KvList } from "~/components/console/kv-list.tsx";
import { Button } from "~/components/ui/button.tsx";
import { formatDateTime } from "~/lib/utils.ts";
import type { ToolCallView } from "./use-agent-stream.ts";
// 会话页工具卡片的"查看 schema 与本次输入输出"抽屉。
// 本次输入输出取事件流里的摘要:服务端已脱敏(凭证键一律遮盖),超长部分截断;schema 取能力清单(GET /capabilities/tools)。
/** 摘要尽量按 JSON 美化;截断后的摘要不是合法 JSON,原样显示 */
export function parseSummary(text: string | null): { value: unknown; truncated: boolean } {
if (text === null) return { value: null, truncated: false };
const truncated = /…\(\d+ more\)$/.test(text);
if (truncated) return { value: text, truncated };
try {
return { value: JSON.parse(text), truncated };
} catch {
return { value: text, truncated };
}
}
export function ToolCallIo({ call }: { call: ToolCallView }) {
const [open, setOpen] = useState(false);
return (
<>
{open ? setOpen(false)} /> : null}
>
);
}
function ToolCallIoSheet({ call, onClose }: { call: ToolCallView; onClose: () => void }) {
const tools = useCapabilityTools();
const tool = tools.data?.items.find((t) => t.id === call.capabilityId) ?? null;
const input = parseSummary(call.inputSummary);
const output = parseSummary(call.outputSummary);
const failed = call.status === "failed" || call.status === "denied";
return (
!o && onClose()}
title={tool?.title ?? call.capabilityId}
description={call.capabilityId}
width="lg"
>
{input.truncated || output.truncated ? (
只保存前 500 个字符,其余已截断。
) : null}
{tools.isPending ? (
) : tools.error ? (
tools.refetch()} plain />
) : tool ? (
) : (
这个能力未注册,没有 schema。
)}
{tool ? (
) : null}
);
}