mirror of
https://github.com/pgsty/minio.git
synced 2026-11-10 17:45:32 +03:00
Integrate complete R3 input-error regression fix
Signed-off-by: Feng Ruohang <rh@vonng.com>
This commit is contained in:
@@ -104,7 +104,7 @@ jobs:
|
|||||||
- name: Run multipart listing, cancellation and cleanup tests under race detector
|
- name: Run multipart listing, cancellation and cleanup tests under race detector
|
||||||
env:
|
env:
|
||||||
MINIO_API_REQUESTS_MAX: "10000"
|
MINIO_API_REQUESTS_MAX: "10000"
|
||||||
run: go test -race ./cmd -run '^Test(Multipart|PaginateMultipartUploads|ListMultipartUploads|CleanupStaleUploads|ExtractModTime)' -count=1 -timeout=5m
|
run: go test -race ./cmd -run '^Test(ObjectCompleteMultipartUpload|Multipart|PaginateMultipartUploads|ListMultipartUploads|CleanupStaleUploads|ExtractModTime)' -count=1 -timeout=5m
|
||||||
|
|
||||||
- name: Run listing metadata recovery, pagination and cancellation tests under race detector
|
- name: Run listing metadata recovery, pagination and cancellation tests under race detector
|
||||||
run: go test -race ./cmd -run '^Test(ListFallback|ListingCache|ListingMerge|ListingRecovery|ListingPending|ListingEntry|ListingSecondLock|StreamMetadataParts|LocalLockerListing|DistributedListing|MergeXLV2LatestNullCrossParity|CountXLV2MixedECGroups|ListCrossParity|ListObjectVersionsCrossParityNull|MigrationCrossParity)' -count=1 -timeout=5m
|
run: go test -race ./cmd -run '^Test(ListFallback|ListingCache|ListingMerge|ListingRecovery|ListingPending|ListingEntry|ListingSecondLock|StreamMetadataParts|LocalLockerListing|DistributedListing|MergeXLV2LatestNullCrossParity|CountXLV2MixedECGroups|ListCrossParity|ListObjectVersionsCrossParityNull|MigrationCrossParity)' -count=1 -timeout=5m
|
||||||
|
|||||||
@@ -2419,13 +2419,17 @@ func (z *erasureServerPools) CompleteMultipartUpload(ctx context.Context, bucket
|
|||||||
|
|
||||||
// Hold write locks to verify uploaded parts, also disallows any
|
// Hold write locks to verify uploaded parts, also disallows any
|
||||||
// parallel PutObjectPart() requests.
|
// parallel PutObjectPart() requests.
|
||||||
uploadIDLock := z.NewNSLock(bucket, pathJoin(object, uploadID))
|
// An empty upload ID aliases the object lock already held above.
|
||||||
wlkctx, err := uploadIDLock.GetLock(ctx, globalOperationTimeout)
|
// Let the storage layer return its normal missing bucket/upload error.
|
||||||
if err != nil {
|
if uploadID != "" {
|
||||||
return objInfo, err
|
uploadIDLock := z.NewNSLock(bucket, pathJoin(object, uploadID))
|
||||||
|
wlkctx, err := uploadIDLock.GetLock(ctx, globalOperationTimeout)
|
||||||
|
if err != nil {
|
||||||
|
return objInfo, err
|
||||||
|
}
|
||||||
|
ctx = wlkctx.Context()
|
||||||
|
defer uploadIDLock.Unlock(wlkctx)
|
||||||
}
|
}
|
||||||
ctx = wlkctx.Context()
|
|
||||||
defer uploadIDLock.Unlock(wlkctx)
|
|
||||||
|
|
||||||
if z.SinglePool() {
|
if z.SinglePool() {
|
||||||
return z.serverPools[0].CompleteMultipartUpload(ctx, bucket, object, uploadID, uploadedParts, opts)
|
return z.serverPools[0].CompleteMultipartUpload(ctx, bucket, object, uploadID, uploadedParts, opts)
|
||||||
|
|||||||
@@ -707,3 +707,35 @@ func (r *nativeRestorePartGateReader) Read(p []byte) (int, error) {
|
|||||||
}
|
}
|
||||||
return r.ReadCloser.Read(p)
|
return r.ReadCloser.Read(p)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Invalid upload paths must retain the backend's normal error precedence,
|
||||||
|
// rather than reacquiring the object lock as the upload lock.
|
||||||
|
func TestMultipartCompletionLockAlias(t *testing.T) {
|
||||||
|
for _, pools := range []int{1, 2} {
|
||||||
|
for _, id := range []string{"", ".", "./"} {
|
||||||
|
t.Run(fmt.Sprintf("pools=%d/id=%q", pools, id), func(t *testing.T) {
|
||||||
|
r := newRestoreSafetyTest(t, pools, versioning.Enabled)
|
||||||
|
for _, missingBucket := range []bool{false, true} {
|
||||||
|
bucket := r.bucket
|
||||||
|
if missingBucket {
|
||||||
|
bucket = "missing-bucket"
|
||||||
|
}
|
||||||
|
ctx, cancel := context.WithTimeout(t.Context(), 200*time.Millisecond)
|
||||||
|
_, err := r.z.CompleteMultipartUpload(ctx, bucket, r.object, id, nil, ObjectOptions{})
|
||||||
|
cancel()
|
||||||
|
if id != "" {
|
||||||
|
if !errors.As(err, &MalformedUploadID{}) {
|
||||||
|
t.Errorf("malformed upload: %v", err)
|
||||||
|
}
|
||||||
|
} else if missingBucket {
|
||||||
|
if !isErrBucketNotFound(err) {
|
||||||
|
t.Errorf("missing bucket: %v", err)
|
||||||
|
}
|
||||||
|
} else if !errors.As(err, &InvalidUploadID{}) {
|
||||||
|
t.Errorf("invalid upload: %v", err)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user