mirror of
https://github.com/rustfs/rustfs.git
synced 2026-10-04 12:31:36 +00:00
fix(ci): restore checks and multipart migration retries (#8196)
* fix(ci): restore multipart lint and full E2E membership checks * fix(ecstore): preserve multipart completion identity during migration
This commit is contained in:
@@ -1,2 +1,2 @@
|
||||
sha256-darwin=9e9687ded961aa4e619a15def6e1ee0a5153be05423d009ee7a58126624c83e7
|
||||
sha256-linux=364666693c2bf258997643c9d87e07e7b7501e58175f190d201d53c81946eb20
|
||||
sha256-darwin=a6aee967387226b6e6937a0e625db53048c8b2f502636820a09c6ad791341b44
|
||||
sha256-linux=6b8b8f3dbdd63414fc969716ae3d7c2ec71712395630bae8bd419de2f32195b3
|
||||
|
||||
@@ -2321,6 +2321,18 @@ mod decommission_lock_order_tests {
|
||||
.expect("the multipart target must publish before capacity progress save");
|
||||
assert!(published.is_multipart(), "published target must retain multipart identity");
|
||||
assert_eq!(published.version_id.map(|version| version.to_string()), Some(source_version.clone()));
|
||||
for prefix in [
|
||||
rustfs_utils::http::RUSTFS_INTERNAL_PREFIX,
|
||||
rustfs_utils::http::MINIO_INTERNAL_PREFIX,
|
||||
] {
|
||||
assert_eq!(
|
||||
published
|
||||
.user_defined
|
||||
.get(&format!("{prefix}{}", rustfs_utils::http::SUFFIX_MULTIPART_UPLOAD_ID)),
|
||||
Some(&source_upload.upload_id),
|
||||
"migration must preserve the source completion identity under both internal prefixes"
|
||||
);
|
||||
}
|
||||
let mut published_reader = lossy_store.pools[2]
|
||||
.get_object_reader(
|
||||
&bucket,
|
||||
|
||||
@@ -3108,7 +3108,9 @@ impl crate::storage_api_contracts::multipart::MultipartOperations for SetDisks {
|
||||
// on the object is what lets a retried CompleteMultipartUpload return this
|
||||
// version instead of NoSuchUpload. insert_str writes both internal prefixes;
|
||||
// a later conflicting pair fails closed in the replay matcher.
|
||||
if !upload_id.is_empty() {
|
||||
// Internal migration must preserve the source completion identity rather
|
||||
// than replace it (or invent one) with the temporary transfer upload id.
|
||||
if !opts.data_movement && !upload_id.is_empty() {
|
||||
insert_str(&mut fi.metadata, rustfs_utils::http::SUFFIX_MULTIPART_UPLOAD_ID, upload_id.to_owned());
|
||||
}
|
||||
|
||||
@@ -5115,6 +5117,10 @@ mod tests {
|
||||
)
|
||||
.await
|
||||
.expect("completed data movement object should be readable");
|
||||
assert!(
|
||||
!rustfs_utils::http::contains_key_str(&completed.user_defined, rustfs_utils::http::SUFFIX_MULTIPART_UPLOAD_ID),
|
||||
"migration of a source without a completion identity must not invent one"
|
||||
);
|
||||
assert!(!rustfs_utils::http::contains_key_str(
|
||||
&completed.user_defined,
|
||||
rustfs_utils::http::SUFFIX_DATA_MOVEMENT_UPLOAD
|
||||
@@ -8822,10 +8828,9 @@ mod tests {
|
||||
..Default::default()
|
||||
}];
|
||||
|
||||
assert_eq!(
|
||||
assert!(
|
||||
completed_multipart_upload_matches(&metadata, &parts, false, upload_id, &requested, "bucket", "object")
|
||||
.expect("quoted ETag must match the stored part"),
|
||||
true
|
||||
.expect("quoted ETag must match the stored part")
|
||||
);
|
||||
let wrong_etag = vec![CompletePart {
|
||||
part_num: 1,
|
||||
@@ -8836,15 +8841,13 @@ mod tests {
|
||||
completed_multipart_upload_matches(&metadata, &parts, false, upload_id, &wrong_etag, "bucket", "object"),
|
||||
Err(StorageError::InvalidPart(1, _, _))
|
||||
));
|
||||
assert_eq!(
|
||||
completed_multipart_upload_matches(&metadata, &parts, false, "other-upload", &requested, "bucket", "object")
|
||||
.expect("a different upload id is not this completion"),
|
||||
false
|
||||
assert!(
|
||||
!completed_multipart_upload_matches(&metadata, &parts, false, "other-upload", &requested, "bucket", "object")
|
||||
.expect("a different upload id is not this completion")
|
||||
);
|
||||
assert_eq!(
|
||||
completed_multipart_upload_matches(&metadata, &parts, true, upload_id, &requested, "bucket", "object")
|
||||
.expect("a delete marker is not the completed object"),
|
||||
false
|
||||
assert!(
|
||||
!completed_multipart_upload_matches(&metadata, &parts, true, upload_id, &requested, "bucket", "object")
|
||||
.expect("a delete marker is not the completed object")
|
||||
);
|
||||
|
||||
metadata.insert(
|
||||
|
||||
@@ -891,8 +891,8 @@ impl DefaultMultipartUsecase {
|
||||
key: Some(key.clone()),
|
||||
e_tag: obj_info.etag.clone().map(|etag| to_s3s_etag(&etag)),
|
||||
location: Some(location),
|
||||
server_side_encryption: server_side_encryption.clone(),
|
||||
ssekms_key_id: ssekms_key_id.clone(),
|
||||
server_side_encryption,
|
||||
ssekms_key_id,
|
||||
checksum_crc32,
|
||||
checksum_crc32c,
|
||||
checksum_sha1,
|
||||
|
||||
Reference in New Issue
Block a user