รวมไฟล์ขนาดใหญ่ในคำขอแบบหลายโมดัลและจัดการไฟล์โดยใช้ Cloud Storage for Firebase

ใช้ได้เฉพาะเมื่อใช้ Vertex AI Gemini API เป็น ผู้ให้บริการ API ของคุณเท่านั้น

เมื่อเรียก Vertex AI Gemini API จากแอปโดยใช้ Firebase AI Logic SDK คุณสามารถแจ้งให้โมเดล Gemini สร้างข้อความ ตามอินพุตมัลติโมดัล เช่น รูปภาพ, PDF, วิดีโอ และเสียง

สำหรับอินพุตที่ไม่ใช่ข้อความ (เช่น ไฟล์สื่อ) คุณสามารถเลือกใช้ Cloud Storage for Firebase เพื่อรวมไฟล์ไว้ในคำขอได้ โดยภาพรวมแล้ว สิ่งที่คุณต้องทราบเกี่ยวกับฟีเจอร์นี้มีดังนี้


คู่มือโซลูชันนี้อธิบายวิธีตั้งค่า Cloud Storage for Firebase, อัปโหลด ไฟล์ไปยังบัคเก็ต Cloud Storage for Firebase จากแอป แล้วรวมประเภท MIME และ URL ของ ไฟล์ Cloud Storage for Firebase ไว้ในคำขอแบบมัลติโมดัลไปยัง Gemini API

คุณต้องการดูตัวอย่างโค้ดไหม หรือคุณตั้งค่า Cloud Storage for Firebase ไว้แล้วและพร้อมที่จะเริ่มใช้กับ คำขอแบบมัลติโมดัลแล้วใช่ไหม

ข้ามไปที่ตัวอย่างโค้ด

เหตุใดจึงควรใช้ Cloud Storage for Firebase กับแอป

Cloud Storage for Firebase ใช้โครงสร้างพื้นฐานที่รวดเร็ว ปลอดภัย และ ปรับขนาดได้แบบเดียวกับ Google Cloud Storage เพื่อจัดเก็บ Blob และไฟล์ และ Client SDK ได้รับการสร้างขึ้นมาโดยเฉพาะสำหรับแอปบนอุปกรณ์เคลื่อนที่และเว็บ

สำหรับ Firebase AI Logic SDK ขนาดคำขอสูงสุดคือ 20 MB คุณจะได้รับข้อผิดพลาด HTTP 413 หากคำขอมีขนาดใหญ่เกินไป หากขนาดไฟล์จะ ทำให้ขนาดคำขอทั้งหมดเกิน 20 MB ให้ใช้ Cloud Storage for Firebase URL เพื่อรวมไฟล์ไว้ในคำขอแบบมัลติโมดัล อย่างไรก็ตาม หากไฟล์มีขนาดเล็ก คุณมักจะส่งไฟล์เป็นข้อมูลแบบอินไลน์ได้โดยตรง (โปรดทราบว่าไฟล์ที่ระบุเป็นข้อมูลแบบอินไลน์จะได้รับการเข้ารหัสเป็น base64 ระหว่างการส่ง ซึ่งจะเพิ่มขนาดของคำขอ)

สิทธิประโยชน์เพิ่มเติมบางประการของการใช้ Cloud Storage for Firebase มีดังนี้

  • คุณสามารถให้ผู้ใช้ปลายทางอัปโหลดรูปภาพจากแอปไปยังบัคเก็ต Cloud Storage for Firebase ได้โดยตรง จากนั้นคุณสามารถรวมรูปภาพเหล่านั้นไว้ใน พรอมต์แบบมัลติโมดัลได้เพียงแค่ระบุประเภท MIME ของไฟล์และ Cloud Storage for Firebase URL (ซึ่งเป็นตัวระบุไฟล์)

  • คุณสามารถประหยัดเวลาและแบนด์วิดท์ของผู้ใช้ปลายทางได้หากผู้ใช้ต้องระบุรูปภาพ โดยเฉพาะอย่างยิ่งหากคุณภาพเครือข่ายไม่ดีหรือไม่เสถียร

    • หากการอัปโหลดหรือดาวน์โหลดไฟล์ถูกขัดจังหวะ Cloud Storage for Firebase SDK จะรีสตาร์ทการดำเนินการโดยอัตโนมัติจากจุดที่หยุดไว้
    • คุณสามารถใช้ไฟล์ที่อัปโหลดไฟล์เดียวกันได้หลายครั้งโดยไม่ต้องให้ผู้ใช้ปลายทางอัปโหลดไฟล์เดียวกันทุกครั้งที่จำเป็นในแอป (เช่น ในคำขอแบบมัลติโมดัลใหม่)
  • คุณสามารถจำกัดการเข้าถึงไฟล์ที่จัดเก็บไว้ใน Cloud Storage for Firebase ของผู้ใช้ปลายทางได้โดยใช้ Firebase Security Rules, ซึ่งอนุญาตให้เฉพาะผู้ใช้ที่ได้รับอนุญาตเท่านั้นที่อัปโหลด ดาวน์โหลด หรือลบไฟล์ได้

  • คุณสามารถเข้าถึงไฟล์ในบัคเก็ตได้จาก Firebase หรือจาก Google Cloud ซึ่งช่วยให้คุณมีความยืดหยุ่นในการประมวลผลฝั่งเซิร์ฟเวอร์ เช่น การกรองรูปภาพหรือการแปลงรหัสวิดีโอโดยใช้ Google Cloud Storage API

ไฟล์และ URL ประเภทใดบ้างที่รองรับ

ข้อกำหนดสำหรับไฟล์และ URL เมื่อคุณต้องการใช้ Cloud Storage for Firebase URL กับ Firebase AI Logic SDK มีดังนี้

  • ไฟล์ต้องเป็นไปตาม ข้อกำหนดของไฟล์อินพุตสำหรับคำขอแบบมัลติโมดัล ซึ่งรวมถึงข้อกำหนดต่างๆ เช่น ประเภท MIME และขนาดไฟล์

  • ไฟล์ต้องจัดเก็บไว้ในบัคเก็ต Cloud Storage for Firebase (ซึ่งหมายความว่าบริการของ Firebase เช่น Firebase Security Rules จะเข้าถึงบัคเก็ตได้) หากคุณดูบัคเก็ตใน Firebaseคอนโซล ได้ แสดงว่าบัคเก็ตนั้นเป็นบัคเก็ต Cloud Storage for Firebase

  • บัคเก็ต Cloud Storage for Firebase ต้องอยู่ในโปรเจ็กต์ Firebase เดียวกันกับที่คุณลงทะเบียนแอป

  • URL ของ Cloud Storage for Firebase ของไฟล์ต้องขึ้นต้นด้วย gs:// ซึ่งเป็น วิธีสร้าง URL ทั้งหมดของ Google Cloud Storage

  • URL ของไฟล์ต้องไม่ใช่ URL ของ "เบราว์เซอร์" (เช่น URL ของรูปภาพที่คุณพบในอินเทอร์เน็ต)

นอกจากนี้ Firebase Security Rules สำหรับบัคเก็ตต้องอนุญาต การเข้าถึงไฟล์ที่เหมาะสม เช่น

  • หากคุณมีกฎสาธารณะ ผู้ใช้หรือไคลเอ็นต์ ทุกคน จะเข้าถึงไฟล์ได้

  • หากคุณมีกฎที่เข้มงวด (แนะนำอย่างยิ่ง) Firebase จะตรวจสอบว่าผู้ใช้หรือ ไคลเอ็นต์ที่ลงชื่อเข้าใช้มีสิทธิ์เข้าถึงไฟล์เพียงพอก่อนที่จะอนุญาตให้เรียกผ่าน URL ที่ระบุ

ใช้ URL ของ Cloud Storage for Firebase กับ Firebase AI Logic

ใช้ได้เฉพาะเมื่อใช้ Vertex AI Gemini API เป็น ผู้ให้บริการ API ของคุณเท่านั้น

ขั้นตอนที่ 1: ตั้งค่า Cloud Storage for Firebase

คุณดูวิธีการตั้งค่า Cloud Storage for Firebase โดยละเอียดได้ใน คู่มือเริ่มต้นใช้งาน: iOS+ | Android | เว็บ | Flutter | Unity

งานระดับสูงที่คุณต้องทำมีดังนี้

  1. สร้างหรือนำเข้าบัคเก็ต Cloud Storage for Firebase ในโปรเจ็กต์ Firebase

  2. ใช้ Firebase Security Rules กับบัคเก็ตนี้ Security Rules ช่วยให้คุณรักษาความปลอดภัยไฟล์ได้โดยจำกัดการเข้าถึงของผู้ใช้ปลายทางที่ได้รับอนุญาต

  3. เพิ่มไลบรารีของไคลเอ็นต์สำหรับ Cloud Storage for Firebase ลงในแอป

    โปรดทราบว่าคุณสามารถข้ามงานนี้ได้ แต่จากนั้นคุณต้องรวมค่าประเภท MIME และ URL ไว้ในคำขออย่างชัดเจน เสมอ

ขั้นตอนที่ 2: อัปโหลดไฟล์ไปยังบัคเก็ต

ในเอกสารประกอบของ Cloud Storage คุณสามารถดูวิธีต่างๆ ในการอัปโหลดไฟล์ไปยังบัคเก็ตได้ เช่น คุณสามารถอัปโหลดไฟล์ในเครื่องจากอุปกรณ์ของผู้ใช้ปลายทาง เช่น รูปภาพและวิดีโอจากกล้อง ดูข้อมูลเพิ่มเติม: iOS+ | Android | เว็บ | Flutter | Unity

เมื่อคุณอัปโหลดไฟล์ไปยังบัคเก็ต Cloud Storage จะใช้ ข้อมูล 2 รายการต่อไปนี้กับไฟล์โดยอัตโนมัติ คุณจะต้องรวมค่าเหล่านี้ไว้ในคำขอ (ตามที่แสดงในขั้นตอนถัดไปของคู่มือนี้)

  • ประเภท MIME: นี่คือประเภทสื่อของไฟล์ (เช่น image/png) เราจะพยายามตรวจหาประเภท MIME ระหว่างการอัปโหลดและใช้ ข้อมูลเมตาดังกล่าวกับออบเจ็กต์ในบัคเก็ตโดยอัตโนมัติ อย่างไรก็ตาม คุณสามารถระบุประเภท MIME ระหว่างการอัปโหลดได้

  • Cloud Storage for Firebase URL: นี่คือตัวระบุที่ไม่ซ้ำกันสำหรับไฟล์ URL ต้องขึ้นต้นด้วย gs://

ขั้นตอนที่ 3: รวมประเภท MIME และ URL ของไฟล์ไว้ในคำขอแบบมัลติโมดัล

เมื่อจัดเก็บไฟล์ไว้ในบัคเก็ตแล้ว คุณสามารถรวมประเภท MIME และ URL ของไฟล์ไว้ในคำขอได้ โปรดทราบว่าตัวอย่างเหล่านี้แสดงคำขอ generateContent แบบไม่สตรีม แต่คุณยังใช้ URL กับการสตรีมและการแชทได้ด้วย

หากต้องการรวมไฟล์ไว้ในคำขอ คุณสามารถใช้ตัวเลือกใดตัวเลือกหนึ่งต่อไปนี้

ตัวเลือกที่ 1: รวมประเภท MIME และ URL โดยใช้การอ้างอิง Storage

ก่อนที่จะลองใช้ตัวอย่างนี้ โปรดตรวจสอบว่าคุณได้ทำตาม คู่มือเริ่มต้นใช้งานสำหรับ Firebase AI Logic SDK แล้ว

ใช้ตัวเลือกนี้หากคุณเพิ่งอัปโหลดไฟล์ไปยังบัคเก็ต และต้องการรวมไฟล์ (ผ่านการอ้างอิง Storage) ไว้ในคำขอทันที การเรียก ต้องใช้ทั้งประเภท MIME และ URL Cloud Storage for Firebase

Swift

// Upload an image file using Cloud Storage for Firebase.
let storageRef = Storage.storage().reference(withPath: "images/image.jpg")
guard let imageURL = Bundle.main.url(forResource: "image", withExtension: "jpg") else {
  fatalError("File 'image.jpg' not found in main bundle.")
}
let metadata = try await storageRef.putFileAsync(from: imageURL)

// Get the MIME type and Cloud Storage for Firebase URL.
guard let mimeType = metadata.contentType else {
  fatalError("The MIME type of the uploaded image is nil.")
}
// Construct a URL in the required format.
let storageURL = "gs://\(storageRef.bucket)/\(storageRef.fullPath)"

let prompt = "What's in this picture?"
// Construct the imagePart with the MIME type and the URL.
let imagePart = FileDataPart(uri: storageURL, mimeType: mimeType)

// To generate text output, call generateContent with the prompt and the imagePart.
let result = try await model.generateContent(prompt, imagePart)
if let text = result.text {
  print(text)
}

Kotlin

สำหรับ Kotlin เมธอดใน SDK นี้เป็นฟังก์ชันระงับและต้องเรียก จาก ขอบเขตของโครูทีน
// Upload an image file using Cloud Storage for Firebase.
val storageRef = Firebase.storage.reference.child("images/image.jpg")
val fileUri = Uri.fromFile(File("image.jpg"))
try {
    val taskSnapshot = storageRef.putFile(fileUri).await()
    // Get the MIME type and Cloud Storage for Firebase file path.
    val mimeType = taskSnapshot.metadata?.contentType
    val bucket = taskSnapshot.metadata?.bucket
    val filePath = taskSnapshot.metadata?.path

    if (mimeType != null && bucket != null) {
        // Construct a URL in the required format.
        val storageUrl = "gs://$bucket/$filePath"
        // Construct a prompt that includes text, the MIME type, and the URL.
        val prompt = content {
            fileData(mimeType = mimeType, uri = storageUrl)
            text("What's in this picture?")
        }
        // To generate text output, call generateContent with the prompt.
        val response = model.generateContent(prompt)
        println(response.text)
    }
} catch (e: StorageException) {
    // An error occurred while uploading the file.
} catch (e: GoogleGenerativeAIException) {
    // An error occurred while generating text.
}

Java

สำหรับ Java เมธอดใน SDK นี้จะแสดงผลเป็น ListenableFuture
// Upload an image file using Cloud Storage for Firebase.
StorageReference storage = FirebaseStorage.getInstance().getReference("images/image.jpg");
Uri fileUri = Uri.fromFile(new File("images/image.jpg"));

storage.putFile(fileUri).addOnSuccessListener(taskSnapshot -> {
    // Get the MIME type and Cloud Storage for Firebase file path.
    String mimeType = taskSnapshot.getMetadata().getContentType();
    String bucket = taskSnapshot.getMetadata().getBucket();
    String filePath = taskSnapshot.getMetadata().getPath();

    if (mimeType != null && bucket != null) {
        // Construct a URL in the required format.
        String storageUrl = "gs://" + bucket + "/" + filePath;
        // Create a prompt that includes text, the MIME type, and the URL.
        Content prompt = new Content.Builder()
                .addFileData(storageUrl, mimeType)
                .addText("What's in this picture?")
                .build();

        // To generate text output, call generateContent with the prompt.
        GenerativeModelFutures modelFutures = GenerativeModelFutures.from(model);
        ListenableFuture<GenerateContentResponse> response = modelFutures.generateContent(prompt);
        Futures.addCallback(response, new FutureCallback<>() {
            @Override
            public void onSuccess(GenerateContentResponse result) {
                String resultText = result.getText();
                System.out.println(resultText);
            }

            @Override
            public void onFailure(@NonNull Throwable t) {
                t.printStackTrace();
            }
        }, executor);
    }
}).addOnFailureListener(e -> {
    // An error occurred while uploading the file.
    e.printStackTrace();
});

Web

// Upload an image file using Cloud Storage for Firebase.
const storageRef = ref(storage, "image.jpg");
const uploadResult = await uploadBytes(storageRef, file);

// Get the MIME type and Cloud Storage for Firebase URL.
// toString() is the simplest way to construct the Cloud Storage for Firebase URL
// in the required format.
const mimeType = uploadResult.metadata.contentType;
const storageUrl = uploadResult.ref.toString();

// Construct the imagePart with the MIME type and the URL.
const imagePart = { fileData: { mimeType, fileUri: storageUrl }};

// To generate text output, call generateContent with the prompt and imagePart.
const result = await model.generateContent([prompt, imagePart]);
console.log(result.response.text());

Dart

// Upload an image file using Cloud Storage for Firebase.
final storageRef = FirebaseStorage.instance.ref();
final imageRef = storageRef.child("images/image.jpg");
await imageRef.putData(data);

// Get the MIME type and Cloud Storage for Firebase file path.
final metadata = await imageRef.getMetadata();
final mimeType = metadata.contentType;
final bucket = imageRef.bucket;
final fullPath = imageRef.fullPath;

final prompt = TextPart("What's in the picture?");
// Construct a URL in the required format.
final storageUrl = 'gs://$bucket/$fullPath';
// Construct the filePart with the MIME type and the URL.
final filePart = FileData(mimeType, storageUrl);
// To generate text output, call generateContent with the text and the filePart.
final response = await model.generateContent([
  Content.multi([prompt, filePart])
]);
print(response.text);

Unity

var storageRef = FirebaseStorage.DefaultInstance.GetReference("images/image.jpg");
var metadata = await storageRef.PutFileAsync(filePathToJpg);

// Get the MIME type and Cloud Storage for Firebase URL.
var mimeType = metadata.ContentType;
// Construct a URL in the required format.
var storageURL = new Uri($"gs://{storageRef.Bucket}/{storageRef.Path}");

var prompt = ModelContent.Text("What's in this picture?");
// Construct a FileData that explicitly includes the MIME type and
// Cloud Storage for Firebase URL values.
var fileData = ModelContent.FileData(mimeType, storageURL);

// To generate text output, call GenerateContentAsync with the prompt and fileData.
var response = await model.GenerateContentAsync(new [] { prompt, fileData });
UnityEngine.Debug.Log(response.Text ?? "No text in response.");

ตัวเลือกที่ 2: รวมประเภท MIME และ URL อย่างชัดเจน

ก่อนที่จะลองใช้ตัวอย่างนี้ โปรดตรวจสอบว่าคุณได้ทำตาม คู่มือเริ่มต้นใช้งานสำหรับ Firebase AI Logic SDK แล้ว

ใช้ตัวเลือกนี้หากคุณทราบค่าประเภท MIME และ Cloud Storage for Firebase URL และต้องการรวมค่าเหล่านั้นไว้ใน คำขอแบบมัลติโมดัลอย่างชัดเจน การเรียกต้องใช้ทั้งประเภท MIME และ URL

Swift

let prompt = "What's in this picture?"
// Construct an imagePart that explicitly includes the MIME type and
// Cloud Storage for Firebase URL values.
let imagePart = FileDataPart(uri: "gs://bucket-name/path/image.jpg", mimeType: "image/jpeg")

// To generate text output, call generateContent with the prompt and imagePart.
let result = try await model.generateContent(prompt, imagePart)
if let text = result.text {
  print(text)
}

Kotlin

สำหรับ Kotlin เมธอดใน SDK นี้เป็นฟังก์ชันระงับและต้องเรียก จาก ขอบเขตของโครูทีน
// Construct a prompt that explicitly includes the MIME type and Cloud Storage for Firebase URL values.
val prompt = content {
    fileData(mimeType = "image/jpeg", uri = "gs://bucket-name/path/image.jpg")
    text("What's in this picture?")
}
// To generate text output, call generateContent with the prompt.
val response = model.generateContent(prompt)
println(response.text)

Java

สำหรับ Java เมธอดใน SDK นี้จะแสดงผลเป็น ListenableFuture
// Construct a prompt that explicitly includes the MIME type and Cloud Storage for Firebase URL values.
Content prompt = new Content.Builder()
        .addFilePart("gs://bucket-name/path/image.jpg", "image/jpeg")
        .addText("What's in this picture?")
        .build();

// To generate text output, call generateContent with the prompt
GenerativeModelFutures modelFutures = GenerativeModelFutures.from(model);
ListenableFuture<GenerateContentResponse> response = modelFutures.generateContent(prompt);
Futures.addCallback(response, new FutureCallback<>() {
    @Override
    public void onSuccess(GenerateContentResponse result) {
        String resultText = result.getText();
        System.out.println(resultText);
    }

    @Override
    public void onFailure(@NonNull Throwable t) {
        t.printStackTrace();
    }
}, executor);

Web

const prompt = "What's in this picture?";
// Construct an imagePart that explicitly includes the MIME type and Cloud Storage for Firebase URL values.
const imagePart = { fileData: { mimeType: "image/jpeg", fileUri: "gs://bucket-name/path/image.jpg" }};

// To generate text output, call generateContent with the prompt and imagePart.
const result = await model.generateContent([prompt, imagePart]);
console.log(result.response.text());

Dart

final prompt = TextPart("What's in the picture?");
// Construct a filePart that explicitly includes the MIME type and Cloud Storage for Firebase URL values.
final filePart = FileData('image/jpeg', 'gs://bucket-name/path/image.jpg'),
// To generate text output, call generateContent with the prompt and filePart.
final response = await model.generateContent([
  Content.multi([prompt, filePart])
]);
print(response.text);

Unity

var prompt = ModelContent.Text("What's in this picture?");
// Construct a FileData that explicitly includes the MIME type and
// Cloud Storage for Firebase URL values.
var fileData = ModelContent.FileData(
  mimeType: "image/jpeg",
  uri: new Uri("gs://bucket-name/path/image.jpg")
);

// To generate text output, call GenerateContentAsync with the prompt and fileData.
var response = await model.GenerateContentAsync(new [] { prompt, fileData });
UnityEngine.Debug.Log(response.Text ?? "No text in response.");