From: Casey Bodley Date: Tue, 4 Feb 2025 16:09:12 +0000 (-0500) Subject: radosgw-admin: support 'account rm --purge-data' X-Git-Tag: testing/wip-khiremat-testing-20250424.121018-squid-debug~10^2~1 X-Git-Url: http://git-server-git.apps.pok.os.sepia.ceph.com/?a=commitdiff_plain;h=3ee5183bca4b65a85a5e2ea7bea7cbd59d6fe9bb;p=ceph-ci.git radosgw-admin: support 'account rm --purge-data' analogous to 'user rm --purge-data'. instead of failing if the account still owns buckets, remove the remaining buckets/objects Signed-off-by: Casey Bodley (cherry picked from commit 83bacbb47457dea380ac1958f73c82132a8f7fd4) --- diff --git a/src/rgw/rgw_account.cc b/src/rgw/rgw_account.cc index af61be8b500..fd9c479337c 100644 --- a/src/rgw/rgw_account.cc +++ b/src/rgw/rgw_account.cc @@ -312,15 +312,36 @@ int remove(const DoutPrefixProvider* dpp, constexpr bool need_stats = false; rgw::sal::BucketList buckets; - ret = driver->list_buckets(dpp, info.id, info.tenant, marker, marker, - max_items, need_stats, buckets, y); - if (ret < 0) { - return ret; - } - if (!buckets.buckets.empty()) { - err_msg = "The account cannot be deleted until all buckets are removed."; - return -ENOTEMPTY; - } + do { + ret = driver->list_buckets(dpp, info.id, info.tenant, + buckets.next_marker, "", + max_items, need_stats, buckets, y); + if (ret < 0) { + err_msg = "Unable to list account buckets"; + return ret; + } + + if (!buckets.buckets.empty() && !op_state.purge_data) { + err_msg = "The account cannot be deleted until all buckets are removed."; + return -EEXIST; // change to code that maps to 409: conflict + } + + for (const auto& ent : buckets.buckets) { + std::unique_ptr bucket; + ret = driver->load_bucket(dpp, ent.bucket, &bucket, y); + if (ret < 0) { + err_msg = fmt::format("unable to load bucket {}", ent.bucket.name); + return ret; + } + + constexpr bool delete_objects = true; + ret = bucket->remove(dpp, delete_objects, y); + if (ret < 0) { + err_msg = fmt::format("unable to delete bucket {}", ent.bucket.name); + return ret; + } + } + } while (!buckets.next_marker.empty()); rgw::sal::RoleList roles; ret = driver->list_account_roles(dpp, y, info.id, path_prefix, diff --git a/src/rgw/rgw_account.h b/src/rgw/rgw_account.h index 2a6f3e23797..d3c9055f101 100644 --- a/src/rgw/rgw_account.h +++ b/src/rgw/rgw_account.h @@ -53,6 +53,7 @@ struct AdminOpState { std::optional quota_max_size; std::optional quota_max_objects; std::optional quota_enabled; + bool purge_data = false; }; /// create an account diff --git a/src/rgw/rgw_admin.cc b/src/rgw/rgw_admin.cc index 7bdd0544899..f86a7c33907 100644 --- a/src/rgw/rgw_admin.cc +++ b/src/rgw/rgw_admin.cc @@ -11523,6 +11523,7 @@ next: .max_groups = max_groups, .max_access_keys = max_access_keys, .max_buckets = max_buckets, + .purge_data = static_cast(purge_data), }; std::string err_msg;