我正在尝试通过聊天完成功能将Google Drive中的文件发送到OpenAI API。
我已经完成了身份验证,并且能够列出文件并获取所需的文件。Google API返回的数据是Blob格式。
我遇到的问题是,当我尝试将Blob转换为base64编码的字符串时,会从Supabase Edge Function中得到RangeError
或DOMException
错误。
这是我目前的代码片段(在身份验证和files.get之后):
const fileDownload = await driveApi.files.get({ fileId: 'file_id_string', alt: 'media',});console.log('file download', fileDownload.data);const blob: Blob = fileDownload.data;const arrayBuffer = await blob.arrayBuffer();const uint8Array = new Uint8Array(arrayBuffer);// 尝试1const charCodeString = String.fromCharCode(...uint8Array); // <-- 在这里失败const base64String = btoa(charCodeString);// 尝试2const decodedString = new TextDecoder().decode(uint8Array);const base64String = btoa(decodedString); // <-- 在这里失败// 一旦我正确获取base64String后取消注释// await openai.chat.completions.create({// model: 'gpt-4o-mini',// response_format: 'json_object',// messages: [// { role: 'user', content: [{ url: base64String, type: 'image_url' }] },// ],// });
# 尝试1的错误信息 RangeError: Maximum call stack size exceeded at Object.handler (file:///repos/supabase-personal/supabase/functions/openai/index.ts:32:38) at Object.runMicrotasks (ext:core/01_core.js:642:26) at processTicksAndRejections (ext:deno_node/_next_tick.ts:39:10) at runNextTicks (ext:deno_node/_next_tick.ts:48:3) at eventLoopTick (ext:core/01_core.js:175:21) at async respond (ext:sb_core_main_js/js/http.js:163:14)# 尝试2的错误信息DOMException: The string to be encoded contains characters outside of the Latin1 range. at new DOMException (ext:deno_web/01_dom_exception.js:116:20) at btoa (ext:deno_web/05_base64.js:52:13) at Object.handler (file:///repos/supabase-personal/supabase/functions/openai/index.ts:37:26) at Object.runMicrotasks (ext:core/01_core.js:642:26) at processTicksAndRejections (ext:deno_node/_next_tick.ts:39:10) at runNextTicks (ext:deno_node/_next_tick.ts:48:3) at eventLoopTick (ext:core/01_core.js:175:21) at async respond (ext:sb_core_main_js/js/http.js:163:14)
非常感谢任何提供的帮助!
根据OpenAI的文档,我期望将文件转换为base64格式发送到聊天完成端点。是否有更简单或更好的方法来实现这一点?
回答:
我认为您的目标如下。
- 您希望下载除Google文档文件(文档、电子表格、幻灯片等)之外的文件,并将其转换为base64数据。
- 您希望使用Node.js的googleapis来实现这一点。
在这种情况下,如何进行以下修改?
修改后的脚本:
const fileId = "file_id_string"; // 请设置您的文件ID。const fileDownload = await driveApi.files.get( { fileId, alt: "media" }, { responseType: "stream" });let buf = [];fileDownload.data.on("data", (e) => buf.push(e));fileDownload.data.on("end", () => { const buffer = Buffer.concat(buf); const base64String = buffer.toString("base64"); console.log(base64String);});
或者,当使用responseType: "arraybuffer"
时,如何进行以下修改?
const fileId = "file_id_string"; // 请设置您的文件ID。const fileDownload = await driveApi.files.get( { fileId, alt: "media" }, { responseType: "arraybuffer" });const base64String = Buffer.from(fileDownload.data).toString("base64");console.log(base64String);
- 通过这种方式,下载的文件将被转换为
base64String
中的base64数据。