import type { ExcalidrawImperativeAPI } from "../../packages/excalidraw/types"; import { DiagramToCodePlugin, exportToBlob, getTextFromElements, MIME_TYPES, TTDDialog, } from "../../packages/excalidraw"; import { getDataURL } from "../../packages/excalidraw/data/blob"; import { safelyParseJSON } from "../../packages/excalidraw/utils"; export const AIComponents = ({ excalidrawAPI, }: { excalidrawAPI: ExcalidrawImperativeAPI; }) => { return ( <> { const appState = excalidrawAPI.getAppState(); const blob = await exportToBlob({ elements: children, appState: { ...appState, exportBackground: true, viewBackgroundColor: appState.viewBackgroundColor, }, exportingFrame: frame, files: excalidrawAPI.getFiles(), mimeType: MIME_TYPES.jpg, }); const dataURL = await getDataURL(blob); const textFromFrameChildren = getTextFromElements(children); const response = await fetch( `${ import.meta.env.VITE_APP_AI_BACKEND }/v1/ai/diagram-to-code/generate`, { method: "POST", headers: { Accept: "application/json", "Content-Type": "application/json", }, body: JSON.stringify({ texts: textFromFrameChildren, image: dataURL, theme: appState.theme, }), }, ); if (!response.ok) { const text = await response.text(); const errorJSON = safelyParseJSON(text); if (!errorJSON) { throw new Error(text); } if (errorJSON.statusCode === 429) { return { html: `
Too many requests today,
please try again tomorrow!


You can also try Excalidraw+ to get more requests.
`, }; } throw new Error(errorJSON.message || text); } try { const { html } = await response.json(); if (!html) { throw new Error("Generation failed (invalid response)"); } return { html, }; } catch (error: any) { throw new Error("Generation failed (invalid response)"); } }} /> { try { const response = await fetch( `${ import.meta.env.VITE_APP_AI_BACKEND }/v1/ai/text-to-diagram/generate`, { method: "POST", headers: { Accept: "application/json", "Content-Type": "application/json", }, body: JSON.stringify({ prompt: input }), }, ); const rateLimit = response.headers.has("X-Ratelimit-Limit") ? parseInt(response.headers.get("X-Ratelimit-Limit") || "0", 10) : undefined; const rateLimitRemaining = response.headers.has( "X-Ratelimit-Remaining", ) ? parseInt( response.headers.get("X-Ratelimit-Remaining") || "0", 10, ) : undefined; const json = await response.json(); if (!response.ok) { if (response.status === 429) { return { rateLimit, rateLimitRemaining, error: new Error( "Too many requests today, please try again tomorrow!", ), }; } throw new Error(json.message || "Generation failed..."); } const generatedResponse = json.generatedResponse; if (!generatedResponse) { throw new Error("Generation failed..."); } return { generatedResponse, rateLimit, rateLimitRemaining }; } catch (err: any) { throw new Error("Request failed"); } }} /> ); };