fix(storage): 补齐嵌套结果二进制转存
生产真实 Gemini 图片任务可能在标准 data 之外保留嵌套 Base64,导致最终持久化关口拒绝任务成功。\n\n在所有生成结果返回前统一执行递归转存,并对仍未被常规媒体转换识别的二进制回退到本地结果物化,确保 PostgreSQL 不接收原始二进制。\n\n验证:go test ./... -count=1;go vet ./...;使用生产 Gemini Flash Image 平台配置完成本地真实图片编辑请求,文件哈希一致且持久化结果无内联二进制。
This commit is contained in:
@@ -236,6 +236,52 @@ func TestGeneratedAssetUploadPolicyFromName(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestFinalizeGeneratedAssetsUploadsNestedInlineBinaryUnderDefaultPolicy(t *testing.T) {
|
||||
storageDir := t.TempDir()
|
||||
service := &Service{cfg: config.Config{LocalGeneratedStorageDir: storageDir}}
|
||||
payload := append([]byte{0x89, 'P', 'N', 'G', 0x0d, 0x0a, 0x1a, 0x0a}, bytes.Repeat([]byte{0}, 160)...)
|
||||
encoded := base64.StdEncoding.EncodeToString(payload)
|
||||
result := map[string]any{
|
||||
"id": "image-edit",
|
||||
"provider_result": map[string]any{
|
||||
"binary_data_base64": encoded,
|
||||
"mime_type": "image/png",
|
||||
},
|
||||
}
|
||||
|
||||
finalized, err := service.finalizeGeneratedAssets(
|
||||
context.Background(),
|
||||
"task-nested-binary",
|
||||
"images.edits",
|
||||
result,
|
||||
defaultGeneratedAssetUploadPolicy(),
|
||||
nil,
|
||||
true,
|
||||
0,
|
||||
)
|
||||
if err != nil {
|
||||
t.Fatalf("finalize generated assets: %v", err)
|
||||
}
|
||||
if TaskResultHasInlineBinary(finalized) {
|
||||
t.Fatal("finalized result still contains inline binary")
|
||||
}
|
||||
nested := finalized["provider_result"].(map[string]any)
|
||||
reference, ok := nested["binary_data_base64"].(map[string]any)
|
||||
if !ok {
|
||||
t.Fatalf("nested binary should be replaced by an asset reference: %+v", nested)
|
||||
}
|
||||
if urlValue := stringFromAny(reference["url"]); !strings.HasPrefix(urlValue, "/static/generated/gateway-result-task-nested-binary-01-") {
|
||||
t.Fatalf("unexpected local static URL: %s", urlValue)
|
||||
}
|
||||
entries, err := os.ReadDir(storageDir)
|
||||
if err != nil {
|
||||
t.Fatalf("read generated storage: %v", err)
|
||||
}
|
||||
if len(entries) != 1 {
|
||||
t.Fatalf("expected one localized result file, got %d", len(entries))
|
||||
}
|
||||
}
|
||||
|
||||
func TestResolvedGeneratedAssetContentTypePrefersDetectedMedia(t *testing.T) {
|
||||
pngPayload := []byte{0x89, 'P', 'N', 'G', 0x0d, 0x0a, 0x1a, 0x0a, 0, 0, 0, 0}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user