Open3
Gemini Files API メモ
Google Gemini でファイル関連の API についてのメモ
Python および TypeScript 向けの SDK が提供されているが、ここでは RESTful API を使用した方法を記述する(理由は後述)。具体的な手順は以下の 2 ステップで構成される。
- アップロード用のプリサインド URL の取得
- 取得した URL を使用したファイルのアップロード
取得するアップロード用 URL には Gemini API Key が含まれて返されるが、ファイルのアップロード時には API Key を削除しても問題ない。ただし、ステップ 1(URL 取得)とステップ 2(ファイルアップロード)のリクエストは、同一のオリジン(ホスト)から実行する必要がある。異なるオリジンを使用すると CORS エラーが発生する可能性がある。
Presigned url を取得してからアップロードするサンプル。
export interface GoogleUploadFile {
name: string;
displayName: string;
mimeType: string;
sizeBytes: string;
createTime: string;
updateTime: string;
expirationTime: string;
sha256Hash: string;
uri: string;
state: string;
source: string;
}
export interface GoogleUploadResponse {
file: GoogleUploadFile;
}
const GOOGLE_API_ENDPOINT = "https://generativelanguage.googleapis.com/upload/v1beta/files";
export async function getGoogleUploadUrl({
name,
type,
size,
}: {
name: string;
type: string;
size: number;
}): Promise<string> {
const GOOGLE_UPLOAD_URL = `${GOOGLE_API_ENDPOINT}?key=${process.env.GOOGLE_GENERATIVE_AI_API_KEY}`;
const initResponse = await fetch(GOOGLE_UPLOAD_URL, {
method: "POST",
headers: {
"X-Goog-Upload-Protocol": "resumable",
"X-Goog-Upload-Command": "start",
"X-Goog-Upload-Header-Content-Length": size.toString(),
"X-Goog-Upload-Header-Content-Type": type,
"Content-Type": "application/json",
},
body: JSON.stringify({
file: {
display_name: name,
},
}),
});
if (!initResponse.ok) {
const errorText = await initResponse.text();
throw new Error(`Failed to initiate upload: ${errorText}`);
}
// Get the upload URL from the response headers
const uploadUrl = initResponse.headers.get("x-goog-upload-url");
if (!uploadUrl) {
throw new Error("No upload URL received from Google API");
}
const urlObj = new URL(uploadUrl);
urlObj.searchParams.delete("key"); // Remove the API key from the URL
const uploadUrlWithoutKey = urlObj.toString();
console.log("Upload URL received:", uploadUrlWithoutKey);
return uploadUrlWithoutKey;
}
export async function uploadToGoogle(url: string, file: File) {
const uploadResponse = await fetch(url, {
method: "PUT",
headers: {
"Content-Type": file.type,
"Content-Length": file.size.toString(),
"X-Goog-Upload-Offset": "0",
"X-Goog-Upload-Command": "upload, finalize",
"Access-Control-Allow-Origin": "*",
},
body: file,
});
if (!uploadResponse.ok) {
const errorText = await uploadResponse.text();
console.error(`Failed to upload file: ${errorText}`);
return;
}
const responseData = (await uploadResponse.json()) as GoogleUploadResponse;
console.log(responseData);
return { success: true, file: responseData.file };
}