fix: harden upstream path + binary-body validation (gadfly round 1)
- upstreamPath rejects '..' in model ids AND in the rest path — the rest can embed SERVER-SUPPLIED components (ACE-Step result file URLs), so dot-dot/scheme smuggling toward other proxy endpoints is refused - singleImageResult requires positive image evidence (sniffed magic OR declared image/*): an empty-Content-Type error page can no longer pass as 'the image' via sniffImageMIME's PNG-default labelling - upscale/background responses get a dedicated 256MB cap (the 64MB cap is JSON-sized; a 4x PNG legitimately exceeds it) - mesh JSON-detection widened (512-byte whitespace-tolerant peek + reject declared application/json) - Transcribe now reuses buildMultipart; transcriptionFilename takes (filename, mime) so diarize shares it without a fake request struct; truncateForError stops shadowing builtin cap; OnlyMask doc de-ambiguated Co-Authored-By: Claude Fable 5 <[email protected]>
This commit is contained in:
@@ -251,3 +251,32 @@ func TestUpstreamPathRejectsSeparators(t *testing.T) {
|
||||
t.Errorf("path prefix wrong: %q", got)
|
||||
}
|
||||
}
|
||||
|
||||
func TestUpscaleRejectsEmptyContentTypeNonImage(t *testing.T) {
|
||||
srv := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||
w.Header()["Content-Type"] = nil // suppress auto-detection: NO Content-Type at all
|
||||
_, _ = w.Write([]byte("502 bad gateway"))
|
||||
}))
|
||||
defer srv.Close()
|
||||
|
||||
p := New(WithBaseURL(srv.URL), WithHTTPClient(srv.Client()))
|
||||
up, _ := p.UpscaleModel("mediautils")
|
||||
_, err := up.Upscale(context.Background(),
|
||||
imagegen.UpscaleRequest{Image: imagegen.Image{Data: pngFixture(t)}})
|
||||
var apiErr *llm.APIError
|
||||
if !errors.As(err, &apiErr) {
|
||||
t.Fatalf("err = %v, want APIError for headerless non-image body", err)
|
||||
}
|
||||
}
|
||||
|
||||
func TestUpstreamPathRejectsDotDot(t *testing.T) {
|
||||
if _, err := upstreamPath("..", "/x"); err == nil {
|
||||
t.Error("model '..' accepted")
|
||||
}
|
||||
if _, err := upstreamPath("m", "/v1/audio?path=../../api/models/unload"); err == nil {
|
||||
t.Error("dot-dot rest accepted")
|
||||
}
|
||||
if _, err := upstreamPath("m", "/v1/audio?path=https://evil.example/x"); err == nil {
|
||||
t.Error("absolute-URL rest accepted")
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user