Skip to main content

gproxy_protocol/transform/gemini/model_list/openai/
utils.rs

1use http::StatusCode;
2
3use crate::gemini::types::{GeminiApiError, GeminiApiErrorResponse, GeminiModelInfo};
4use crate::openai::types::{OpenAiApiErrorResponse, OpenAiModel};
5
6fn ensure_models_prefix(value: &str) -> String {
7    if value.starts_with("models/") {
8        value.to_string()
9    } else {
10        format!("models/{value}")
11    }
12}
13
14fn google_status_from_http(status_code: StatusCode) -> Option<String> {
15    let status = match status_code.as_u16() {
16        400 => "INVALID_ARGUMENT",
17        401 => "UNAUTHENTICATED",
18        403 => "PERMISSION_DENIED",
19        404 => "NOT_FOUND",
20        409 => "ABORTED",
21        429 => "RESOURCE_EXHAUSTED",
22        500 => "INTERNAL",
23        503 | 529 => "UNAVAILABLE",
24        504 => "DEADLINE_EXCEEDED",
25        _ => return None,
26    };
27    Some(status.to_string())
28}
29
30pub fn gemini_model_info_from_openai_model(model: OpenAiModel) -> GeminiModelInfo {
31    GeminiModelInfo {
32        name: ensure_models_prefix(&model.id),
33        base_model_id: Some(model.id.clone()),
34        version: None,
35        display_name: Some(model.id),
36        description: None,
37        input_token_limit: None,
38        output_token_limit: None,
39        supported_generation_methods: None,
40        thinking: None,
41        temperature: None,
42        max_temperature: None,
43        top_p: None,
44        top_k: None,
45    }
46}
47
48pub fn gemini_error_response_from_openai(
49    status_code: StatusCode,
50    body: OpenAiApiErrorResponse,
51) -> GeminiApiErrorResponse {
52    GeminiApiErrorResponse {
53        error: GeminiApiError {
54            code: i32::from(status_code.as_u16()),
55            message: body.error.message,
56            status: google_status_from_http(status_code),
57            details: None,
58        },
59    }
60}