1use serde::{Deserialize, Serialize};
2use time::OffsetDateTime;
3
4pub use crate::gemini::count_tokens::types::{
5 GeminiBlob, GeminiContent, GeminiFunctionCall, GeminiFunctionResponse, GeminiGenerationConfig,
6 GeminiModalityTokenCount, GeminiTool, HttpMethod,
7};
8pub use crate::gemini::generate_content::types::{
9 GeminiGroundingMetadata, GeminiUrlContextMetadata,
10};
11pub use crate::gemini::types::{
12 GeminiApiError, GeminiApiErrorResponse, GeminiResponseHeaders, JsonObject,
13};
14
15#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
17pub struct GeminiBidiGenerateContentClientMessage {
18 #[serde(flatten)]
20 pub message_type: GeminiBidiGenerateContentClientMessageType,
21}
22
23#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
24#[serde(untagged)]
25#[allow(clippy::large_enum_variant)]
26pub enum GeminiBidiGenerateContentClientMessageType {
27 Setup {
28 setup: GeminiBidiGenerateContentSetup,
29 },
30 ClientContent {
31 #[serde(rename = "clientContent")]
32 client_content: GeminiBidiGenerateContentClientContent,
33 },
34 RealtimeInput {
35 #[serde(rename = "realtimeInput")]
36 realtime_input: GeminiBidiGenerateContentRealtimeInput,
37 },
38 ToolResponse {
39 #[serde(rename = "toolResponse")]
40 tool_response: GeminiBidiGenerateContentToolResponse,
41 },
42}
43
44#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
46pub struct GeminiBidiGenerateContentSetup {
47 pub model: String,
49 #[serde(
50 rename = "generationConfig",
51 default,
52 skip_serializing_if = "Option::is_none"
53 )]
54 pub generation_config: Option<GeminiGenerationConfig>,
55 #[serde(
56 rename = "systemInstruction",
57 default,
58 skip_serializing_if = "Option::is_none"
59 )]
60 pub system_instruction: Option<GeminiContent>,
61 #[serde(default, skip_serializing_if = "Option::is_none")]
62 pub tools: Option<Vec<GeminiTool>>,
63 #[serde(
64 rename = "realtimeInputConfig",
65 default,
66 skip_serializing_if = "Option::is_none"
67 )]
68 pub realtime_input_config: Option<GeminiRealtimeInputConfig>,
69 #[serde(
70 rename = "sessionResumption",
71 default,
72 skip_serializing_if = "Option::is_none"
73 )]
74 pub session_resumption: Option<GeminiSessionResumptionConfig>,
75 #[serde(
76 rename = "contextWindowCompression",
77 default,
78 skip_serializing_if = "Option::is_none"
79 )]
80 pub context_window_compression: Option<GeminiContextWindowCompressionConfig>,
81 #[serde(
82 rename = "inputAudioTranscription",
83 default,
84 skip_serializing_if = "Option::is_none"
85 )]
86 pub input_audio_transcription: Option<GeminiAudioTranscriptionConfig>,
87 #[serde(
88 rename = "outputAudioTranscription",
89 default,
90 skip_serializing_if = "Option::is_none"
91 )]
92 pub output_audio_transcription: Option<GeminiAudioTranscriptionConfig>,
93 #[serde(default, skip_serializing_if = "Option::is_none")]
94 pub proactivity: Option<GeminiProactivityConfig>,
95 #[serde(
96 rename = "prefixTurns",
97 default,
98 skip_serializing_if = "Option::is_none"
99 )]
100 pub prefix_turns: Option<Vec<GeminiContent>>,
101 #[serde(
102 rename = "historyConfig",
103 default,
104 skip_serializing_if = "Option::is_none"
105 )]
106 pub history_config: Option<GeminiHistoryConfig>,
107}
108
109#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
111pub struct GeminiBidiGenerateContentClientContent {
112 #[serde(default, skip_serializing_if = "Option::is_none")]
113 pub turns: Option<Vec<GeminiContent>>,
114 #[serde(
115 rename = "turnComplete",
116 default,
117 skip_serializing_if = "Option::is_none"
118 )]
119 pub turn_complete: Option<bool>,
120}
121
122#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
124pub struct GeminiBidiGenerateContentRealtimeInput {
125 #[serde(
127 rename = "mediaChunks",
128 default,
129 skip_serializing_if = "Option::is_none"
130 )]
131 pub media_chunks: Option<Vec<GeminiBlob>>,
132 #[serde(default, skip_serializing_if = "Option::is_none")]
133 pub audio: Option<GeminiBlob>,
134 #[serde(default, skip_serializing_if = "Option::is_none")]
135 pub video: Option<GeminiBlob>,
136 #[serde(
137 rename = "activityStart",
138 default,
139 skip_serializing_if = "Option::is_none"
140 )]
141 pub activity_start: Option<GeminiActivityStart>,
142 #[serde(
143 rename = "activityEnd",
144 default,
145 skip_serializing_if = "Option::is_none"
146 )]
147 pub activity_end: Option<GeminiActivityEnd>,
148 #[serde(
149 rename = "audioStreamEnd",
150 default,
151 skip_serializing_if = "Option::is_none"
152 )]
153 pub audio_stream_end: Option<bool>,
154 #[serde(default, skip_serializing_if = "Option::is_none")]
155 pub text: Option<String>,
156}
157
158#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize, Default)]
159pub struct GeminiActivityStart {}
160
161#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize, Default)]
162pub struct GeminiActivityEnd {}
163
164#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
165pub struct GeminiBidiGenerateContentToolResponse {
166 #[serde(
167 rename = "functionResponses",
168 default,
169 skip_serializing_if = "Option::is_none"
170 )]
171 pub function_responses: Option<Vec<GeminiFunctionResponse>>,
172}
173
174#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
176pub struct GeminiBidiGenerateContentServerMessage {
177 #[serde(
178 rename = "usageMetadata",
179 default,
180 skip_serializing_if = "Option::is_none"
181 )]
182 pub usage_metadata: Option<GeminiLiveUsageMetadata>,
183 #[serde(flatten)]
185 pub message_type: GeminiBidiGenerateContentServerMessageType,
186}
187
188#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
189#[serde(untagged)]
190#[allow(clippy::large_enum_variant)]
191pub enum GeminiBidiGenerateContentServerMessageType {
192 SetupComplete {
193 #[serde(rename = "setupComplete")]
194 setup_complete: GeminiBidiGenerateContentSetupComplete,
195 },
196 ServerContent {
197 #[serde(rename = "serverContent")]
198 server_content: GeminiBidiGenerateContentServerContent,
199 },
200 ToolCall {
201 #[serde(rename = "toolCall")]
202 tool_call: GeminiBidiGenerateContentToolCall,
203 },
204 ToolCallCancellation {
205 #[serde(rename = "toolCallCancellation")]
206 tool_call_cancellation: GeminiBidiGenerateContentToolCallCancellation,
207 },
208 GoAway {
209 #[serde(rename = "goAway")]
210 go_away: GeminiGoAway,
211 },
212 SessionResumptionUpdate {
213 #[serde(rename = "sessionResumptionUpdate")]
214 session_resumption_update: GeminiSessionResumptionUpdate,
215 },
216}
217
218#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize, Default)]
219pub struct GeminiBidiGenerateContentSetupComplete {}
220
221#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
222pub struct GeminiBidiGenerateContentServerContent {
223 #[serde(
224 rename = "generationComplete",
225 default,
226 skip_serializing_if = "Option::is_none"
227 )]
228 pub generation_complete: Option<bool>,
229 #[serde(
230 rename = "turnComplete",
231 default,
232 skip_serializing_if = "Option::is_none"
233 )]
234 pub turn_complete: Option<bool>,
235 #[serde(default, skip_serializing_if = "Option::is_none")]
236 pub interrupted: Option<bool>,
237 #[serde(
238 rename = "groundingMetadata",
239 default,
240 skip_serializing_if = "Option::is_none"
241 )]
242 pub grounding_metadata: Option<GeminiGroundingMetadata>,
243 #[serde(
244 rename = "inputTranscription",
245 default,
246 skip_serializing_if = "Option::is_none"
247 )]
248 pub input_transcription: Option<GeminiBidiGenerateContentTranscription>,
249 #[serde(
250 rename = "outputTranscription",
251 default,
252 skip_serializing_if = "Option::is_none"
253 )]
254 pub output_transcription: Option<GeminiBidiGenerateContentTranscription>,
255 #[serde(
256 rename = "urlContextMetadata",
257 default,
258 skip_serializing_if = "Option::is_none"
259 )]
260 pub url_context_metadata: Option<GeminiUrlContextMetadata>,
261 #[serde(rename = "modelTurn", default, skip_serializing_if = "Option::is_none")]
262 pub model_turn: Option<GeminiContent>,
263}
264
265#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
266pub struct GeminiBidiGenerateContentTranscription {
267 pub text: String,
268}
269
270#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
271pub struct GeminiBidiGenerateContentToolCall {
272 #[serde(
273 rename = "functionCalls",
274 default,
275 skip_serializing_if = "Option::is_none"
276 )]
277 pub function_calls: Option<Vec<GeminiFunctionCall>>,
278}
279
280#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize, Default)]
281pub struct GeminiBidiGenerateContentToolCallCancellation {
282 #[serde(default, skip_serializing_if = "Option::is_none")]
283 pub ids: Option<Vec<String>>,
284}
285
286#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
287pub struct GeminiGoAway {
288 #[serde(rename = "timeLeft")]
290 pub time_left: String,
291}
292
293#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
294pub struct GeminiLiveUsageMetadata {
295 #[serde(
296 rename = "promptTokenCount",
297 default,
298 skip_serializing_if = "Option::is_none"
299 )]
300 pub prompt_token_count: Option<u64>,
301 #[serde(
302 rename = "cachedContentTokenCount",
303 default,
304 skip_serializing_if = "Option::is_none"
305 )]
306 pub cached_content_token_count: Option<u64>,
307 #[serde(
308 rename = "responseTokenCount",
309 default,
310 skip_serializing_if = "Option::is_none"
311 )]
312 pub response_token_count: Option<u64>,
313 #[serde(
314 rename = "toolUsePromptTokenCount",
315 default,
316 skip_serializing_if = "Option::is_none"
317 )]
318 pub tool_use_prompt_token_count: Option<u64>,
319 #[serde(
320 rename = "thoughtsTokenCount",
321 default,
322 skip_serializing_if = "Option::is_none"
323 )]
324 pub thoughts_token_count: Option<u64>,
325 #[serde(
326 rename = "totalTokenCount",
327 default,
328 skip_serializing_if = "Option::is_none"
329 )]
330 pub total_token_count: Option<u64>,
331 #[serde(
332 rename = "promptTokensDetails",
333 default,
334 skip_serializing_if = "Option::is_none"
335 )]
336 pub prompt_tokens_details: Option<Vec<GeminiModalityTokenCount>>,
337 #[serde(
338 rename = "cacheTokensDetails",
339 default,
340 skip_serializing_if = "Option::is_none"
341 )]
342 pub cache_tokens_details: Option<Vec<GeminiModalityTokenCount>>,
343 #[serde(
344 rename = "responseTokensDetails",
345 default,
346 skip_serializing_if = "Option::is_none"
347 )]
348 pub response_tokens_details: Option<Vec<GeminiModalityTokenCount>>,
349 #[serde(
350 rename = "toolUsePromptTokensDetails",
351 default,
352 skip_serializing_if = "Option::is_none"
353 )]
354 pub tool_use_prompt_tokens_details: Option<Vec<GeminiModalityTokenCount>>,
355}
356
357#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize, Default)]
358pub struct GeminiHistoryConfig {
359 #[serde(
360 rename = "initialHistoryInClientContent",
361 default,
362 skip_serializing_if = "Option::is_none"
363 )]
364 pub initial_history_in_client_content: Option<bool>,
365}
366
367#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize, Default)]
368pub struct GeminiAudioTranscriptionConfig {}
369
370#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
371pub struct GeminiRealtimeInputConfig {
372 #[serde(
373 rename = "automaticActivityDetection",
374 default,
375 skip_serializing_if = "Option::is_none"
376 )]
377 pub automatic_activity_detection: Option<GeminiAutomaticActivityDetection>,
378 #[serde(
379 rename = "activityHandling",
380 default,
381 skip_serializing_if = "Option::is_none"
382 )]
383 pub activity_handling: Option<GeminiActivityHandling>,
384 #[serde(
385 rename = "turnCoverage",
386 default,
387 skip_serializing_if = "Option::is_none"
388 )]
389 pub turn_coverage: Option<GeminiTurnCoverage>,
390}
391
392#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
393pub struct GeminiAutomaticActivityDetection {
394 #[serde(default, skip_serializing_if = "Option::is_none")]
395 pub disabled: Option<bool>,
396 #[serde(
397 rename = "startOfSpeechSensitivity",
398 default,
399 skip_serializing_if = "Option::is_none"
400 )]
401 pub start_of_speech_sensitivity: Option<GeminiStartSensitivity>,
402 #[serde(
403 rename = "prefixPaddingMs",
404 default,
405 skip_serializing_if = "Option::is_none"
406 )]
407 pub prefix_padding_ms: Option<i32>,
408 #[serde(
409 rename = "endOfSpeechSensitivity",
410 default,
411 skip_serializing_if = "Option::is_none"
412 )]
413 pub end_of_speech_sensitivity: Option<GeminiEndSensitivity>,
414 #[serde(
415 rename = "silenceDurationMs",
416 default,
417 skip_serializing_if = "Option::is_none"
418 )]
419 pub silence_duration_ms: Option<i32>,
420}
421
422#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
423pub enum GeminiActivityHandling {
424 #[serde(rename = "ACTIVITY_HANDLING_UNSPECIFIED")]
425 ActivityHandlingUnspecified,
426 #[serde(rename = "START_OF_ACTIVITY_INTERRUPTS")]
427 StartOfActivityInterrupts,
428 #[serde(rename = "NO_INTERRUPTION")]
429 NoInterruption,
430}
431
432#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
433pub enum GeminiStartSensitivity {
434 #[serde(rename = "START_SENSITIVITY_UNSPECIFIED")]
435 StartSensitivityUnspecified,
436 #[serde(rename = "START_SENSITIVITY_HIGH")]
437 StartSensitivityHigh,
438 #[serde(rename = "START_SENSITIVITY_LOW")]
439 StartSensitivityLow,
440}
441
442#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
443pub enum GeminiEndSensitivity {
444 #[serde(rename = "END_SENSITIVITY_UNSPECIFIED")]
445 EndSensitivityUnspecified,
446 #[serde(rename = "END_SENSITIVITY_HIGH")]
447 EndSensitivityHigh,
448 #[serde(rename = "END_SENSITIVITY_LOW")]
449 EndSensitivityLow,
450}
451
452#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
453pub enum GeminiTurnCoverage {
454 #[serde(rename = "TURN_COVERAGE_UNSPECIFIED")]
455 TurnCoverageUnspecified,
456 #[serde(rename = "TURN_INCLUDES_ONLY_ACTIVITY")]
457 TurnIncludesOnlyActivity,
458 #[serde(rename = "TURN_INCLUDES_ALL_INPUT")]
459 TurnIncludesAllInput,
460 #[serde(rename = "TURN_INCLUDES_AUDIO_ACTIVITY_AND_ALL_VIDEO")]
461 TurnIncludesAudioActivityAndAllVideo,
462}
463
464#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize, Default)]
465pub struct GeminiSessionResumptionConfig {
466 #[serde(default, skip_serializing_if = "Option::is_none")]
467 pub handle: Option<String>,
468}
469
470#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
471pub struct GeminiSessionResumptionUpdate {
472 #[serde(rename = "newHandle", default, skip_serializing_if = "Option::is_none")]
473 pub new_handle: Option<String>,
474 #[serde(default, skip_serializing_if = "Option::is_none")]
475 pub resumable: Option<bool>,
476}
477
478#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
479pub struct GeminiContextWindowCompressionConfig {
480 #[serde(
481 rename = "slidingWindow",
482 default,
483 skip_serializing_if = "Option::is_none"
484 )]
485 pub sliding_window: Option<GeminiSlidingWindow>,
486 #[serde(
487 rename = "triggerTokens",
488 default,
489 skip_serializing_if = "Option::is_none"
490 )]
491 pub trigger_tokens: Option<i64>,
492}
493
494#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
495pub struct GeminiSlidingWindow {
496 #[serde(
497 rename = "targetTokens",
498 default,
499 skip_serializing_if = "Option::is_none"
500 )]
501 pub target_tokens: Option<i64>,
502}
503
504#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
505pub struct GeminiProactivityConfig {
506 #[serde(
507 rename = "proactiveAudio",
508 default,
509 skip_serializing_if = "Option::is_none"
510 )]
511 pub proactive_audio: Option<bool>,
512}
513
514#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
516pub struct GeminiCreateAuthTokenRequest {
517 #[serde(rename = "authToken")]
518 pub auth_token: GeminiAuthToken,
519}
520
521#[derive(Debug, Clone, PartialEq, Serialize, Deserialize, Default)]
523pub struct GeminiAuthToken {
524 #[serde(default, skip_serializing_if = "Option::is_none")]
525 pub name: Option<String>,
526 #[serde(
527 rename = "expireTime",
528 default,
529 with = "time::serde::rfc3339::option",
530 skip_serializing_if = "Option::is_none"
531 )]
532 pub expire_time: Option<OffsetDateTime>,
533 #[serde(
534 rename = "newSessionExpireTime",
535 default,
536 with = "time::serde::rfc3339::option",
537 skip_serializing_if = "Option::is_none"
538 )]
539 pub new_session_expire_time: Option<OffsetDateTime>,
540 #[serde(rename = "fieldMask", default, skip_serializing_if = "Option::is_none")]
542 pub field_mask: Option<String>,
543 #[serde(
544 rename = "bidiGenerateContentSetup",
545 default,
546 skip_serializing_if = "Option::is_none"
547 )]
548 pub bidi_generate_content_setup: Option<GeminiBidiGenerateContentSetup>,
549 #[serde(default, skip_serializing_if = "Option::is_none")]
550 pub uses: Option<i32>,
551}