google-genai 1.10.0__py3-none-any.whl → 1.12.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/_api_client.py +100 -31
- google/genai/_automatic_function_calling_util.py +4 -24
- google/genai/_common.py +40 -37
- google/genai/_extra_utils.py +72 -12
- google/genai/_live_converters.py +2487 -0
- google/genai/_replay_api_client.py +32 -26
- google/genai/_transformers.py +119 -25
- google/genai/batches.py +45 -45
- google/genai/caches.py +126 -126
- google/genai/chats.py +13 -9
- google/genai/client.py +3 -2
- google/genai/errors.py +6 -6
- google/genai/files.py +38 -38
- google/genai/live.py +138 -1029
- google/genai/models.py +455 -387
- google/genai/operations.py +33 -33
- google/genai/pagers.py +2 -2
- google/genai/py.typed +1 -0
- google/genai/tunings.py +70 -70
- google/genai/types.py +964 -45
- google/genai/version.py +1 -1
- {google_genai-1.10.0.dist-info → google_genai-1.12.0.dist-info}/METADATA +1 -1
- google_genai-1.12.0.dist-info/RECORD +29 -0
- {google_genai-1.10.0.dist-info → google_genai-1.12.0.dist-info}/WHEEL +1 -1
- google_genai-1.10.0.dist-info/RECORD +0 -27
- {google_genai-1.10.0.dist-info → google_genai-1.12.0.dist-info}/licenses/LICENSE +0 -0
- {google_genai-1.10.0.dist-info → google_genai-1.12.0.dist-info}/top_level.txt +0 -0
google/genai/live.py
CHANGED
@@ -33,25 +33,16 @@ from . import _transformers as t
|
|
33
33
|
from . import client
|
34
34
|
from . import types
|
35
35
|
from ._api_client import BaseApiClient
|
36
|
-
from ._common import experimental_warning
|
37
36
|
from ._common import get_value_by_path as getv
|
38
37
|
from ._common import set_value_by_path as setv
|
39
|
-
from .
|
40
|
-
from .models import _Content_from_vertex
|
38
|
+
from . import _live_converters as live_converters
|
41
39
|
from .models import _Content_to_mldev
|
42
40
|
from .models import _Content_to_vertex
|
43
|
-
|
44
|
-
from .models import _GenerateContentConfig_to_vertex
|
45
|
-
from .models import _SafetySetting_to_mldev
|
46
|
-
from .models import _SafetySetting_to_vertex
|
47
|
-
from .models import _SpeechConfig_to_mldev
|
48
|
-
from .models import _SpeechConfig_to_vertex
|
49
|
-
from .models import _Tool_to_mldev
|
50
|
-
from .models import _Tool_to_vertex
|
41
|
+
|
51
42
|
|
52
43
|
try:
|
53
|
-
from websockets.asyncio.client import ClientConnection
|
54
|
-
from websockets.asyncio.client import connect
|
44
|
+
from websockets.asyncio.client import ClientConnection
|
45
|
+
from websockets.asyncio.client import connect
|
55
46
|
except ModuleNotFoundError:
|
56
47
|
# This try/except is for TAP, mypy complains about it which is why we have the type: ignore
|
57
48
|
from websockets.client import ClientConnection # type: ignore
|
@@ -65,71 +56,11 @@ _FUNCTION_RESPONSE_REQUIRES_ID = (
|
|
65
56
|
)
|
66
57
|
|
67
58
|
|
68
|
-
def _ClientContent_to_mldev(
|
69
|
-
api_client: BaseApiClient,
|
70
|
-
from_object: types.LiveClientContent,
|
71
|
-
) -> dict:
|
72
|
-
client_content = from_object.model_dump(exclude_none=True, mode='json')
|
73
|
-
if 'turns' in client_content:
|
74
|
-
client_content['turns'] = [
|
75
|
-
_Content_to_mldev(api_client=api_client, from_object=item)
|
76
|
-
for item in client_content['turns']
|
77
|
-
]
|
78
|
-
return client_content
|
79
|
-
|
80
|
-
|
81
|
-
def _ClientContent_to_vertex(
|
82
|
-
api_client: BaseApiClient,
|
83
|
-
from_object: types.LiveClientContent,
|
84
|
-
) -> dict:
|
85
|
-
client_content = from_object.model_dump(exclude_none=True, mode='json')
|
86
|
-
if 'turns' in client_content:
|
87
|
-
client_content['turns'] = [
|
88
|
-
_Content_to_vertex(api_client=api_client, from_object=item)
|
89
|
-
for item in client_content['turns']
|
90
|
-
]
|
91
|
-
return client_content
|
92
|
-
|
93
|
-
|
94
|
-
def _ToolResponse_to_mldev(
|
95
|
-
api_client: BaseApiClient,
|
96
|
-
from_object: types.LiveClientToolResponse,
|
97
|
-
) -> dict:
|
98
|
-
tool_response = from_object.model_dump(exclude_none=True, mode='json')
|
99
|
-
for response in tool_response.get('function_responses', []):
|
100
|
-
if response.get('id') is None:
|
101
|
-
raise ValueError(_FUNCTION_RESPONSE_REQUIRES_ID)
|
102
|
-
return tool_response
|
103
|
-
|
104
|
-
|
105
|
-
def _ToolResponse_to_vertex(
|
106
|
-
api_client: BaseApiClient,
|
107
|
-
from_object: types.LiveClientToolResponse,
|
108
|
-
) -> dict:
|
109
|
-
tool_response = from_object.model_dump(exclude_none=True, mode='json')
|
110
|
-
return tool_response
|
111
|
-
|
112
|
-
def _AudioTranscriptionConfig_to_mldev(
|
113
|
-
api_client: BaseApiClient,
|
114
|
-
from_object: types.AudioTranscriptionConfig,
|
115
|
-
) -> dict:
|
116
|
-
audio_transcription: dict[str, Any] = {}
|
117
|
-
return audio_transcription
|
118
|
-
|
119
|
-
|
120
|
-
def _AudioTranscriptionConfig_to_vertex(
|
121
|
-
api_client: BaseApiClient,
|
122
|
-
from_object: types.AudioTranscriptionConfig,
|
123
|
-
) -> dict:
|
124
|
-
audio_transcription: dict[str, Any] = {}
|
125
|
-
return audio_transcription
|
126
|
-
|
127
|
-
|
128
59
|
class AsyncSession:
|
129
60
|
"""[Preview] AsyncSession."""
|
130
61
|
|
131
62
|
def __init__(
|
132
|
-
self, api_client:
|
63
|
+
self, api_client: BaseApiClient, websocket: ClientConnection
|
133
64
|
):
|
134
65
|
self._api_client = api_client
|
135
66
|
self._ws = websocket
|
@@ -149,7 +80,7 @@ class AsyncSession:
|
|
149
80
|
]
|
150
81
|
] = None,
|
151
82
|
end_of_turn: Optional[bool] = False,
|
152
|
-
):
|
83
|
+
) -> None:
|
153
84
|
"""[Deprecated] Send input to the model.
|
154
85
|
|
155
86
|
> **Warning**: This method is deprecated and will be removed in a future
|
@@ -196,7 +127,7 @@ class AsyncSession:
|
|
196
127
|
]
|
197
128
|
] = None,
|
198
129
|
turn_complete: bool = True,
|
199
|
-
):
|
130
|
+
) -> None:
|
200
131
|
"""Send non-realtime, turn based content to the model.
|
201
132
|
|
202
133
|
There are two ways to send messages to the live API:
|
@@ -238,8 +169,14 @@ class AsyncSession:
|
|
238
169
|
```
|
239
170
|
import google.genai
|
240
171
|
from google.genai import types
|
172
|
+
import os
|
173
|
+
|
174
|
+
if os.environ.get('GOOGLE_GENAI_USE_VERTEXAI'):
|
175
|
+
MODEL_NAME = 'gemini-2.0-flash-live-preview-04-09'
|
176
|
+
else:
|
177
|
+
MODEL_NAME = 'gemini-2.0-flash-live-001';
|
241
178
|
|
242
|
-
client = genai.Client(
|
179
|
+
client = genai.Client()
|
243
180
|
async with client.aio.live.connect(
|
244
181
|
model=MODEL_NAME,
|
245
182
|
config={"response_modalities": ["TEXT"]}
|
@@ -253,21 +190,31 @@ class AsyncSession:
|
|
253
190
|
print(msg.text)
|
254
191
|
```
|
255
192
|
"""
|
256
|
-
client_content =
|
193
|
+
client_content = t.t_client_content(turns, turn_complete)
|
257
194
|
|
258
195
|
if self._api_client.vertexai:
|
259
|
-
client_content_dict =
|
196
|
+
client_content_dict = live_converters._LiveClientContent_to_vertex(
|
260
197
|
api_client=self._api_client, from_object=client_content
|
261
198
|
)
|
262
199
|
else:
|
263
|
-
client_content_dict =
|
200
|
+
client_content_dict = live_converters._LiveClientContent_to_mldev(
|
264
201
|
api_client=self._api_client, from_object=client_content
|
265
202
|
)
|
266
203
|
|
267
204
|
await self._ws.send(json.dumps({'client_content': client_content_dict}))
|
268
205
|
|
269
|
-
async def send_realtime_input(
|
270
|
-
|
206
|
+
async def send_realtime_input(
|
207
|
+
self,
|
208
|
+
*,
|
209
|
+
media: Optional[types.BlobImageUnionDict] = None,
|
210
|
+
audio: Optional[types.BlobOrDict] = None,
|
211
|
+
audio_stream_end: Optional[bool] = None,
|
212
|
+
video: Optional[types.BlobImageUnionDict] = None,
|
213
|
+
text: Optional[str] = None,
|
214
|
+
activity_start: Optional[types.ActivityStartOrDict] = None,
|
215
|
+
activity_end: Optional[types.ActivityEndOrDict] = None,
|
216
|
+
) -> None:
|
217
|
+
"""Send realtime input to the model, only send one argument per call.
|
271
218
|
|
272
219
|
Use `send_realtime_input` for realtime audio chunks and video
|
273
220
|
frames(images).
|
@@ -291,7 +238,15 @@ class AsyncSession:
|
|
291
238
|
|
292
239
|
import PIL.Image
|
293
240
|
|
294
|
-
|
241
|
+
import os
|
242
|
+
|
243
|
+
if os.environ.get('GOOGLE_GENAI_USE_VERTEXAI'):
|
244
|
+
MODEL_NAME = 'gemini-2.0-flash-live-preview-04-09'
|
245
|
+
else:
|
246
|
+
MODEL_NAME = 'gemini-2.0-flash-live-001';
|
247
|
+
|
248
|
+
|
249
|
+
client = genai.Client()
|
295
250
|
|
296
251
|
async with client.aio.live.connect(
|
297
252
|
model=MODEL_NAME,
|
@@ -309,9 +264,46 @@ class AsyncSession:
|
|
309
264
|
print(f'{msg.text}')
|
310
265
|
```
|
311
266
|
"""
|
312
|
-
|
313
|
-
|
314
|
-
|
267
|
+
kwargs:dict[str, Any] = {}
|
268
|
+
if media is not None:
|
269
|
+
kwargs['media'] = media
|
270
|
+
if audio is not None:
|
271
|
+
kwargs['audio'] = audio
|
272
|
+
if audio_stream_end is not None:
|
273
|
+
kwargs['audio_stream_end'] = audio_stream_end
|
274
|
+
if video is not None:
|
275
|
+
kwargs['video'] = video
|
276
|
+
if text is not None:
|
277
|
+
kwargs['text'] = text
|
278
|
+
if activity_start is not None:
|
279
|
+
kwargs['activity_start'] = activity_start
|
280
|
+
if activity_end is not None:
|
281
|
+
kwargs['activity_end'] = activity_end
|
282
|
+
|
283
|
+
if len(kwargs) != 1:
|
284
|
+
raise ValueError(
|
285
|
+
f'Only one argument can be set, got {len(kwargs)}:'
|
286
|
+
f' {list(kwargs.keys())}'
|
287
|
+
)
|
288
|
+
realtime_input = types.LiveSendRealtimeInputParameters.model_validate(
|
289
|
+
kwargs
|
290
|
+
)
|
291
|
+
|
292
|
+
if self._api_client.vertexai:
|
293
|
+
realtime_input_dict = (
|
294
|
+
live_converters._LiveSendRealtimeInputParameters_to_vertex(
|
295
|
+
api_client=self._api_client, from_object=realtime_input
|
296
|
+
)
|
297
|
+
)
|
298
|
+
else:
|
299
|
+
realtime_input_dict = (
|
300
|
+
live_converters._LiveSendRealtimeInputParameters_to_mldev(
|
301
|
+
api_client=self._api_client, from_object=realtime_input
|
302
|
+
)
|
303
|
+
)
|
304
|
+
realtime_input_dict = _common.convert_to_dict(realtime_input_dict)
|
305
|
+
realtime_input_dict = _common.encode_unserializable_types(
|
306
|
+
realtime_input_dict
|
315
307
|
)
|
316
308
|
await self._ws.send(json.dumps({'realtime_input': realtime_input_dict}))
|
317
309
|
|
@@ -322,7 +314,7 @@ class AsyncSession:
|
|
322
314
|
types.FunctionResponseOrDict,
|
323
315
|
Sequence[types.FunctionResponseOrDict],
|
324
316
|
],
|
325
|
-
):
|
317
|
+
) -> None:
|
326
318
|
"""Send a tool response to the session.
|
327
319
|
|
328
320
|
Use `send_tool_response` to reply to `LiveServerToolCall` messages
|
@@ -340,7 +332,14 @@ class AsyncSession:
|
|
340
332
|
from google import genai
|
341
333
|
from google.genai import types
|
342
334
|
|
343
|
-
|
335
|
+
import os
|
336
|
+
|
337
|
+
if os.environ.get('GOOGLE_GENAI_USE_VERTEXAI'):
|
338
|
+
MODEL_NAME = 'gemini-2.0-flash-live-preview-04-09'
|
339
|
+
else:
|
340
|
+
MODEL_NAME = 'gemini-2.0-flash-live-001';
|
341
|
+
|
342
|
+
client = genai.Client()
|
344
343
|
|
345
344
|
tools = [{'function_declarations': [{'name': 'turn_on_the_lights'}]}]
|
346
345
|
config = {
|
@@ -349,13 +348,13 @@ class AsyncSession:
|
|
349
348
|
}
|
350
349
|
|
351
350
|
async with client.aio.live.connect(
|
352
|
-
model='gemini-2.0-flash-
|
351
|
+
model='models/gemini-2.0-flash-live-001',
|
353
352
|
config=config
|
354
353
|
) as session:
|
355
354
|
prompt = "Turn on the lights please"
|
356
355
|
await session.send_client_content(
|
357
|
-
turns=prompt
|
358
|
-
|
356
|
+
turns={"parts": [{'text': prompt}]}
|
357
|
+
)
|
359
358
|
|
360
359
|
async for chunk in session.receive():
|
361
360
|
if chunk.server_content:
|
@@ -376,15 +375,19 @@ class AsyncSession:
|
|
376
375
|
|
377
376
|
print('_'*80)
|
378
377
|
"""
|
379
|
-
tool_response =
|
378
|
+
tool_response = t.t_tool_response(function_responses)
|
380
379
|
if self._api_client.vertexai:
|
381
|
-
tool_response_dict =
|
380
|
+
tool_response_dict = live_converters._LiveClientToolResponse_to_vertex(
|
382
381
|
api_client=self._api_client, from_object=tool_response
|
383
382
|
)
|
384
383
|
else:
|
385
|
-
tool_response_dict =
|
384
|
+
tool_response_dict = live_converters._LiveClientToolResponse_to_mldev(
|
386
385
|
api_client=self._api_client, from_object=tool_response
|
387
386
|
)
|
387
|
+
for response in tool_response_dict.get('functionResponses', []):
|
388
|
+
if response.get('id') is None:
|
389
|
+
raise ValueError(_FUNCTION_RESPONSE_REQUIRES_ID)
|
390
|
+
|
388
391
|
await self._ws.send(json.dumps({'tool_response': tool_response_dict}))
|
389
392
|
|
390
393
|
async def receive(self) -> AsyncIterator[types.LiveServerMessage]:
|
@@ -503,9 +506,9 @@ class AsyncSession:
|
|
503
506
|
response = {}
|
504
507
|
|
505
508
|
if self._api_client.vertexai:
|
506
|
-
response_dict =
|
509
|
+
response_dict = live_converters._LiveServerMessage_from_vertex(self._api_client, response)
|
507
510
|
else:
|
508
|
-
response_dict =
|
511
|
+
response_dict = live_converters._LiveServerMessage_from_mldev(self._api_client, response)
|
509
512
|
|
510
513
|
return types.LiveServerMessage._from_response(
|
511
514
|
response=response_dict, kwargs=parameter_model.model_dump()
|
@@ -516,7 +519,7 @@ class AsyncSession:
|
|
516
519
|
data_stream: AsyncIterator[bytes],
|
517
520
|
mime_type: str,
|
518
521
|
stop_event: asyncio.Event,
|
519
|
-
):
|
522
|
+
) -> None:
|
520
523
|
async for data in data_stream:
|
521
524
|
model_input = types.LiveClientRealtimeInput(
|
522
525
|
media_chunks=[types.Blob(data=data, mime_type=mime_type)]
|
@@ -527,464 +530,6 @@ class AsyncSession:
|
|
527
530
|
# Give a chance for the receiver to process the last response.
|
528
531
|
stop_event.set()
|
529
532
|
|
530
|
-
def _LiveServerContent_from_mldev(
|
531
|
-
self,
|
532
|
-
from_object: Union[dict, object],
|
533
|
-
) -> Dict[str, Any]:
|
534
|
-
to_object: dict[str, Any] = {}
|
535
|
-
if getv(from_object, ['modelTurn']) is not None:
|
536
|
-
setv(
|
537
|
-
to_object,
|
538
|
-
['model_turn'],
|
539
|
-
_Content_from_mldev(
|
540
|
-
self._api_client,
|
541
|
-
getv(from_object, ['modelTurn']),
|
542
|
-
),
|
543
|
-
)
|
544
|
-
if getv(from_object, ['turnComplete']) is not None:
|
545
|
-
setv(to_object, ['turn_complete'], getv(from_object, ['turnComplete']))
|
546
|
-
if getv(from_object, ['generationComplete']) is not None:
|
547
|
-
setv(
|
548
|
-
to_object,
|
549
|
-
['generation_complete'],
|
550
|
-
getv(from_object, ['generationComplete']),
|
551
|
-
)
|
552
|
-
if getv(from_object, ['inputTranscription']) is not None:
|
553
|
-
setv(
|
554
|
-
to_object,
|
555
|
-
['input_transcription'],
|
556
|
-
getv(from_object, ['inputTranscription']),
|
557
|
-
)
|
558
|
-
if getv(from_object, ['outputTranscription']) is not None:
|
559
|
-
setv(
|
560
|
-
to_object,
|
561
|
-
['output_transcription'],
|
562
|
-
getv(from_object, ['outputTranscription']),
|
563
|
-
)
|
564
|
-
if getv(from_object, ['interrupted']) is not None:
|
565
|
-
setv(to_object, ['interrupted'], getv(from_object, ['interrupted']))
|
566
|
-
return to_object
|
567
|
-
|
568
|
-
def _LiveToolCall_from_mldev(
|
569
|
-
self,
|
570
|
-
from_object: Union[dict, object],
|
571
|
-
) -> Dict[str, Any]:
|
572
|
-
to_object: dict[str, Any] = {}
|
573
|
-
if getv(from_object, ['functionCalls']) is not None:
|
574
|
-
setv(
|
575
|
-
to_object,
|
576
|
-
['function_calls'],
|
577
|
-
getv(from_object, ['functionCalls']),
|
578
|
-
)
|
579
|
-
return to_object
|
580
|
-
|
581
|
-
def _LiveToolCall_from_vertex(
|
582
|
-
self,
|
583
|
-
from_object: Union[dict, object],
|
584
|
-
) -> Dict[str, Any]:
|
585
|
-
to_object: dict[str, Any] = {}
|
586
|
-
if getv(from_object, ['functionCalls']) is not None:
|
587
|
-
setv(
|
588
|
-
to_object,
|
589
|
-
['function_calls'],
|
590
|
-
getv(from_object, ['functionCalls']),
|
591
|
-
)
|
592
|
-
return to_object
|
593
|
-
|
594
|
-
def _LiveServerGoAway_from_mldev(
|
595
|
-
self,
|
596
|
-
from_object: Union[dict, object],
|
597
|
-
parent_object: Optional[dict] = None,
|
598
|
-
) -> dict:
|
599
|
-
to_object: dict[str, Any] = {}
|
600
|
-
if getv(from_object, ['timeLeft']) is not None:
|
601
|
-
setv(to_object, ['time_left'], getv(from_object, ['timeLeft']))
|
602
|
-
|
603
|
-
return to_object
|
604
|
-
|
605
|
-
def _LiveServerSessionResumptionUpdate_from_mldev(
|
606
|
-
self,
|
607
|
-
from_object: Union[dict, object],
|
608
|
-
parent_object: Optional[dict] = None,
|
609
|
-
) -> dict:
|
610
|
-
to_object: dict[str, Any] = {}
|
611
|
-
if getv(from_object, ['newHandle']) is not None:
|
612
|
-
setv(to_object, ['new_handle'], getv(from_object, ['newHandle']))
|
613
|
-
|
614
|
-
if getv(from_object, ['resumable']) is not None:
|
615
|
-
setv(to_object, ['resumable'], getv(from_object, ['resumable']))
|
616
|
-
|
617
|
-
if getv(from_object, ['lastConsumedClientMessageIndex']) is not None:
|
618
|
-
setv(
|
619
|
-
to_object,
|
620
|
-
['last_consumed_client_message_index'],
|
621
|
-
getv(from_object, ['lastConsumedClientMessageIndex']),
|
622
|
-
)
|
623
|
-
|
624
|
-
return to_object
|
625
|
-
|
626
|
-
def _ModalityTokenCount_from_mldev(
|
627
|
-
self,
|
628
|
-
from_object: Union[dict, object],
|
629
|
-
) -> Dict[str, Any]:
|
630
|
-
to_object: Dict[str, Any] = {}
|
631
|
-
if getv(from_object, ['modality']) is not None:
|
632
|
-
setv(to_object, ['modality'], getv(from_object, ['modality']))
|
633
|
-
if getv(from_object, ['tokenCount']) is not None:
|
634
|
-
setv(to_object, ['token_count'], getv(from_object, ['tokenCount']))
|
635
|
-
return to_object
|
636
|
-
|
637
|
-
def _UsageMetadata_from_mldev(
|
638
|
-
self,
|
639
|
-
from_object: Union[dict, object],
|
640
|
-
) -> Dict[str, Any]:
|
641
|
-
to_object: dict[str, Any] = {}
|
642
|
-
if getv(from_object, ['promptTokenCount']) is not None:
|
643
|
-
setv(
|
644
|
-
to_object,
|
645
|
-
['prompt_token_count'],
|
646
|
-
getv(from_object, ['promptTokenCount']),
|
647
|
-
)
|
648
|
-
if getv(from_object, ['cachedContentTokenCount']) is not None:
|
649
|
-
setv(
|
650
|
-
to_object,
|
651
|
-
['cached_content_token_count'],
|
652
|
-
getv(from_object, ['cachedContentTokenCount']),
|
653
|
-
)
|
654
|
-
if getv(from_object, ['responseTokenCount']) is not None:
|
655
|
-
setv(
|
656
|
-
to_object,
|
657
|
-
['response_token_count'],
|
658
|
-
getv(from_object, ['responseTokenCount']),
|
659
|
-
)
|
660
|
-
if getv(from_object, ['toolUsePromptTokenCount']) is not None:
|
661
|
-
setv(
|
662
|
-
to_object,
|
663
|
-
['tool_use_prompt_token_count'],
|
664
|
-
getv(from_object, ['toolUsePromptTokenCount']),
|
665
|
-
)
|
666
|
-
if getv(from_object, ['thoughtsTokenCount']) is not None:
|
667
|
-
setv(
|
668
|
-
to_object,
|
669
|
-
['thoughts_token_count'],
|
670
|
-
getv(from_object, ['thoughtsTokenCount']),
|
671
|
-
)
|
672
|
-
if getv(from_object, ['totalTokenCount']) is not None:
|
673
|
-
setv(
|
674
|
-
to_object,
|
675
|
-
['total_token_count'],
|
676
|
-
getv(from_object, ['totalTokenCount']),
|
677
|
-
)
|
678
|
-
if getv(from_object, ['promptTokensDetails']) is not None:
|
679
|
-
setv(
|
680
|
-
to_object,
|
681
|
-
['prompt_tokens_details'],
|
682
|
-
[
|
683
|
-
self._ModalityTokenCount_from_mldev(item)
|
684
|
-
for item in getv(from_object, ['promptTokensDetails'])
|
685
|
-
],
|
686
|
-
)
|
687
|
-
if getv(from_object, ['cacheTokensDetails']) is not None:
|
688
|
-
setv(
|
689
|
-
to_object,
|
690
|
-
['cache_tokens_details'],
|
691
|
-
[
|
692
|
-
self._ModalityTokenCount_from_mldev(item)
|
693
|
-
for item in getv(from_object, ['cacheTokensDetails'])
|
694
|
-
],
|
695
|
-
)
|
696
|
-
if getv(from_object, ['responseTokensDetails']) is not None:
|
697
|
-
setv(
|
698
|
-
to_object,
|
699
|
-
['response_tokens_details'],
|
700
|
-
[
|
701
|
-
self._ModalityTokenCount_from_mldev(item)
|
702
|
-
for item in getv(from_object, ['responseTokensDetails'])
|
703
|
-
],
|
704
|
-
)
|
705
|
-
if getv(from_object, ['toolUsePromptTokensDetails']) is not None:
|
706
|
-
setv(
|
707
|
-
to_object,
|
708
|
-
['tool_use_prompt_tokens_details'],
|
709
|
-
[
|
710
|
-
self._ModalityTokenCount_from_mldev(item)
|
711
|
-
for item in getv(from_object, ['toolUsePromptTokensDetails'])
|
712
|
-
],
|
713
|
-
)
|
714
|
-
return to_object
|
715
|
-
|
716
|
-
def _LiveServerMessage_from_mldev(
|
717
|
-
self,
|
718
|
-
from_object: Union[dict, object],
|
719
|
-
) -> Dict[str, Any]:
|
720
|
-
to_object: dict[str, Any] = {}
|
721
|
-
if getv(from_object, ['serverContent']) is not None:
|
722
|
-
setv(
|
723
|
-
to_object,
|
724
|
-
['server_content'],
|
725
|
-
self._LiveServerContent_from_mldev(
|
726
|
-
getv(from_object, ['serverContent'])
|
727
|
-
),
|
728
|
-
)
|
729
|
-
if getv(from_object, ['toolCall']) is not None:
|
730
|
-
setv(
|
731
|
-
to_object,
|
732
|
-
['tool_call'],
|
733
|
-
self._LiveToolCall_from_mldev(getv(from_object, ['toolCall'])),
|
734
|
-
)
|
735
|
-
if getv(from_object, ['toolCallCancellation']) is not None:
|
736
|
-
setv(
|
737
|
-
to_object,
|
738
|
-
['tool_call_cancellation'],
|
739
|
-
getv(from_object, ['toolCallCancellation']),
|
740
|
-
)
|
741
|
-
|
742
|
-
if getv(from_object, ['goAway']) is not None:
|
743
|
-
setv(
|
744
|
-
to_object,
|
745
|
-
['go_away'],
|
746
|
-
self._LiveServerGoAway_from_mldev(
|
747
|
-
getv(from_object, ['goAway']), to_object
|
748
|
-
),
|
749
|
-
)
|
750
|
-
|
751
|
-
if getv(from_object, ['sessionResumptionUpdate']) is not None:
|
752
|
-
setv(
|
753
|
-
to_object,
|
754
|
-
['session_resumption_update'],
|
755
|
-
self._LiveServerSessionResumptionUpdate_from_mldev(
|
756
|
-
getv(from_object, ['sessionResumptionUpdate']),
|
757
|
-
to_object,
|
758
|
-
),
|
759
|
-
)
|
760
|
-
|
761
|
-
return to_object
|
762
|
-
|
763
|
-
if getv(from_object, ['usageMetadata']) is not None:
|
764
|
-
setv(
|
765
|
-
to_object,
|
766
|
-
['usage_metadata'],
|
767
|
-
self._UsageMetadata_from_mldev(getv(from_object, ['usageMetadata'])),
|
768
|
-
)
|
769
|
-
return to_object
|
770
|
-
|
771
|
-
def _LiveServerContent_from_vertex(
|
772
|
-
self,
|
773
|
-
from_object: Union[dict, object],
|
774
|
-
) -> Dict[str, Any]:
|
775
|
-
to_object: dict[str, Any] = {}
|
776
|
-
if getv(from_object, ['modelTurn']) is not None:
|
777
|
-
setv(
|
778
|
-
to_object,
|
779
|
-
['model_turn'],
|
780
|
-
_Content_from_vertex(
|
781
|
-
self._api_client,
|
782
|
-
getv(from_object, ['modelTurn']),
|
783
|
-
),
|
784
|
-
)
|
785
|
-
if getv(from_object, ['turnComplete']) is not None:
|
786
|
-
setv(to_object, ['turn_complete'], getv(from_object, ['turnComplete']))
|
787
|
-
if getv(from_object, ['generationComplete']) is not None:
|
788
|
-
setv(
|
789
|
-
to_object,
|
790
|
-
['generation_complete'],
|
791
|
-
getv(from_object, ['generationComplete']),
|
792
|
-
)
|
793
|
-
if getv(from_object, ['inputTranscription']) is not None:
|
794
|
-
setv(
|
795
|
-
to_object,
|
796
|
-
['input_transcription'],
|
797
|
-
getv(from_object, ['inputTranscription']),
|
798
|
-
)
|
799
|
-
if getv(from_object, ['outputTranscription']) is not None:
|
800
|
-
setv(
|
801
|
-
to_object,
|
802
|
-
['output_transcription'],
|
803
|
-
getv(from_object, ['outputTranscription']),
|
804
|
-
)
|
805
|
-
if getv(from_object, ['interrupted']) is not None:
|
806
|
-
setv(to_object, ['interrupted'], getv(from_object, ['interrupted']))
|
807
|
-
return to_object
|
808
|
-
|
809
|
-
def _LiveServerGoAway_from_vertex(
|
810
|
-
self,
|
811
|
-
from_object: Union[dict, object],
|
812
|
-
) -> dict:
|
813
|
-
to_object: dict[str, Any] = {}
|
814
|
-
if getv(from_object, ['timeLeft']) is not None:
|
815
|
-
setv(to_object, ['time_left'], getv(from_object, ['timeLeft']))
|
816
|
-
|
817
|
-
return to_object
|
818
|
-
|
819
|
-
def _LiveServerSessionResumptionUpdate_from_vertex(
|
820
|
-
self,
|
821
|
-
from_object: Union[dict, object],
|
822
|
-
) -> dict:
|
823
|
-
to_object: dict[str, Any] = {}
|
824
|
-
if getv(from_object, ['newHandle']) is not None:
|
825
|
-
setv(to_object, ['new_handle'], getv(from_object, ['newHandle']))
|
826
|
-
|
827
|
-
if getv(from_object, ['resumable']) is not None:
|
828
|
-
setv(to_object, ['resumable'], getv(from_object, ['resumable']))
|
829
|
-
|
830
|
-
if getv(from_object, ['lastConsumedClientMessageIndex']) is not None:
|
831
|
-
setv(
|
832
|
-
to_object,
|
833
|
-
['last_consumed_client_message_index'],
|
834
|
-
getv(from_object, ['lastConsumedClientMessageIndex']),
|
835
|
-
)
|
836
|
-
|
837
|
-
return to_object
|
838
|
-
|
839
|
-
|
840
|
-
def _ModalityTokenCount_from_vertex(
|
841
|
-
self,
|
842
|
-
from_object: Union[dict, object],
|
843
|
-
) -> Dict[str, Any]:
|
844
|
-
to_object: Dict[str, Any] = {}
|
845
|
-
if getv(from_object, ['modality']) is not None:
|
846
|
-
setv(to_object, ['modality'], getv(from_object, ['modality']))
|
847
|
-
if getv(from_object, ['tokenCount']) is not None:
|
848
|
-
setv(to_object, ['token_count'], getv(from_object, ['tokenCount']))
|
849
|
-
return to_object
|
850
|
-
|
851
|
-
def _UsageMetadata_from_vertex(
|
852
|
-
self,
|
853
|
-
from_object: Union[dict, object],
|
854
|
-
) -> Dict[str, Any]:
|
855
|
-
to_object: dict[str, Any] = {}
|
856
|
-
if getv(from_object, ['promptTokenCount']) is not None:
|
857
|
-
setv(
|
858
|
-
to_object,
|
859
|
-
['prompt_token_count'],
|
860
|
-
getv(from_object, ['promptTokenCount']),
|
861
|
-
)
|
862
|
-
if getv(from_object, ['cachedContentTokenCount']) is not None:
|
863
|
-
setv(
|
864
|
-
to_object,
|
865
|
-
['cached_content_token_count'],
|
866
|
-
getv(from_object, ['cachedContentTokenCount']),
|
867
|
-
)
|
868
|
-
if getv(from_object, ['candidatesTokenCount']) is not None:
|
869
|
-
setv(
|
870
|
-
to_object,
|
871
|
-
['response_token_count'],
|
872
|
-
getv(from_object, ['candidatesTokenCount']),
|
873
|
-
)
|
874
|
-
if getv(from_object, ['toolUsePromptTokenCount']) is not None:
|
875
|
-
setv(
|
876
|
-
to_object,
|
877
|
-
['tool_use_prompt_token_count'],
|
878
|
-
getv(from_object, ['toolUsePromptTokenCount']),
|
879
|
-
)
|
880
|
-
if getv(from_object, ['thoughtsTokenCount']) is not None:
|
881
|
-
setv(
|
882
|
-
to_object,
|
883
|
-
['thoughts_token_count'],
|
884
|
-
getv(from_object, ['thoughtsTokenCount']),
|
885
|
-
)
|
886
|
-
if getv(from_object, ['totalTokenCount']) is not None:
|
887
|
-
setv(
|
888
|
-
to_object,
|
889
|
-
['total_token_count'],
|
890
|
-
getv(from_object, ['totalTokenCount']),
|
891
|
-
)
|
892
|
-
if getv(from_object, ['promptTokensDetails']) is not None:
|
893
|
-
setv(
|
894
|
-
to_object,
|
895
|
-
['prompt_tokens_details'],
|
896
|
-
[
|
897
|
-
self._ModalityTokenCount_from_vertex(item)
|
898
|
-
for item in getv(from_object, ['promptTokensDetails'])
|
899
|
-
],
|
900
|
-
)
|
901
|
-
if getv(from_object, ['cacheTokensDetails']) is not None:
|
902
|
-
setv(
|
903
|
-
to_object,
|
904
|
-
['cache_tokens_details'],
|
905
|
-
[
|
906
|
-
self._ModalityTokenCount_from_vertex(item)
|
907
|
-
for item in getv(from_object, ['cacheTokensDetails'])
|
908
|
-
],
|
909
|
-
)
|
910
|
-
if getv(from_object, ['toolUsePromptTokensDetails']) is not None:
|
911
|
-
setv(
|
912
|
-
to_object,
|
913
|
-
['tool_use_prompt_tokens_details'],
|
914
|
-
[
|
915
|
-
self._ModalityTokenCount_from_vertex(item)
|
916
|
-
for item in getv(from_object, ['toolUsePromptTokensDetails'])
|
917
|
-
],
|
918
|
-
)
|
919
|
-
if getv(from_object, ['candidatesTokensDetails']) is not None:
|
920
|
-
setv(
|
921
|
-
to_object,
|
922
|
-
['response_tokens_details'],
|
923
|
-
[
|
924
|
-
self._ModalityTokenCount_from_vertex(item)
|
925
|
-
for item in getv(from_object, ['candidatesTokensDetails'])
|
926
|
-
],
|
927
|
-
)
|
928
|
-
if getv(from_object, ['trafficType']) is not None:
|
929
|
-
setv(
|
930
|
-
to_object,
|
931
|
-
['traffic_type'],
|
932
|
-
getv(from_object, ['trafficType']),
|
933
|
-
)
|
934
|
-
return to_object
|
935
|
-
|
936
|
-
def _LiveServerMessage_from_vertex(
|
937
|
-
self,
|
938
|
-
from_object: Union[dict, object],
|
939
|
-
) -> Dict[str, Any]:
|
940
|
-
to_object: dict[str, Any] = {}
|
941
|
-
if getv(from_object, ['serverContent']) is not None:
|
942
|
-
setv(
|
943
|
-
to_object,
|
944
|
-
['server_content'],
|
945
|
-
self._LiveServerContent_from_vertex(
|
946
|
-
getv(from_object, ['serverContent'])
|
947
|
-
),
|
948
|
-
)
|
949
|
-
if getv(from_object, ['toolCall']) is not None:
|
950
|
-
setv(
|
951
|
-
to_object,
|
952
|
-
['tool_call'],
|
953
|
-
self._LiveToolCall_from_vertex(getv(from_object, ['toolCall'])),
|
954
|
-
)
|
955
|
-
if getv(from_object, ['toolCallCancellation']) is not None:
|
956
|
-
setv(
|
957
|
-
to_object,
|
958
|
-
['tool_call_cancellation'],
|
959
|
-
getv(from_object, ['toolCallCancellation']),
|
960
|
-
)
|
961
|
-
|
962
|
-
if getv(from_object, ['goAway']) is not None:
|
963
|
-
setv(
|
964
|
-
to_object,
|
965
|
-
['go_away'],
|
966
|
-
self._LiveServerGoAway_from_vertex(
|
967
|
-
getv(from_object, ['goAway'])
|
968
|
-
),
|
969
|
-
)
|
970
|
-
|
971
|
-
if getv(from_object, ['sessionResumptionUpdate']) is not None:
|
972
|
-
setv(
|
973
|
-
to_object,
|
974
|
-
['session_resumption_update'],
|
975
|
-
self._LiveServerSessionResumptionUpdate_from_vertex(
|
976
|
-
getv(from_object, ['sessionResumptionUpdate']),
|
977
|
-
),
|
978
|
-
)
|
979
|
-
|
980
|
-
if getv(from_object, ['usageMetadata']) is not None:
|
981
|
-
setv(
|
982
|
-
to_object,
|
983
|
-
['usage_metadata'],
|
984
|
-
self._UsageMetadata_from_vertex(getv(from_object, ['usageMetadata'])),
|
985
|
-
)
|
986
|
-
return to_object
|
987
|
-
|
988
533
|
def _parse_client_message(
|
989
534
|
self,
|
990
535
|
input: Optional[
|
@@ -1288,472 +833,14 @@ class AsyncSession:
|
|
1288
833
|
|
1289
834
|
return client_message
|
1290
835
|
|
1291
|
-
async def close(self):
|
836
|
+
async def close(self) -> None:
|
1292
837
|
# Close the websocket connection.
|
1293
838
|
await self._ws.close()
|
1294
839
|
|
1295
840
|
|
1296
|
-
def _t_content_strict(content: types.ContentOrDict):
|
1297
|
-
if isinstance(content, dict):
|
1298
|
-
return types.Content.model_validate(content)
|
1299
|
-
elif isinstance(content, types.Content):
|
1300
|
-
return content
|
1301
|
-
else:
|
1302
|
-
raise ValueError(
|
1303
|
-
f'Could not convert input (type "{type(content)}") to '
|
1304
|
-
'`types.Content`'
|
1305
|
-
)
|
1306
|
-
|
1307
|
-
|
1308
|
-
def _t_contents_strict(
|
1309
|
-
contents: Union[Sequence[types.ContentOrDict], types.ContentOrDict]):
|
1310
|
-
if isinstance(contents, Sequence):
|
1311
|
-
return [_t_content_strict(content) for content in contents]
|
1312
|
-
else:
|
1313
|
-
return [_t_content_strict(contents)]
|
1314
|
-
|
1315
|
-
|
1316
|
-
def _t_client_content(
|
1317
|
-
turns: Optional[
|
1318
|
-
Union[Sequence[types.ContentOrDict], types.ContentOrDict]
|
1319
|
-
] = None,
|
1320
|
-
turn_complete: bool = True,
|
1321
|
-
) -> types.LiveClientContent:
|
1322
|
-
if turns is None:
|
1323
|
-
return types.LiveClientContent(turn_complete=turn_complete)
|
1324
|
-
|
1325
|
-
try:
|
1326
|
-
return types.LiveClientContent(
|
1327
|
-
turns=_t_contents_strict(contents=turns),
|
1328
|
-
turn_complete=turn_complete,
|
1329
|
-
)
|
1330
|
-
except Exception as e:
|
1331
|
-
raise ValueError(
|
1332
|
-
f'Could not convert input (type "{type(turns)}") to '
|
1333
|
-
'`types.LiveClientContent`'
|
1334
|
-
) from e
|
1335
|
-
|
1336
|
-
|
1337
|
-
def _t_realtime_input(
|
1338
|
-
media: t.BlobUnion,
|
1339
|
-
) -> types.LiveClientRealtimeInput:
|
1340
|
-
try:
|
1341
|
-
return types.LiveClientRealtimeInput(media_chunks=[t.t_blob(blob=media)])
|
1342
|
-
except Exception as e:
|
1343
|
-
raise ValueError(
|
1344
|
-
f'Could not convert input (type "{type(input)}") to '
|
1345
|
-
'`types.LiveClientRealtimeInput`'
|
1346
|
-
) from e
|
1347
|
-
|
1348
|
-
|
1349
|
-
def _t_tool_response(
|
1350
|
-
input: Union[
|
1351
|
-
types.FunctionResponseOrDict,
|
1352
|
-
Sequence[types.FunctionResponseOrDict],
|
1353
|
-
],
|
1354
|
-
) -> types.LiveClientToolResponse:
|
1355
|
-
if not input:
|
1356
|
-
raise ValueError(f'A tool response is required, got: \n{input}')
|
1357
|
-
|
1358
|
-
try:
|
1359
|
-
return types.LiveClientToolResponse(
|
1360
|
-
function_responses=t.t_function_responses(function_responses=input)
|
1361
|
-
)
|
1362
|
-
except Exception as e:
|
1363
|
-
raise ValueError(
|
1364
|
-
f'Could not convert input (type "{type(input)}") to '
|
1365
|
-
'`types.LiveClientToolResponse`'
|
1366
|
-
) from e
|
1367
|
-
|
1368
|
-
|
1369
841
|
class AsyncLive(_api_module.BaseModule):
|
1370
842
|
"""[Preview] AsyncLive."""
|
1371
843
|
|
1372
|
-
def _LiveSetup_to_mldev(
|
1373
|
-
self, model: str, config: Optional[types.LiveConnectConfig] = None
|
1374
|
-
):
|
1375
|
-
|
1376
|
-
to_object: dict[str, Any] = {}
|
1377
|
-
if getv(config, ['generation_config']) is not None:
|
1378
|
-
setv(
|
1379
|
-
to_object,
|
1380
|
-
['generationConfig'],
|
1381
|
-
_GenerateContentConfig_to_mldev(
|
1382
|
-
self._api_client,
|
1383
|
-
getv(config, ['generation_config']),
|
1384
|
-
to_object,
|
1385
|
-
),
|
1386
|
-
)
|
1387
|
-
if getv(config, ['response_modalities']) is not None:
|
1388
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1389
|
-
to_object['generationConfig']['responseModalities'] = getv(
|
1390
|
-
config, ['response_modalities']
|
1391
|
-
)
|
1392
|
-
else:
|
1393
|
-
to_object['generationConfig'] = {
|
1394
|
-
'responseModalities': getv(config, ['response_modalities'])
|
1395
|
-
}
|
1396
|
-
if getv(config, ['speech_config']) is not None:
|
1397
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1398
|
-
to_object['generationConfig']['speechConfig'] = _SpeechConfig_to_mldev(
|
1399
|
-
self._api_client,
|
1400
|
-
t.t_speech_config(
|
1401
|
-
self._api_client, getv(config, ['speech_config'])
|
1402
|
-
),
|
1403
|
-
to_object,
|
1404
|
-
)
|
1405
|
-
else:
|
1406
|
-
to_object['generationConfig'] = {
|
1407
|
-
'speechConfig': _SpeechConfig_to_mldev(
|
1408
|
-
self._api_client,
|
1409
|
-
t.t_speech_config(
|
1410
|
-
self._api_client, getv(config, ['speech_config'])
|
1411
|
-
),
|
1412
|
-
to_object,
|
1413
|
-
)
|
1414
|
-
}
|
1415
|
-
if getv(config, ['temperature']) is not None:
|
1416
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1417
|
-
to_object['generationConfig']['temperature'] = getv(
|
1418
|
-
config, ['temperature']
|
1419
|
-
)
|
1420
|
-
else:
|
1421
|
-
to_object['generationConfig'] = {
|
1422
|
-
'temperature': getv(config, ['temperature'])
|
1423
|
-
}
|
1424
|
-
if getv(config, ['top_p']) is not None:
|
1425
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1426
|
-
to_object['generationConfig']['topP'] = getv(config, ['top_p'])
|
1427
|
-
else:
|
1428
|
-
to_object['generationConfig'] = {'topP': getv(config, ['top_p'])}
|
1429
|
-
if getv(config, ['top_k']) is not None:
|
1430
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1431
|
-
to_object['generationConfig']['topK'] = getv(config, ['top_k'])
|
1432
|
-
else:
|
1433
|
-
to_object['generationConfig'] = {'topK': getv(config, ['top_k'])}
|
1434
|
-
if getv(config, ['max_output_tokens']) is not None:
|
1435
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1436
|
-
to_object['generationConfig']['maxOutputTokens'] = getv(
|
1437
|
-
config, ['max_output_tokens']
|
1438
|
-
)
|
1439
|
-
else:
|
1440
|
-
to_object['generationConfig'] = {
|
1441
|
-
'maxOutputTokens': getv(config, ['max_output_tokens'])
|
1442
|
-
}
|
1443
|
-
if getv(config, ['media_resolution']) is not None:
|
1444
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1445
|
-
to_object['generationConfig']['mediaResolution'] = getv(
|
1446
|
-
config, ['media_resolution']
|
1447
|
-
)
|
1448
|
-
else:
|
1449
|
-
to_object['generationConfig'] = {
|
1450
|
-
'mediaResolution': getv(config, ['media_resolution'])
|
1451
|
-
}
|
1452
|
-
if getv(config, ['seed']) is not None:
|
1453
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1454
|
-
to_object['generationConfig']['seed'] = getv(config, ['seed'])
|
1455
|
-
else:
|
1456
|
-
to_object['generationConfig'] = {'seed': getv(config, ['seed'])}
|
1457
|
-
if getv(config, ['system_instruction']) is not None:
|
1458
|
-
setv(
|
1459
|
-
to_object,
|
1460
|
-
['systemInstruction'],
|
1461
|
-
_Content_to_mldev(
|
1462
|
-
self._api_client,
|
1463
|
-
t.t_content(
|
1464
|
-
self._api_client, getv(config, ['system_instruction'])
|
1465
|
-
),
|
1466
|
-
to_object,
|
1467
|
-
),
|
1468
|
-
)
|
1469
|
-
if getv(config, ['tools']) is not None:
|
1470
|
-
setv(
|
1471
|
-
to_object,
|
1472
|
-
['tools'],
|
1473
|
-
[
|
1474
|
-
_Tool_to_mldev(
|
1475
|
-
self._api_client, t.t_tool(self._api_client, item), to_object
|
1476
|
-
)
|
1477
|
-
for item in t.t_tools(self._api_client, getv(config, ['tools']))
|
1478
|
-
],
|
1479
|
-
)
|
1480
|
-
if getv(config, ['input_audio_transcription']) is not None:
|
1481
|
-
raise ValueError('input_audio_transcription is not supported in MLDev '
|
1482
|
-
'API.')
|
1483
|
-
if getv(config, ['output_audio_transcription']) is not None:
|
1484
|
-
setv(
|
1485
|
-
to_object,
|
1486
|
-
['outputAudioTranscription'],
|
1487
|
-
_AudioTranscriptionConfig_to_mldev(
|
1488
|
-
self._api_client,
|
1489
|
-
getv(config, ['output_audio_transcription']),
|
1490
|
-
),
|
1491
|
-
)
|
1492
|
-
|
1493
|
-
if getv(config, ['session_resumption']) is not None:
|
1494
|
-
setv(
|
1495
|
-
to_object,
|
1496
|
-
['sessionResumption'],
|
1497
|
-
self._LiveClientSessionResumptionConfig_to_mldev(
|
1498
|
-
getv(config, ['session_resumption'])
|
1499
|
-
),
|
1500
|
-
)
|
1501
|
-
|
1502
|
-
if getv(config, ['context_window_compression']) is not None:
|
1503
|
-
setv(
|
1504
|
-
to_object,
|
1505
|
-
['contextWindowCompression'],
|
1506
|
-
self._ContextWindowCompressionConfig_to_mldev(
|
1507
|
-
getv(config, ['context_window_compression']),
|
1508
|
-
),
|
1509
|
-
)
|
1510
|
-
|
1511
|
-
return_value = {'setup': {'model': model}}
|
1512
|
-
return_value['setup'].update(to_object)
|
1513
|
-
return return_value
|
1514
|
-
|
1515
|
-
def _SlidingWindow_to_mldev(
|
1516
|
-
self,
|
1517
|
-
from_object: Union[dict, object],
|
1518
|
-
) -> dict:
|
1519
|
-
to_object: dict[str, Any] = {}
|
1520
|
-
if getv(from_object, ['target_tokens']) is not None:
|
1521
|
-
setv(to_object, ['targetTokens'], getv(from_object, ['target_tokens']))
|
1522
|
-
|
1523
|
-
return to_object
|
1524
|
-
|
1525
|
-
|
1526
|
-
def _ContextWindowCompressionConfig_to_mldev(
|
1527
|
-
self,
|
1528
|
-
from_object: Union[dict, object],
|
1529
|
-
) -> dict:
|
1530
|
-
to_object: dict[str, Any] = {}
|
1531
|
-
if getv(from_object, ['trigger_tokens']) is not None:
|
1532
|
-
setv(to_object, ['triggerTokens'], getv(from_object, ['trigger_tokens']))
|
1533
|
-
|
1534
|
-
if getv(from_object, ['sliding_window']) is not None:
|
1535
|
-
setv(
|
1536
|
-
to_object,
|
1537
|
-
['slidingWindow'],
|
1538
|
-
self._SlidingWindow_to_mldev(
|
1539
|
-
getv(from_object, ['sliding_window'])
|
1540
|
-
),
|
1541
|
-
)
|
1542
|
-
|
1543
|
-
return to_object
|
1544
|
-
|
1545
|
-
def _LiveClientSessionResumptionConfig_to_mldev(
|
1546
|
-
self,
|
1547
|
-
from_object: Union[dict, object]
|
1548
|
-
) -> dict:
|
1549
|
-
to_object: dict[str, Any] = {}
|
1550
|
-
if getv(from_object, ['handle']) is not None:
|
1551
|
-
setv(to_object, ['handle'], getv(from_object, ['handle']))
|
1552
|
-
|
1553
|
-
if getv(from_object, ['transparent']) is not None:
|
1554
|
-
raise ValueError('The `transparent` field is not supported in MLDev API')
|
1555
|
-
|
1556
|
-
return to_object
|
1557
|
-
|
1558
|
-
def _LiveSetup_to_vertex(
|
1559
|
-
self, model: str, config: Optional[types.LiveConnectConfig] = None
|
1560
|
-
):
|
1561
|
-
|
1562
|
-
to_object: dict[str, Any] = {}
|
1563
|
-
|
1564
|
-
if getv(config, ['generation_config']) is not None:
|
1565
|
-
setv(
|
1566
|
-
to_object,
|
1567
|
-
['generationConfig'],
|
1568
|
-
_GenerateContentConfig_to_vertex(
|
1569
|
-
self._api_client,
|
1570
|
-
getv(config, ['generation_config']),
|
1571
|
-
to_object,
|
1572
|
-
),
|
1573
|
-
)
|
1574
|
-
if getv(config, ['response_modalities']) is not None:
|
1575
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1576
|
-
to_object['generationConfig']['responseModalities'] = getv(
|
1577
|
-
config, ['response_modalities']
|
1578
|
-
)
|
1579
|
-
else:
|
1580
|
-
to_object['generationConfig'] = {
|
1581
|
-
'responseModalities': getv(config, ['response_modalities'])
|
1582
|
-
}
|
1583
|
-
else:
|
1584
|
-
# Set default to AUDIO to align with MLDev API.
|
1585
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1586
|
-
to_object['generationConfig'].update({'responseModalities': ['AUDIO']})
|
1587
|
-
else:
|
1588
|
-
to_object.update(
|
1589
|
-
{'generationConfig': {'responseModalities': ['AUDIO']}}
|
1590
|
-
)
|
1591
|
-
if getv(config, ['speech_config']) is not None:
|
1592
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1593
|
-
to_object['generationConfig']['speechConfig'] = _SpeechConfig_to_vertex(
|
1594
|
-
self._api_client,
|
1595
|
-
t.t_speech_config(
|
1596
|
-
self._api_client, getv(config, ['speech_config'])
|
1597
|
-
),
|
1598
|
-
to_object,
|
1599
|
-
)
|
1600
|
-
else:
|
1601
|
-
to_object['generationConfig'] = {
|
1602
|
-
'speechConfig': _SpeechConfig_to_vertex(
|
1603
|
-
self._api_client,
|
1604
|
-
t.t_speech_config(
|
1605
|
-
self._api_client, getv(config, ['speech_config'])
|
1606
|
-
),
|
1607
|
-
to_object,
|
1608
|
-
)
|
1609
|
-
}
|
1610
|
-
if getv(config, ['temperature']) is not None:
|
1611
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1612
|
-
to_object['generationConfig']['temperature'] = getv(
|
1613
|
-
config, ['temperature']
|
1614
|
-
)
|
1615
|
-
else:
|
1616
|
-
to_object['generationConfig'] = {
|
1617
|
-
'temperature': getv(config, ['temperature'])
|
1618
|
-
}
|
1619
|
-
if getv(config, ['top_p']) is not None:
|
1620
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1621
|
-
to_object['generationConfig']['topP'] = getv(config, ['top_p'])
|
1622
|
-
else:
|
1623
|
-
to_object['generationConfig'] = {'topP': getv(config, ['top_p'])}
|
1624
|
-
if getv(config, ['top_k']) is not None:
|
1625
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1626
|
-
to_object['generationConfig']['topK'] = getv(config, ['top_k'])
|
1627
|
-
else:
|
1628
|
-
to_object['generationConfig'] = {'topK': getv(config, ['top_k'])}
|
1629
|
-
if getv(config, ['max_output_tokens']) is not None:
|
1630
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1631
|
-
to_object['generationConfig']['maxOutputTokens'] = getv(
|
1632
|
-
config, ['max_output_tokens']
|
1633
|
-
)
|
1634
|
-
else:
|
1635
|
-
to_object['generationConfig'] = {
|
1636
|
-
'maxOutputTokens': getv(config, ['max_output_tokens'])
|
1637
|
-
}
|
1638
|
-
if getv(config, ['media_resolution']) is not None:
|
1639
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1640
|
-
to_object['generationConfig']['mediaResolution'] = getv(
|
1641
|
-
config, ['media_resolution']
|
1642
|
-
)
|
1643
|
-
else:
|
1644
|
-
to_object['generationConfig'] = {
|
1645
|
-
'mediaResolution': getv(config, ['media_resolution'])
|
1646
|
-
}
|
1647
|
-
if getv(config, ['seed']) is not None:
|
1648
|
-
if getv(to_object, ['generationConfig']) is not None:
|
1649
|
-
to_object['generationConfig']['seed'] = getv(config, ['seed'])
|
1650
|
-
else:
|
1651
|
-
to_object['generationConfig'] = {'seed': getv(config, ['seed'])}
|
1652
|
-
if getv(config, ['system_instruction']) is not None:
|
1653
|
-
setv(
|
1654
|
-
to_object,
|
1655
|
-
['systemInstruction'],
|
1656
|
-
_Content_to_vertex(
|
1657
|
-
self._api_client,
|
1658
|
-
t.t_content(
|
1659
|
-
self._api_client, getv(config, ['system_instruction'])
|
1660
|
-
),
|
1661
|
-
to_object,
|
1662
|
-
),
|
1663
|
-
)
|
1664
|
-
if getv(config, ['tools']) is not None:
|
1665
|
-
setv(
|
1666
|
-
to_object,
|
1667
|
-
['tools'],
|
1668
|
-
[
|
1669
|
-
_Tool_to_vertex(
|
1670
|
-
self._api_client, t.t_tool(self._api_client, item), to_object
|
1671
|
-
)
|
1672
|
-
for item in t.t_tools(self._api_client, getv(config, ['tools']))
|
1673
|
-
],
|
1674
|
-
)
|
1675
|
-
if getv(config, ['input_audio_transcription']) is not None:
|
1676
|
-
setv(
|
1677
|
-
to_object,
|
1678
|
-
['inputAudioTranscription'],
|
1679
|
-
_AudioTranscriptionConfig_to_vertex(
|
1680
|
-
self._api_client,
|
1681
|
-
getv(config, ['input_audio_transcription']),
|
1682
|
-
),
|
1683
|
-
)
|
1684
|
-
if getv(config, ['output_audio_transcription']) is not None:
|
1685
|
-
setv(
|
1686
|
-
to_object,
|
1687
|
-
['outputAudioTranscription'],
|
1688
|
-
_AudioTranscriptionConfig_to_vertex(
|
1689
|
-
self._api_client,
|
1690
|
-
getv(config, ['output_audio_transcription']),
|
1691
|
-
),
|
1692
|
-
)
|
1693
|
-
|
1694
|
-
if getv(config, ['session_resumption']) is not None:
|
1695
|
-
setv(
|
1696
|
-
to_object,
|
1697
|
-
['sessionResumption'],
|
1698
|
-
self._LiveClientSessionResumptionConfig_to_vertex(
|
1699
|
-
getv(config, ['session_resumption'])
|
1700
|
-
),
|
1701
|
-
)
|
1702
|
-
|
1703
|
-
if getv(config, ['context_window_compression']) is not None:
|
1704
|
-
setv(
|
1705
|
-
to_object,
|
1706
|
-
['contextWindowCompression'],
|
1707
|
-
self._ContextWindowCompressionConfig_to_vertex(
|
1708
|
-
getv(config, ['context_window_compression']),
|
1709
|
-
),
|
1710
|
-
)
|
1711
|
-
|
1712
|
-
return_value = {'setup': {'model': model}}
|
1713
|
-
return_value['setup'].update(to_object)
|
1714
|
-
return return_value
|
1715
|
-
|
1716
|
-
def _SlidingWindow_to_vertex(
|
1717
|
-
self,
|
1718
|
-
from_object: Union[dict, object],
|
1719
|
-
) -> dict:
|
1720
|
-
to_object: dict[str, Any] = {}
|
1721
|
-
if getv(from_object, ['target_tokens']) is not None:
|
1722
|
-
setv(to_object, ['targetTokens'], getv(from_object, ['target_tokens']))
|
1723
|
-
|
1724
|
-
return to_object
|
1725
|
-
|
1726
|
-
def _ContextWindowCompressionConfig_to_vertex(
|
1727
|
-
self,
|
1728
|
-
from_object: Union[dict, object],
|
1729
|
-
) -> dict:
|
1730
|
-
to_object: dict[str, Any] = {}
|
1731
|
-
if getv(from_object, ['trigger_tokens']) is not None:
|
1732
|
-
setv(to_object, ['triggerTokens'], getv(from_object, ['trigger_tokens']))
|
1733
|
-
|
1734
|
-
if getv(from_object, ['sliding_window']) is not None:
|
1735
|
-
setv(
|
1736
|
-
to_object,
|
1737
|
-
['slidingWindow'],
|
1738
|
-
self._SlidingWindow_to_mldev(
|
1739
|
-
getv(from_object, ['sliding_window'])
|
1740
|
-
),
|
1741
|
-
)
|
1742
|
-
|
1743
|
-
return to_object
|
1744
|
-
|
1745
|
-
def _LiveClientSessionResumptionConfig_to_vertex(
|
1746
|
-
self,
|
1747
|
-
from_object: Union[dict, object]
|
1748
|
-
) -> dict:
|
1749
|
-
to_object: dict[str, Any] = {}
|
1750
|
-
if getv(from_object, ['handle']) is not None:
|
1751
|
-
setv(to_object, ['handle'], getv(from_object, ['handle']))
|
1752
|
-
|
1753
|
-
if getv(from_object, ['transparent']) is not None:
|
1754
|
-
setv(to_object, ['transparent'], getv(from_object, ['transparent']))
|
1755
|
-
|
1756
|
-
return to_object
|
1757
844
|
|
1758
845
|
@contextlib.asynccontextmanager
|
1759
846
|
async def connect(
|
@@ -1778,6 +865,8 @@ class AsyncLive(_api_module.BaseModule):
|
|
1778
865
|
print(message)
|
1779
866
|
"""
|
1780
867
|
base_url = self._api_client._websocket_base_url()
|
868
|
+
if isinstance(base_url, bytes):
|
869
|
+
base_url = base_url.decode('utf-8')
|
1781
870
|
transformed_model = t.t_model(self._api_client, model)
|
1782
871
|
|
1783
872
|
parameter_model = _t_live_connect_config(self._api_client, config)
|
@@ -1787,22 +876,30 @@ class AsyncLive(_api_module.BaseModule):
|
|
1787
876
|
version = self._api_client._http_options.api_version
|
1788
877
|
uri = f'{base_url}/ws/google.ai.generativelanguage.{version}.GenerativeService.BidiGenerateContent?key={api_key}'
|
1789
878
|
headers = self._api_client._http_options.headers
|
879
|
+
|
1790
880
|
request_dict = _common.convert_to_dict(
|
1791
|
-
|
1792
|
-
|
1793
|
-
|
881
|
+
live_converters._LiveConnectParameters_to_mldev(
|
882
|
+
api_client=self._api_client,
|
883
|
+
from_object=types.LiveConnectParameters(
|
884
|
+
model=transformed_model,
|
885
|
+
config=parameter_model,
|
886
|
+
).model_dump(exclude_none=True)
|
1794
887
|
)
|
1795
888
|
)
|
889
|
+
del request_dict['config']
|
890
|
+
|
891
|
+
setv(request_dict, ['setup', 'model'], transformed_model)
|
892
|
+
|
1796
893
|
request = json.dumps(request_dict)
|
1797
894
|
else:
|
1798
895
|
# Get bearer token through Application Default Credentials.
|
1799
|
-
creds, _ = google.auth.default(
|
896
|
+
creds, _ = google.auth.default( # type: ignore[no-untyped-call]
|
1800
897
|
scopes=['https://www.googleapis.com/auth/cloud-platform']
|
1801
898
|
)
|
1802
899
|
|
1803
900
|
# creds.valid is False, and creds.token is None
|
1804
901
|
# Need to refresh credentials to populate those
|
1805
|
-
auth_req = google.auth.transport.requests.Request()
|
902
|
+
auth_req = google.auth.transport.requests.Request() # type: ignore[no-untyped-call]
|
1806
903
|
creds.refresh(auth_req)
|
1807
904
|
bearer_token = creds.token
|
1808
905
|
headers = self._api_client._http_options.headers
|
@@ -1819,11 +916,19 @@ class AsyncLive(_api_module.BaseModule):
|
|
1819
916
|
f'projects/{project}/locations/{location}/' + transformed_model
|
1820
917
|
)
|
1821
918
|
request_dict = _common.convert_to_dict(
|
1822
|
-
|
1823
|
-
|
1824
|
-
|
919
|
+
live_converters._LiveConnectParameters_to_vertex(
|
920
|
+
api_client=self._api_client,
|
921
|
+
from_object=types.LiveConnectParameters(
|
922
|
+
model=transformed_model,
|
923
|
+
config=parameter_model,
|
924
|
+
).model_dump(exclude_none=True)
|
1825
925
|
)
|
1826
926
|
)
|
927
|
+
del request_dict['config']
|
928
|
+
|
929
|
+
if getv(request_dict, ['setup', 'generationConfig', 'responseModalities']) is None:
|
930
|
+
setv(request_dict, ['setup', 'generationConfig', 'responseModalities'], ['AUDIO'])
|
931
|
+
|
1827
932
|
request = json.dumps(request_dict)
|
1828
933
|
|
1829
934
|
try:
|
@@ -1849,19 +954,23 @@ def _t_live_connect_config(
|
|
1849
954
|
if config is None:
|
1850
955
|
parameter_model = types.LiveConnectConfig()
|
1851
956
|
elif isinstance(config, dict):
|
1852
|
-
|
1853
|
-
if system_instruction is not None:
|
957
|
+
if getv(config, ['system_instruction']) is not None:
|
1854
958
|
converted_system_instruction = t.t_content(
|
1855
|
-
api_client,
|
959
|
+
api_client, getv(config, ['system_instruction'])
|
1856
960
|
)
|
1857
961
|
else:
|
1858
962
|
converted_system_instruction = None
|
1859
|
-
parameter_model = types.LiveConnectConfig(
|
1860
|
-
|
1861
|
-
**config
|
1862
|
-
) # type: ignore
|
963
|
+
parameter_model = types.LiveConnectConfig(**config)
|
964
|
+
parameter_model.system_instruction = converted_system_instruction
|
1863
965
|
else:
|
966
|
+
if config.system_instruction is None:
|
967
|
+
system_instruction = None
|
968
|
+
else:
|
969
|
+
system_instruction = t.t_content(
|
970
|
+
api_client, getv(config, ['system_instruction'])
|
971
|
+
)
|
1864
972
|
parameter_model = config
|
973
|
+
parameter_model.system_instruction = system_instruction
|
1865
974
|
|
1866
975
|
if parameter_model.generation_config is not None:
|
1867
976
|
warnings.warn(
|