Files
cdsl-cad/frontend/src/lib/cad-messages.ts
T

56 lines
2.1 KiB
TypeScript

import type { CadError, CadProgress, CadResult, CadUIMessage } from "./cad-types";
type AnyPart = { type?: unknown; text?: unknown; data?: unknown; id?: unknown };
type AnyMessage = { id?: unknown; role?: unknown; parts?: unknown };
type CadPart = CadUIMessage["parts"][number];
export function normalizeCadMessages(input: unknown): CadUIMessage[] {
if (!Array.isArray(input)) return [];
return input.flatMap((message): CadUIMessage[] => {
const candidate = message as AnyMessage;
if (candidate.role !== "user" && candidate.role !== "assistant") return [];
const parts = Array.isArray(candidate.parts) ? candidate.parts : [];
const normalizedParts = parts.flatMap((part): CadPart[] => {
const item = part as AnyPart;
if (item.type === "text") {
return [{ type: "text", text: String(item.text || "") }];
}
if (item.type === "data-cad-progress") {
return [{ type: "data-cad-progress", id: stringId(item.id), data: item.data as CadProgress }];
}
if (item.type === "data-cad-result") {
return [{ type: "data-cad-result", id: stringId(item.id), data: item.data as CadResult }];
}
if (item.type === "data-cad-error") {
return [{ type: "data-cad-error", id: stringId(item.id), data: item.data as CadError }];
}
return [];
});
return [{
id: typeof candidate.id === "string" ? candidate.id : crypto.randomUUID(),
role: candidate.role,
parts: normalizedParts,
}];
});
}
export function messagesForBackend(messages: CadUIMessage[]) {
return messages
.filter((message) => message.role === "user" || message.role === "assistant")
.map((message) => ({
id: message.id,
role: message.role,
parts: message.parts.flatMap((part): { type: string; text?: string; data?: unknown }[] => {
if (part.type === "text") return [{ type: "text", text: part.text }];
if (part.type.startsWith("data-cad-") && "data" in part) {
return [{ type: part.type, data: part.data }];
}
return [];
}),
}));
}
function stringId(value: unknown) {
return typeof value === "string" ? value : undefined;
}