From bb76e8b22baef07dd79ea0f07d146192a56e7bec Mon Sep 17 00:00:00 2001 From: Danborad <1948863412@qq.com> Date: Thu, 6 Aug 2026 13:20:06 +0800 Subject: [PATCH] =?UTF-8?q?fix(video):=20=E8=A7=86=E9=A2=91=E7=BB=93?= =?UTF-8?q?=E6=9E=9C=E4=B8=8B=E8=BD=BD=20-=20=E8=A1=A5=E9=BD=90=20Grok=20?= =?UTF-8?q?=E5=90=8C=E6=BA=90=E8=AE=A4=E8=AF=81=20(#158)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Danborad --- backend/internal/service/provider.go | 25 +++++++++++++++++++++-- backend/internal/service/provider_test.go | 16 ++++++++++----- 2 files changed, 34 insertions(+), 7 deletions(-) diff --git a/backend/internal/service/provider.go b/backend/internal/service/provider.go index f65bed745..cdcc4ed3f 100644 --- a/backend/internal/service/provider.go +++ b/backend/internal/service/provider.go @@ -1035,7 +1035,7 @@ func runVideoTask(ctx context.Context, input canvasGenerationInput) (map[string] status := strings.ToLower(stringField(state, "status")) if status == "completed" || status == "succeeded" || status == "success" || status == "done" { if videoURL := newAPIVideoResultURL(state); videoURL != "" { - data, mimeType, err := getExternalBinary(withProviderRequestKind(ctx, "download"), videoURL) + data, mimeType, err := getProviderExternalBinary(withProviderRequestKind(ctx, "download"), input.Config, videoURL) if err != nil { return nil, fmt.Errorf("视频结果下载失败(任务 %s):%w", id, err) } @@ -1291,7 +1291,7 @@ func queryNewAPIChannel2VideoTask(ctx context.Context, input canvasGenerationInp if videoURL == "" { return nil, status, fmt.Errorf("NewAPI Video Generations 任务 %s 已成功但没有返回视频地址", id) } - data, mimeType, err := getExternalBinary(withProviderRequestKind(ctx, "download"), videoURL) + data, mimeType, err := getProviderExternalBinary(withProviderRequestKind(ctx, "download"), input.Config, videoURL) if err != nil { return nil, status, fmt.Errorf("NewAPI Video Generations 视频结果下载失败(任务 %s):%w", id, err) } @@ -1871,6 +1871,27 @@ func getExternalBinary(ctx context.Context, rawURL string) ([]byte, string, erro return doBinary(req) } +func getProviderExternalBinary(ctx context.Context, config providerConfig, rawURL string) ([]byte, string, error) { + req, err := http.NewRequestWithContext(ctx, http.MethodGet, rawURL, nil) + if err != nil { + return nil, "", err + } + if sameProviderOrigin(config.BaseURL, rawURL) { + req.Header.Set("Authorization", "Bearer "+config.APIKey) + ApplyOutboundHeaders(req, config.Headers) + } + return doBinary(req) +} + +func sameProviderOrigin(baseURL string, rawURL string) bool { + base, baseErr := url.Parse(strings.TrimSpace(baseURL)) + target, targetErr := url.Parse(strings.TrimSpace(rawURL)) + if baseErr != nil || targetErr != nil || base.Scheme == "" || base.Host == "" || target.Scheme == "" || target.Host == "" { + return false + } + return strings.EqualFold(base.Scheme, target.Scheme) && strings.EqualFold(base.Host, target.Host) +} + func doJSON(req *http.Request, target interface{}) error { data, mimeType, err := doBinary(req) if err != nil { diff --git a/backend/internal/service/provider_test.go b/backend/internal/service/provider_test.go index 5d087a07a..019162627 100644 --- a/backend/internal/service/provider_test.go +++ b/backend/internal/service/provider_test.go @@ -401,8 +401,8 @@ func TestRunVideoTaskUsesNestedURLBeforeResultURL(t *testing.T) { w.Header().Set("Content-Type", "application/json") _, _ = w.Write([]byte(`{"code":"success","data":{"task_id":"video-1","status":"SUCCESS","result_url":"` + server.URL + `/v1/videos/video-1/content","data":{"status":"completed","url":"` + server.URL + `/files/video.mp4"}}}`)) case "GET /files/video.mp4": - if authorization := r.Header.Get("Authorization"); authorization != "" { - t.Errorf("file Authorization = %q, want empty", authorization) + if authorization := r.Header.Get("Authorization"); authorization != "Bearer test-key" { + t.Errorf("file Authorization = %q, want Bearer test-key", authorization) } w.Header().Set("Content-Type", "video/mp4") _, _ = w.Write([]byte("video")) @@ -512,8 +512,8 @@ func TestRunVideoTaskUsesXAIVideoGenerationEndpoint(t *testing.T) { w.Header().Set("Content-Type", "application/json") _, _ = w.Write([]byte(`{"status":"done","video":{"url":"` + server.URL + `/files/video.mp4"}}`)) case "GET /files/video.mp4": - if authorization := r.Header.Get("Authorization"); authorization != "" { - t.Errorf("file Authorization = %q, want empty", authorization) + if authorization := r.Header.Get("Authorization"); authorization != "Bearer test-key" { + t.Errorf("file Authorization = %q, want Bearer test-key", authorization) } w.Header().Set("Content-Type", "video/mp4") _, _ = w.Write([]byte("video")) @@ -779,6 +779,9 @@ func TestRunNewAPIChannel1VideoTaskDownloadsSucceededObject(t *testing.T) { w.Header().Set("Content-Type", "application/json") _, _ = w.Write([]byte(`{"id":"channel-1-task","status":"SUCCEEDED","object":"` + server.URL + `/video.mp4"}`)) case "GET /video.mp4": + if authorization := r.Header.Get("Authorization"); authorization != "" { + t.Errorf("file Authorization = %q, want empty", authorization) + } w.Header().Set("Content-Type", "video/mp4") _, _ = w.Write([]byte("video")) default: @@ -819,7 +822,7 @@ func TestRunNewAPIChannel2VideoTaskDownloadsTemporaryResult(t *testing.T) { if err := json.NewDecoder(r.Body).Decode(&body); err != nil { t.Fatalf("decode request: %v", err) } - if body["model"] != "grok-image-video" || body["seconds"] != "10" || body["aspect_ratio"] != "9:16" || body["resolution"] != "720p" { + if body["model"] != "grok-image-video" || body["seconds"] != "15" || body["aspect_ratio"] != "9:16" || body["resolution"] != "720p" { t.Errorf("body = %#v", body) } images, ok := body["image_urls"].([]interface{}) @@ -837,6 +840,9 @@ func TestRunNewAPIChannel2VideoTaskDownloadsTemporaryResult(t *testing.T) { w.Header().Set("Content-Type", "application/json") _, _ = w.Write([]byte(`{"code":"success","data":{"task_id":"grok-task","status":"SUCCESS","result_url":"` + server.URL + `/video.mp4"}}`)) case "GET /video.mp4": + if authorization := r.Header.Get("Authorization"); authorization != "Bearer test-key" { + t.Errorf("file Authorization = %q, want Bearer test-key", authorization) + } w.Header().Set("Content-Type", "video/mp4") _, _ = w.Write([]byte("video")) default: