Repository Public
1This guide explains the different ways you can include media files such as2images, audio, video, and documents when making requests to the Gemini API.3The new methods are supported in all of the Gemini API endpoints, including4Batch, Interactions and Live API.5Choosing the right method depends on the size of your file, where your data is6currently stored, and how frequently you plan to use the file.78The simplest way to include a file as your input is to read a local file and9include it in a prompt. The following example shows how to read a local PDF10file. PDFs are limited to 50MB for this method. See the11[Input method comparison table](https://ai.google.dev/gemini-api/docs/generate-content/file-input-methods#method-comparison) for a complete list of file12input types and limits.1314### Python1516 from google import genai17 from google.genai import types18 import pathlib1920 client = genai.Client()2122 filepath = pathlib.Path('my_local_file.pdf')2324 prompt = "Summarize this document"25 response = client.models.generate_content(26 model="gemini-3.8-flash",27 contents=[28 types.Part.from_bytes(29 data=filepath.read_bytes(),30 mime_type='application/pdf',31 ),32 prompt33 ]34 )35 print(response.text)3637### JavaScript3839 import { GoogleGenAI } from "@google/genai";40 import * as fs from 'node:fs';4142 const ai = new GoogleGenAI({});43 const prompt = "Summarize this document";4445 async function main() {46 const filePath = path.join('content', 'my_local_file.pdf'); // Adjust path as needed4748 const contents = [49 { text: prompt },50 {51 inlineData: {52 mimeType: 'application/pdf',53 data: fs.readFileSync(filePath).toString("base64")54 }55 }56 ];5758 const response = await ai.models.generateContent({59 model: "gemini-3.8-flash",60 contents: contents61 });62 console.log(response.text);63 }6465 main();6667### REST6869 # Encode the local file to base6470 B64_CONTENT=$(base64 -w 0 my_local_file.pdf)7172 curl -X POST "https://generativelanguage.googleapis.com/v1beta/models/gemini-3.8-flash:generateContent" \73 -H "x-goog-api-key: $GEMINI_API_KEY" \74 -H 'Content-Type: application/json' \75 -d '{76 "contents": [77 {78 "parts": [79 {"text": "Summarize this document"}80 ]81 },82 {83 "parts": [84 {85 "inlineData": {86 "mimeType": "application/pdf",87 "data": "'"${B64_CONTENT}"'"88 }89 }90 ]91 }92 ]93 }'9495## Input method comparison9697The following table compares each input method with file limits and best use98cases. Note that the file size limit may vary depending on the file type and99model/tokenizer used to process the file.100101| Method | Best for | Max file size | Persistence |102|---|---|---|---|103| **Inline data** | Quick testing, small files, real-time applications. | 100 MB per request/payload (**50 MB for PDFs**) | None (sent with every request) |104| **File API upload** | Large files, files used multiple times. | 2 GB per file, up to 20GB per project | 48 Hours |105| **File API GCS URI registration** | Large files already in Google Cloud Storage, files used multiple times. | 2 GB per file, no overall storage limits | None (fetched per request). One time registration can give access for up to 30 days. |106| **External URLs** | Public data or data in cloud buckets (AWS, Azure, GCS) without re-uploading. | 100 MB per request/payload | None (fetched per request) |107108## Inline data109110For smaller files (under 100MB, or 50MB for PDFs), you can pass the data111directly in the request payload. This is the simplest method for quick tests or112applications handling real-time, transient data. You can provide data as113base64 encoded strings or by reading local files directly.114115For an example of reading from a local file, see the example at the beginning of116this page.117118### Fetch from a URL119120You can also fetch a file from a URL, convert it to bytes, and include it in the121input.122123### Python124125 from google import genai126 from google.genai import types127 import httpx128129 client = genai.Client()130131 doc_url = "https://discovery.ucl.ac.uk/id/eprint/10089234/1/343019_3_art_0_py4t4l_convrt.pdf"132 doc_data = httpx.get(doc_url).content133134 prompt = "Summarize this document"135136 response = client.models.generate_content(137 model="gemini-3.8-flash",138 contents=[139 types.Part.from_bytes(140 data=doc_data,141 mime_type='application/pdf',142 ),143 prompt144 ]145 )146 print(response.text)147148### JavaScript149150 import { GoogleGenAI } from "@google/genai";151152 const ai = new GoogleGenAI({});153 const docUrl = 'https://discovery.ucl.ac.uk/id/eprint/10089234/1/343019_3_art_0_py4t4l_convrt.pdf';154 const prompt = "Summarize this document";155156 async function main() {157 const pdfResp = await fetch(docUrl)158 .then((response) => response.arrayBuffer());159160 const contents = [161 { text: prompt },162 {163 inlineData: {164 mimeType: 'application/pdf',165 data: Buffer.from(pdfResp).toString("base64")166 }167 }168 ];169170 const response = await ai.models.generateContent({171 model: "gemini-3.8-flash",172 contents: contents173 });174 console.log(response.text);175 }176177 main();178179### REST180181 DOC_URL="https://discovery.ucl.ac.uk/id/eprint/10089234/1/343019_3_art_0_py4t4l_convrt.pdf"182 PROMPT="Summarize this document"183 DISPLAY_NAME="base64_pdf"184185 # Download the PDF186 wget -O "${DISPLAY_NAME}.pdf" "${DOC_URL}"187188 # Check for FreeBSD base64 and set flags accordingly189 if [[ "$(base64 --version 2>&1)" = *"FreeBSD"* ]]; then190 B64FLAGS="--input"191 else192 B64FLAGS="-w0"193 fi194195 # Base64 encode the PDF196 ENCODED_PDF=$(base64 $B64FLAGS "${DISPLAY_NAME}.pdf")197198 # Generate content using the base64 encoded PDF199 curl "https://generativelanguage.googleapis.com/v1beta/models/gemini-3.8-flash:generateContent" \200 -H "x-goog-api-key: $GEMINI_API_KEY" \201 -H 'Content-Type: application/json' \202 -X POST \203 -d '{204 "contents": [{205 "parts":[206 {"inline_data": {"mime_type": "application/pdf", "data": "'"$ENCODED_PDF"'"}},207 {"text": "'$PROMPT'"}208 ]209 }]210 }' 2> /dev/null > response.json211212 cat response.json213 echo214215 jq ".candidates[].content.parts[].text" response.json216217## Gemini File API218219The File API is designed for larger files (up to 2GB) or files you intend to220use in multiple requests.221222### Standard file upload223224Upload a local file to the Gemini API. Files uploaded this way are stored225temporarily (48 hours) and processed for efficient retrieval by the model.226227### Python228229 from google import genai230 client = genai.Client()231232 # Upload the file233 audio_file = client.files.upload(file="path/to/your/sample.mp3")234 prompt = "Describe this audio clip"235236 # Use the uploaded file in a prompt237 response = client.models.generate_content(238 model="gemini-3.8-flash",239 contents=[prompt, audio_file]240 )241 print(response.text)242243### JavaScript244245 import {246 GoogleGenAI,247 createUserContent,248 createPartFromUri,249 } from "@google/genai";250251 const ai = new GoogleGenAI({});252 const prompt = "Describe this audio clip";253254 async function main() {255 const filePath = "path/to/your/sample.mp3"; // Adjust path as needed256257 const myfile = await ai.files.upload({258 file: filePath,259 config: { mimeType: "audio/mpeg" },260 });261262 const response = await ai.models.generateContent({263 model: "gemini-3.8-flash",264 contents: createUserContent([265 prompt,266 createPartFromUri(myfile.uri, myfile.mimeType),267 ]),268 });269 console.log(response.text);270271 }272 await main();273274### REST275276 AUDIO_PATH="path/to/sample.mp3"277 MIME_TYPE=$(file -b --mime-type "${AUDIO_PATH}")278 NUM_BYTES=$(wc -c < "${AUDIO_PATH}")279 DISPLAY_NAME=AUDIO280281 tmp_header_file=upload-header.tmp282283 # Initial resumable request defining metadata.284 # The upload url is in the response headers dump them to a file.285 curl "${BASE_URL}/upload/v1beta/files" \286 -H "x-goog-api-key: $GEMINI_API_KEY" \287 -D "${tmp_header_file}" \288 -H "X-Goog-Upload-Protocol: resumable" \289 -H "X-Goog-Upload-Command: start" \290 -H "X-Goog-Upload-Header-Content-Length: ${NUM_BYTES}" \291 -H "X-Goog-Upload-Header-Content-Type: ${MIME_TYPE}" \292 -H "Content-Type: application/json" \293 -d "{'file': {'display_name': '${DISPLAY_NAME}'}}" 2> /dev/null294295 upload_url=$(grep -i "x-goog-upload-url: " "${tmp_header_file}" | cut -d" " -f2 | tr -d "\r")296 rm "${tmp_header_file}"297298 # Upload the actual bytes.299 curl "${upload_url}" \300 -H "Content-Length: ${NUM_BYTES}" \301 -H "X-Goog-Upload-Offset: 0" \302 -H "X-Goog-Upload-Command: upload, finalize" \303 --data-binary "@${AUDIO_PATH}" 2> /dev/null > file_info.json304305 file_uri=$(jq ".file.uri" file_info.json)306 echo file_uri=$file_uri307308 # Now generate content using that file309 curl "https://generativelanguage.googleapis.com/v1beta/models/gemini-3.8-flash:generateContent" \310 -H "x-goog-api-key: $GEMINI_API_KEY" \311 -H 'Content-Type: application/json' \312 -X POST \313 -d '{314 "contents": [{315 "parts":[316 {"text": "Describe this audio clip"},317 {"file_data":{"mime_type": "${MIME_TYPE}", "file_uri": '$file_uri'}}]318 }]319 }' 2> /dev/null > response.json320321 cat response.json322 echo323324 jq ".candidates[].content.parts[].text" response.json325326### Register Google Cloud Storage files327328If your data is already in Google Cloud Storage, you don't need to329download and re-upload it. You can register it directly with the File API.3303311. Grant **Service Agent** access to each bucket332333 1. Enable the Gemini API in your Google Cloud project.334335 2. Create the Service Agent:336337 `gcloud beta services identity create --service=generativelanguage.googleapis.com --project=<your_project>`338 3. **Grant the Gemini API Service Agent permissions** to read your storage339 buckets.340341 The user needs to assign the `Storage Object Viewer`342 [IAM role](https://docs.cloud.google.com/storage/docs/access-control/iam-roles#storage.objectViewer)343 to this service agent on the specific storage buckets they intend to use.344345 This access doesn't expire by default, but can be changed at any time. You can346 also use the347 [Google Cloud Storage IAM SDK](https://cloud.google.com/iam/docs/write-policy-client-libraries)348 commands to grant permissions.3492. Authenticate your service350351 **Prerequisites**352 - Enable API353 - Create a service account/agent with appropriate permissions.354355 You first need to authenticate as the service that has storage object viewer356 permissions. How this happens depends on the environment in which your file357 management code will be running.358359 **Outside of Google Cloud**360361 If your code is running from outside of Google Cloud, such as your desktop,362 download the account credentials from the Google Cloud Console with the363 following steps:364 1. Browse to the [Service Account console](https://console.cloud.google.com/iam-admin/serviceaccounts)365 2. Select the relevant service account366 3. Select the **Keys** tab and choose **Add key, Create new key**367 4. Choose the **JSON** key type, and note where the file was downloaded to on your machine.368369 For more details, see the official Google Cloud documentation on [service account key370 management](https://docs.cloud.google.com/iam/docs/keys-create-delete).371372 Then use the following commands to authenticate. These commands assume your373 service account file is in the current directory, named `service-account.json`.374375 ### Python376377 from google.oauth2.service_account import Credentials378379 GCS_READ_SCOPES = [ 380 'https://www.googleapis.com/auth/devstorage.read_only',381 'https://www.googleapis.com/auth/cloud-platform'382 ]383384 SERVICE_ACCOUNT_FILE = 'service-account.json'385386 credentials = Credentials.from_service_account_file(387 SERVICE_ACCOUNT_FILE,388 scopes=GCS_READ_SCOPES389 )390391 ### Javascript392393 const { GoogleAuth } = require('google-auth-library');394395 const GCS_READ_SCOPES = [396 'https://www.googleapis.com/auth/devstorage.read_only',397 'https://www.googleapis.com/auth/cloud-platform'398 ];399400 const SERVICE_ACCOUNT_FILE = 'service-account.json';401402 const auth = new GoogleAuth({403 keyFile: SERVICE_ACCOUNT_FILE,404 scopes: GCS_READ_SCOPES405 });406407 ### CLI408409 gcloud auth application-default login \410 --client-id-file=service-account.json \411 --scopes='https://www.googleapis.com/auth/cloud-platform,https://www.googleapis.com/auth/devstorage.read_only'412413 **On Google Cloud**414415 If you are running directly in Google Cloud, for example by using [Cloud416 Run functions](https://cloud.google.com/functions) or a417 [Compute Engine instance](https://cloud.google.com/products/compute), you will418 have implicit credentials but will need to re-authenticate to grant the419 appropriate scopes.420421 ### Python422423 This code expects that the service is running in an environment where424 [Application Default Credentials](https://docs.cloud.google.com/docs/authentication/application-default-credentials)425 can be obtained automatically, such as Cloud Run or Compute Engine.426427 import google.auth428429 GCS_READ_SCOPES = [ 430 'https://www.googleapis.com/auth/devstorage.read_only',431 'https://www.googleapis.com/auth/cloud-platform'432 ]433434 credentials, project = google.auth.default(scopes=GCS_READ_SCOPES)435436 ### JavaScript437438 This code expects that the service is running in an environment where439 [Application Default Credentials](https://docs.cloud.google.com/docs/authentication/application-default-credentials)440 can be obtained automatically, such as Cloud Run or Compute Engine.441442 const { GoogleAuth } = require('google-auth-library');443444 const auth = new GoogleAuth({445 scopes: [446 'https://www.googleapis.com/auth/devstorage.read_only',447 'https://www.googleapis.com/auth/cloud-platform'448 ]449 });450451 ### CLI452453 This is an interactive command. For services like Compute Engine you can attach scopes to454 the running service at the config level. See the [user-managed service455 docs](https://docs.cloud.google.com/compute/docs/access/create-enable-service-accounts-for-instances#using)456 for an example.457458 gcloud auth application-default login \459 --scopes="https://www.googleapis.com/auth/cloud-platform,https://www.googleapis.com/auth/devstorage.read_only"4604613. File registration (Files API)462463 Use the Files API to register files and produce a Files API path that can464 directly be used in the Gemini API.465466 ### Python467468 from google import genai469 from google.genai.types import Part470471 # Note that you must provide an API key in the GEMINI_API_KEY472 # environment variable, but it is unused for the registration endpoint.473 client = genai.Client()474475 registered_gcs_files = client.files.register_files(476 uris=["gs://my_bucket/some_object.pdf", "gs://bucket2/object2.txt"],477 # Use the credentials obtained in the previous step.478 auth=credentials479 )480 prompt = "Summarize this file."481482 # call generateContent for each file483 for f in registered_gcs_files.files:484 print(f.name)485 response = client.models.generate_content(486 model="gemini-3.8-flash",487 contents=[Part.from_uri(488 file_uri=f.uri,489 mime_type=f.mime_type,490 ),491 prompt],492 )493 print(response.text)494495 ### CLI496497 access_token=$(gcloud auth application-default print-access-token)498 project_id=$(gcloud config get-value project)499 curl -X POST https://generativelanguage.googleapis.com/v1beta/files:register \500 -H 'Content-Type: application/json' \501 -H "Authorization: Bearer ${access_token}" \502 -H "x-goog-user-project: ${project_id}" \503 -d '{"uris": ["gs://bucket/object1", "gs://bucket/object2"]}'504505## External HTTP / Signed URLs506507You can pass publicly accessible HTTPS URLs or pre-signed URLs (compatible with508[S3 Presigned509URLs](https://docs.aws.amazon.com/AmazonS3/latest/userguide/ShareObjectPreSignedURL.html)510and Azure SAS) directly in your generation request. The Gemini API will fetch511the content securely during processing. This is ideal for files up to 100MB that512you don't want to re-upload.513514> [!NOTE]515> **Note:** Gemini 2.0 family of models are not supported516517You can use public or signed URLs as input by using the URLs in the518`https://ai.google.dev/api/caching#FileData` field.519520### Python521522 from google import genai523 from google.genai.types import Part524525 uri = "https://ontheline.trincoll.edu/images/bookdown/sample-local-pdf.pdf"526 prompt = "Summarize this file"527528 client = genai.Client()529530 response = client.models.generate_content(531 model="gemini-3.8-flash",532 contents=[533 Part.from_uri(534 file_uri=uri,535 mime_type="application/pdf",536 ),537 prompt538 ],539 )540 print(response.text)541542### Javascript543544 import { GoogleGenAI, createPartFromUri } from '@google/genai';545546 const client = new GoogleGenAI({});547548 const uri = "https://ontheline.trincoll.edu/images/bookdown/sample-local-pdf.pdf";549550 async function main() {551 const response = await client.models.generateContent({552 model: 'gemini-3.8-flash',553 contents: [554 // equivalent to Part.from_uri(file_uri=uri, mime_type="...")555 createPartFromUri(uri, "application/pdf"),556 "summarize this file",557 ],558 });559560 console.log(response.text);561 }562563 main();564565### REST566567 curl "https://generativelanguage.googleapis.com/v1beta/models/gemini-3.8-flash:generateContent \568 -H 'x-goog-api-key: $GEMINI_API_KEY' \569 -H 'Content-Type: application/json' \570 -d '{571 "contents":[572 {573 "parts":[574 {"text": "Summarize this pdf"},575 {576 "file_data": {577 "mime_type":"application/pdf",578 "file_uri": "https://ontheline.trincoll.edu/images/bookdown/sample-local-pdf.pdf"579 }580 }581 ]582 }583 ]584 }'585586### Accessibility587588Verify that the URLs you provide don't lead to pages that require a login or589are behind a paywall. For private databases, ensure you create a signed URL590with the correct access permissions and expiry.591592### Safety checks593594The system performs a content moderation check on the URL to confirm they meet595safety and policy standards (e.g. non-opted out \& paywalled596content). If the URL you provided fails this check, you will get an597`url_retrieval_status` of `URL_RETRIEVAL_STATUS_UNSAFE`.598599### Supported content types600601This list of supported file types and limitations is intended as initial602guidance and is not comprehensive. The effective603set of supported types is subject to change and can vary based on the specific604model and tokenizer version in use. Unsupported types will result in an error.605Additionally, content retrieval for these file types606currently only supports publicly accessible URLs.607608#### Text file types609610- `text/html`611- `text/css`612- `text/plain`613- `text/xml`614- `text/csv`615- `text/rtf`616- `text/javascript`617618#### Application file types619620- `application/json`621- `application/pdf`622623#### Image file types624625- `image/bmp`626- `image/jpeg`627- `image/png`628- `image/webp`629630#### Video file types631632- `video/mp4`633- `video/mpeg`634- `video/quicktime`635- `video/avi`636- `video/x-flv`637- `video/mpg`638- `video/webm`639- `video/wmv`640- `video/3gpp`641642## Best practices643644- **Choose the right method:** Use inline data for small, transient files. Use the File API for larger or frequently used files. Use external URLs for data already hosted online.645- **Specify MIME Types:** Always provide the correct MIME type for the file data to ensure proper processing.646- **Handle Errors:** Implement error handling in your code to manage potential issues like network failures, file access problems, or API errors.647- **Manage GCS Permissions:** When using GCS registration, grant the Gemini API Service Agent only the necessary `Storage Object Viewer` role on the specific buckets.648- **Signed URL Security:** Ensure signed URLs have an appropriate expiration time and limited permissions.649650## Limitations651652- File size limits vary by method (see [comparison table](https://ai.google.dev/gemini-api/docs/generate-content/file-input-methods#method-comparison)) and file type.653- Inline data increases request payload size.654- File API uploads are temporary and expire after 48 hours.655- External URL fetching is limited to 100MB per payload and supports specific content types.656- Google Cloud Storage registration requires proper IAM setup and OAuth token management.657658## What's next659660- Try writing your own multimodal prompts using [Google AI Studio](http://aistudio.google.com/).661- For information on including files in your prompts, see the [Vision](https://ai.google.dev/gemini-api/docs/vision), [Audio](https://ai.google.dev/gemini-api/docs/audio), and [Document processing](https://ai.google.dev/gemini-api/docs/document-processing) guides.662- For more guidance on prompt design, like tuning sampling parameters, see the [Prompt strategies](https://ai.google.dev/gemini-api/docs/prompt-strategies) guide.