import type { MessageBlock } from "@rakazo/contracts"; export const TURN_ATTACHMENT_UNAVAILABLE = "An attachment in this message could not be loaded. Tell the user the attachment was unavailable and do not guess its contents."; export const STEERING_ATTACHMENT_UNAVAILABLE = TURN_ATTACHMENT_UNAVAILABLE; export function missingTurnImagesInstruction( blocks: MessageBlock[] | undefined, images: { length: number } | undefined, ): string { const expected = blocks?.filter((block) => block.kind === "image").length ?? 0; const loaded = images?.length ?? 0; return expected > 0 && loaded < expected ? TURN_ATTACHMENT_UNAVAILABLE : ""; } export async function settleSteeringAttachmentLoads( images: Promise, files: Promise, blocks?: MessageBlock[], signal?: AbortSignal, ): Promise<{ images: TImage[] | undefined; files: TFile[]; unavailableInstruction: string; }> { const [loadedImages, loadedFiles] = await Promise.allSettled([images, files]); if (signal?.aborted) { if (loadedImages.status === "rejected") throw loadedImages.reason; if (loadedFiles.status === "rejected") throw loadedFiles.reason; } const expectedImageCount = blocks?.filter((block) => block.kind === "image").length ?? 0; const loadedImageCount = loadedImages.status === "fulfilled" ? (loadedImages.value?.length ?? 0) : 0; const unavailable = loadedImages.status === "rejected" || loadedFiles.status === "rejected" || loadedImageCount < expectedImageCount; return { images: loadedImages.status === "fulfilled" ? loadedImages.value : undefined, files: loadedFiles.status === "fulfilled" ? loadedFiles.value : [], unavailableInstruction: unavailable ? STEERING_ATTACHMENT_UNAVAILABLE : "", }; }