mirror of
https://github.com/katanemo/plano.git
synced 2026-04-25 00:36:34 +02:00
bug fix - allow image content to pass through (#539)
fixes https://github.com/katanemo/archgw/issues/535
This commit is contained in:
parent
92a425facd
commit
04c7e5a175
3 changed files with 69 additions and 0 deletions
|
|
@ -32,6 +32,8 @@ pub async fn chat_completions(
|
|||
|
||||
let chat_request_bytes = request.collect().await?.to_bytes();
|
||||
|
||||
debug!("Received request body (raw utf8): {}", String::from_utf8_lossy(&chat_request_bytes));
|
||||
|
||||
let chat_request_parsed = serde_json::from_slice::<serde_json::Value>(&chat_request_bytes)
|
||||
.inspect_err(|err| {
|
||||
warn!(
|
||||
|
|
|
|||
|
|
@ -35,9 +35,16 @@ pub enum MultiPartContentType {
|
|||
ImageUrl,
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, Serialize, Deserialize, PartialEq)]
|
||||
pub struct ImageUrl {
|
||||
pub url: String,
|
||||
}
|
||||
|
||||
#[skip_serializing_none]
|
||||
#[derive(Debug, Clone, Serialize, Deserialize, PartialEq)]
|
||||
pub struct MultiPartContent {
|
||||
pub text: Option<String>,
|
||||
pub image_url: Option<ImageUrl>,
|
||||
#[serde(rename = "type")]
|
||||
pub content_type: MultiPartContentType,
|
||||
}
|
||||
|
|
@ -307,10 +314,12 @@ mod tests {
|
|||
MultiPartContent {
|
||||
text: Some("This is a text part.".to_string()),
|
||||
content_type: MultiPartContentType::Text,
|
||||
image_url: None,
|
||||
},
|
||||
MultiPartContent {
|
||||
text: Some("https://example.com/image.png".to_string()),
|
||||
content_type: MultiPartContentType::ImageUrl,
|
||||
image_url: None,
|
||||
},
|
||||
]);
|
||||
assert_eq!(multi_part_content.to_string(), "This is a text part.");
|
||||
|
|
@ -364,6 +373,61 @@ mod tests {
|
|||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_chat_completions_request_image_content() {
|
||||
const CHAT_COMPLETIONS_REQUEST: &str = r#"
|
||||
{
|
||||
"stream": true,
|
||||
"model": "openai/gpt-4o",
|
||||
"messages": [
|
||||
{
|
||||
"role": "user",
|
||||
"content": [
|
||||
{
|
||||
"type": "text",
|
||||
"text": "describe this photo pls"
|
||||
},
|
||||
{
|
||||
"type": "image_url",
|
||||
"image_url": {
|
||||
"url": "data:image/jpeg;base64,/9j/4AAQSkZJRgABAQAAAQABAAD/...=="
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}"#;
|
||||
|
||||
let chat_completions_request: ChatCompletionsRequest =
|
||||
serde_json::from_str(CHAT_COMPLETIONS_REQUEST).unwrap();
|
||||
assert_eq!(chat_completions_request.model, "openai/gpt-4o");
|
||||
if let Some(ContentType::MultiPart(multi_part_content)) =
|
||||
chat_completions_request.messages[0].content.as_ref()
|
||||
{
|
||||
assert_eq!(multi_part_content.len(), 2);
|
||||
assert_eq!(
|
||||
multi_part_content[0].content_type,
|
||||
MultiPartContentType::Text
|
||||
);
|
||||
assert_eq!(
|
||||
multi_part_content[0].text,
|
||||
Some("describe this photo pls".to_string())
|
||||
);
|
||||
assert_eq!(
|
||||
multi_part_content[1].content_type,
|
||||
MultiPartContentType::ImageUrl
|
||||
);
|
||||
assert_eq!(
|
||||
multi_part_content[1].image_url,
|
||||
Some(ImageUrl {
|
||||
url: "data:image/jpeg;base64,/9j/4AAQSkZJRgABAQAAAQABAAD/...==".to_string(),
|
||||
})
|
||||
);
|
||||
} else {
|
||||
panic!("Expected MultiPartContent");
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_sse_streaming() {
|
||||
let json_data = r#"data: {"id":"chatcmpl-123","object":"chat.completion.chunk","created":1700000000,"model":"gpt-3.5-turbo","choices":[{"index":0,"delta":{"role":"assistant"},"finish_reason":null}]}
|
||||
|
|
|
|||
|
|
@ -12,6 +12,9 @@ llm_providers:
|
|||
- access_key: $OPENAI_API_KEY
|
||||
model: openai/gpt-4o-mini
|
||||
|
||||
- access_key: $OPENAI_API_KEY
|
||||
model: openai/gpt-4.1
|
||||
|
||||
- access_key: $OPENAI_API_KEY
|
||||
model: openai/gpt-4o
|
||||
default: true
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue