From ef463fe1afd02c4f649af51ec9934febef9c7b3c Mon Sep 17 00:00:00 2001 From: Chris Lu Date: Sat, 19 Sep 2026 23:56:25 -0700 Subject: [PATCH] s3: read complete-request checksum values from headers or query Presigned CompleteMultipartUpload requests hoist x-amz-checksum-type and the full-object checksum header into the signed query string, so a header-only lookup would skip BadDigest validation for them. --- weed/s3api/filer_multipart.go | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/weed/s3api/filer_multipart.go b/weed/s3api/filer_multipart.go index e5dd9c8c1..964400f6b 100644 --- a/weed/s3api/filer_multipart.go +++ b/weed/s3api/filer_multipart.go @@ -581,7 +581,8 @@ func (s3a *S3ApiServer) prepareMultipartCompletionState(r *http.Request, input * glog.Errorf("completeMultipartUpload: %v", typeErr) return nil, nil, s3err.ErrInvalidRequest } - if completeType := r.Header.Get(s3_constants.AmzChecksumType); completeType != "" && !strings.EqualFold(completeType, resolvedType) { + query := parseRequestQuery(r) + if completeType := lookupHeaderOrQuery(r, query, s3_constants.AmzChecksumType); completeType != "" && !strings.EqualFold(completeType, resolvedType) { return nil, nil, s3err.ErrBadDigest } checksumType = resolvedType @@ -621,7 +622,7 @@ func (s3a *S3ApiServer) prepareMultipartCompletionState(r *http.Request, input * glog.Errorf("completeMultipartUpload: %s checksum computation failed: %v", checksumType, checksumErr) return nil, nil, s3err.ErrInvalidPart } - if objectChecksum := r.Header.Get(checksumHeaderName); objectChecksum != "" && objectChecksum != checksumValue { + if objectChecksum := lookupHeaderOrQuery(r, query, checksumHeaderName); objectChecksum != "" && objectChecksum != checksumValue { return nil, nil, s3err.ErrBadDigest } }