handleFileUpload, images working
This commit is contained in:
@@ -40,7 +40,6 @@ import {
|
|||||||
import {
|
import {
|
||||||
fileToImageBlock,
|
fileToImageBlock,
|
||||||
fileToPDFBlock,
|
fileToPDFBlock,
|
||||||
toOpenAIPDFBlock,
|
|
||||||
} from "@/lib/multimodal-utils";
|
} from "@/lib/multimodal-utils";
|
||||||
import type { Base64ContentBlock } from "@langchain/core/messages";
|
import type { Base64ContentBlock } from "@langchain/core/messages";
|
||||||
|
|
||||||
@@ -183,14 +182,14 @@ export function Thread() {
|
|||||||
// TODO: check configurable object for modelname camelcase or snakecase else do openai format
|
// TODO: check configurable object for modelname camelcase or snakecase else do openai format
|
||||||
const isOpenAI = true;
|
const isOpenAI = true;
|
||||||
|
|
||||||
const pdfBlocks = pdfUrlList.map(toOpenAIPDFBlock);
|
|
||||||
|
|
||||||
const newHumanMessage: Message = {
|
const newHumanMessage: Message = {
|
||||||
id: uuidv4(),
|
id: uuidv4(),
|
||||||
type: "human",
|
type: "human",
|
||||||
content: [
|
content: [
|
||||||
{ type: "text", text: input },
|
{ type: "text", text: input },
|
||||||
...pdfBlocks,
|
...pdfUrlList,
|
||||||
|
...imageUrlList,
|
||||||
] as Message["content"],
|
] as Message["content"],
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -217,23 +216,30 @@ export function Thread() {
|
|||||||
setPdfUrlList([]);
|
setPdfUrlList([]);
|
||||||
};
|
};
|
||||||
|
|
||||||
const handleImageUpload = async (e: ChangeEvent<HTMLInputElement>) => {
|
const handleFileUpload = async (e: ChangeEvent<HTMLInputElement>) => {
|
||||||
const files = e.target.files;
|
const files = e.target.files;
|
||||||
if (files) {
|
if (!files) return;
|
||||||
const imageBlocks = await Promise.all(
|
const fileArray = Array.from(files);
|
||||||
Array.from(files).map(fileToImageBlock),
|
const imageFiles = fileArray.filter((file) => file.type.startsWith("image"));
|
||||||
|
const pdfFiles = fileArray.filter((file) => file.type === "application/pdf");
|
||||||
|
const invalidFiles = fileArray.filter(
|
||||||
|
(file) => !file.type.startsWith("image/") && file.type !== "application/pdf",
|
||||||
|
);
|
||||||
|
|
||||||
|
if (invalidFiles.length > 0) {
|
||||||
|
toast.error(
|
||||||
|
"You have uploaded invalid file type. Please upload an image or a PDF.",
|
||||||
);
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (imageFiles.length) {
|
||||||
|
console.log("imageFiles", imageFiles);
|
||||||
|
const imageBlocks = await Promise.all(imageFiles.map(fileToImageBlock));
|
||||||
setImageUrlList((prev) => [...prev, ...imageBlocks]);
|
setImageUrlList((prev) => [...prev, ...imageBlocks]);
|
||||||
}
|
}
|
||||||
e.target.value = "";
|
|
||||||
};
|
|
||||||
|
|
||||||
const handlePDFUpload = async (e: ChangeEvent<HTMLInputElement>) => {
|
if (pdfFiles.length) {
|
||||||
const files = e.target.files;
|
const pdfBlocks = await Promise.all(pdfFiles.map(fileToPDFBlock));
|
||||||
if (files) {
|
|
||||||
const pdfBlocks = await Promise.all(
|
|
||||||
Array.from(files).map(fileToPDFBlock),
|
|
||||||
);
|
|
||||||
setPdfUrlList((prev) => [...prev, ...pdfBlocks]);
|
setPdfUrlList((prev) => [...prev, ...pdfBlocks]);
|
||||||
}
|
}
|
||||||
e.target.value = "";
|
e.target.value = "";
|
||||||
@@ -595,15 +601,15 @@ export function Thread() {
|
|||||||
>
|
>
|
||||||
<Plus className="size-5 text-gray-600" />
|
<Plus className="size-5 text-gray-600" />
|
||||||
<span className="text-sm text-gray-600">
|
<span className="text-sm text-gray-600">
|
||||||
Upload PDF
|
Upload PDF or Image
|
||||||
</span>
|
</span>
|
||||||
</Label>
|
</Label>
|
||||||
<input
|
<input
|
||||||
id="file-input"
|
id="file-input"
|
||||||
type="file"
|
type="file"
|
||||||
onChange={handlePDFUpload}
|
onChange={handleFileUpload}
|
||||||
multiple
|
multiple
|
||||||
accept="application/pdf"
|
accept="image/*,application/pdf"
|
||||||
className="hidden"
|
className="hidden"
|
||||||
/>
|
/>
|
||||||
<div className="flex items-center space-x-2">
|
<div className="flex items-center space-x-2">
|
||||||
|
|||||||
@@ -9,7 +9,7 @@ export async function fileToImageBlock(
|
|||||||
return {
|
return {
|
||||||
type: "image",
|
type: "image",
|
||||||
source_type: "base64",
|
source_type: "base64",
|
||||||
mime_type: file.type,
|
mime_type: "image/jpeg",
|
||||||
data,
|
data,
|
||||||
metadata: { name: file.name },
|
metadata: { name: file.name },
|
||||||
};
|
};
|
||||||
@@ -27,19 +27,6 @@ export async function fileToPDFBlock(file: File): Promise<Base64ContentBlock> {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
// in lib/multimodal-utils.ts
|
|
||||||
export function toOpenAIPDFBlock(
|
|
||||||
block: Base64ContentBlock,
|
|
||||||
): Base64ContentBlock {
|
|
||||||
return {
|
|
||||||
type: "file",
|
|
||||||
source_type: "base64",
|
|
||||||
data: block.data,
|
|
||||||
mime_type: block.mime_type ?? "application/pdf",
|
|
||||||
metadata: { filename: block.metadata?.filename ?? "file.pdf" },
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
// Helper to convert File to base64 string
|
// Helper to convert File to base64 string
|
||||||
export async function fileToBase64(file: File): Promise<string> {
|
export async function fileToBase64(file: File): Promise<string> {
|
||||||
return new Promise<string>((resolve, reject) => {
|
return new Promise<string>((resolve, reject) => {
|
||||||
|
|||||||
Reference in New Issue
Block a user