fix(media): 资源交付 - 按内容识别上传类型并统一重试与附件交付 (#678)
Co-authored-by: ddcat666 <26564566+ddcat666@users.noreply.github.com>
This commit is contained in:
39
backend/internal/handler/resource_content_delivery_test.go
Normal file
39
backend/internal/handler/resource_content_delivery_test.go
Normal file
@@ -0,0 +1,39 @@
|
||||
package handler
|
||||
|
||||
import (
|
||||
"io"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"strings"
|
||||
"testing"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
"infinite-canvas/backend/internal/assets"
|
||||
"infinite-canvas/backend/internal/model"
|
||||
"infinite-canvas/backend/internal/service"
|
||||
)
|
||||
|
||||
func TestNonMediaDeliveryAttachment(t *testing.T) {
|
||||
gin.SetMode(gin.TestMode)
|
||||
for _, mimeType := range []string{"text/html", "image/svg+xml", "application/pdf", "application/octet-stream", "image/png"} {
|
||||
t.Run(mimeType, func(t *testing.T) {
|
||||
router := gin.New()
|
||||
router.GET("/file", func(c *gin.Context) {
|
||||
r := &model.Resource{ID: "file", MimeType: mimeType}
|
||||
serveResourceDelivery(c, &service.ResourceDelivery{Resource: r, Access: &assets.ResourceAccess{Delivery: assets.DeliveryLocal}, Stream: &service.ResourceStream{Resource: r, Body: io.NopCloser(strings.NewReader("content")), StatusCode: 200, ContentLength: 7}}, "", "inline")
|
||||
})
|
||||
w := httptest.NewRecorder()
|
||||
router.ServeHTTP(w, httptest.NewRequest(http.MethodGet, "/file", nil))
|
||||
if w.Code != 200 {
|
||||
t.Fatalf("status=%d", w.Code)
|
||||
}
|
||||
if mimeType == "image/png" {
|
||||
if w.Header().Get("Content-Disposition") != "inline" {
|
||||
t.Fatal("media no longer inline")
|
||||
}
|
||||
} else if !strings.HasPrefix(w.Header().Get("Content-Disposition"), "attachment") || !strings.Contains(w.Header().Get("Content-Security-Policy"), "sandbox") {
|
||||
t.Fatalf("unsafe non-media headers: %v", w.Header())
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -3,6 +3,7 @@ package handler
|
||||
import (
|
||||
"fmt"
|
||||
"io"
|
||||
"mime"
|
||||
"net/http"
|
||||
"strings"
|
||||
|
||||
@@ -69,6 +70,12 @@ func serveResourceDelivery(c *gin.Context, delivery *service.ResourceDelivery, c
|
||||
c.Header("Content-Disposition", disposition)
|
||||
}
|
||||
resource := stream.Resource
|
||||
if !assets.InlineMediaType(resource.MimeType) {
|
||||
if dispositionType, _, _ := mime.ParseMediaType(disposition); dispositionType != "attachment" {
|
||||
c.Header("Content-Disposition", "attachment")
|
||||
}
|
||||
c.Header("Content-Security-Policy", "sandbox; default-src 'none'")
|
||||
}
|
||||
mimeType := resource.MimeType
|
||||
if mimeType == "" {
|
||||
mimeType = "application/octet-stream"
|
||||
|
||||
Reference in New Issue
Block a user