Skip to content

Commit 86aeb72

Browse files
authored
Merge pull request #2346 from QuantumNous/nano-banana-multi-turn
feat(gemini): implement markdown image handling in text processing
2 parents 36a739e + 4dbdbde commit 86aeb72

File tree

1 file changed

+62
-3
lines changed

1 file changed

+62
-3
lines changed

relay/channel/gemini/relay-gemini.go

Lines changed: 62 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -446,9 +446,68 @@ func CovertOpenAI2Gemini(c *gin.Context, textRequest dto.GeneralOpenAIRequest, i
446446
if part.Text == "" {
447447
continue
448448
}
449-
parts = append(parts, dto.GeminiPart{
450-
Text: part.Text,
451-
})
449+
// check markdown image ![image](data:image/jpeg;base64,xxxxxxxxxxxx)
450+
// 使用字符串查找而非正则,避免大文本性能问题
451+
text := part.Text
452+
hasMarkdownImage := false
453+
for {
454+
// 快速检查是否包含 markdown 图片标记
455+
startIdx := strings.Index(text, "![")
456+
if startIdx == -1 {
457+
break
458+
}
459+
// 找到 ](
460+
bracketIdx := strings.Index(text[startIdx:], "](data:")
461+
if bracketIdx == -1 {
462+
break
463+
}
464+
bracketIdx += startIdx
465+
// 找到闭合的 )
466+
closeIdx := strings.Index(text[bracketIdx+2:], ")")
467+
if closeIdx == -1 {
468+
break
469+
}
470+
closeIdx += bracketIdx + 2
471+
472+
hasMarkdownImage = true
473+
// 添加图片前的文本
474+
if startIdx > 0 {
475+
textBefore := text[:startIdx]
476+
if textBefore != "" {
477+
parts = append(parts, dto.GeminiPart{
478+
Text: textBefore,
479+
})
480+
}
481+
}
482+
// 提取 data URL (从 "](" 后面开始,到 ")" 之前)
483+
dataUrl := text[bracketIdx+2 : closeIdx]
484+
imageNum += 1
485+
if constant.GeminiVisionMaxImageNum != -1 && imageNum > constant.GeminiVisionMaxImageNum {
486+
return nil, fmt.Errorf("too many images in the message, max allowed is %d", constant.GeminiVisionMaxImageNum)
487+
}
488+
format, base64String, err := service.DecodeBase64FileData(dataUrl)
489+
if err != nil {
490+
return nil, fmt.Errorf("decode markdown base64 image data failed: %s", err.Error())
491+
}
492+
imgPart := dto.GeminiPart{
493+
InlineData: &dto.GeminiInlineData{
494+
MimeType: format,
495+
Data: base64String,
496+
},
497+
}
498+
if shouldAttachThoughtSignature {
499+
imgPart.ThoughtSignature = json.RawMessage(strconv.Quote(thoughtSignatureBypassValue))
500+
}
501+
parts = append(parts, imgPart)
502+
// 继续处理剩余文本
503+
text = text[closeIdx+1:]
504+
}
505+
// 添加剩余文本或原始文本(如果没有找到 markdown 图片)
506+
if !hasMarkdownImage {
507+
parts = append(parts, dto.GeminiPart{
508+
Text: part.Text,
509+
})
510+
}
452511
} else if part.Type == dto.ContentTypeImageURL {
453512
imageNum += 1
454513

0 commit comments

Comments
 (0)