File analysis
UC AI is multimodal. With it, you can analyze a PDF, an image, or another document directly in your Oracle database. An AI model then extracts information from the file, answers a question about it, or analyzes its content.
UC AI converts each file to base64 content, and sends it in your message array to the AI provider. You can combine the file content with a text prompt.
Supported file types:
- PDF - extract text, analyze a table, answer a question about the content
- Image (JPEG, PNG, WebP, and more) - describe an image, identify an object, read text in an image
- Other document formats - each provider supports its own set
This guide shows how to build file analysis with the UC AI message API. It has one example for a PDF, and one for an image.
Example 1: Analyze a PDF file
Section titled âExample 1: Analyze a PDF fileâThis example uses a PDF with a table of characters from the TV show âThe Officeâ. The table holds this data:
| First Name | Last Name | |
|---|---|---|
| Michael | Scott | michael.scott@dundermifflin.com |
| Pam | Beesly | pam.beesly@dundermifflin.com |
| Jim | Halpert | jim.halpert@dundermifflin.com |
| Angela | Martin | angela.martin@dundermifflin.com |
| Dwight | Schrute | dwight.schrute@dundermifflin.com |
| Kevin | Malone | kevin.malone@dundermifflin.com |
The call must carry the file, so build the message array yourself. It holds a system message, a user message, and the file content.
declare l_messages json_array_t := json_array_t(); l_content json_array_t := json_array_t(); l_result json_object_t; l_final_message clob; l_blob blob;begin -- Select the file first: a subquery is not allowed as a parameter of a PL/SQL call select blob_content into l_blob from your_table where id = 1;
-- Create a system message to set the context for the AI l_messages.append(uc_ai_message_api.create_system_message( 'You are an assistant answering trivia questions about TV Shows. Please answer in super short sentences.'));
-- The user message consists of two parts: the file content and a text content
-- Add the file content to the user message l_content.append(uc_ai_message_api.create_file_content( p_media_type => 'application/pdf', p_data_blob => l_blob, p_filename => 'change_me.pdf' ));
-- Add text content to the user message l_content.append(uc_ai_message_api.create_text_content( 'What is the TV show called of the characters that are inside the attached PDF?' )); -- Add the user message with the file content and text content to the messages array l_messages.append(uc_ai_message_api.create_user_message(l_content));
-- Call the AI service to generate a response based on the messages l_result := uc_ai_google.generate_text( p_messages => l_messages, p_model => uc_ai_google.c_model_gemini_3_7_flash, p_max_tool_calls => 3 );
l_final_message := l_result.get_clob('final_message'); sys.dbms_output.put_line('Last message: ' || l_final_message); -- > The AI should respond with "The Office" or similarend;Example 2: Analyze an image file
Section titled âExample 2: Analyze an image fileâThis example uses an image of an apple. The call sends the image to the AI service and asks for a description.
declare l_messages json_array_t := json_array_t(); l_content json_array_t := json_array_t(); l_result json_object_t; l_res_clob clob; l_final_message clob;begin -- Create a system message to set the context for the AI l_messages.append(uc_ai_message_api.create_system_message( 'You are an image analysis assistant.'));
-- The user message consists of two parts: the file content and a text content -- Add the file content to the user message l_content.append(uc_ai_message_api.create_file_content( p_media_type => 'image/webp', p_data_blob => uc_ai_test_utils.get_apple_webp, p_filename => 'data.webp' )); -- Add text content to the user message l_content.append(uc_ai_message_api.create_text_content( 'What is the fruit depicted in the attached image?' )); -- Add the user message with the file content and text content to the messages array l_messages.append(uc_ai_message_api.create_user_message(l_content));
l_result := uc_ai_anthropic.generate_text( p_messages => l_messages, p_model => uc_ai_anthropic.c_model_claude_4_5_haiku, p_max_tool_calls => 3 );
l_final_message := l_result.get_clob('final_message'); sys.dbms_output.put_line('Last message: ' || l_final_message); -- > The AI should respond with "Apple"Provider support and limits
Section titled âProvider support and limitsâEvery provider uses the same message API for file input. The accepted file types
differ by provider and by model. If the framework cannot map a file to the format
of the provider, it rejects the file with ORA-20303 (unhandled format).
| Provider | Images | Documents | Notes |
|---|---|---|---|
| Anthropic | JPEG, PNG, GIF, WebP | ||
| OpenAI | JPEG, PNG, GIF, WebP | ||
| JPEG, PNG, GIF, WebP | PDF (+ more) | ||
| Mistral | JPEG, PNG, WebP | UC AI sends a PDF as a document_url | |
| Ollama | depends on the model | â | UC AI sends every file as an image |
| OCI | PNG, JPG only (⤠5 MB) | PDF only | GENERIC-format vision models only. A Cohere model accepts no file |
OCI specifics
Section titled âOCI specificsâOCI Generative AI supports file input only through its GENERIC chat format. Use a
GENERIC-format vision model, for example Meta Llama vision, Google Gemini, or
xAI Grok. A Cohere model rejects file content. An image must be a PNG or a
JPG, and not larger than 5 MB. A document must be a PDF. OCI rejects WebP,
GIF, and every other type with ORA-20303.
You can also pass a detail hint in the provider options. The values are AUTO
(the default), HIGH, and LOW:
l_content.append(uc_ai_message_api.create_file_content( p_media_type => 'image/png', p_data_blob => :my_png, p_filename => 'chart.png', p_provider_options => json_object_t('{"detail":"HIGH"}')));Extract text without a chat model
Section titled âExtract text without a chat modelâTo get the text and the structure of a document, and not an answer about it, use OCR. uc_ai.ocr reads a PDF or an image with Mistral, OCI Document Understanding or Ollama. It returns Markdown, pages, and the position and confidence of each text block.
Turn a document into rows
Section titled âTurn a document into rowsâThis guide sends a file and gets an answer. To turn that answer into rows, you need a response schema, checks that decide what you can post unattended, and an inbox loop.