mirror of
https://github.com/rustfs/rustfs.git
synced 2026-08-28 07:57:01 +00:00
fix(bucket): propagate bucket deletion to peer metadata caches (backlog#646) (#4326)
The peer `DeleteBucketMetadata` RPC handler was a stub that returned success without doing anything, and the delete-bucket flow never sent the notification in the first place. As a result, after a bucket was deleted other nodes kept serving its stale cached metadata. Wire the whole path end to end: - ecstore: add an in-memory `remove_bucket_metadata` (free fn) and `BucketMetadataSys::remove`, the counterpart to `set_bucket_metadata`, and export it through the `api::bucket::metadata_sys` facade. - node_service: `handle_delete_bucket_metadata` now validates the bucket name and actually drops the cached metadata for it. - bucket_usecase: after a successful delete_bucket, notify peers via `notification_sys.delete_bucket_metadata` in the background, symmetric to the existing `notify_bucket_metadata_reload` path. Also update the delete-bucket-metadata unit test to assert the empty-bucket rejection instead of the old always-success stub, and drop an unused `tracing::debug` test import left over from #4322. Verified: cargo fmt; cargo check -p rustfs-ecstore; cargo test -p rustfs --lib --features rio-v2 test_delete_bucket_metadata_empty_bucket; arch guardrail scripts pass.
This commit is contained in:
@@ -452,6 +452,29 @@ fn notify_bucket_metadata_reload(
|
||||
});
|
||||
}
|
||||
|
||||
/// Notify peers to drop their cached metadata for a bucket that was just deleted,
|
||||
/// so they stop serving stale bucket configuration. Runs in the background to
|
||||
/// avoid blocking the delete response.
|
||||
fn notify_bucket_metadata_delete(bucket: String, request_context: Option<request_context::RequestContext>) {
|
||||
spawn_background_with_context(request_context, async move {
|
||||
if let Some(notification_sys) = current_notification_system() {
|
||||
for peer_err in notification_sys
|
||||
.delete_bucket_metadata(&bucket)
|
||||
.await
|
||||
.into_iter()
|
||||
.filter(|e| e.err.is_some())
|
||||
{
|
||||
warn!(
|
||||
bucket = %bucket,
|
||||
host = %peer_err.host,
|
||||
error = ?peer_err.err,
|
||||
"failed to notify peer to delete bucket metadata"
|
||||
);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
fn validate_replication_config_targets(targets: &BucketTargets, config: &ReplicationConfiguration) -> S3Result<()> {
|
||||
let configured_arns = targets
|
||||
.targets
|
||||
@@ -1133,6 +1156,10 @@ impl DefaultBucketUsecase {
|
||||
warn!(bucket = %input.bucket, error = ?err, "site replication delete bucket hook failed");
|
||||
}
|
||||
|
||||
// Notify peers to drop their cached metadata for the now-deleted bucket.
|
||||
let request_context = req.extensions.get::<request_context::RequestContext>().cloned();
|
||||
notify_bucket_metadata_delete(input.bucket.clone(), request_context);
|
||||
|
||||
let result = Ok(S3Response::new(DeleteBucketOutput {}));
|
||||
let _ = helper.complete(&result);
|
||||
result
|
||||
|
||||
Reference in New Issue
Block a user