google-genai 1.53.0__py3-none-any.whl → 1.55.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- google/genai/__init__.py +1 -0
- google/genai/_api_client.py +6 -6
- google/genai/_interactions/__init__.py +117 -0
- google/genai/_interactions/_base_client.py +2019 -0
- google/genai/_interactions/_client.py +511 -0
- google/genai/_interactions/_compat.py +234 -0
- google/genai/_interactions/_constants.py +29 -0
- google/genai/_interactions/_exceptions.py +122 -0
- google/genai/_interactions/_files.py +139 -0
- google/genai/_interactions/_models.py +873 -0
- google/genai/_interactions/_qs.py +165 -0
- google/genai/_interactions/_resource.py +58 -0
- google/genai/_interactions/_response.py +847 -0
- google/genai/_interactions/_streaming.py +354 -0
- google/genai/_interactions/_types.py +276 -0
- google/genai/_interactions/_utils/__init__.py +79 -0
- google/genai/_interactions/_utils/_compat.py +61 -0
- google/genai/_interactions/_utils/_datetime_parse.py +151 -0
- google/genai/_interactions/_utils/_logs.py +40 -0
- google/genai/_interactions/_utils/_proxy.py +80 -0
- google/genai/_interactions/_utils/_reflection.py +57 -0
- google/genai/_interactions/_utils/_resources_proxy.py +39 -0
- google/genai/_interactions/_utils/_streams.py +27 -0
- google/genai/_interactions/_utils/_sync.py +73 -0
- google/genai/_interactions/_utils/_transform.py +472 -0
- google/genai/_interactions/_utils/_typing.py +172 -0
- google/genai/_interactions/_utils/_utils.py +437 -0
- google/genai/_interactions/_version.py +18 -0
- google/genai/_interactions/resources/__init__.py +34 -0
- google/genai/_interactions/resources/interactions.py +1350 -0
- google/genai/_interactions/types/__init__.py +107 -0
- google/genai/_interactions/types/allowed_tools.py +33 -0
- google/genai/_interactions/types/allowed_tools_param.py +35 -0
- google/genai/_interactions/types/annotation.py +42 -0
- google/genai/_interactions/types/annotation_param.py +42 -0
- google/genai/_interactions/types/audio_content.py +38 -0
- google/genai/_interactions/types/audio_content_param.py +45 -0
- google/genai/_interactions/types/audio_mime_type.py +25 -0
- google/genai/_interactions/types/audio_mime_type_param.py +27 -0
- google/genai/_interactions/types/code_execution_call_arguments.py +33 -0
- google/genai/_interactions/types/code_execution_call_arguments_param.py +32 -0
- google/genai/_interactions/types/code_execution_call_content.py +37 -0
- google/genai/_interactions/types/code_execution_call_content_param.py +37 -0
- google/genai/_interactions/types/code_execution_result_content.py +42 -0
- google/genai/_interactions/types/code_execution_result_content_param.py +41 -0
- google/genai/_interactions/types/content_delta.py +358 -0
- google/genai/_interactions/types/content_start.py +79 -0
- google/genai/_interactions/types/content_stop.py +35 -0
- google/genai/_interactions/types/deep_research_agent_config.py +33 -0
- google/genai/_interactions/types/deep_research_agent_config_param.py +32 -0
- google/genai/_interactions/types/document_content.py +36 -0
- google/genai/_interactions/types/document_content_param.py +43 -0
- google/genai/_interactions/types/dynamic_agent_config.py +44 -0
- google/genai/_interactions/types/dynamic_agent_config_param.py +33 -0
- google/genai/_interactions/types/error_event.py +46 -0
- google/genai/_interactions/types/file_search_result_content.py +46 -0
- google/genai/_interactions/types/file_search_result_content_param.py +46 -0
- google/genai/_interactions/types/function.py +38 -0
- google/genai/_interactions/types/function_call_content.py +39 -0
- google/genai/_interactions/types/function_call_content_param.py +39 -0
- google/genai/_interactions/types/function_param.py +37 -0
- google/genai/_interactions/types/function_result_content.py +52 -0
- google/genai/_interactions/types/function_result_content_param.py +54 -0
- google/genai/_interactions/types/generation_config.py +57 -0
- google/genai/_interactions/types/generation_config_param.py +59 -0
- google/genai/_interactions/types/google_search_call_arguments.py +29 -0
- google/genai/_interactions/types/google_search_call_arguments_param.py +31 -0
- google/genai/_interactions/types/google_search_call_content.py +37 -0
- google/genai/_interactions/types/google_search_call_content_param.py +37 -0
- google/genai/_interactions/types/google_search_result.py +35 -0
- google/genai/_interactions/types/google_search_result_content.py +43 -0
- google/genai/_interactions/types/google_search_result_content_param.py +44 -0
- google/genai/_interactions/types/google_search_result_param.py +35 -0
- google/genai/_interactions/types/image_content.py +41 -0
- google/genai/_interactions/types/image_content_param.py +48 -0
- google/genai/_interactions/types/image_mime_type.py +23 -0
- google/genai/_interactions/types/image_mime_type_param.py +25 -0
- google/genai/_interactions/types/interaction.py +165 -0
- google/genai/_interactions/types/interaction_create_params.py +212 -0
- google/genai/_interactions/types/interaction_event.py +37 -0
- google/genai/_interactions/types/interaction_get_params.py +46 -0
- google/genai/_interactions/types/interaction_sse_event.py +32 -0
- google/genai/_interactions/types/interaction_status_update.py +37 -0
- google/genai/_interactions/types/mcp_server_tool_call_content.py +42 -0
- google/genai/_interactions/types/mcp_server_tool_call_content_param.py +42 -0
- google/genai/_interactions/types/mcp_server_tool_result_content.py +52 -0
- google/genai/_interactions/types/mcp_server_tool_result_content_param.py +54 -0
- google/genai/_interactions/types/model.py +36 -0
- google/genai/_interactions/types/model_param.py +38 -0
- google/genai/_interactions/types/speech_config.py +35 -0
- google/genai/_interactions/types/speech_config_param.py +35 -0
- google/genai/_interactions/types/text_content.py +37 -0
- google/genai/_interactions/types/text_content_param.py +38 -0
- google/genai/_interactions/types/thinking_level.py +22 -0
- google/genai/_interactions/types/thought_content.py +41 -0
- google/genai/_interactions/types/thought_content_param.py +47 -0
- google/genai/_interactions/types/tool.py +100 -0
- google/genai/_interactions/types/tool_choice.py +26 -0
- google/genai/_interactions/types/tool_choice_config.py +28 -0
- google/genai/_interactions/types/tool_choice_config_param.py +29 -0
- google/genai/_interactions/types/tool_choice_param.py +28 -0
- google/genai/_interactions/types/tool_choice_type.py +22 -0
- google/genai/_interactions/types/tool_param.py +97 -0
- google/genai/_interactions/types/turn.py +76 -0
- google/genai/_interactions/types/turn_param.py +73 -0
- google/genai/_interactions/types/url_context_call_arguments.py +29 -0
- google/genai/_interactions/types/url_context_call_arguments_param.py +31 -0
- google/genai/_interactions/types/url_context_call_content.py +37 -0
- google/genai/_interactions/types/url_context_call_content_param.py +37 -0
- google/genai/_interactions/types/url_context_result.py +33 -0
- google/genai/_interactions/types/url_context_result_content.py +43 -0
- google/genai/_interactions/types/url_context_result_content_param.py +44 -0
- google/genai/_interactions/types/url_context_result_param.py +32 -0
- google/genai/_interactions/types/usage.py +106 -0
- google/genai/_interactions/types/usage_param.py +106 -0
- google/genai/_interactions/types/video_content.py +41 -0
- google/genai/_interactions/types/video_content_param.py +48 -0
- google/genai/_interactions/types/video_mime_type.py +36 -0
- google/genai/_interactions/types/video_mime_type_param.py +38 -0
- google/genai/_live_converters.py +34 -3
- google/genai/_tokens_converters.py +5 -0
- google/genai/batches.py +62 -55
- google/genai/client.py +223 -0
- google/genai/errors.py +16 -1
- google/genai/file_search_stores.py +60 -60
- google/genai/files.py +56 -56
- google/genai/interactions.py +17 -0
- google/genai/live.py +4 -3
- google/genai/models.py +15 -3
- google/genai/tests/__init__.py +21 -0
- google/genai/tests/afc/__init__.py +21 -0
- google/genai/tests/afc/test_convert_if_exist_pydantic_model.py +309 -0
- google/genai/tests/afc/test_convert_number_values_for_function_call_args.py +63 -0
- google/genai/tests/afc/test_find_afc_incompatible_tool_indexes.py +240 -0
- google/genai/tests/afc/test_generate_content_stream_afc.py +530 -0
- google/genai/tests/afc/test_generate_content_stream_afc_thoughts.py +77 -0
- google/genai/tests/afc/test_get_function_map.py +176 -0
- google/genai/tests/afc/test_get_function_response_parts.py +277 -0
- google/genai/tests/afc/test_get_max_remote_calls_for_afc.py +130 -0
- google/genai/tests/afc/test_invoke_function_from_dict_args.py +241 -0
- google/genai/tests/afc/test_raise_error_for_afc_incompatible_config.py +159 -0
- google/genai/tests/afc/test_should_append_afc_history.py +53 -0
- google/genai/tests/afc/test_should_disable_afc.py +214 -0
- google/genai/tests/batches/__init__.py +17 -0
- google/genai/tests/batches/test_cancel.py +77 -0
- google/genai/tests/batches/test_create.py +78 -0
- google/genai/tests/batches/test_create_with_bigquery.py +113 -0
- google/genai/tests/batches/test_create_with_file.py +82 -0
- google/genai/tests/batches/test_create_with_gcs.py +125 -0
- google/genai/tests/batches/test_create_with_inlined_requests.py +255 -0
- google/genai/tests/batches/test_delete.py +86 -0
- google/genai/tests/batches/test_embedding.py +157 -0
- google/genai/tests/batches/test_get.py +78 -0
- google/genai/tests/batches/test_list.py +79 -0
- google/genai/tests/caches/__init__.py +17 -0
- google/genai/tests/caches/constants.py +29 -0
- google/genai/tests/caches/test_create.py +210 -0
- google/genai/tests/caches/test_create_custom_url.py +105 -0
- google/genai/tests/caches/test_delete.py +54 -0
- google/genai/tests/caches/test_delete_custom_url.py +52 -0
- google/genai/tests/caches/test_get.py +94 -0
- google/genai/tests/caches/test_get_custom_url.py +52 -0
- google/genai/tests/caches/test_list.py +68 -0
- google/genai/tests/caches/test_update.py +70 -0
- google/genai/tests/caches/test_update_custom_url.py +58 -0
- google/genai/tests/chats/__init__.py +1 -0
- google/genai/tests/chats/test_get_history.py +597 -0
- google/genai/tests/chats/test_send_message.py +844 -0
- google/genai/tests/chats/test_validate_response.py +90 -0
- google/genai/tests/client/__init__.py +17 -0
- google/genai/tests/client/test_async_stream.py +427 -0
- google/genai/tests/client/test_client_close.py +197 -0
- google/genai/tests/client/test_client_initialization.py +1687 -0
- google/genai/tests/client/test_client_requests.py +355 -0
- google/genai/tests/client/test_custom_client.py +77 -0
- google/genai/tests/client/test_http_options.py +178 -0
- google/genai/tests/client/test_replay_client_equality.py +168 -0
- google/genai/tests/client/test_retries.py +846 -0
- google/genai/tests/client/test_upload_errors.py +136 -0
- google/genai/tests/common/__init__.py +17 -0
- google/genai/tests/common/test_common.py +954 -0
- google/genai/tests/conftest.py +162 -0
- google/genai/tests/documents/__init__.py +17 -0
- google/genai/tests/documents/test_delete.py +51 -0
- google/genai/tests/documents/test_get.py +85 -0
- google/genai/tests/documents/test_list.py +72 -0
- google/genai/tests/errors/__init__.py +1 -0
- google/genai/tests/errors/test_api_error.py +417 -0
- google/genai/tests/file_search_stores/__init__.py +17 -0
- google/genai/tests/file_search_stores/test_create.py +66 -0
- google/genai/tests/file_search_stores/test_delete.py +64 -0
- google/genai/tests/file_search_stores/test_get.py +94 -0
- google/genai/tests/file_search_stores/test_import_file.py +112 -0
- google/genai/tests/file_search_stores/test_list.py +57 -0
- google/genai/tests/file_search_stores/test_upload_to_file_search_store.py +141 -0
- google/genai/tests/files/__init__.py +17 -0
- google/genai/tests/files/test_delete.py +46 -0
- google/genai/tests/files/test_download.py +85 -0
- google/genai/tests/files/test_get.py +46 -0
- google/genai/tests/files/test_list.py +72 -0
- google/genai/tests/files/test_upload.py +255 -0
- google/genai/tests/imports/test_no_optional_imports.py +28 -0
- google/genai/tests/interactions/__init__.py +0 -0
- google/genai/tests/interactions/test_integration.py +80 -0
- google/genai/tests/live/__init__.py +16 -0
- google/genai/tests/live/test_live.py +2177 -0
- google/genai/tests/live/test_live_music.py +362 -0
- google/genai/tests/live/test_live_response.py +163 -0
- google/genai/tests/live/test_send_client_content.py +147 -0
- google/genai/tests/live/test_send_realtime_input.py +268 -0
- google/genai/tests/live/test_send_tool_response.py +222 -0
- google/genai/tests/local_tokenizer/__init__.py +17 -0
- google/genai/tests/local_tokenizer/test_local_tokenizer.py +343 -0
- google/genai/tests/local_tokenizer/test_local_tokenizer_loader.py +235 -0
- google/genai/tests/mcp/__init__.py +17 -0
- google/genai/tests/mcp/test_has_mcp_tool_usage.py +89 -0
- google/genai/tests/mcp/test_mcp_to_gemini_tools.py +191 -0
- google/genai/tests/mcp/test_parse_config_for_mcp_sessions.py +201 -0
- google/genai/tests/mcp/test_parse_config_for_mcp_usage.py +130 -0
- google/genai/tests/mcp/test_set_mcp_usage_header.py +72 -0
- google/genai/tests/models/__init__.py +17 -0
- google/genai/tests/models/constants.py +8 -0
- google/genai/tests/models/test_compute_tokens.py +120 -0
- google/genai/tests/models/test_count_tokens.py +159 -0
- google/genai/tests/models/test_delete.py +107 -0
- google/genai/tests/models/test_edit_image.py +264 -0
- google/genai/tests/models/test_embed_content.py +94 -0
- google/genai/tests/models/test_function_call_streaming.py +442 -0
- google/genai/tests/models/test_generate_content.py +2502 -0
- google/genai/tests/models/test_generate_content_cached_content.py +132 -0
- google/genai/tests/models/test_generate_content_config_zero_value.py +103 -0
- google/genai/tests/models/test_generate_content_from_apikey.py +44 -0
- google/genai/tests/models/test_generate_content_http_options.py +40 -0
- google/genai/tests/models/test_generate_content_image_generation.py +143 -0
- google/genai/tests/models/test_generate_content_mcp.py +343 -0
- google/genai/tests/models/test_generate_content_media_resolution.py +97 -0
- google/genai/tests/models/test_generate_content_model.py +139 -0
- google/genai/tests/models/test_generate_content_part.py +821 -0
- google/genai/tests/models/test_generate_content_thought.py +76 -0
- google/genai/tests/models/test_generate_content_tools.py +1761 -0
- google/genai/tests/models/test_generate_images.py +191 -0
- google/genai/tests/models/test_generate_videos.py +759 -0
- google/genai/tests/models/test_get.py +104 -0
- google/genai/tests/models/test_list.py +233 -0
- google/genai/tests/models/test_recontext_image.py +189 -0
- google/genai/tests/models/test_segment_image.py +148 -0
- google/genai/tests/models/test_update.py +95 -0
- google/genai/tests/models/test_upscale_image.py +157 -0
- google/genai/tests/operations/__init__.py +17 -0
- google/genai/tests/operations/test_get.py +38 -0
- google/genai/tests/public_samples/__init__.py +17 -0
- google/genai/tests/public_samples/test_gemini_text_only.py +34 -0
- google/genai/tests/pytest_helper.py +229 -0
- google/genai/tests/shared/__init__.py +16 -0
- google/genai/tests/shared/batches/__init__.py +14 -0
- google/genai/tests/shared/batches/test_create_delete.py +57 -0
- google/genai/tests/shared/batches/test_create_get_cancel.py +56 -0
- google/genai/tests/shared/batches/test_list.py +40 -0
- google/genai/tests/shared/caches/__init__.py +14 -0
- google/genai/tests/shared/caches/test_create_get_delete.py +67 -0
- google/genai/tests/shared/caches/test_create_update_get.py +71 -0
- google/genai/tests/shared/caches/test_list.py +40 -0
- google/genai/tests/shared/chats/__init__.py +14 -0
- google/genai/tests/shared/chats/test_send_message.py +48 -0
- google/genai/tests/shared/chats/test_send_message_stream.py +50 -0
- google/genai/tests/shared/files/__init__.py +14 -0
- google/genai/tests/shared/files/test_list.py +41 -0
- google/genai/tests/shared/files/test_upload_get_delete.py +54 -0
- google/genai/tests/shared/models/__init__.py +14 -0
- google/genai/tests/shared/models/test_compute_tokens.py +41 -0
- google/genai/tests/shared/models/test_count_tokens.py +40 -0
- google/genai/tests/shared/models/test_edit_image.py +67 -0
- google/genai/tests/shared/models/test_embed.py +40 -0
- google/genai/tests/shared/models/test_generate_content.py +39 -0
- google/genai/tests/shared/models/test_generate_content_stream.py +54 -0
- google/genai/tests/shared/models/test_generate_images.py +40 -0
- google/genai/tests/shared/models/test_generate_videos.py +38 -0
- google/genai/tests/shared/models/test_list.py +37 -0
- google/genai/tests/shared/models/test_recontext_image.py +55 -0
- google/genai/tests/shared/models/test_segment_image.py +52 -0
- google/genai/tests/shared/models/test_upscale_image.py +52 -0
- google/genai/tests/shared/tunings/__init__.py +16 -0
- google/genai/tests/shared/tunings/test_create.py +46 -0
- google/genai/tests/shared/tunings/test_create_get_cancel.py +56 -0
- google/genai/tests/shared/tunings/test_list.py +39 -0
- google/genai/tests/tokens/__init__.py +16 -0
- google/genai/tests/tokens/test_create.py +154 -0
- google/genai/tests/transformers/__init__.py +17 -0
- google/genai/tests/transformers/test_blobs.py +71 -0
- google/genai/tests/transformers/test_bytes.py +15 -0
- google/genai/tests/transformers/test_duck_type.py +96 -0
- google/genai/tests/transformers/test_function_responses.py +72 -0
- google/genai/tests/transformers/test_schema.py +653 -0
- google/genai/tests/transformers/test_t_batch.py +286 -0
- google/genai/tests/transformers/test_t_content.py +160 -0
- google/genai/tests/transformers/test_t_contents.py +398 -0
- google/genai/tests/transformers/test_t_part.py +85 -0
- google/genai/tests/transformers/test_t_parts.py +87 -0
- google/genai/tests/transformers/test_t_tool.py +157 -0
- google/genai/tests/transformers/test_t_tools.py +195 -0
- google/genai/tests/tunings/__init__.py +16 -0
- google/genai/tests/tunings/test_cancel.py +39 -0
- google/genai/tests/tunings/test_end_to_end.py +106 -0
- google/genai/tests/tunings/test_get.py +67 -0
- google/genai/tests/tunings/test_list.py +75 -0
- google/genai/tests/tunings/test_tune.py +268 -0
- google/genai/tests/types/__init__.py +16 -0
- google/genai/tests/types/test_bytes_internal.py +271 -0
- google/genai/tests/types/test_bytes_type.py +152 -0
- google/genai/tests/types/test_future.py +101 -0
- google/genai/tests/types/test_optional_types.py +36 -0
- google/genai/tests/types/test_part_type.py +616 -0
- google/genai/tests/types/test_schema_from_json_schema.py +417 -0
- google/genai/tests/types/test_schema_json_schema.py +468 -0
- google/genai/tests/types/test_types.py +2903 -0
- google/genai/tunings.py +57 -57
- google/genai/types.py +229 -121
- google/genai/version.py +1 -1
- {google_genai-1.53.0.dist-info → google_genai-1.55.0.dist-info}/METADATA +4 -2
- google_genai-1.55.0.dist-info/RECORD +345 -0
- google_genai-1.53.0.dist-info/RECORD +0 -41
- {google_genai-1.53.0.dist-info → google_genai-1.55.0.dist-info}/WHEEL +0 -0
- {google_genai-1.53.0.dist-info → google_genai-1.55.0.dist-info}/licenses/LICENSE +0 -0
- {google_genai-1.53.0.dist-info → google_genai-1.55.0.dist-info}/top_level.txt +0 -0
|
@@ -0,0 +1,417 @@
|
|
|
1
|
+
# Copyright 2025 Google LLC
|
|
2
|
+
#
|
|
3
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
+
# you may not use this file except in compliance with the License.
|
|
5
|
+
# You may obtain a copy of the License at
|
|
6
|
+
#
|
|
7
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
+
#
|
|
9
|
+
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
+
# See the License for the specific language governing permissions and
|
|
13
|
+
# limitations under the License.
|
|
14
|
+
#
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
"""Unit Tests for the APIError class.
|
|
18
|
+
|
|
19
|
+
End to end tests should be in models/test_generate_content.py.
|
|
20
|
+
"""
|
|
21
|
+
|
|
22
|
+
import pickle
|
|
23
|
+
|
|
24
|
+
import httpx
|
|
25
|
+
import pytest
|
|
26
|
+
|
|
27
|
+
from ... import errors
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
def test_constructor_code_none_error_in_json_code_in_error():
|
|
31
|
+
|
|
32
|
+
actual_error = errors.APIError(
|
|
33
|
+
None,
|
|
34
|
+
{
|
|
35
|
+
'error': {
|
|
36
|
+
'code': 400,
|
|
37
|
+
'message': 'error message',
|
|
38
|
+
'status': 'INVALID_ARGUMENT',
|
|
39
|
+
}
|
|
40
|
+
},
|
|
41
|
+
httpx.Response(status_code=400),
|
|
42
|
+
)
|
|
43
|
+
|
|
44
|
+
assert actual_error.code == 400
|
|
45
|
+
assert actual_error.message == 'error message'
|
|
46
|
+
assert actual_error.status == 'INVALID_ARGUMENT'
|
|
47
|
+
assert actual_error.details == {
|
|
48
|
+
'error': {
|
|
49
|
+
'code': 400,
|
|
50
|
+
'message': 'error message',
|
|
51
|
+
'status': 'INVALID_ARGUMENT',
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
|
|
56
|
+
def test_constructor_code_none_error_in_json_code_outside_error():
|
|
57
|
+
|
|
58
|
+
actual_error = errors.APIError(
|
|
59
|
+
None,
|
|
60
|
+
{
|
|
61
|
+
'code': 400,
|
|
62
|
+
'error': {
|
|
63
|
+
'code': 500,
|
|
64
|
+
'message': 'error message',
|
|
65
|
+
'status': 'INVALID_ARGUMENT',
|
|
66
|
+
},
|
|
67
|
+
},
|
|
68
|
+
httpx.Response(status_code=400),
|
|
69
|
+
)
|
|
70
|
+
|
|
71
|
+
assert actual_error.code == 400
|
|
72
|
+
assert actual_error.message == 'error message'
|
|
73
|
+
assert actual_error.status == 'INVALID_ARGUMENT'
|
|
74
|
+
assert actual_error.details == {
|
|
75
|
+
'code': 400,
|
|
76
|
+
'error': {
|
|
77
|
+
'code': 500,
|
|
78
|
+
'message': 'error message',
|
|
79
|
+
'status': 'INVALID_ARGUMENT',
|
|
80
|
+
},
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
|
|
84
|
+
def test_constructor_code_not_present():
|
|
85
|
+
|
|
86
|
+
actual_error = errors.APIError(
|
|
87
|
+
None,
|
|
88
|
+
{
|
|
89
|
+
'error': {
|
|
90
|
+
'message': 'error message',
|
|
91
|
+
'status': 'INVALID_ARGUMENT',
|
|
92
|
+
}
|
|
93
|
+
},
|
|
94
|
+
httpx.Response(status_code=400),
|
|
95
|
+
)
|
|
96
|
+
|
|
97
|
+
assert actual_error.code is None
|
|
98
|
+
assert actual_error.message == 'error message'
|
|
99
|
+
assert actual_error.status == 'INVALID_ARGUMENT'
|
|
100
|
+
assert actual_error.details == {
|
|
101
|
+
'error': {
|
|
102
|
+
'message': 'error message',
|
|
103
|
+
'status': 'INVALID_ARGUMENT',
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
|
|
108
|
+
def test_constructor_code_exist_error_in_json():
|
|
109
|
+
|
|
110
|
+
actual_error = errors.APIError(
|
|
111
|
+
400,
|
|
112
|
+
{
|
|
113
|
+
'error': {
|
|
114
|
+
'code': 400,
|
|
115
|
+
'message': 'error message',
|
|
116
|
+
'status': 'INVALID_ARGUMENT',
|
|
117
|
+
}
|
|
118
|
+
},
|
|
119
|
+
httpx.Response(status_code=400),
|
|
120
|
+
)
|
|
121
|
+
|
|
122
|
+
assert actual_error.code == 400
|
|
123
|
+
assert actual_error.message == 'error message'
|
|
124
|
+
assert actual_error.status == 'INVALID_ARGUMENT'
|
|
125
|
+
assert actual_error.details == {
|
|
126
|
+
'error': {
|
|
127
|
+
'code': 400,
|
|
128
|
+
'message': 'error message',
|
|
129
|
+
'status': 'INVALID_ARGUMENT',
|
|
130
|
+
}
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
|
|
134
|
+
def test_constructor_error_not_in_json():
|
|
135
|
+
|
|
136
|
+
actual_error = errors.APIError(
|
|
137
|
+
400,
|
|
138
|
+
{
|
|
139
|
+
'message': 'error message',
|
|
140
|
+
'status': 'INVALID_ARGUMENT',
|
|
141
|
+
'code': 400,
|
|
142
|
+
},
|
|
143
|
+
httpx.Response(status_code=400),
|
|
144
|
+
)
|
|
145
|
+
|
|
146
|
+
assert actual_error.code == 400
|
|
147
|
+
assert actual_error.message == 'error message'
|
|
148
|
+
assert actual_error.status == 'INVALID_ARGUMENT'
|
|
149
|
+
assert actual_error.details == {
|
|
150
|
+
'message': 'error message',
|
|
151
|
+
'status': 'INVALID_ARGUMENT',
|
|
152
|
+
'code': 400,
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
|
|
156
|
+
def test_constructor_error_in_json_status_outside_error():
|
|
157
|
+
|
|
158
|
+
actual_error = errors.APIError(
|
|
159
|
+
400,
|
|
160
|
+
{
|
|
161
|
+
'status': 'OUTER_INVALID_ARGUMENT_STATUS',
|
|
162
|
+
'error': {
|
|
163
|
+
'code': 400,
|
|
164
|
+
'message': 'error message',
|
|
165
|
+
'status': 'INNER_INVALID_ARGUMENT_STATUS',
|
|
166
|
+
},
|
|
167
|
+
},
|
|
168
|
+
httpx.Response(status_code=400),
|
|
169
|
+
)
|
|
170
|
+
|
|
171
|
+
assert actual_error.code == 400
|
|
172
|
+
assert actual_error.message == 'error message'
|
|
173
|
+
assert actual_error.status == 'OUTER_INVALID_ARGUMENT_STATUS'
|
|
174
|
+
assert actual_error.details == {
|
|
175
|
+
'status': 'OUTER_INVALID_ARGUMENT_STATUS',
|
|
176
|
+
'error': {
|
|
177
|
+
'code': 400,
|
|
178
|
+
'message': 'error message',
|
|
179
|
+
'status': 'INNER_INVALID_ARGUMENT_STATUS',
|
|
180
|
+
},
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
|
|
184
|
+
def test_constructor_status_not_present():
|
|
185
|
+
|
|
186
|
+
actual_error = errors.APIError(
|
|
187
|
+
400,
|
|
188
|
+
{
|
|
189
|
+
'error': {
|
|
190
|
+
'code': 400,
|
|
191
|
+
'message': 'error message',
|
|
192
|
+
}
|
|
193
|
+
},
|
|
194
|
+
httpx.Response(status_code=400),
|
|
195
|
+
)
|
|
196
|
+
|
|
197
|
+
assert actual_error.code == 400
|
|
198
|
+
assert actual_error.message == 'error message'
|
|
199
|
+
assert actual_error.status == None
|
|
200
|
+
assert actual_error.details == {
|
|
201
|
+
'error': {
|
|
202
|
+
'code': 400,
|
|
203
|
+
'message': 'error message',
|
|
204
|
+
}
|
|
205
|
+
}
|
|
206
|
+
|
|
207
|
+
|
|
208
|
+
def test_constructor_error_in_json_message_outside_error():
|
|
209
|
+
|
|
210
|
+
actual_error = errors.APIError(
|
|
211
|
+
400,
|
|
212
|
+
{
|
|
213
|
+
'message': 'OUTER_ERROR_MESSAGE',
|
|
214
|
+
'error': {
|
|
215
|
+
'code': 400,
|
|
216
|
+
'message': 'INNER_ERROR_MESSAGE',
|
|
217
|
+
'status': 'INVALID_ARGUMENT',
|
|
218
|
+
},
|
|
219
|
+
},
|
|
220
|
+
httpx.Response(status_code=400),
|
|
221
|
+
)
|
|
222
|
+
|
|
223
|
+
assert actual_error.code == 400
|
|
224
|
+
assert actual_error.message == 'OUTER_ERROR_MESSAGE'
|
|
225
|
+
assert actual_error.status == 'INVALID_ARGUMENT'
|
|
226
|
+
assert actual_error.details == {
|
|
227
|
+
'message': 'OUTER_ERROR_MESSAGE',
|
|
228
|
+
'error': {
|
|
229
|
+
'code': 400,
|
|
230
|
+
'message': 'INNER_ERROR_MESSAGE',
|
|
231
|
+
'status': 'INVALID_ARGUMENT',
|
|
232
|
+
},
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
|
|
236
|
+
def test_constructor_message_not_present():
|
|
237
|
+
|
|
238
|
+
actual_error = errors.APIError(
|
|
239
|
+
400,
|
|
240
|
+
{
|
|
241
|
+
'error': {
|
|
242
|
+
'code': 400,
|
|
243
|
+
'status': 'INVALID_ARGUMENT',
|
|
244
|
+
}
|
|
245
|
+
},
|
|
246
|
+
httpx.Response(status_code=400),
|
|
247
|
+
)
|
|
248
|
+
|
|
249
|
+
assert actual_error.code == 400
|
|
250
|
+
assert actual_error.message is None
|
|
251
|
+
assert actual_error.status == 'INVALID_ARGUMENT'
|
|
252
|
+
assert actual_error.details == {
|
|
253
|
+
'error': {
|
|
254
|
+
'code': 400,
|
|
255
|
+
'status': 'INVALID_ARGUMENT',
|
|
256
|
+
}
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
|
|
260
|
+
def test_raise_for_response_code_exist_json_decoder_error():
|
|
261
|
+
class FakeResponse(httpx.Response):
|
|
262
|
+
|
|
263
|
+
def read(self) -> bytes:
|
|
264
|
+
self._content = b'{"data": {"key1": "value1", "key2"}'
|
|
265
|
+
return self._content
|
|
266
|
+
|
|
267
|
+
try:
|
|
268
|
+
errors.APIError.raise_for_response(
|
|
269
|
+
FakeResponse(
|
|
270
|
+
status_code=503,
|
|
271
|
+
extensions={'reason_phrase': b'Service Unavailable'},
|
|
272
|
+
)
|
|
273
|
+
)
|
|
274
|
+
except errors.ServerError as actual_error:
|
|
275
|
+
assert actual_error.code == 503
|
|
276
|
+
assert actual_error.message == '{"data": {"key1": "value1", "key2"}'
|
|
277
|
+
assert actual_error.status == 'Service Unavailable'
|
|
278
|
+
assert actual_error.details == {
|
|
279
|
+
'message': '{"data": {"key1": "value1", "key2"}',
|
|
280
|
+
'status': 'Service Unavailable',
|
|
281
|
+
}
|
|
282
|
+
|
|
283
|
+
|
|
284
|
+
def test_raise_for_response_client_error():
|
|
285
|
+
class FakeResponse(httpx.Response):
|
|
286
|
+
|
|
287
|
+
def read(self) -> bytes:
|
|
288
|
+
self._content = (
|
|
289
|
+
b'{"error": {"code": 400, "message": "error message", "status":'
|
|
290
|
+
b' "INVALID_ARGUMENT"}}'
|
|
291
|
+
)
|
|
292
|
+
return self._content
|
|
293
|
+
|
|
294
|
+
try:
|
|
295
|
+
errors.APIError.raise_for_response(FakeResponse(status_code=400))
|
|
296
|
+
except errors.ClientError as actual_error:
|
|
297
|
+
assert actual_error.code == 400
|
|
298
|
+
assert actual_error.message == 'error message'
|
|
299
|
+
assert actual_error.status == 'INVALID_ARGUMENT'
|
|
300
|
+
assert actual_error.details == {
|
|
301
|
+
'error': {
|
|
302
|
+
'code': 400,
|
|
303
|
+
'message': 'error message',
|
|
304
|
+
'status': 'INVALID_ARGUMENT',
|
|
305
|
+
}
|
|
306
|
+
}
|
|
307
|
+
|
|
308
|
+
|
|
309
|
+
def test_raise_for_response_server_error():
|
|
310
|
+
class FakeResponse(httpx.Response):
|
|
311
|
+
|
|
312
|
+
def read(self) -> bytes:
|
|
313
|
+
self._content = (
|
|
314
|
+
b'{"error": {"code": 500, "message": "error message", "status":'
|
|
315
|
+
b' "SERVER_INTERNAL ERROR"}}'
|
|
316
|
+
)
|
|
317
|
+
return self._content
|
|
318
|
+
|
|
319
|
+
try:
|
|
320
|
+
errors.APIError.raise_for_response(FakeResponse(status_code=500))
|
|
321
|
+
except errors.ServerError as actual_error:
|
|
322
|
+
assert actual_error.code == 500
|
|
323
|
+
assert actual_error.message == 'error message'
|
|
324
|
+
assert actual_error.status == 'SERVER_INTERNAL ERROR'
|
|
325
|
+
assert actual_error.details == {
|
|
326
|
+
'error': {
|
|
327
|
+
'code': 500,
|
|
328
|
+
'message': 'error message',
|
|
329
|
+
'status': 'SERVER_INTERNAL ERROR',
|
|
330
|
+
}
|
|
331
|
+
}
|
|
332
|
+
|
|
333
|
+
|
|
334
|
+
def test_api_error_is_picklable():
|
|
335
|
+
pickled_error = pickle.loads(pickle.dumps(errors.APIError(1, {})))
|
|
336
|
+
assert isinstance(pickled_error, errors.APIError)
|
|
337
|
+
|
|
338
|
+
|
|
339
|
+
@pytest.mark.asyncio
|
|
340
|
+
async def test_raise_for_async_response_client_error():
|
|
341
|
+
class FakeResponse(httpx.Response):
|
|
342
|
+
|
|
343
|
+
async def aread(self) -> bytes:
|
|
344
|
+
self._content = (
|
|
345
|
+
b'{"error": {"code": 400, "message": "error message", "status":'
|
|
346
|
+
b' "INVALID_ARGUMENT"}}'
|
|
347
|
+
)
|
|
348
|
+
return self._content
|
|
349
|
+
|
|
350
|
+
try:
|
|
351
|
+
await errors.APIError.raise_for_async_response(
|
|
352
|
+
FakeResponse(status_code=400)
|
|
353
|
+
)
|
|
354
|
+
except errors.ClientError as actual_error:
|
|
355
|
+
assert actual_error.code == 400
|
|
356
|
+
assert actual_error.message == 'error message'
|
|
357
|
+
assert actual_error.status == 'INVALID_ARGUMENT'
|
|
358
|
+
assert actual_error.details == {
|
|
359
|
+
'error': {
|
|
360
|
+
'code': 400,
|
|
361
|
+
'message': 'error message',
|
|
362
|
+
'status': 'INVALID_ARGUMENT',
|
|
363
|
+
}
|
|
364
|
+
}
|
|
365
|
+
|
|
366
|
+
|
|
367
|
+
@pytest.mark.asyncio
|
|
368
|
+
async def test_raise_for_async_response_server_error():
|
|
369
|
+
class FakeResponse(httpx.Response):
|
|
370
|
+
|
|
371
|
+
async def aread(self) -> bytes:
|
|
372
|
+
self._content = (
|
|
373
|
+
b'{"error": {"code": 500, "message": "error message", "status":'
|
|
374
|
+
b' "SERVER_INTERNAL ERROR"}}'
|
|
375
|
+
)
|
|
376
|
+
return self._content
|
|
377
|
+
|
|
378
|
+
try:
|
|
379
|
+
await errors.APIError.raise_for_async_response(
|
|
380
|
+
FakeResponse(status_code=500)
|
|
381
|
+
)
|
|
382
|
+
except errors.ServerError as actual_error:
|
|
383
|
+
assert actual_error.code == 500
|
|
384
|
+
assert actual_error.message == 'error message'
|
|
385
|
+
assert actual_error.status == 'SERVER_INTERNAL ERROR'
|
|
386
|
+
assert actual_error.details == {
|
|
387
|
+
'error': {
|
|
388
|
+
'code': 500,
|
|
389
|
+
'message': 'error message',
|
|
390
|
+
'status': 'SERVER_INTERNAL ERROR',
|
|
391
|
+
}
|
|
392
|
+
}
|
|
393
|
+
|
|
394
|
+
|
|
395
|
+
@pytest.mark.asyncio
|
|
396
|
+
async def test_raise_for_async_response_code_exist_json_decoder_error():
|
|
397
|
+
class FakeResponse(httpx.Response):
|
|
398
|
+
|
|
399
|
+
async def aread(self) -> bytes:
|
|
400
|
+
self._content = b'{"data": {"key1": "value1", "key2"}'
|
|
401
|
+
return self._content
|
|
402
|
+
|
|
403
|
+
try:
|
|
404
|
+
await errors.APIError.raise_for_async_response(
|
|
405
|
+
FakeResponse(
|
|
406
|
+
status_code=503,
|
|
407
|
+
extensions={'reason_phrase': b'Service Unavailable'},
|
|
408
|
+
)
|
|
409
|
+
)
|
|
410
|
+
except errors.ServerError as actual_error:
|
|
411
|
+
assert actual_error.code == 503
|
|
412
|
+
assert actual_error.message == '{"data": {"key1": "value1", "key2"}'
|
|
413
|
+
assert actual_error.status == 'Service Unavailable'
|
|
414
|
+
assert actual_error.details == {
|
|
415
|
+
'message': '{"data": {"key1": "value1", "key2"}',
|
|
416
|
+
'status': 'Service Unavailable',
|
|
417
|
+
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
# Copyright 2025 Google LLC
|
|
2
|
+
#
|
|
3
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
+
# you may not use this file except in compliance with the License.
|
|
5
|
+
# You may obtain a copy of the License at
|
|
6
|
+
#
|
|
7
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
+
#
|
|
9
|
+
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
+
# See the License for the specific language governing permissions and
|
|
13
|
+
# limitations under the License.
|
|
14
|
+
#
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
"""Tests for the Google GenAI SDK's file search stores module."""
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
# Copyright 2025 Google LLC
|
|
2
|
+
#
|
|
3
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
+
# you may not use this file except in compliance with the License.
|
|
5
|
+
# You may obtain a copy of the License at
|
|
6
|
+
#
|
|
7
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
+
#
|
|
9
|
+
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
+
# See the License for the specific language governing permissions and
|
|
13
|
+
# limitations under the License.
|
|
14
|
+
#
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
"""Tests for file_search_stores.create()."""
|
|
18
|
+
|
|
19
|
+
import pytest
|
|
20
|
+
|
|
21
|
+
from ... import types
|
|
22
|
+
from .. import pytest_helper
|
|
23
|
+
|
|
24
|
+
# All tests will be run for both Vertex and MLDev.
|
|
25
|
+
test_table: list[pytest_helper.TestTableItem] = [
|
|
26
|
+
pytest_helper.TestTableItem(
|
|
27
|
+
name="test_display_name",
|
|
28
|
+
parameters=types._CreateFileSearchStoreParameters(
|
|
29
|
+
config=types.CreateFileSearchStoreConfig(
|
|
30
|
+
display_name="My File Search Store"
|
|
31
|
+
)
|
|
32
|
+
),
|
|
33
|
+
exception_if_vertex="only supported in the Gemini Developer client",
|
|
34
|
+
),
|
|
35
|
+
pytest_helper.TestTableItem(
|
|
36
|
+
name="test_basic",
|
|
37
|
+
parameters=types._CreateFileSearchStoreParameters(),
|
|
38
|
+
exception_if_vertex="only supported in the Gemini Developer client",
|
|
39
|
+
),
|
|
40
|
+
]
|
|
41
|
+
|
|
42
|
+
pytestmark = [
|
|
43
|
+
pytest.mark.usefixtures("mock_timestamped_unique_name"),
|
|
44
|
+
pytest_helper.setup(
|
|
45
|
+
file=__file__,
|
|
46
|
+
globals_for_file=globals(),
|
|
47
|
+
test_method="file_search_stores.create",
|
|
48
|
+
test_table=test_table,
|
|
49
|
+
),
|
|
50
|
+
]
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
@pytest.mark.asyncio
|
|
54
|
+
async def test_async_display_name(client):
|
|
55
|
+
with pytest_helper.exception_if_vertex(client, ValueError):
|
|
56
|
+
file_search_store = await client.aio.file_search_stores.create(
|
|
57
|
+
config=types.CreateFileSearchStoreConfig(
|
|
58
|
+
display_name="My File Search Store"
|
|
59
|
+
)
|
|
60
|
+
)
|
|
61
|
+
|
|
62
|
+
|
|
63
|
+
@pytest.mark.asyncio
|
|
64
|
+
async def test_async_basic(client):
|
|
65
|
+
with pytest_helper.exception_if_vertex(client, ValueError):
|
|
66
|
+
file_search_store = await client.aio.file_search_stores.create()
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
# Copyright 2025 Google LLC
|
|
2
|
+
#
|
|
3
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
+
# you may not use this file except in compliance with the License.
|
|
5
|
+
# You may obtain a copy of the License at
|
|
6
|
+
#
|
|
7
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
+
#
|
|
9
|
+
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
+
# See the License for the specific language governing permissions and
|
|
13
|
+
# limitations under the License.
|
|
14
|
+
#
|
|
15
|
+
|
|
16
|
+
"""Tests for file_search_stores.delete()."""
|
|
17
|
+
|
|
18
|
+
import pytest
|
|
19
|
+
|
|
20
|
+
from ... import types
|
|
21
|
+
from .. import pytest_helper
|
|
22
|
+
|
|
23
|
+
# All tests will be run for both Vertex and MLDev.
|
|
24
|
+
test_table: list[pytest_helper.TestTableItem] = [
|
|
25
|
+
pytest_helper.TestTableItem(
|
|
26
|
+
name="test_delete_with_name",
|
|
27
|
+
parameters=types._DeleteFileSearchStoreParameters(
|
|
28
|
+
name="fileSearchStores/acxjj7m366ln-aw6xyp94icll",
|
|
29
|
+
),
|
|
30
|
+
exception_if_vertex="only supported in the Gemini Developer client",
|
|
31
|
+
),
|
|
32
|
+
pytest_helper.TestTableItem(
|
|
33
|
+
name="test_delete_with_name_and_force",
|
|
34
|
+
parameters=types._DeleteFileSearchStoreParameters(
|
|
35
|
+
name="fileSearchStores/7igesc9r2zw9-0mpxpsqubv7s",
|
|
36
|
+
config=types.DeleteFileSearchStoreConfig(force=True),
|
|
37
|
+
),
|
|
38
|
+
exception_if_vertex="only supported in the Gemini Developer client",
|
|
39
|
+
),
|
|
40
|
+
]
|
|
41
|
+
|
|
42
|
+
pytestmark = pytest_helper.setup(
|
|
43
|
+
file=__file__,
|
|
44
|
+
globals_for_file=globals(),
|
|
45
|
+
test_method="file_search_stores.delete",
|
|
46
|
+
test_table=test_table,
|
|
47
|
+
)
|
|
48
|
+
|
|
49
|
+
|
|
50
|
+
@pytest.mark.asyncio
|
|
51
|
+
async def test_async_delete(client):
|
|
52
|
+
with pytest_helper.exception_if_vertex(client, ValueError):
|
|
53
|
+
await client.aio.file_search_stores.delete(
|
|
54
|
+
name="fileSearchStores/my-file-search-store-l65kcyel9lkz"
|
|
55
|
+
)
|
|
56
|
+
|
|
57
|
+
|
|
58
|
+
@pytest.mark.asyncio
|
|
59
|
+
async def test_async_force_delete(client):
|
|
60
|
+
with pytest_helper.exception_if_vertex(client, ValueError):
|
|
61
|
+
await client.aio.file_search_stores.delete(
|
|
62
|
+
name="fileSearchStores/my-file-search-store-vjtrjw6re8oz",
|
|
63
|
+
config=types.DeleteFileSearchStoreConfig(force=True),
|
|
64
|
+
)
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
# Copyright 2025 Google LLC
|
|
2
|
+
#
|
|
3
|
+
# Licensed under the Apache License, Version 2.0 (the "License");
|
|
4
|
+
# you may not use this file except in compliance with the License.
|
|
5
|
+
# You may obtain a copy of the License at
|
|
6
|
+
#
|
|
7
|
+
# http://www.apache.org/licenses/LICENSE-2.0
|
|
8
|
+
#
|
|
9
|
+
# Unless required by applicable law or agreed to in writing, software
|
|
10
|
+
# distributed under the License is distributed on an "AS IS" BASIS,
|
|
11
|
+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
12
|
+
# See the License for the specific language governing permissions and
|
|
13
|
+
# limitations under the License.
|
|
14
|
+
#
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
"""Tests for file_search_stores.get()."""
|
|
18
|
+
|
|
19
|
+
import pytest
|
|
20
|
+
|
|
21
|
+
from ... import types
|
|
22
|
+
from .. import pytest_helper
|
|
23
|
+
|
|
24
|
+
# A FileSearchStore name known to exist in the test environment.
|
|
25
|
+
# Replace with a real one from your test setup.
|
|
26
|
+
_EXISTING_FILE_SEARCH_STORE_NAME = "fileSearchStores/5en07ei3kojo-yo8sjqgvx2xf"
|
|
27
|
+
_NON_EXISTENT_FILE_SEARCH_STORE_NAME = (
|
|
28
|
+
"fileSearchStores/non-existent-file-search-store"
|
|
29
|
+
)
|
|
30
|
+
_INVALID_FILE_SEARCH_STORE_NAME = (
|
|
31
|
+
"fileSearchStores/_invalid_file_search_store_name"
|
|
32
|
+
)
|
|
33
|
+
_NOT_A_FILE_SEARCH_STORE_NAME = "genai-test-file-search-store"
|
|
34
|
+
|
|
35
|
+
# All tests will be run for both Vertex and MLDev.
|
|
36
|
+
test_table: list[pytest_helper.TestTableItem] = [
|
|
37
|
+
pytest_helper.TestTableItem(
|
|
38
|
+
name="test_get_success",
|
|
39
|
+
parameters=types._GetFileSearchStoreParameters(
|
|
40
|
+
name=_EXISTING_FILE_SEARCH_STORE_NAME
|
|
41
|
+
),
|
|
42
|
+
exception_if_vertex="only supported in the Gemini Developer client",
|
|
43
|
+
),
|
|
44
|
+
pytest_helper.TestTableItem(
|
|
45
|
+
name="test_get_not_found",
|
|
46
|
+
parameters=types._GetFileSearchStoreParameters(
|
|
47
|
+
name=_NON_EXISTENT_FILE_SEARCH_STORE_NAME
|
|
48
|
+
),
|
|
49
|
+
exception_if_vertex="only supported in the Gemini Developer client",
|
|
50
|
+
# Expect an exception to be raised by the mock
|
|
51
|
+
exception_if_mldev="PERMISSION_DENIED",
|
|
52
|
+
),
|
|
53
|
+
pytest_helper.TestTableItem(
|
|
54
|
+
name="test_get_invalid_name",
|
|
55
|
+
parameters=types._GetFileSearchStoreParameters(
|
|
56
|
+
name=_INVALID_FILE_SEARCH_STORE_NAME
|
|
57
|
+
),
|
|
58
|
+
exception_if_vertex="only supported in the Gemini Developer client",
|
|
59
|
+
# Validation should catch this before the API call
|
|
60
|
+
exception_if_mldev="INVALID_ARGUMENT",
|
|
61
|
+
),
|
|
62
|
+
pytest_helper.TestTableItem(
|
|
63
|
+
name="test_get_not_a_file_search_store_name",
|
|
64
|
+
parameters=types._GetFileSearchStoreParameters(
|
|
65
|
+
name=_NOT_A_FILE_SEARCH_STORE_NAME
|
|
66
|
+
),
|
|
67
|
+
exception_if_vertex="only supported in the Gemini Developer client",
|
|
68
|
+
exception_if_mldev="Not Found",
|
|
69
|
+
),
|
|
70
|
+
]
|
|
71
|
+
|
|
72
|
+
pytestmark = pytest_helper.setup(
|
|
73
|
+
file=__file__,
|
|
74
|
+
globals_for_file=globals(),
|
|
75
|
+
test_method="file_search_stores.get",
|
|
76
|
+
test_table=test_table,
|
|
77
|
+
)
|
|
78
|
+
|
|
79
|
+
|
|
80
|
+
@pytest.mark.asyncio
|
|
81
|
+
async def test_async_get(client):
|
|
82
|
+
with pytest_helper.exception_if_vertex(client, ValueError):
|
|
83
|
+
# This test relies on the mocking/replays set up by pytest_helper
|
|
84
|
+
# For a success case:
|
|
85
|
+
try:
|
|
86
|
+
file_search_store = await client.aio.file_search_stores.get(
|
|
87
|
+
name=_EXISTING_FILE_SEARCH_STORE_NAME
|
|
88
|
+
)
|
|
89
|
+
assert file_search_store is not None
|
|
90
|
+
assert file_search_store.name == _EXISTING_FILE_SEARCH_STORE_NAME
|
|
91
|
+
except Exception as e:
|
|
92
|
+
# Depending on the mock setup, errors might be raised directly
|
|
93
|
+
print(f"Async get failed: {e}")
|
|
94
|
+
raise
|