]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
rgw: use rgw_owner in RGWBucketInfo
authorCasey Bodley <cbodley@redhat.com>
Fri, 10 Nov 2023 17:31:11 +0000 (12:31 -0500)
committerCasey Bodley <cbodley@redhat.com>
Fri, 12 Apr 2024 19:34:26 +0000 (15:34 -0400)
Signed-off-by: Casey Bodley <cbodley@redhat.com>
(cherry picked from commit 65c80d7e63f12a76857726bab929261717adb75b)

46 files changed:
src/rgw/driver/d4n/rgw_sal_d4n.cc
src/rgw/driver/d4n/rgw_sal_d4n.h
src/rgw/driver/daos/rgw_sal_daos.cc
src/rgw/driver/daos/rgw_sal_daos.h
src/rgw/driver/dbstore/common/dbstore.cc
src/rgw/driver/dbstore/common/dbstore.h
src/rgw/driver/dbstore/sqlite/sqliteDB.cc
src/rgw/driver/dbstore/tests/dbstore_tests.cc
src/rgw/driver/motr/rgw_sal_motr.cc
src/rgw/driver/motr/rgw_sal_motr.h
src/rgw/driver/posix/rgw_sal_posix.cc
src/rgw/driver/posix/rgw_sal_posix.h
src/rgw/driver/rados/rgw_bucket.cc
src/rgw/driver/rados/rgw_bucket.h
src/rgw/driver/rados/rgw_bucket_sync.cc
src/rgw/driver/rados/rgw_cr_rados.cc
src/rgw/driver/rados/rgw_data_sync.cc
src/rgw/driver/rados/rgw_notify.cc
src/rgw/driver/rados/rgw_rados.cc
src/rgw/driver/rados/rgw_rados.h
src/rgw/driver/rados/rgw_reshard.cc
src/rgw/driver/rados/rgw_sal_rados.cc
src/rgw/driver/rados/rgw_sal_rados.h
src/rgw/driver/rados/rgw_sync_module_aws.cc
src/rgw/driver/rados/rgw_sync_module_es.cc
src/rgw/rgw_admin.cc
src/rgw/rgw_auth.cc
src/rgw/rgw_common.cc
src/rgw/rgw_common.h
src/rgw/rgw_crypt.cc
src/rgw/rgw_lc.cc
src/rgw/rgw_lua_request.cc
src/rgw/rgw_op.cc
src/rgw/rgw_quota.cc
src/rgw/rgw_rest.cc
src/rgw/rgw_rest_s3.cc
src/rgw/rgw_rest_swift.cc
src/rgw/rgw_sal.h
src/rgw/rgw_sal_dbstore.cc
src/rgw/rgw_sal_dbstore.h
src/rgw/rgw_sal_filter.cc
src/rgw/rgw_sal_filter.h
src/rgw/rgw_sal_store.h
src/rgw/rgw_swift_auth.cc
src/rgw/rgw_user.cc
src/test/rgw/test_rgw_lua.cc

index 71a18c62c5b744fa36ffb2797ecbe5942be49a65..6776681423326f8a560031408219d86cdb87995c 100644 (file)
@@ -67,6 +67,7 @@ int D4NFilterBucket::create(const DoutPrefixProvider* dpp,
 }
 
 int D4NFilterObject::copy_object(const ACLOwner& owner,
+                              const rgw_user& remote_user,
                               req_info* info,
                               const rgw_zone_id& source_zone,
                               rgw::sal::Object* dest_object,
@@ -138,7 +139,7 @@ int D4NFilterObject::copy_object(const ACLOwner& owner,
     ldpp_dout(dpp, 20) << "D4N Filter: Cache copy object operation succeeded." << dendl;
   }
 
-  return next->copy_object(owner, info, source_zone,
+  return next->copy_object(owner, remote_user, info, source_zone,
                            nextObject(dest_object),
                            nextBucket(dest_bucket),
                            nextBucket(src_bucket),
index 7caf7e067d2c1ad53902a0c25d828cf40a56a570..b593925f21ae1984e479cc8b1dacda17c1d13949 100644 (file)
@@ -123,6 +123,7 @@ class D4NFilterObject : public FilterObject {
     virtual ~D4NFilterObject() = default;
 
     virtual int copy_object(const ACLOwner& owner,
+               const rgw_user& remote_user,
                req_info* info, const rgw_zone_id& source_zone,
                rgw::sal::Object* dest_object, rgw::sal::Bucket* dest_bucket,
                rgw::sal::Bucket* src_bucket,
index 98e708d645eb7e4b54a1d3d3c129ac5400e74232..765655d7430f90e8a4026dfea22329c868ef0f32 100644 (file)
@@ -499,8 +499,8 @@ int DaosBucket::read_stats_async(
   return DAOS_NOT_IMPLEMENTED_LOG(dpp);
 }
 
-int DaosBucket::sync_user_stats(const DoutPrefixProvider* dpp,
-                                optional_yield y) {
+int DaosBucket::sync_owner_stats(const DoutPrefixProvider* dpp,
+                                 optional_yield y) {
   return DAOS_NOT_IMPLEMENTED_LOG(dpp);
 }
 
@@ -508,7 +508,7 @@ int DaosBucket::check_bucket_shards(const DoutPrefixProvider* dpp) {
   return DAOS_NOT_IMPLEMENTED_LOG(dpp);
 }
 
-int DaosBucket::chown(const DoutPrefixProvider* dpp, User& new_user,
+int DaosBucket::chown(const DoutPrefixProvider* dpp, const rgw_owner& new_user,
                       optional_yield y) {
   return DAOS_NOT_IMPLEMENTED_LOG(dpp);
 }
@@ -1207,7 +1207,8 @@ int DaosObject::delete_object(const DoutPrefixProvider* dpp, optional_yield y,
 }
 
 int DaosObject::copy_object(
-    const ACLOwner& owner, req_info* info, const rgw_zone_id& source_zone,
+    const ACLOwner& owner, const rgw_user& remote_user,
+    req_info* info, const rgw_zone_id& source_zone,
     rgw::sal::Object* dest_object, rgw::sal::Bucket* dest_bucket,
     rgw::sal::Bucket* src_bucket, const rgw_placement_rule& dest_placement,
     ceph::real_time* src_mtime, ceph::real_time* mtime,
@@ -1221,13 +1222,13 @@ int DaosObject::copy_object(
   return DAOS_NOT_IMPLEMENTED_LOG(dpp);
 }
 
-int DaosObject::swift_versioning_restore(const ACLOwner& owner, bool& restored,
-                                         const DoutPrefixProvider* dpp) {
+int DaosObject::swift_versioning_restore(const ACLOwner& owner, const rgw_user& remote_user, bool& restored,
+                                         const DoutPrefixProvider* dpp, optional_yield y) {
   return DAOS_NOT_IMPLEMENTED_LOG(dpp);
 }
 
-int DaosObject::swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
-                                      optional_yield y) {
+int DaosObject::swift_versioning_copy(const ACLOwner& owner, const rgw_user& remote_user,
+                                      const DoutPrefixProvider* dpp, optional_yield y) {
   return DAOS_NOT_IMPLEMENTED_LOG(dpp);
 }
 
index a01c2c2d0c327f3a2e2fc3f9aa4d36caeba9a262..b4f65c5d82fe71253e721e27a650d4181b873624 100644 (file)
@@ -312,10 +312,10 @@ class DaosBucket : public StoreBucket {
                                const bucket_index_layout_generation& idx_layout,
                                int shard_id,
                                boost::intrusive_ptr<ReadStatsCB> ctx) override;
-  virtual int sync_user_stats(const DoutPrefixProvider* dpp,
-                              optional_yield y) override;
+  virtual int sync_owner_stats(const DoutPrefixProvider* dpp,
+                               optional_yield y) override;
   virtual int check_bucket_shards(const DoutPrefixProvider* dpp) override;
-  virtual int chown(const DoutPrefixProvider* dpp, User& new_user,
+  virtual int chown(const DoutPrefixProvider* dpp, const rgw_owner& new_user,
                     optional_yield y) override;
   virtual int put_info(const DoutPrefixProvider* dpp, bool exclusive,
                        ceph::real_time mtime) override;
@@ -602,7 +602,8 @@ class DaosObject : public StoreObject {
   virtual int delete_object(const DoutPrefixProvider* dpp, optional_yield y,
                             uint32_t flags) override;
   virtual int copy_object(
-      const ACLOwner& owner, req_info* info, const rgw_zone_id& source_zone,
+      const ACLOwner& owner, const rgw_user& remote_user,
+      req_info* info, const rgw_zone_id& source_zone,
       rgw::sal::Object* dest_object, rgw::sal::Bucket* dest_bucket,
       rgw::sal::Bucket* src_bucket, const rgw_placement_rule& dest_placement,
       ceph::real_time* src_mtime, ceph::real_time* mtime,
@@ -657,10 +658,10 @@ class DaosObject : public StoreObject {
                               Formatter* f) override;
 
   /* Swift versioning */
-  virtual int swift_versioning_restore(const ACLOwner& owner, bool& restored,
-                                       const DoutPrefixProvider* dpp) override;
-  virtual int swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
-                                    optional_yield y) override;
+  virtual int swift_versioning_restore(const ACLOwner& owner, const rgw_user& remote_user, bool& restored,
+                                       const DoutPrefixProvider* dpp, optional_yield y) override;
+  virtual int swift_versioning_copy(const ACLOwner& owner, const rgw_user& remote_user,
+                                    const DoutPrefixProvider* dpp, optional_yield y) override;
 
   /* OPs */
   virtual std::unique_ptr<ReadOp> get_read_op() override;
index 5a4ae021ead3100d4cb38c29da6e45502bb322fb..d548bc4d8c0420ea6df55dcb0af8054eca76d18e 100644 (file)
@@ -474,7 +474,7 @@ out:
 }
 
 int DB::create_bucket(const DoutPrefixProvider *dpp,
-    const rgw_user& owner, const rgw_bucket& bucket,
+    const rgw_owner& owner, const rgw_bucket& bucket,
     const std::string& zonegroup_id,
     const rgw_placement_rule& placement_rule,
     const std::map<std::string, bufferlist>& attrs,
@@ -502,7 +502,7 @@ int DB::create_bucket(const DoutPrefixProvider *dpp,
   orig_info.bucket.name = bucket.name;
   ret = get_bucket_info(dpp, string("name"), "", orig_info, nullptr, nullptr, nullptr);
 
-  if (!ret && !orig_info.owner.id.empty()) {
+  if (!ret && !orig_info.bucket.bucket_id.empty()) {
     /* already exists. Return the old info */
     info = std::move(orig_info);
     return ret;
@@ -543,7 +543,7 @@ int DB::create_bucket(const DoutPrefixProvider *dpp,
   params.op.bucket.info = info;
   params.op.bucket.bucket_attrs = attrs;
   params.op.bucket.mtime = ceph::real_time();
-  params.op.user.uinfo.user_id.id = owner.id;
+  params.op.bucket.owner = to_string(owner);
 
   ret = ProcessOp(dpp, "InsertBucket", &params);
 
@@ -576,7 +576,7 @@ out:
 }
 
 int DB::list_buckets(const DoutPrefixProvider *dpp, const std::string& query_str,
-    rgw_user& user,
+    std::string& owner,
     const string& marker,
     const string& end_marker,
     uint64_t max,
@@ -589,7 +589,7 @@ int DB::list_buckets(const DoutPrefixProvider *dpp, const std::string& query_str
   DBOpParams params = {};
   InitializeParams(dpp, &params);
 
-  params.op.user.uinfo.user_id = user;
+  params.op.bucket.owner = owner;
   params.op.bucket.min_marker = marker;
   params.op.bucket.max_marker = end_marker;
   params.op.list_max_count = max;
@@ -619,7 +619,7 @@ int DB::list_buckets(const DoutPrefixProvider *dpp, const std::string& query_str
 
   if (query_str == "all") {
     // userID/OwnerID may have changed. Update it.
-    user.id = params.op.bucket.info.owner.id;
+    owner = to_string(params.op.bucket.info.owner);
   }
 
 out:
@@ -629,7 +629,7 @@ out:
 int DB::update_bucket(const DoutPrefixProvider *dpp, const std::string& query_str,
     RGWBucketInfo& info,
     bool exclusive,
-    const rgw_user* powner_id,
+    const rgw_owner* powner,
     map<std::string, bufferlist>* pattrs,
     ceph::real_time* pmtime,
     RGWObjVersionTracker* pobjv)
@@ -650,7 +650,7 @@ int DB::update_bucket(const DoutPrefixProvider *dpp, const std::string& query_st
     goto out;
   }
 
-  if (!orig_info.owner.id.empty() && exclusive) {
+  if (!orig_info.bucket.bucket_id.empty() && exclusive) {
     /* already exists. Return the old info */
 
     info = std::move(orig_info);
@@ -672,17 +672,17 @@ int DB::update_bucket(const DoutPrefixProvider *dpp, const std::string& query_st
 
   params.op.bucket.info.bucket.name = info.bucket.name;
 
-  if (powner_id) {
-    params.op.user.uinfo.user_id.id = powner_id->id;
+  if (powner) {
+    params.op.bucket.owner = to_string(*powner);
   } else {
-    params.op.user.uinfo.user_id.id = orig_info.owner.id;
+    params.op.bucket.owner = to_string(orig_info.owner);
   }
 
   /* Update version & mtime */
   params.op.bucket.bucket_version.ver = ++(bucket_version.ver);
 
   if (pmtime) {
-    params.op.bucket.mtime = *pmtime;;
+    params.op.bucket.mtime = *pmtime;
   } else {
     params.op.bucket.mtime = ceph::real_time();
   }
@@ -1771,7 +1771,7 @@ int DB::Object::Write::_do_write_meta(const DoutPrefixProvider *dpp,
   params.op.obj.state.exists = true;
   params.op.obj.state.size = size;
   params.op.obj.state.accounted_size = accounted_size;
-  params.op.obj.owner = target->get_bucket_info().owner.id;
+  params.op.obj.owner = to_string(target->get_bucket_info().owner);
   params.op.obj.category = meta.category;
 
   if (meta.mtime) {
@@ -2201,12 +2201,11 @@ void *DB::GC::entry() {
 
     do {
       std::string& marker = bucket_marker;
-      rgw_user user;
-      user.id = user_marker;
+      std::string owner = user_marker;
       buckets.clear();
       is_truncated = false;
 
-      int r = db->list_buckets(dpp, "all", user, marker, string(),
+      int r = db->list_buckets(dpp, "all", owner, marker, string(),
                        max, false, &buckets, &is_truncated);
  
       if (r < 0) { //do nothing? retry later ?
@@ -2222,7 +2221,7 @@ void *DB::GC::entry() {
          ldpp_dout(dpp, 2) << " delete_stale_objs failed for bucket( " << bname <<")" << dendl;
         }
         bucket_marker = bname;
-        user_marker = user.id;
+        user_marker = owner;
 
         /* XXX: If using locks, unlock here and reacquire in the next iteration */
         cv.wait_for(lk, std::chrono::milliseconds(100));
index 8cf6f70f751568e52f49f8dace89e01025e44a1e..3f8191f5a9211a135c3587a7481c92bf98ebddc4 100644 (file)
@@ -35,7 +35,7 @@ struct DBOpUserInfo {
 struct DBOpBucketInfo {
   RGWBucketEnt ent; // maybe not needed. not used in create/get_bucket
   RGWBucketInfo info;
-  RGWUser* owner = nullptr;
+  std::string owner;
   rgw::sal::Attrs bucket_attrs;
   obj_version bucket_version;
   ceph::real_time mtime;
@@ -482,9 +482,7 @@ class DBOp {
       BucketVersion   INTEGER,    \
       BucketVersionTag TEXT,      \
       Mtime   BLOB,   \
-      PRIMARY KEY (BucketName) \
-      FOREIGN KEY (OwnerID) \
-      REFERENCES '{}' (UserID) ON DELETE CASCADE ON UPDATE CASCADE \n);";
+      PRIMARY KEY (BucketName) \n);";
 
     static constexpr std::string_view CreateObjectTableTriggerQ =
       "CREATE TRIGGER IF NOT EXISTS '{}' \
@@ -931,22 +929,20 @@ class RemoveBucketOp: virtual public DBOp {
 class GetBucketOp: virtual public DBOp {
   private:
     static constexpr std::string_view Query = "SELECT  \
-                          BucketName, BucketTable.Tenant, Marker, BucketID, Size, SizeRounded, CreationTime, \
-                          Count, BucketTable.PlacementName, BucketTable.PlacementStorageClass, OwnerID, Flags, Zonegroup, \
+                          BucketName, Tenant, Marker, BucketID, Size, SizeRounded, CreationTime, \
+                          Count, PlacementName, PlacementStorageClass, OwnerID, Flags, Zonegroup, \
                           HasInstanceObj, Quota, RequesterPays, HasWebsite, WebsiteConf, \
                           SwiftVersioning, SwiftVerLocation, \
                           MdsearchConfig, NewBucketInstanceID, ObjectLock, \
-                          SyncPolicyInfoGroups, BucketAttrs, BucketVersion, BucketVersionTag, Mtime, NS \
-                          from '{}' as BucketTable INNER JOIN '{}' ON OwnerID = UserID where BucketName = {}";
+                          SyncPolicyInfoGroups, BucketAttrs, BucketVersion, BucketVersionTag, Mtime \
+                          from '{}' where BucketName = {}";
 
   public:
     virtual ~GetBucketOp() {}
 
     static std::string Schema(DBOpPrepareParams &params) {
-      //return fmt::format(Query, params.op.bucket.bucket_name,
-      //          params.bucket_table, params.user_table);
       return fmt::format(Query,
-          params.bucket_table, params.user_table,
+          params.bucket_table,
           params.op.bucket.bucket_name);
     }
 };
@@ -1596,7 +1592,7 @@ class DB {
         RGWBucketInfo& info, rgw::sal::Attrs* pattrs, ceph::real_time* pmtime,
         obj_version* pbucket_version);
     int create_bucket(const DoutPrefixProvider *dpp,
-        const rgw_user& owner, const rgw_bucket& bucket,
+        const rgw_owner& owner, const rgw_bucket& bucket,
         const std::string& zonegroup_id,
         const rgw_placement_rule& placement_rule,
         const std::map<std::string, bufferlist>& attrs,
@@ -1611,7 +1607,7 @@ class DB {
 
     int remove_bucket(const DoutPrefixProvider *dpp, const RGWBucketInfo info);
     int list_buckets(const DoutPrefixProvider *dpp, const std::string& query_str,
-        rgw_user& user,
+        std::string& owner,
         const std::string& marker,
         const std::string& end_marker,
         uint64_t max,
@@ -1620,7 +1616,7 @@ class DB {
         bool *is_truncated);
     int update_bucket(const DoutPrefixProvider *dpp, const std::string& query_str,
         RGWBucketInfo& info, bool exclusive,
-        const rgw_user* powner_id, std::map<std::string, bufferlist>* pattrs,
+        const rgw_owner* powner, std::map<std::string, bufferlist>* pattrs,
         ceph::real_time* pmtime, RGWObjVersionTracker* pobjv);
 
     uint64_t get_max_head_size() { return ObjHeadSize; }
@@ -1909,7 +1905,6 @@ class DB {
         DB::Object *target;
 
         struct DeleteParams {
-          rgw_user bucket_owner;
           int versioning_status;
           ACLOwner obj_owner; /* needed for creation of deletion marker */
           uint64_t olh_epoch;
index 81c716c27f184dba26a328786e84a349b9f0036a..554d8fe94cfee53678d20321cb01178df095ee70 100644 (file)
@@ -2,6 +2,7 @@
 // vim: ts=8 sw=2 smarttab
 
 #include "sqliteDB.h"
+#include "rgw_account.h"
 
 using namespace std;
 
@@ -421,12 +422,8 @@ static int list_bucket(const DoutPrefixProvider *dpp, DBOpInfo &op, sqlite3_stmt
   op.bucket.info.placement_rule = op.bucket.ent.placement_rule;
   op.bucket.info.creation_time = op.bucket.ent.creation_time;
 
-  op.bucket.info.owner.id = (const char*)sqlite3_column_text(stmt, OwnerID);
-  op.bucket.info.owner.tenant = op.bucket.ent.bucket.tenant;
-
-  if (op.name == "GetBucket") {
-    op.bucket.info.owner.ns = (const char*)sqlite3_column_text(stmt, Bucket_User_NS);
-  }
+  const char* owner_id = (const char*)sqlite3_column_text(stmt, OwnerID);
+  op.bucket.info.owner = parse_owner(owner_id);
 
   op.bucket.info.flags = sqlite3_column_int(stmt, Flags);
   op.bucket.info.zonegroup = (const char*)sqlite3_column_text(stmt, Zonegroup);
@@ -1339,7 +1336,7 @@ int SQLInsertBucket::Bind(const DoutPrefixProvider *dpp, struct DBOpParams *para
 
   // user_id here is copied as OwnerID in the bucket table.
   SQL_BIND_INDEX(dpp, stmt, index, p_params.op.user.user_id, sdb);
-  SQL_BIND_TEXT(dpp, stmt, index, params->op.user.uinfo.user_id.id.c_str(), sdb);
+  SQL_BIND_TEXT(dpp, stmt, index, params->op.bucket.owner.c_str(), sdb);
 
   SQL_BIND_INDEX(dpp, stmt, index, p_params.op.bucket.bucket_name, sdb);
   SQL_BIND_TEXT(dpp, stmt, index, params->op.bucket.info.bucket.name.c_str(), sdb);
@@ -1567,7 +1564,7 @@ int SQLUpdateBucket::Bind(const DoutPrefixProvider *dpp, struct DBOpParams *para
   }
 
   SQL_BIND_INDEX(dpp, *stmt, index, p_params.op.user.user_id, sdb);
-  SQL_BIND_TEXT(dpp, *stmt, index, params->op.user.uinfo.user_id.id.c_str(), sdb);
+  SQL_BIND_TEXT(dpp, *stmt, index, params->op.bucket.owner.c_str(), sdb);
 
   SQL_BIND_INDEX(dpp, *stmt, index, p_params.op.bucket.bucket_name, sdb);
   SQL_BIND_TEXT(dpp, *stmt, index, params->op.bucket.info.bucket.name.c_str(), sdb);
@@ -1732,7 +1729,7 @@ int SQLListUserBuckets::Bind(const DoutPrefixProvider *dpp, struct DBOpParams *p
 
   if (params->op.query_str != "all") { 
     SQL_BIND_INDEX(dpp, *pstmt, index, p_params.op.user.user_id, sdb);
-    SQL_BIND_TEXT(dpp, *pstmt, index, params->op.user.uinfo.user_id.id.c_str(), sdb);
+    SQL_BIND_TEXT(dpp, *pstmt, index, params->op.bucket.owner.c_str(), sdb);
   }
 
   SQL_BIND_INDEX(dpp, *pstmt, index, p_params.op.bucket.min_marker, sdb);
index 14fe9c37e754d178f91e06191fcc2256fcb098aa..c89addeade1d23c93e5928b73e8ccad118d65882 100644 (file)
@@ -96,6 +96,7 @@ namespace {
         GlobalParams.op.user.uinfo.display_name = user1;
         GlobalParams.op.user.uinfo.user_id.id = user_id1;
         GlobalParams.op.bucket.info.bucket.name = bucket1;
+        GlobalParams.op.bucket.owner = user_id1;
         GlobalParams.op.obj.state.obj.bucket = GlobalParams.op.bucket.info.bucket;
         GlobalParams.op.obj.state.obj.key.name = object1;
         GlobalParams.op.obj.state.obj.key.instance = "inst1";
@@ -444,7 +445,7 @@ TEST_F(DBStoreTest, GetBucket) {
   ASSERT_EQ(params.op.bucket.info.objv_tracker.read_version.ver, 3);
   ASSERT_EQ(params.op.bucket.info.objv_tracker.read_version.tag, "read_tag");
   ASSERT_EQ(params.op.bucket.mtime, bucket_mtime);
-  ASSERT_EQ(params.op.bucket.info.owner.id, "user_id1");
+  ASSERT_EQ(to_string(params.op.bucket.info.owner), "user_id1");
   bufferlist k, k2;
   string acl;
   map<std::string, bufferlist>::iterator it2 = params.op.bucket.bucket_attrs.begin();
@@ -507,7 +508,7 @@ TEST_F(DBStoreTest, GetBucketQueryByName) {
   ASSERT_EQ(ret, 0);
   ASSERT_EQ(binfo.bucket.name, "bucket2");
   ASSERT_EQ(binfo.bucket.tenant, "tenant");
-  ASSERT_EQ(binfo.owner.id, "user_id1");
+  ASSERT_EQ(to_string(binfo.owner), "user_id1");
   ASSERT_EQ(binfo.objv_tracker.read_version.ver, 1);
   ASSERT_FALSE(binfo.objv_tracker.read_version.tag.empty());
   ASSERT_EQ(binfo.zonegroup, "zid");
@@ -523,14 +524,12 @@ TEST_F(DBStoreTest, GetBucketQueryByName) {
 TEST_F(DBStoreTest, ListUserBuckets) {
   struct DBOpParams params = GlobalParams;
   int ret = -1;
-  rgw_user owner;
+  std::string owner = "user_id1";
   int max = 2;
   bool need_stats = true;
   bool is_truncated = false;
   RGWUserBuckets ulist;
 
-  owner.id = "user_id1";
-
   marker1 = "";
   do {
     is_truncated = false;
@@ -560,8 +559,7 @@ TEST_F(DBStoreTest, ListUserBuckets) {
 TEST_F(DBStoreTest, BucketChown) {
   int ret = -1;
   RGWBucketInfo info;
-  rgw_user user;
-  user.id = "user_id2";
+  rgw_owner user = rgw_user{"user_id2"};
 
   info.bucket.name = "bucket5";
 
@@ -581,7 +579,7 @@ TEST_F(DBStoreTest, ListAllBuckets) {
 TEST_F(DBStoreTest, ListAllBuckets2) {
   struct DBOpParams params = GlobalParams;
   int ret = -1;
-  rgw_user owner;
+  std::string owner; // empty
   int max = 2;
   bool need_stats = true;
   bool is_truncated = false;
@@ -595,7 +593,7 @@ TEST_F(DBStoreTest, ListAllBuckets2) {
     ASSERT_EQ(ret, 0);
 
     cout << "^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ \n";
-    cout << "ownerID : " << owner.id << "\n";
+    cout << "ownerID : " << owner << "\n";
     cout << "marker1 :" << marker1 << "\n";
 
     cout << "is_truncated :" << is_truncated << "\n";
index 92c07ff95e48a80c221c7c9016e1895425c152db..32ede60d8df86317615d8245ea0c15c3107f6eb0 100644 (file)
@@ -607,7 +607,7 @@ int MotrBucket::remove(const DoutPrefixProvider *dpp, bool delete_children, opti
   }
 
   // 4. Sync user stats.
-  ret = this->sync_user_stats(dpp, y);
+  ret = this->sync_owner_stats(dpp, y);
   if (ret < 0) {
      ldout(store->ctx(), 1) << "WARNING: failed sync user stats before bucket delete. ret=" <<  ret << dendl;
   }
@@ -808,8 +808,8 @@ int MotrBucket::read_stats_async(const DoutPrefixProvider *dpp,
   return 0;
 }
 
-int MotrBucket::sync_user_stats(const DoutPrefixProvider *dpp, optional_yield y,
-                                RGWBucketEnt* ent)
+int MotrBucket::sync_owner_stats(const DoutPrefixProvider *dpp, optional_yield y,
+                                 RGWBucketEnt* ent)
 {
   return 0;
 }
@@ -820,7 +820,7 @@ int MotrBucket::check_bucket_shards(const DoutPrefixProvider *dpp,
   return 0;
 }
 
-int MotrBucket::chown(const DoutPrefixProvider *dpp, User& new_user, optional_yield y)
+int MotrBucket::chown(const DoutPrefixProvider *dpp, const rgw_owner& new_user, optional_yield y)
 {
   // TODO: update bucket with new owner
   return 0;
@@ -1511,6 +1511,7 @@ int MotrObject::delete_object(const DoutPrefixProvider* dpp, optional_yield y, u
 }
 
 int MotrObject::copy_object(const ACLOwner& owner,
+    const rgw_user& remote_user,
     req_info* info,
     const rgw_zone_id& source_zone,
     rgw::sal::Object* dest_object,
@@ -1541,14 +1542,14 @@ int MotrObject::copy_object(const ACLOwner& owner,
       return 0;
 }
 
-int MotrObject::swift_versioning_restore(const ACLOwner& owner, bool& restored,
-    const DoutPrefixProvider* dpp)
+int MotrObject::swift_versioning_restore(const ACLOwner& owner, const rgw_user& remote_user, bool& restored,
+    const DoutPrefixProvider* dpp, optional_yield y)
 {
   return 0;
 }
 
-int MotrObject::swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
-    optional_yield y)
+int MotrObject::swift_versioning_copy(const ACLOwner& owner, const rgw_user& remote_user,
+    const DoutPrefixProvider* dpp, optional_yield y)
 {
   return 0;
 }
index 9f7cbd9059dc26f94e5a54f25b8e6bfc62be8de7..8865b93be880443cf1a86036dc283811dead169f 100644 (file)
@@ -375,11 +375,11 @@ class MotrBucket : public StoreBucket {
     virtual int read_stats_async(const DoutPrefixProvider *dpp,
                                  const bucket_index_layout_generation& idx_layout,
                                  int shard_id, boost::intrusive_ptr<ReadStatsCB> ctx) override;
-    int sync_user_stats(const DoutPrefixProvider *dpp, optional_yield y,
-                        RGWBucketEnt* ent) override;
+    int sync_owner_stats(const DoutPrefixProvider *dpp, optional_yield y,
+                         RGWBucketEnt* ent) override;
     int check_bucket_shards(const DoutPrefixProvider *dpp,
                             uint64_t num_objs) override;
-    virtual int chown(const DoutPrefixProvider *dpp, User& new_user, optional_yield y) override;
+    virtual int chown(const DoutPrefixProvider *dpp, const rgw_owner& new_user, optional_yield y) override;
     virtual int put_info(const DoutPrefixProvider *dpp, bool exclusive, ceph::real_time mtime) override;
     virtual bool is_owner(User* user) override;
     virtual int check_empty(const DoutPrefixProvider *dpp, optional_yield y) override;
@@ -680,6 +680,7 @@ class MotrObject : public StoreObject {
         optional_yield y,
         uint32_t flags) override;
     virtual int copy_object(const ACLOwner& owner,
+        const rgw_user& remote_user,
         req_info* info, const rgw_zone_id& source_zone,
         rgw::sal::Object* dest_object, rgw::sal::Bucket* dest_bucket,
         rgw::sal::Bucket* src_bucket,
@@ -718,10 +719,10 @@ class MotrObject : public StoreObject {
     virtual int dump_obj_layout(const DoutPrefixProvider *dpp, optional_yield y, Formatter* f) override;
 
     /* Swift versioning */
-    virtual int swift_versioning_restore(const ACLOwner& owner, bool& restored,
-        const DoutPrefixProvider* dpp) override;
-    virtual int swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
-        optional_yield y) override;
+    virtual int swift_versioning_restore(const ACLOwner& owner, const rgw_user& remote_user,
+        bool& restored, const DoutPrefixProvider* dpp, optional_yield y) override;
+    virtual int swift_versioning_copy(const ACLOwner& owner, const rgw_user& remote_user,
+        const DoutPrefixProvider* dpp, optional_yield y) override;
 
     /* OPs */
     virtual std::unique_ptr<ReadOp> get_read_op() override;
index c4e753bb3a1699ddd3b984928154ed51ad72c801..1dc548c360cd04b301b344a08f354fc03e0a531a 100644 (file)
@@ -967,8 +967,8 @@ int POSIXBucket::read_stats_async(const DoutPrefixProvider *dpp,
   return 0;
 }
 
-int POSIXBucket::sync_user_stats(const DoutPrefixProvider *dpp, optional_yield y,
-                                 RGWBucketEnt* ent)
+int POSIXBucket::sync_owner_stats(const DoutPrefixProvider *dpp, optional_yield y,
+                                  RGWBucketEnt* ent)
 {
   return 0;
 }
@@ -979,7 +979,7 @@ int POSIXBucket::check_bucket_shards(const DoutPrefixProvider* dpp,
   return 0;
 }
 
-int POSIXBucket::chown(const DoutPrefixProvider* dpp, const rgw_user& new_owner, optional_yield y)
+int POSIXBucket::chown(const DoutPrefixProvider* dpp, const rgw_owner& new_owner, optional_yield y)
 {
   /* TODO map user to UID/GID, and change it */
   return 0;
@@ -1488,6 +1488,7 @@ int POSIXObject::delete_object(const DoutPrefixProvider* dpp,
 }
 
 int POSIXObject::copy_object(const ACLOwner& owner,
+                              const rgw_user& remote_user,
                               req_info* info,
                               const rgw_zone_id& source_zone,
                               rgw::sal::Object* dest_object,
@@ -1690,14 +1691,14 @@ int POSIXObject::dump_obj_layout(const DoutPrefixProvider *dpp, optional_yield y
     return 0;
 }
 
-int POSIXObject::swift_versioning_restore(const ACLOwner& owner, bool& restored,
+int POSIXObject::swift_versioning_restore(const ACLOwner& owner, const rgw_user& remote_user, bool& restored,
                                       const DoutPrefixProvider* dpp, optional_yield y)
 {
   return 0;
 }
 
-int POSIXObject::swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
-                                   optional_yield y)
+int POSIXObject::swift_versioning_copy(const ACLOwner& owner, const rgw_user& remote_user,
+                                   const DoutPrefixProvider* dpp, optional_yield y)
 {
   return 0;
 }
index e00f6e74c92c738e5934f2b4afe50a4dbf164309..785192afee1607a273022bbfd82c5c468b63eca7 100644 (file)
@@ -196,11 +196,11 @@ public:
   virtual int read_stats_async(const DoutPrefixProvider *dpp,
                               const bucket_index_layout_generation& idx_layout,
                               int shard_id, boost::intrusive_ptr<ReadStatsCB> ctx) override;
-  virtual int sync_user_stats(const DoutPrefixProvider *dpp, optional_yield y,
-                              RGWBucketEnt* ent) override;
+  virtual int sync_owner_stats(const DoutPrefixProvider *dpp, optional_yield y,
+                               RGWBucketEnt* ent) override;
   virtual int check_bucket_shards(const DoutPrefixProvider* dpp,
                                   uint64_t num_objs, optional_yield y) override;
-  virtual int chown(const DoutPrefixProvider* dpp, const rgw_user& new_owner, optional_yield y) override;
+  virtual int chown(const DoutPrefixProvider* dpp, const rgw_owner& new_owner, optional_yield y) override;
   virtual int put_info(const DoutPrefixProvider* dpp, bool exclusive,
                       ceph::real_time mtime, optional_yield y) override;
   virtual int check_empty(const DoutPrefixProvider* dpp, optional_yield y) override;
@@ -321,6 +321,7 @@ public:
                            optional_yield y,
                            uint32_t flags) override;
   virtual int copy_object(const ACLOwner& owner,
+               const rgw_user& remote_user,
                req_info* info, const rgw_zone_id& source_zone,
                rgw::sal::Object* dest_object, rgw::sal::Bucket* dest_bucket,
                rgw::sal::Bucket* src_bucket,
@@ -367,10 +368,10 @@ public:
                         optional_yield y) override;
   virtual bool placement_rules_match(rgw_placement_rule& r1, rgw_placement_rule& r2) override;
   virtual int dump_obj_layout(const DoutPrefixProvider *dpp, optional_yield y, Formatter* f) override;
-  virtual int swift_versioning_restore(const ACLOwner& owner, bool& restored,
+  virtual int swift_versioning_restore(const ACLOwner& owner, const rgw_user& remote_user, bool& restored,
                                       const DoutPrefixProvider* dpp, optional_yield y) override;
-  virtual int swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
-                                   optional_yield y) override;
+  virtual int swift_versioning_copy(const ACLOwner& owner, const rgw_user& remote_user,
+                                   const DoutPrefixProvider* dpp, optional_yield y) override;
   virtual std::unique_ptr<ReadOp> get_read_op() override;
   virtual std::unique_ptr<DeleteOp> get_delete_op() override;
   virtual int omap_get_vals_by_keys(const DoutPrefixProvider *dpp, const std::string& oid,
index 8cde25fc1990d9eb689d8ecd0daf6f2ce79646e3..5af2230a024d3d89a075bb432c6ef802a3a8f96c 100644 (file)
@@ -1074,7 +1074,7 @@ int RGWBucketAdminOp::link(rgw::sal::Driver* driver, RGWBucketAdminOpState& op_s
   auto* rados = radosdriver->getRados()->get_rados_handle();
   int r = radosdriver->ctl()->bucket->unlink_bucket(*rados, owner.id, old_bucket->get_info().bucket, y, dpp, false);
   if (r < 0) {
-    set_err_msg(err, "could not unlink policy from user " + owner.id.to_str());
+    set_err_msg(err, "could not unlink bucket from owner " + to_string(owner.id));
     return r;
   }
 
@@ -3284,11 +3284,12 @@ int RGWBucketCtl::read_buckets_stats(std::vector<RGWBucketEnt>& buckets,
   });
 }
 
-int RGWBucketCtl::sync_user_stats(const DoutPrefixProvider *dpp, 
-                                  const rgw_user& user_id,
-                                  const RGWBucketInfo& bucket_info,
-                                 optional_yield y,
-                                  RGWBucketEnt* pent)
+int RGWBucketCtl::sync_owner_stats(const DoutPrefixProvider *dpp,
+                                   librados::Rados& rados,
+                                   const rgw_owner& owner,
+                                   const RGWBucketInfo& bucket_info,
+                                   optional_yield y,
+                                   RGWBucketEnt* pent)
 {
   RGWBucketEnt ent;
   if (!pent) {
@@ -3300,7 +3301,16 @@ int RGWBucketCtl::sync_user_stats(const DoutPrefixProvider *dpp,
     return r;
   }
 
-  return svc.user->flush_bucket_stats(dpp, user_id, *pent, y);
+  // flush stats to the user/account owner object
+  const rgw_raw_obj& obj = std::visit(fu2::overload(
+      [&] (const rgw_user& user) {
+        return svc.user->get_buckets_obj(user);
+      },
+      [&] (const rgw_account_id& id) {
+        const RGWZoneParams& zone = svc.zone->get_zone_params();
+        return rgwrados::account::get_buckets_obj(zone, id);
+      }), owner);
+  return rgwrados::buckets::write_stats(dpp, y, rados, obj, *pent);
 }
 
 int RGWBucketCtl::get_sync_policy_handler(std::optional<rgw_zone_id> zone,
index 52098b839c7b0c912289d151da474c8b9749fa5a..d4acaeb41414349a74c467d3fbd1f6769d0d3d10 100644 (file)
@@ -705,10 +705,12 @@ public:
                         const DoutPrefixProvider *dpp);
 
   /* quota related */
-  int sync_user_stats(const DoutPrefixProvider *dpp, 
-                      const rgw_user& user_id, const RGWBucketInfo& bucket_info,
-                     optional_yield y,
-                      RGWBucketEnt* pent);
+  int sync_owner_stats(const DoutPrefixProvider *dpp,
+                       librados::Rados& rados,
+                       const rgw_owner& owner,
+                       const RGWBucketInfo& bucket_info,
+                       optional_yield y,
+                       RGWBucketEnt* pent);
 
   /* bucket sync */
   int get_sync_policy_handler(std::optional<rgw_zone_id> zone,
index 6ff76c16a9070194584389f0f5e28257e183d864..dafbb6df46f4ce107ce876372947905c9a5ff260 100644 (file)
@@ -768,15 +768,6 @@ RGWBucketSyncPolicyHandler::RGWBucketSyncPolicyHandler(const RGWBucketSyncPolicy
                                                                                                        bucket_attrs(std::move(_bucket_attrs)) {
   if (_bucket_info.sync_policy) {
     sync_policy = *_bucket_info.sync_policy;
-
-    for (auto& entry : sync_policy.groups) {
-      for (auto& pipe : entry.second.pipes) {
-        if (pipe.params.mode == rgw_sync_pipe_params::MODE_USER &&
-            pipe.params.user.empty()) {
-          pipe.params.user = _bucket_info.owner;
-        }
-      }
-    }
   }
   legacy_config = parent->legacy_config;
   bucket = _bucket_info.bucket;
index 51ebf95197eb20072d15cb079e12c6921a08414a..396c556926f3e9858281176f96467aba334f18b2 100644 (file)
@@ -932,7 +932,7 @@ int RGWAsyncRemoveObj::_send_request(const DoutPrefixProvider *dpp)
 
   std::unique_ptr<rgw::sal::Object::DeleteOp> del_op = obj->get_delete_op();
 
-  del_op->params.bucket_owner.id = bucket->get_info().owner;
+  del_op->params.bucket_owner = bucket->get_info().owner;
   del_op->params.obj_owner = policy.get_owner();
   if (del_if_older) {
     del_op->params.unmod_since = timestamp;
index 0796afcfa6fed8aefdfb471aadbd61309e5c36fc..84e13049319a4956d5dd4e8dafbb3e287c07bc82 100644 (file)
@@ -2850,7 +2850,7 @@ int RGWFetchObjFilter_Sync::filter(CephContext *cct,
     rgw_user& acl_translation_owner = params.dest.acl_translation->owner;
     if (!acl_translation_owner.empty()) {
       if (params.mode == rgw_sync_pipe_params::MODE_USER &&
-          acl_translation_owner != dest_bucket_info.owner) {
+          rgw_owner{acl_translation_owner} != dest_bucket_info.owner) {
         ldout(cct, 0) << "ERROR: " << __func__ << ": acl translation was requested, but user (" << acl_translation_owner
           << ") is not dest bucket owner (" << dest_bucket_info.owner << ")" << dendl;
         return -EPERM;
index 542be2ce5551a73253bdcc97706705e46d3de51d..78062773ef315166d5529660da6526ecbcbe051f 100644 (file)
@@ -899,7 +899,7 @@ static inline void populate_event(reservation_t& res,
   event.x_amz_id_2 = res.store->getRados()->host_id; // RGW on which the change was made
   // configurationId is filled from notification configuration
   event.bucket_name = res.bucket->get_name();
-  event.bucket_ownerIdentity = res.bucket->get_owner().id;
+  event.bucket_ownerIdentity = to_string(res.bucket->get_owner());
   const auto region = res.store->get_zone()->get_zonegroup().get_api_name();
   rgw::ARN bucket_arn(res.bucket->get_key());
   bucket_arn.region = region; 
index 1f07922976602e1a6ee5998de2df6a48c415976c..95f05f149a062029901f6fe7c146830d329b5b32 100644 (file)
@@ -2300,7 +2300,7 @@ void RGWRados::create_bucket_id(string *bucket_id)
 int RGWRados::create_bucket(const DoutPrefixProvider* dpp,
                             optional_yield y,
                             const rgw_bucket& bucket,
-                            const rgw_user& owner,
+                            const rgw_owner& owner,
                             const std::string& zonegroup_id,
                             const rgw_placement_rule& placement_rule,
                             const RGWZonePlacementInfo* zone_placement,
@@ -2854,6 +2854,7 @@ bool RGWRados::swift_versioning_enabled(const RGWBucketInfo& bucket_info) const
 
 int RGWRados::swift_versioning_copy(RGWObjectCtx& obj_ctx,
                                     const ACLOwner& owner,
+                                    const rgw_user& remote_user,
                                     RGWBucketInfo& bucket_info,
                                     const rgw_obj& obj,
                                     const DoutPrefixProvider *dpp,
@@ -2911,6 +2912,7 @@ int RGWRados::swift_versioning_copy(RGWObjectCtx& obj_ctx,
 
   r = copy_obj(obj_ctx,
                owner,
+               remote_user,
                NULL, /* req_info *info */
                no_zone,
                dest_obj,
@@ -2950,6 +2952,7 @@ int RGWRados::swift_versioning_copy(RGWObjectCtx& obj_ctx,
 
 int RGWRados::swift_versioning_restore(RGWObjectCtx& obj_ctx,
                                        const ACLOwner& owner,
+                                       const rgw_user& remote_user,
                                        RGWBucketInfo& bucket_info,
                                        rgw_obj& obj,
                                        bool& restored,
@@ -3008,6 +3011,7 @@ int RGWRados::swift_versioning_restore(RGWObjectCtx& obj_ctx,
 
     int ret = copy_obj(obj_ctx,
                        owner,
+                       remote_user,
                        nullptr,       /* req_info *info */
                        no_zone,
                        obj,           /* dest obj */
@@ -4602,6 +4606,7 @@ int RGWRados::copy_obj_to_remote_dest(const DoutPrefixProvider *dpp,
  */
 int RGWRados::copy_obj(RGWObjectCtx& obj_ctx,
                const ACLOwner& owner,
+               const rgw_user& remote_user,
                req_info *info,
                const rgw_zone_id& source_zone,
                const rgw_obj& dest_obj,
@@ -4660,7 +4665,7 @@ int RGWRados::copy_obj(RGWObjectCtx& obj_ctx,
   if (remote_src || !source_zone.empty()) {
     rgw_zone_set_entry source_trace_entry{source_zone.id, std::nullopt};
     const req_context rctx{dpp, y, nullptr};
-    return fetch_remote_obj(obj_ctx, owner.id, info, source_zone,
+    return fetch_remote_obj(obj_ctx, remote_user, info, source_zone,
                dest_obj, src_obj, dest_bucket_info, &src_bucket_info,
                dest_placement, src_mtime, mtime, mod_ptr,
                unmod_ptr, high_precision_time,
@@ -4737,7 +4742,7 @@ int RGWRados::copy_obj(RGWObjectCtx& obj_ctx,
 
   if (remote_dest) {
     /* dest is in a different zonegroup, copy it there */
-    return copy_obj_to_remote_dest(dpp, astate, attrs, read_op, owner.id, dest_obj, mtime, y);
+    return copy_obj_to_remote_dest(dpp, astate, attrs, read_op, remote_user, dest_obj, mtime, y);
   }
   uint64_t max_chunk_size;
 
@@ -5706,7 +5711,7 @@ int RGWRados::Object::Delete::delete_obj(optional_yield y, const DoutPrefixProvi
 
       struct rgw_bucket_dir_entry_meta meta;
 
-      meta.owner = params.obj_owner.id.to_str();
+      meta.owner = to_string(params.obj_owner.id);
       meta.owner_display_name = params.obj_owner.display_name;
 
       if (real_clock::is_zero(params.mtime)) {
@@ -6982,7 +6987,7 @@ int RGWRados::Bucket::UpdateIndex::complete(const DoutPrefixProvider *dpp, int64
   if (user_data)
     ent.meta.user_data = *user_data;
 
-  ent.meta.owner = owner.id.to_str();
+  ent.meta.owner = to_string(owner.id);
   ent.meta.owner_display_name = owner.display_name;
   ent.meta.content_type = content_type;
   ent.meta.appendable = appendable;
@@ -10227,7 +10232,7 @@ int RGWRados::check_disk_state(const DoutPrefixProvider *dpp,
   object.meta.etag = etag;
   object.meta.content_type = content_type;
   object.meta.storage_class = storage_class;
-  object.meta.owner = owner.id.to_str();
+  object.meta.owner = to_string(owner.id);
   object.meta.owner_display_name = owner.display_name;
   object.meta.appendable = appendable;
 
@@ -10257,7 +10262,7 @@ int RGWRados::check_disk_state(const DoutPrefixProvider *dpp,
     list_state.tag = astate->obj_tag.c_str();
   }
 
-  list_state.meta.owner = owner.id.to_str();
+  list_state.meta.owner = to_string(owner.id);
   list_state.meta.owner_display_name = owner.display_name;
 
   list_state.exists = true;
@@ -10381,7 +10386,7 @@ int RGWRados::add_bucket_to_reshard(const DoutPrefixProvider *dpp, const RGWBuck
 
   cls_rgw_reshard_entry entry;
   entry.time = real_clock::now();
-  entry.tenant = bucket_info.owner.tenant;
+  entry.tenant = bucket_info.bucket.tenant;
   entry.bucket_name = bucket_info.bucket.name;
   entry.bucket_id = bucket_info.bucket.bucket_id;
   entry.old_num_shards = num_source_shards;
@@ -10390,7 +10395,7 @@ int RGWRados::add_bucket_to_reshard(const DoutPrefixProvider *dpp, const RGWBuck
   return reshard.add(dpp, entry, y);
 }
 
-int RGWRados::check_quota(const DoutPrefixProvider *dpp, const rgw_user& bucket_owner, rgw_bucket& bucket,
+int RGWRados::check_quota(const DoutPrefixProvider *dpp, const rgw_owner& bucket_owner, rgw_bucket& bucket,
                           RGWQuota& quota,
                          uint64_t obj_size, optional_yield y,
                          bool check_size_only)
index dd471136a4281a02b2ae22890ffdfbd12d445177..481a94a140dc91cf75bbcc9a02e9d55c7f7a15f0 100644 (file)
@@ -633,7 +633,7 @@ public:
   int create_bucket(const DoutPrefixProvider* dpp,
                     optional_yield y,
                     const rgw_bucket& bucket,
-                    const rgw_user& owner,
+                    const rgw_owner& owner,
                     const std::string& zonegroup_id,
                     const rgw_placement_rule& placement_rule,
                     const RGWZonePlacementInfo* zone_placement,
@@ -797,7 +797,7 @@ public:
         const std::string *ptag;
         std::list<rgw_obj_index_key> *remove_objs;
         ceph::real_time set_mtime;
-        rgw_user bucket_owner; // for quota stats update
+        rgw_owner bucket_owner; // for quota stats update
         ACLOwner owner; // owner/owner_display_name for bucket index
         RGWObjCategory category;
         int flags;
@@ -839,7 +839,7 @@ public:
       RGWRados::Object *target;
 
       struct DeleteParams {
-        rgw_user bucket_owner; // for quota stats update
+        rgw_owner bucket_owner; // for quota stats update
         int versioning_status; // versioning flags defined in enum RGWBucketFlags
         ACLOwner obj_owner;    // needed for creation of deletion marker
         uint64_t olh_epoch;
@@ -1073,12 +1073,14 @@ public:
 
   int swift_versioning_copy(RGWObjectCtx& obj_ctx,              /* in/out */
                             const ACLOwner& owner,              /* in */
+                            const rgw_user& remote_user,        /* in */
                             RGWBucketInfo& bucket_info,         /* in */
                             const rgw_obj& obj,                 /* in */
                             const DoutPrefixProvider *dpp,      /* in */
                             optional_yield y);                  /* in */
   int swift_versioning_restore(RGWObjectCtx& obj_ctx,           /* in/out */
                                const ACLOwner& owner,           /* in */
+                               const rgw_user& remote_user,     /* in */
                                RGWBucketInfo& bucket_info,      /* in */
                                rgw_obj& obj,                    /* in/out */
                                bool& restored,                  /* out */
@@ -1174,7 +1176,8 @@ public:
    * Returns: 0 on success, -ERR# otherwise.
    */
   int copy_obj(RGWObjectCtx& obj_ctx,
-               const ACLOwner& owner,
+               const ACLOwner& owner, // owner of destination object
+               const rgw_user& remote_user, // uid for fetch_remote_obj() auth
                req_info *info,
                const rgw_zone_id& source_zone,
                const rgw_obj& dest_obj,
@@ -1579,7 +1582,7 @@ public:
   int fix_tail_obj_locator(const DoutPrefixProvider *dpp, RGWBucketInfo& bucket_info,
                            rgw_obj_key& key, bool fix, bool *need_fix, optional_yield y);
 
-  int check_quota(const DoutPrefixProvider *dpp, const rgw_user& bucket_owner, rgw_bucket& bucket,
+  int check_quota(const DoutPrefixProvider *dpp, const rgw_owner& bucket_owner, rgw_bucket& bucket,
                   RGWQuota& quota, uint64_t obj_size,
                  optional_yield y, bool check_size_only = false);
 
index 7a54da7fe7d08afa39baba2af377ed746f27e563..c1011bd60a5503ce27aa086f270404c692e21574 100644 (file)
@@ -1056,7 +1056,7 @@ int RGWReshard::update(const DoutPrefixProvider *dpp, const RGWBucketInfo& bucke
   cls_rgw_reshard_entry entry;
   entry.bucket_name = bucket_info.bucket.name;
   entry.bucket_id = bucket_info.bucket.bucket_id;
-  entry.tenant = bucket_info.owner.tenant;
+  entry.tenant = bucket_info.bucket.tenant;
 
   int ret = get(dpp, entry);
   if (ret < 0) {
index e965a8e233a0210c8940bcf7fda6be4bb47f9be4..a25a4a58d913d047a1a384a95b973a3e03343631 100644 (file)
@@ -68,6 +68,7 @@
 #include "cls/rgw/cls_rgw_client.h"
 
 #include "account.h"
+#include "buckets.h"
 #include "rgw_pubsub.h"
 #include "topic.h"
 
@@ -335,7 +336,8 @@ int RadosBucket::remove(const DoutPrefixProvider* dpp,
     }
   }
 
-  ret = store->ctl()->bucket->sync_user_stats(dpp, info.owner, info, y, nullptr);
+  librados::Rados& rados = *store->getRados()->get_rados_handle();
+  ret = store->ctl()->bucket->sync_owner_stats(dpp, rados, info.owner, info, y, nullptr);
   if (ret < 0) {
      ldout(store->ctx(), 1) << "WARNING: failed sync user stats before bucket delete. ret=" <<  ret << dendl;
   }
@@ -353,14 +355,13 @@ int RadosBucket::remove(const DoutPrefixProvider* dpp,
 
   // if bucket has notification definitions associated with it
   // they should be removed (note that any pending notifications on the bucket are still going to be sent)
-  const RGWPubSub ps(store, info.owner.tenant, *store->svc()->site);
+  const RGWPubSub ps(store, info.bucket.tenant, *store->svc()->site);
   const RGWPubSub::Bucket ps_bucket(ps, this);
   const auto ps_ret = ps_bucket.remove_notifications(dpp, y);
   if (ps_ret < 0 && ps_ret != -ENOENT) {
     ldpp_dout(dpp, -1) << "ERROR: unable to remove notifications from bucket. ret=" << ps_ret << dendl;
   }
 
-  librados::Rados& rados = *store->getRados()->get_rados_handle();
   ret = store->ctl()->bucket->unlink_bucket(rados, info.owner,
                                             info.bucket, y, dpp, false);
   if (ret < 0) {
@@ -487,7 +488,7 @@ int RadosBucket::remove_bypass_gc(int concurrent_max, bool
     return ret;
   }
 
-  sync_user_stats(dpp, y, nullptr);
+  sync_owner_stats(dpp, y, nullptr);
   if (ret < 0) {
      ldpp_dout(dpp, 1) << "WARNING: failed sync user stats before bucket delete. ret=" <<  ret << dendl;
   }
@@ -551,10 +552,11 @@ int RadosBucket::read_stats_async(const DoutPrefixProvider *dpp,
   return store->getRados()->get_bucket_stats_async(dpp, get_info(), idx_layout, shard_id, ctx);
 }
 
-int RadosBucket::sync_user_stats(const DoutPrefixProvider *dpp, optional_yield y,
-                                 RGWBucketEnt* ent)
+int RadosBucket::sync_owner_stats(const DoutPrefixProvider *dpp, optional_yield y,
+                                  RGWBucketEnt* ent)
 {
-  return store->ctl()->bucket->sync_user_stats(dpp, info.owner, info, y, ent);
+  librados::Rados& rados = *store->getRados()->get_rados_handle();
+  return store->ctl()->bucket->sync_owner_stats(dpp, rados, info.owner, info, y, ent);
 }
 
 int RadosBucket::check_bucket_shards(const DoutPrefixProvider* dpp,
@@ -563,18 +565,19 @@ int RadosBucket::check_bucket_shards(const DoutPrefixProvider* dpp,
   return store->getRados()->check_bucket_shards(info, num_objs, dpp, y);
 }
 
-int RadosBucket::link(const DoutPrefixProvider* dpp, const rgw_user& new_user, optional_yield y, bool update_entrypoint, RGWObjVersionTracker* objv)
+int RadosBucket::link(const DoutPrefixProvider* dpp, const rgw_owner& new_owner,
+                      optional_yield y, bool update_entrypoint, RGWObjVersionTracker* objv)
 {
   RGWBucketEntryPoint ep;
   ep.bucket = info.bucket;
-  ep.owner = new_user;
+  ep.owner = new_owner;
   ep.creation_time = get_creation_time();
   ep.linked = true;
   Attrs ep_attrs;
   rgw_ep_info ep_data{ep, ep_attrs};
 
   librados::Rados& rados = *store->getRados()->get_rados_handle();
-  int r = store->ctl()->bucket->link_bucket(rados, new_user, info.bucket,
+  int r = store->ctl()->bucket->link_bucket(rados, new_owner, info.bucket,
                                            get_creation_time(), y, dpp, update_entrypoint,
                                            &ep_data);
   if (r < 0)
@@ -586,14 +589,14 @@ int RadosBucket::link(const DoutPrefixProvider* dpp, const rgw_user& new_user, o
   return r;
 }
 
-int RadosBucket::unlink(const DoutPrefixProvider* dpp, const rgw_user& owner, optional_yield y, bool update_entrypoint)
+int RadosBucket::unlink(const DoutPrefixProvider* dpp, const rgw_owner& owner, optional_yield y, bool update_entrypoint)
 {
   librados::Rados& rados = *store->getRados()->get_rados_handle();
   return store->ctl()->bucket->unlink_bucket(rados, owner, info.bucket,
                                              y, dpp, update_entrypoint);
 }
 
-int RadosBucket::chown(const DoutPrefixProvider* dpp, const rgw_user& new_owner, optional_yield y)
+int RadosBucket::chown(const DoutPrefixProvider* dpp, const rgw_owner& new_owner, optional_yield y)
 {
   std::string obj_marker;
   // unlink from the owner, but don't update the entrypoint until link()
@@ -642,14 +645,22 @@ int RadosBucket::read_usage(const DoutPrefixProvider *dpp, uint64_t start_epoch,
                               RGWUsageIter& usage_iter,
                               map<rgw_user_bucket, rgw_usage_log_entry>& usage)
 {
-  return store->getRados()->read_usage(dpp, info.owner, get_name(), start_epoch,
+  const rgw_user* user = std::get_if<rgw_user>(&info.owner);
+  if (!user) {
+    return -ENOTSUP; // not supported for account owners
+  }
+  return store->getRados()->read_usage(dpp, *user, get_name(), start_epoch,
                                       end_epoch, max_entries, is_truncated,
                                       usage_iter, usage);
 }
 
 int RadosBucket::trim_usage(const DoutPrefixProvider *dpp, uint64_t start_epoch, uint64_t end_epoch, optional_yield y)
 {
-  return store->getRados()->trim_usage(dpp, info.owner, get_name(), start_epoch, end_epoch, y);
+  const rgw_user* user = std::get_if<rgw_user>(&info.owner);
+  if (!user) {
+    return -ENOTSUP; // not supported for account owners
+  }
+  return store->getRados()->trim_usage(dpp, *user, get_name(), start_epoch, end_epoch, y);
 }
 
 int RadosBucket::remove_objs_from_index(const DoutPrefixProvider *dpp, std::list<rgw_obj_index_key>& objs_to_unlink)
@@ -1092,14 +1103,21 @@ int RadosStore::load_account_stats(const DoutPrefixProvider* dpp,
                                    ceph::real_time& last_synced,
                                    ceph::real_time& last_updated)
 {
-  return -ENOTSUP;
+  const RGWZoneParams& zone = svc()->zone->get_zone_params();
+  const rgw_raw_obj& obj = rgwrados::account::get_buckets_obj(zone, id);
+  librados::Rados& rados = *getRados()->get_rados_handle();
+  return rgwrados::buckets::read_stats(dpp, y, rados, obj, stats,
+                                       &last_synced, &last_updated);
 }
 
 int RadosStore::load_account_stats_async(const DoutPrefixProvider* dpp,
                                          std::string_view id,
                                          boost::intrusive_ptr<ReadStatsCB> cb)
 {
-  return -ENOTSUP;
+  const RGWZoneParams& zone = svc()->zone->get_zone_params();
+  const rgw_raw_obj& obj = rgwrados::account::get_buckets_obj(zone, id);
+  librados::Rados& rados = *getRados()->get_rados_handle();
+  return rgwrados::buckets::read_stats_async(dpp, rados, obj, std::move(cb));
 }
 
 std::unique_ptr<Object> RadosStore::get_object(const rgw_obj_key& k)
@@ -2255,7 +2273,7 @@ RadosObject::RadosDeleteOp::RadosDeleteOp(RadosObject *_source) :
 
 int RadosObject::RadosDeleteOp::delete_obj(const DoutPrefixProvider* dpp, optional_yield y, uint32_t flags)
 {
-  parent_op.params.bucket_owner = params.bucket_owner.id;
+  parent_op.params.bucket_owner = params.bucket_owner;
   parent_op.params.versioning_status = params.versioning_status;
   parent_op.params.obj_owner = params.obj_owner;
   parent_op.params.olh_epoch = params.olh_epoch;
@@ -2295,6 +2313,7 @@ int RadosObject::delete_object(const DoutPrefixProvider* dpp,
 }
 
 int RadosObject::copy_object(const ACLOwner& owner,
+                               const rgw_user& remote_user,
                                req_info* info,
                                const rgw_zone_id& source_zone,
                                rgw::sal::Object* dest_object,
@@ -2324,6 +2343,7 @@ int RadosObject::copy_object(const ACLOwner& owner,
 {
   return store->getRados()->copy_obj(*rados_ctx,
                                     owner,
+                                    remote_user,
                                     info,
                                     source_zone,
                                     dest_object->get_obj(),
@@ -2359,22 +2379,23 @@ int RadosObject::RadosReadOp::iterate(const DoutPrefixProvider* dpp, int64_t ofs
   return parent_op.iterate(dpp, ofs, end, cb, y);
 }
 
-int RadosObject::swift_versioning_restore(const ACLOwner& owner, bool& restored,
+int RadosObject::swift_versioning_restore(const ACLOwner& owner, const rgw_user& remote_user, bool& restored,
                                          const DoutPrefixProvider* dpp, optional_yield y)
 {
   rgw_obj obj = get_obj();
   return store->getRados()->swift_versioning_restore(*rados_ctx,
-                                                    owner,
+                                                    owner, remote_user,
                                                     bucket->get_info(),
                                                     obj,
                                                     restored,
                                                     dpp, y);
 }
 
-int RadosObject::swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp, optional_yield y)
+int RadosObject::swift_versioning_copy(const ACLOwner& owner, const rgw_user& remote_user,
+                                       const DoutPrefixProvider* dpp, optional_yield y)
 {
   return store->getRados()->swift_versioning_copy(*rados_ctx,
-                                        owner,
+                                        owner, remote_user,
                                         bucket->get_info(),
                                         get_obj(),
                                         dpp,
@@ -2491,7 +2512,7 @@ int RadosMultipartUpload::abort(const DoutPrefixProvider *dpp, CephContext *cct,
   }
 
   std::unique_ptr<rgw::sal::Object::DeleteOp> del_op = meta_obj->get_delete_op();
-  del_op->params.bucket_owner.id = bucket->get_info().owner;
+  del_op->params.bucket_owner = bucket->get_info().owner;
   del_op->params.versioning_status = 0;
   if (!remove_objs.empty()) {
     del_op->params.remove_objs = &remove_objs;
index 83ba68832b3a6df299877037d13a6665701ec732..5aebda3d32ed6c0c00e7e591a7c49f0aae75ae3e 100644 (file)
@@ -453,6 +453,7 @@ class RadosObject : public StoreObject {
     virtual int delete_object(const DoutPrefixProvider* dpp,
                              optional_yield y, uint32_t flags) override;
     virtual int copy_object(const ACLOwner& owner,
+               const rgw_user& remote_user,
                req_info* info, const rgw_zone_id& source_zone,
                rgw::sal::Object* dest_object, rgw::sal::Bucket* dest_bucket,
                rgw::sal::Bucket* src_bucket,
@@ -514,10 +515,10 @@ class RadosObject : public StoreObject {
     virtual int dump_obj_layout(const DoutPrefixProvider *dpp, optional_yield y, Formatter* f) override;
 
     /* Swift versioning */
-    virtual int swift_versioning_restore(const ACLOwner& owner, bool& restored,
+    virtual int swift_versioning_restore(const ACLOwner& owner, const rgw_user& remote_user, bool& restored,
                                         const DoutPrefixProvider* dpp, optional_yield y) override;
-    virtual int swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
-                                     optional_yield y) override;
+    virtual int swift_versioning_copy(const ACLOwner& owner, const rgw_user& remote_user,
+                                     const DoutPrefixProvider* dpp, optional_yield y) override;
 
     /* OPs */
     virtual std::unique_ptr<ReadOp> get_read_op() override;
@@ -601,11 +602,11 @@ class RadosBucket : public StoreBucket {
     virtual int read_stats_async(const DoutPrefixProvider *dpp,
                                  const bucket_index_layout_generation& idx_layout,
                                  int shard_id, boost::intrusive_ptr<ReadStatsCB> ctx) override;
-    int sync_user_stats(const DoutPrefixProvider *dpp, optional_yield y,
-                        RGWBucketEnt* ent) override;
+    int sync_owner_stats(const DoutPrefixProvider *dpp, optional_yield y,
+                         RGWBucketEnt* ent) override;
     int check_bucket_shards(const DoutPrefixProvider* dpp, uint64_t num_objs,
                             optional_yield y) override;
-    virtual int chown(const DoutPrefixProvider* dpp, const rgw_user& new_owner, optional_yield y) override;
+    virtual int chown(const DoutPrefixProvider* dpp, const rgw_owner& new_owner, optional_yield y) override;
     virtual int put_info(const DoutPrefixProvider* dpp, bool exclusive, ceph::real_time mtime, optional_yield y) override;
     virtual int check_empty(const DoutPrefixProvider* dpp, optional_yield y) override;
     virtual int check_quota(const DoutPrefixProvider *dpp, RGWQuota& quota, uint64_t obj_size, optional_yield y, bool check_size_only = false) override;
@@ -645,8 +646,8 @@ class RadosBucket : public StoreBucket {
         optional_yield y, const DoutPrefixProvider *dpp) override;
 
   private:
-    int link(const DoutPrefixProvider* dpp, const rgw_user& new_owner, optional_yield y, bool update_entrypoint = true, RGWObjVersionTracker* objv = nullptr);
-    int unlink(const DoutPrefixProvider* dpp, const rgw_user& owner, optional_yield y, bool update_entrypoint = true);
+    int link(const DoutPrefixProvider* dpp, const rgw_owner& new_owner, optional_yield y, bool update_entrypoint = true, RGWObjVersionTracker* objv = nullptr);
+    int unlink(const DoutPrefixProvider* dpp, const rgw_owner& owner, optional_yield y, bool update_entrypoint = true);
     friend class RadosUser;
 };
 
index 3c269a7494986d026d24fdd61cd2897289c03458..a0ca43f8422ce6a015463777dfb91ac26db4d925 100644 (file)
@@ -615,9 +615,9 @@ struct AWSSyncConfig {
                   const rgw_obj_key& obj) {
     string bucket_str;
     string owner;
-    if (!bucket_info.owner.tenant.empty()) {
-      bucket_str = owner = bucket_info.owner.tenant + "-";
-      owner += bucket_info.owner.id;
+    if (!bucket_info.bucket.tenant.empty()) {
+      bucket_str = owner = bucket_info.bucket.tenant + "-";
+      owner += to_string(bucket_info.owner);
     }
     bucket_str += bucket_info.bucket.name;
 
index e3353dc1fc7c590c0aff96aaf20af9f5c78d2ac9..414fbeac4c990ee8697615a55d486007a9dd97e9 100644 (file)
@@ -229,7 +229,7 @@ struct ElasticConfig {
 
   bool should_handle_operation(RGWBucketInfo& bucket_info) {
     return index_buckets.exists(bucket_info.bucket.name) &&
-           allow_owners.exists(bucket_info.owner.to_str());
+           allow_owners.exists(to_string(bucket_info.owner));
   }
 };
 
@@ -501,12 +501,12 @@ struct es_obj_metadata {
 
         const RGWAccessControlList& acl = policy.get_acl();
 
-        permissions.insert(policy.get_owner().id.to_str());
+        permissions.insert(to_string(policy.get_owner().id));
         for (const auto& acliter : acl.get_grant_map()) {
           const ACLGrant& grant = acliter.second;
           const auto* user = grant.get_user();
           if (user && (grant.get_permission().get_permissions() & RGW_PERM_READ) != 0) {
-            permissions.insert(user->id.to_str());
+            permissions.insert(to_string(user->id));
           }
         }
       } else if (attr_name == RGW_ATTR_TAGS) {
index 05afc60ceb19f80ae8ec078ecf4857c67312e323..bd4d3e77291eaf6790bada53e4cc72bb26297f27 100644 (file)
@@ -3178,8 +3178,6 @@ class SyncPolicyContext
 
   rgw_sync_policy_info *policy{nullptr};
 
-  std::optional<rgw_user> owner;
-
 public:
   SyncPolicyContext(rgw::sal::ConfigStore* cfgstore,
                     std::optional<rgw_bucket> _bucket)
@@ -3205,8 +3203,6 @@ public:
       return ret;
     }
 
-    owner = bucket->get_info().owner;
-
     if (!bucket->get_info().sync_policy) {
       rgw_sync_policy_info new_policy;
       bucket->get_info().set_sync_policy(std::move(new_policy));
@@ -3239,10 +3235,6 @@ public:
   rgw_sync_policy_info& get_policy() {
     return *policy;
   }
-
-  std::optional<rgw_user>& get_owner() {
-    return owner;
-  }
 };
 
 void resolve_zone_id_opt(std::optional<string>& zone_name, std::optional<rgw_zone_id>& zone_id)
@@ -7442,7 +7434,7 @@ int main(int argc, const char **argv)
        return -r;
       }
       formatter->dump_string("bucket_id", entry.bucket_id);
-      formatter->dump_string("bucket_owner", entry.bucket_owner.to_str());
+      formatter->dump_string("bucket_owner", to_string(entry.bucket_owner));
       formatter->dump_string("bucket", entry.bucket);
 
       uint64_t agg_time = 0;
@@ -8887,7 +8879,7 @@ next:
           cerr << "ERROR: could not init bucket: " << cpp_strerror(-ret) << std::endl;
           return -ret;
         }
-        ret = bucket->sync_user_stats(dpp(), null_yield, nullptr);
+        ret = bucket->sync_owner_stats(dpp(), null_yield, nullptr);
         if (ret < 0) {
           cerr << "ERROR: could not sync bucket stats: " <<
            cpp_strerror(-ret) << std::endl;
@@ -10006,11 +9998,9 @@ next:
 
     if (!rgw::sal::User::empty(user)) {
       pipe->params.user = user->get_id();
-    } else if (pipe->params.user.empty()) {
-      auto owner = sync_policy_ctx.get_owner();
-      if (owner) {
-        pipe->params.user = *owner;
-      }
+    } else if (pipe->params.mode == rgw_sync_pipe_params::MODE_USER) {
+      cerr << "ERROR: missing --uid for --mode=user" << std::endl;
+      return EINVAL;
     }
 
     ret = sync_policy_ctx.write_policy();
index 6e9029f4c537b27a8c2e0d742a5225fbcf8db71d..d8a16fba3f266b6eaa523f8166aa3a3c10aa98e2 100644 (file)
@@ -77,8 +77,12 @@ transform_old_authinfo(CephContext* const cct,
 
     ACLOwner get_aclowner() const {
       ACLOwner owner;
-      owner.id = id;
-      owner.display_name = display_name;
+      if (!account_id.empty()) {
+        owner.id.emplace<rgw_account_id>(account_id);
+      } else {
+        owner.id = id;
+        owner.display_name = display_name;
+      }
       return owner;
     }
 
@@ -793,8 +797,12 @@ const std::string rgw::auth::LocalApplier::NO_ACCESS_KEY;
 ACLOwner rgw::auth::LocalApplier::get_aclowner() const
 {
   ACLOwner owner;
-  owner.id = user_info.user_id;
-  owner.display_name = user_info.display_name;
+  if (!user_info.account_id.empty()) {
+    owner.id = user_info.account_id;
+  } else {
+    owner.id = user_info.user_id;
+    owner.display_name = user_info.display_name;
+  }
   return owner;
 }
 
index a3449f2ede9b01d26f961c7957d6800e87d3d7ff..5c664df97999bb1385e500d4874016de913851d5 100644 (file)
@@ -10,6 +10,7 @@
 #include "json_spirit/json_spirit.h"
 #include "common/ceph_json.h"
 #include "common/Formatter.h"
+#include "common/versioned_variant.h"
 
 #include "rgw_op.h"
 #include "rgw_common.h"
@@ -2260,9 +2261,19 @@ RGWBucketInfo::~RGWBucketInfo()
 }
 
 void RGWBucketInfo::encode(bufferlist& bl) const {
-  ENCODE_START(23, 4, bl);
+  // rgw_owner is now encoded at the end. if the owner is a user, duplicate the
+  // encoding of its id/tenant/ns in the existing locations for backward compat.
+  // otherwise, encode empty strings there
+  const rgw_user* user = std::get_if<rgw_user>(&owner);
+  std::string empty;
+
+  ENCODE_START(24, 4, bl);
   encode(bucket, bl);
-  encode(owner.id, bl);
+  if (user) {
+    encode(user->id, bl);
+  } else {
+    encode(empty, bl);
+  }
   encode(flags, bl);
   encode(zonegroup, bl);
   uint64_t ct = real_clock::to_time_t(creation_time);
@@ -2271,7 +2282,11 @@ void RGWBucketInfo::encode(bufferlist& bl) const {
   encode(has_instance_obj, bl);
   encode(quota, bl);
   encode(requester_pays, bl);
-  encode(owner.tenant, bl);
+  if (user) {
+    encode(user->tenant, bl);
+  } else {
+    encode(empty, bl);
+  }
   encode(has_website, bl);
   if (has_website) {
     encode(website_conf, bl);
@@ -2293,17 +2308,24 @@ void RGWBucketInfo::encode(bufferlist& bl) const {
     encode(*sync_policy, bl);
   }
   encode(layout, bl);
-  encode(owner.ns, bl);
+  if (user) {
+    encode(user->ns, bl);
+  } else {
+    encode(empty, bl);
+  }
+  ceph::versioned_variant::encode(owner, bl); // v24
+
   ENCODE_FINISH(bl);
 }
 
 void RGWBucketInfo::decode(bufferlist::const_iterator& bl) {
-  DECODE_START_LEGACY_COMPAT_LEN_32(23, 4, 4, bl);
+  rgw_user user;
+  DECODE_START_LEGACY_COMPAT_LEN_32(24, 4, 4, bl);
   decode(bucket, bl);
   if (struct_v >= 2) {
     string s;
     decode(s, bl);
-    owner.from_str(s);
+    user.from_str(s);
   }
   if (struct_v >= 3)
     decode(flags, bl);
@@ -2329,7 +2351,7 @@ void RGWBucketInfo::decode(bufferlist::const_iterator& bl) {
   if (struct_v >= 12)
     decode(requester_pays, bl);
   if (struct_v >= 13)
-    decode(owner.tenant, bl);
+    decode(user.tenant, bl);
   if (struct_v >= 14) {
     decode(has_website, bl);
     if (has_website) {
@@ -2373,7 +2395,12 @@ void RGWBucketInfo::decode(bufferlist::const_iterator& bl) {
     decode(layout, bl);
   }
   if (struct_v >= 23) {
-    decode(owner.ns, bl);
+    decode(user.ns, bl);
+  }
+  if (struct_v >= 24) {
+    ceph::versioned_variant::decode(owner, bl);
+  } else {
+    owner = std::move(user); // user was decoded piecewise above
   }
 
   if (layout.logs.empty() &&
@@ -2492,7 +2519,7 @@ void RGWBucketInfo::dump(Formatter *f) const
   encode_json("bucket", bucket, f);
   utime_t ut(creation_time);
   encode_json("creation_time", ut, f);
-  encode_json("owner", owner.to_str(), f);
+  encode_json("owner", owner, f);
   encode_json("flags", flags, f);
   encode_json("zonegroup", zonegroup, f);
   encode_json("placement_rule", placement_rule, f);
index dd696e01e43b211d4f15ade3c67dfb9b03817255..d04f7308239989ee64b61202ffd9dd692d97b197 100644 (file)
@@ -964,7 +964,7 @@ class RGWSI_Zone;
 
 struct RGWBucketInfo {
   rgw_bucket bucket;
-  rgw_user owner;
+  rgw_owner owner;
   uint32_t flags{0};
   std::string zonegroup;
   ceph::real_time creation_time;
index 085fda0a44bed4e3d3ea8a52bb05394beff7f0cc..58874bf22b9d0bfce882681029148db2ba0b0337 100644 (file)
@@ -13,6 +13,7 @@
 #include <rgw/rgw_b64.h>
 #include <rgw/rgw_rest_s3.h>
 #include "include/ceph_assert.h"
+#include "include/function2.hpp"
 #include "crypto/crypto_accel.h"
 #include "crypto/crypto_plugin.h"
 #include "rgw/rgw_kms.h"
@@ -964,7 +965,13 @@ std::string expand_key_name(req_state *s, const std::string_view&t)
       continue;
     }
     if (t.compare(i+1, 8, "owner_id") == 0) {
-      r.append(s->bucket->get_info().owner.id);
+      r.append(std::visit(fu2::overload(
+          [] (const rgw_user& user_id) -> const std::string& {
+            return user_id.id;
+          },
+          [] (const rgw_account_id& account_id) -> const std::string& {
+            return account_id;
+          }), s->bucket->get_info().owner));
       i += 9;
       continue;
     }
index deb74465600b2588621a5ec750915f1c048d2d88..4eec850eafd1a96afa835144bbfa02e94c711a52 100644 (file)
@@ -597,7 +597,7 @@ static int remove_expired_obj(const DoutPrefixProvider* dpp,
     = obj->get_bucket()->get_info().versioning_status();
   del_op->params.obj_owner.id = rgw_user{meta.owner};
   del_op->params.obj_owner.display_name = meta.owner_display_name;
-  del_op->params.bucket_owner.id = bucket_info.owner;
+  del_op->params.bucket_owner = bucket_info.owner;
   del_op->params.unmod_since = meta.mtime;
 
   // notification supported only for RADOS driver for now
index d430620ac0d1452846eb9195e6cb3026670aac8b..4119d8f93a5c5041bc384cb6b5ed2936a2274358 100644 (file)
@@ -303,8 +303,19 @@ struct BucketMetaTable : public EmptyMetaTable {
     } else if (strcasecmp(index, "PlacementRule") == 0) {
       create_metatable<PlacementRuleMetaTable>(L, name, index, false, &(bucket->get_info().placement_rule));
     } else if (strcasecmp(index, "User") == 0) {
-      create_metatable<UserMetaTable>(L, name, index, false, 
-          const_cast<rgw_user*>(&bucket->get_owner()));
+      const rgw_owner& owner = bucket->get_owner();
+      if (const rgw_user* u = std::get_if<rgw_user>(&owner); u) {
+        create_metatable<UserMetaTable>(L, name, index, false, const_cast<rgw_user*>(u));
+      } else {
+        lua_pushnil(L);
+      }
+    } else if (strcasecmp(index, "Account") == 0) {
+      const rgw_owner& owner = bucket->get_owner();
+      if (const rgw_account_id* a = std::get_if<rgw_account_id>(&owner); a) {
+        pushstring(L, *a);
+      } else {
+        lua_pushnil(L);
+      }
     } else {
       return error_unknown_field(L, index, name);
     }
index 0cf888b7fffd9d49bad0ea7820ff7d1c1ad6b5f7..04f432c43036c2ed88121d3faa6a3cd13b2500de 100644 (file)
@@ -265,7 +265,7 @@ static int get_user_policy_from_attr(const DoutPrefixProvider *dpp,
 int rgw_op_get_bucket_policy_from_attr(const DoutPrefixProvider *dpp, 
                                        CephContext *cct,
                                       rgw::sal::Driver* driver,
-                                      const rgw_user& bucket_owner,
+                                      const rgw_owner& bucket_owner,
                                       map<string, bufferlist>& bucket_attrs,
                                       RGWAccessControlPolicy& policy,
                                       optional_yield y)
@@ -278,13 +278,7 @@ int rgw_op_get_bucket_policy_from_attr(const DoutPrefixProvider *dpp,
       return ret;
   } else {
     ldpp_dout(dpp, 0) << "WARNING: couldn't find acl header for bucket, generating default" << dendl;
-    std::unique_ptr<rgw::sal::User> user = driver->get_user(bucket_owner);
-    /* object exists, but policy is broken */
-    int r = user->load_user(dpp, y);
-    if (r < 0)
-      return r;
-
-    policy.create_default(user->get_id(), user->get_display_name());
+    policy.create_default(bucket_owner, "");
   }
   return 0;
 }
@@ -486,6 +480,42 @@ static int read_obj_policy(const DoutPrefixProvider *dpp,
   return ret;
 }
 
+// try to read swift account acls from the owning user
+static int get_swift_owner_account_acl(const DoutPrefixProvider* dpp,
+                                       optional_yield y,
+                                       rgw::sal::Driver* driver,
+                                       const ACLOwner& owner,
+                                       RGWAccessControlPolicy& policy)
+{
+  // only rgw_user owners support swift acls
+  const rgw_user* uid = std::get_if<rgw_user>(&owner.id);
+  if (uid == nullptr) {
+    return 0;
+  }
+  if (uid->empty()) {
+    return 0;
+  }
+
+  std::unique_ptr<rgw::sal::User> user = driver->get_user(*uid);
+  int ret = user->read_attrs(dpp, y);
+  if (!ret) {
+    ret = get_user_policy_from_attr(dpp, dpp->get_cct(),
+                                    user->get_attrs(), policy);
+  }
+  if (-ENOENT == ret) {
+    /* In already existing clusters users won't have ACL. In such case
+     * assuming that only account owner has the rights seems to be
+     * reasonable. That allows to have only one verification logic.
+     * NOTE: there is small compatibility kludge for global, empty tenant:
+     *  1. if we try to reach an existing bucket, its owner is considered
+     *     as account owner.
+     *  2. otherwise account owner is identity stored in s->owner. */
+    policy.create_default(owner.id, owner.display_name);
+    ret = 0;
+  }
+  return ret;
+}
+
 /**
  * Get the AccessControlPolicy for an user, bucket or object off of disk.
  * s: The req_state to draw information from.
@@ -588,24 +618,8 @@ int rgw_build_bucket_policies(const DoutPrefixProvider *dpp, rgw::sal::Driver* d
 
   /* handle user ACL only for those APIs which support it */
   if (s->dialect == "swift" && !s->user->get_id().empty()) {
-    std::unique_ptr<rgw::sal::User> acl_user = driver->get_user(acct_acl_user->id);
-
-    ret = acl_user->read_attrs(dpp, y);
-    if (!ret) {
-      ret = get_user_policy_from_attr(dpp, s->cct, acl_user->get_attrs(), s->user_acl);
-    }
-    if (-ENOENT == ret) {
-      /* In already existing clusters users won't have ACL. In such case
-       * assuming that only account owner has the rights seems to be
-       * reasonable. That allows to have only one verification logic.
-       * NOTE: there is small compatibility kludge for global, empty tenant:
-       *  1. if we try to reach an existing bucket, its owner is considered
-       *     as account owner.
-       *  2. otherwise account owner is identity stored in s->user->user_id.  */
-      s->user_acl.create_default(acct_acl_user->id,
-                                 acct_acl_user->display_name);
-      ret = 0;
-    } else if (ret < 0) {
+    ret = get_swift_owner_account_acl(dpp, y, driver, *acct_acl_user, s->user_acl);
+    if (ret < 0) {
       ldpp_dout(dpp, 0) << "NOTICE: couldn't get user attrs for handling ACL "
           "(user_id=" << s->user->get_id() << ", ret=" << ret << ")" << dendl;
       return ret;
@@ -1412,6 +1426,34 @@ int RGWOp::do_aws4_auth_completion()
   return 0;
 }
 
+static int get_owner_quota_info(DoutPrefixProvider* dpp,
+                                optional_yield y,
+                                rgw::sal::Driver* driver,
+                                const rgw_owner& owner,
+                                RGWQuota& quotas)
+{
+  return std::visit(fu2::overload(
+      [&] (const rgw_user& uid) {
+        auto user = driver->get_user(uid);
+        int r = user->load_user(dpp, y);
+        if (r >= 0) {
+          quotas = user->get_info().quota;
+        }
+        return r;
+      },
+      [&] (const rgw_account_id& account_id) {
+        RGWAccountInfo info;
+        rgw::sal::Attrs attrs; // ignored
+        RGWObjVersionTracker objv; // ignored
+        int r = driver->load_account_by_id(dpp, y, account_id, info, attrs, objv);
+        if (r >= 0) {
+          // no bucket quota
+          quotas.user_quota = info.quota;
+        }
+        return r;
+      }), owner);
+}
+
 int RGWOp::init_quota()
 {
   /* no quota enforcement for system requests */
@@ -1428,30 +1470,29 @@ int RGWOp::init_quota()
     return 0;
   }
 
-  std::unique_ptr<rgw::sal::User> owner_user =
-                       driver->get_user(s->bucket->get_info().owner);
-  rgw::sal::User* user;
+  RGWQuota user_quotas;
 
-  if (s->user->get_id() == s->bucket_owner.id) {
-    user = s->user.get();
+  if (s->owner.id == s->bucket_owner.id) {
+    user_quotas = s->user->get_info().quota;
   } else {
-    int r = owner_user->load_user(this, s->yield);
-    if (r < 0)
+    // consult the bucket owner's quota
+    int r = get_owner_quota_info(this, s->yield, driver,
+                                 s->bucket_owner.id, user_quotas);
+    if (r < 0) {
       return r;
-    user = owner_user.get();
-    
+    }
   }
 
   driver->get_quota(quota);
 
   if (s->bucket->get_info().quota.enabled) {
     quota.bucket_quota = s->bucket->get_info().quota;
-  } else if (user->get_info().quota.bucket_quota.enabled) {
-    quota.bucket_quota = user->get_info().quota.bucket_quota;
+  } else if (user_quotas.bucket_quota.enabled) {
+    quota.bucket_quota = user_quotas.bucket_quota;
   }
 
-  if (user->get_info().quota.user_quota.enabled) {
-    quota.user_quota = user->get_info().quota.user_quota;
+  if (user_quotas.user_quota.enabled) {
+    quota.user_quota = user_quotas.user_quota;
   }
 
   return 0;
@@ -3585,7 +3626,7 @@ void RGWCreateBucket::execute(optional_yield y)
       op_ret = s->bucket->load_bucket(this, y);
       if (op_ret < 0) {
         return;
-      } else if (s->bucket->get_owner() != s->user->get_id()) {
+      } else if (!s->auth.identity->is_owner_of(s->bucket->get_owner())) {
         /* New bucket doesn't belong to the account we're operating on. */
         op_ret = -EEXIST;
         return;
@@ -3679,7 +3720,7 @@ void RGWDeleteBucket::execute(optional_yield y)
     }
   }
 
-  op_ret = s->bucket->sync_user_stats(this, y, nullptr);
+  op_ret = s->bucket->sync_owner_stats(this, y, nullptr);
   if ( op_ret < 0) {
      ldpp_dout(this, 1) << "WARNING: failed to sync user stats before bucket delete: op_ret= " << op_ret << dendl;
   }
@@ -4191,7 +4232,8 @@ void RGWPutObj::execute(optional_yield y)
 
   /* Handle object versioning of Swift API. */
   if (! multipart) {
-    op_ret = s->object->swift_versioning_copy(s->owner, this, s->yield);
+    op_ret = s->object->swift_versioning_copy(s->owner, s->user->get_id(),
+                                              this, s->yield);
     if (op_ret < 0) {
       return;
     }
@@ -5323,7 +5365,8 @@ void RGWDeleteObj::execute(optional_yield y)
     s->object->set_atomic();
     
     bool ver_restored = false;
-    op_ret = s->object->swift_versioning_restore(s->owner, ver_restored, this, y);
+    op_ret = s->object->swift_versioning_restore(s->owner, s->user->get_id(),
+                                                 ver_restored, this, y);
     if (op_ret < 0) {
       return;
     }
@@ -5341,7 +5384,7 @@ void RGWDeleteObj::execute(optional_yield y)
 
       std::unique_ptr<rgw::sal::Object::DeleteOp> del_op = s->object->get_delete_op();
       del_op->params.obj_owner = s->owner;
-      del_op->params.bucket_owner = s->bucket_owner;
+      del_op->params.bucket_owner = s->bucket_owner.id;
       del_op->params.versioning_status = s->bucket->get_info().versioning_status();
       del_op->params.unmod_since = unmod_since;
       del_op->params.high_precision_time = s->system_request;
@@ -5799,12 +5842,14 @@ void RGWCopyObj::execute(optional_yield y)
 
   /* Handle object versioning of Swift API. In case of copying to remote this
    * should fail gently (op_ret == 0) as the dst_obj will not exist here. */
-  op_ret = s->object->swift_versioning_copy(s->owner, this, s->yield);
+  op_ret = s->object->swift_versioning_copy(s->owner, s->user->get_id(),
+                                            this, s->yield);
   if (op_ret < 0) {
     return;
   }
 
   op_ret = s->src_object->copy_object(s->owner,
+          s->user->get_id(),
           &s->info,
           source_zone,
           s->object.get(),
@@ -6012,7 +6057,7 @@ void RGWPutACLs::execute(optional_yield y)
   if (op_ret < 0)
     return;
 
-  if (!existing_owner.id.empty() &&
+  if (!existing_owner.empty() &&
       existing_owner.id != new_policy.get_owner().id) {
     s->err.message = "Cannot modify ACL Owner";
     op_ret = -EPERM;
@@ -7261,7 +7306,7 @@ void RGWDeleteMultiObj::handle_individual_object(const rgw_obj_key& o, optional_
   std::unique_ptr<rgw::sal::Object::DeleteOp> del_op = obj->get_delete_op();
   del_op->params.versioning_status = obj->get_bucket()->get_info().versioning_status();
   del_op->params.obj_owner = s->owner;
-  del_op->params.bucket_owner = s->bucket_owner;
+  del_op->params.bucket_owner = s->bucket_owner.id;
   del_op->params.marker_version_id = version_id;
 
   op_ret = del_op->delete_obj(this, y, rgw::sal::FLAG_LOG_OP);
@@ -7436,7 +7481,7 @@ bool RGWBulkDelete::Deleter::delete_single(const acct_path_t& path, optional_yie
     std::unique_ptr<rgw::sal::Object::DeleteOp> del_op = obj->get_delete_op();
     del_op->params.versioning_status = obj->get_bucket()->get_info().versioning_status();
     del_op->params.obj_owner = bowner;
-    del_op->params.bucket_owner = bucket_owner;
+    del_op->params.bucket_owner = bucket_owner.id;
 
     ret = del_op->delete_obj(dpp, y, rgw::sal::FLAG_LOG_OP);
     if (ret < 0) {
index b0f58c0969549a27ac00851b1b08e67163fcf236..ca9eb6a2294fe3f9becc68684305854b88e219b4 100644 (file)
@@ -596,9 +596,9 @@ int RGWOwnerStatsCache::sync_bucket(const rgw_owner& owner, const rgw_bucket& b,
   }
 
   RGWBucketEnt ent;
-  r = bucket->sync_user_stats(dpp, y, &ent);
+  r = bucket->sync_owner_stats(dpp, y, &ent);
   if (r < 0) {
-    ldpp_dout(dpp, 0) << "ERROR: sync_user_stats() for bucket=" << bucket << " returned " << r << dendl;
+    ldpp_dout(dpp, 0) << "ERROR: sync_owner_stats() for bucket=" << bucket << " returned " << r << dendl;
     return r;
   }
 
index 3a4abaabd2069cba352bda8e9680589349710199..56d2e4925f19431ceff47da6a2222e56a54bf23d 100644 (file)
@@ -505,7 +505,9 @@ void dump_owner(req_state *s, const std::string& id, const string& name,
     section = "Owner";
   s->formatter->open_object_section(section);
   s->formatter->dump_string("ID", id);
-  s->formatter->dump_string("DisplayName", name);
+  if (!name.empty()) {
+    s->formatter->dump_string("DisplayName", name);
+  }
   s->formatter->close_section();
 }
 
@@ -588,7 +590,7 @@ void end_header(req_state* s, RGWOp* op, const char *content_type,
   dump_trans_id(s);
 
   if ((!s->is_err()) && s->bucket &&
-      (s->bucket->get_info().owner != s->user->get_id()) &&
+      (!s->auth.identity->is_owner_of(s->bucket->get_info().owner)) &&
       (s->bucket->get_info().requester_pays)) {
     dump_header(s, "x-amz-request-charged", "requester");
   }
index be03ad172e1cfbd49256cabcddd42348c67bffc6..e700886ca5b76cbbccdaf1cbc000779fb60c7640 100644 (file)
@@ -2338,9 +2338,9 @@ static void dump_bucket_metadata(req_state *s, rgw::sal::Bucket* bucket,
   dump_header(s, "X-RGW-Bytes-Used", static_cast<long long>(stats.size));
 
   // only bucket's owner is allowed to get the quota settings of the account
-  if (bucket->get_owner() == s->user->get_id()) {
-    auto user_info = s->user->get_info();
-    auto bucket_quota = s->bucket->get_info().quota; // bucket quota
+  if (s->auth.identity->is_owner_of(bucket->get_owner())) {
+    const auto& user_info = s->user->get_info();
+    const auto& bucket_quota = s->bucket->get_info().quota; // bucket quota
     dump_header(s, "X-RGW-Quota-User-Size", static_cast<long long>(user_info.quota.user_quota.max_size));
     dump_header(s, "X-RGW-Quota-User-Objects", static_cast<long long>(user_info.quota.user_quota.max_objects));
     dump_header(s, "X-RGW-Quota-Max-Buckets", static_cast<long long>(user_info.max_buckets));
index f6bb52e2d1a047175a869e98aa5ea158e8f77414..fe366acf8563a27b8be037540af58758a6d7c5b2 100644 (file)
@@ -2227,10 +2227,17 @@ void RGWFormPost::get_owner_info(const req_state* const s,
     throw ret;
   }
 
-  ldpp_dout(this, 20) << "temp url user (bucket owner): " << bucket->get_info().owner
-                 << dendl;
+  const rgw_owner& owner = bucket->get_owner();
+  const rgw_user* uid = std::get_if<rgw_user>(&owner);
+  if (!uid) {
+    ldpp_dout(this, 20) << "bucket " << *bucket <<  " is not owned by a user "
+        "so has no temp url keys" << dendl;
+    throw -EPERM;
+  }
+
+  ldpp_dout(this, 20) << "temp url user (bucket owner): " << *uid << dendl;
 
-  user = driver->get_user(bucket->get_info().owner);
+  user = driver->get_user(*uid);
   if (user->load_user(s, s->yield) < 0) {
     throw -EPERM;
   }
index 02c7b3c9048bddeb89b35eaf29121839429fc811..5a49610513259081421b2cd03474feaf20d81417 100644 (file)
@@ -738,7 +738,7 @@ class Bucket {
 
     /// Input parameters for create().
     struct CreateParams {
-      rgw_user owner;
+      rgw_owner owner;
       std::string zonegroup_id;
       rgw_placement_rule placement_rule;
       // zone placement is optional on buckets created for another zonegroup
@@ -772,18 +772,18 @@ class Bucket {
                                 const bucket_index_layout_generation& idx_layout,
                                 int shard_id, boost::intrusive_ptr<ReadStatsCB> cb) = 0;
     /** Sync this bucket's stats to the owning user's stats in the backing store */
-    virtual int sync_user_stats(const DoutPrefixProvider *dpp, optional_yield y,
-                                RGWBucketEnt* optional_ent) = 0;
+    virtual int sync_owner_stats(const DoutPrefixProvider *dpp, optional_yield y,
+                                 RGWBucketEnt* optional_ent) = 0;
     /** Check if this bucket needs resharding, and schedule it if it does */
     virtual int check_bucket_shards(const DoutPrefixProvider* dpp,
                                     uint64_t num_objs, optional_yield y) = 0;
     /** Change the owner of this bucket in the backing store.  Current owner must be set.  Does not
      * change ownership of the objects in the bucket. */
-    virtual int chown(const DoutPrefixProvider* dpp, const rgw_user& new_owner, optional_yield y) = 0;
+    virtual int chown(const DoutPrefixProvider* dpp, const rgw_owner& new_owner, optional_yield y) = 0;
     /** Store the cached bucket info into the backing store */
     virtual int put_info(const DoutPrefixProvider* dpp, bool exclusive, ceph::real_time mtime, optional_yield y) = 0;
     /** Get the owner of this bucket */
-    virtual const rgw_user& get_owner() const = 0;
+    virtual const rgw_owner& get_owner() const = 0;
     /** Check in the backing store if this bucket is empty */
     virtual int check_empty(const DoutPrefixProvider* dpp, optional_yield y) = 0;
     /** Check if the given size fits within the quota */
@@ -965,8 +965,8 @@ class Object {
      */
     struct DeleteOp {
       struct Params {
-        ACLOwner bucket_owner;
-        ACLOwner obj_owner;
+        rgw_owner bucket_owner; //< bucket owner for usage/quota accounting
+        ACLOwner obj_owner; //< acl owner for delete marker if necessary
         int versioning_status{0};
         uint64_t olh_epoch{0};
        std::string marker_version_id;
@@ -1000,7 +1000,7 @@ class Object {
                              optional_yield y,
                              uint32_t flags) = 0;
     /** Copy an this object to another object. */
-    virtual int copy_object(const ACLOwner& owner,
+    virtual int copy_object(const ACLOwner& owner, const rgw_user& remote_user,
                req_info* info, const rgw_zone_id& source_zone,
                rgw::sal::Object* dest_object, rgw::sal::Bucket* dest_bucket,
                rgw::sal::Bucket* src_bucket,
@@ -1122,10 +1122,15 @@ class Object {
     virtual rgw_obj get_obj(void) const = 0;
 
     /** Restore the previous swift version of this object */
-    virtual int swift_versioning_restore(const ACLOwner& owner, bool& restored,   /* out */
-                                        const DoutPrefixProvider* dpp, optional_yield y) = 0;
+    virtual int swift_versioning_restore(const ACLOwner& owner,
+                                         const rgw_user& remote_user,
+                                         bool& restored,
+                                         const DoutPrefixProvider* dpp,
+                                         optional_yield y) = 0;
     /** Copy the current version of a swift object to the configured destination bucket*/
-    virtual int swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
+    virtual int swift_versioning_copy(const ACLOwner& owner,
+                                      const rgw_user& remote_user,
+                                     const DoutPrefixProvider* dpp,
                                      optional_yield y) = 0;
 
     /** Get a new ReadOp for this object */
index ee5f5a1f2ebe62f214e6ad252db0eb2fc808fa48..fd7a268fb7a37f839bbb0f7adbe2c01846c19a9e 100644 (file)
@@ -39,7 +39,8 @@ namespace rgw::sal {
     RGWUserBuckets ulist;
     bool is_truncated = false;
 
-    int ret = store->getDB()->list_buckets(dpp, "", info.user_id, marker,
+    std::string owner = info.user_id.to_str();
+    int ret = store->getDB()->list_buckets(dpp, "", owner, marker,
         end_marker, max, need_stats, &ulist, &is_truncated);
     if (ret < 0)
       return ret;
@@ -226,8 +227,8 @@ namespace rgw::sal {
     return 0;
   }
 
-  int DBBucket::sync_user_stats(const DoutPrefixProvider *dpp, optional_yield y,
-                                RGWBucketEnt* ent)
+  int DBBucket::sync_owner_stats(const DoutPrefixProvider *dpp, optional_yield y,
+                                 RGWBucketEnt* ent)
   {
     return 0;
   }
@@ -238,7 +239,7 @@ namespace rgw::sal {
     return 0;
   }
 
-  int DBBucket::chown(const DoutPrefixProvider *dpp, const rgw_user& new_owner, optional_yield y)
+  int DBBucket::chown(const DoutPrefixProvider *dpp, const rgw_owner& new_owner, optional_yield y)
   {
     int ret;
 
@@ -702,7 +703,6 @@ namespace rgw::sal {
 
   int DBObject::DBDeleteOp::delete_obj(const DoutPrefixProvider* dpp, optional_yield y, uint32_t flags)
   {
-    parent_op.params.bucket_owner = params.bucket_owner.id;
     parent_op.params.versioning_status = params.versioning_status;
     parent_op.params.obj_owner = params.obj_owner;
     parent_op.params.olh_epoch = params.olh_epoch;
@@ -732,13 +732,13 @@ namespace rgw::sal {
     DB::Object del_target(store->getDB(), bucket->get_info(), get_obj());
     DB::Object::Delete del_op(&del_target);
 
-    del_op.params.bucket_owner = bucket->get_info().owner;
     del_op.params.versioning_status = bucket->get_info().versioning_status();
 
     return del_op.delete_obj(dpp);
   }
 
   int DBObject::copy_object(const ACLOwner& owner,
+      const rgw_user& remote_user,
       req_info* info,
       const rgw_zone_id& source_zone,
       rgw::sal::Object* dest_object,
@@ -774,14 +774,16 @@ namespace rgw::sal {
     return parent_op.iterate(dpp, ofs, end, cb);
   }
 
-  int DBObject::swift_versioning_restore(const ACLOwner& owner, bool& restored,
+  int DBObject::swift_versioning_restore(const ACLOwner& owner,
+      const rgw_user& remote_user, bool& restored,
       const DoutPrefixProvider* dpp, optional_yield y)
   {
     return 0;
   }
 
-  int DBObject::swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
-      optional_yield y)
+  int DBObject::swift_versioning_copy(const ACLOwner& owner,
+      const rgw_user& remote_user,
+      const DoutPrefixProvider* dpp, optional_yield y)
   {
     return 0;
   }
@@ -794,7 +796,7 @@ namespace rgw::sal {
     int ret;
 
     std::unique_ptr<rgw::sal::Object::DeleteOp> del_op = meta_obj->get_delete_op();
-    del_op->params.bucket_owner.id = bucket->get_info().owner;
+    del_op->params.bucket_owner = bucket->get_info().owner;
     del_op->params.versioning_status = 0;
 
     // Since the data objects are associated with meta obj till
@@ -834,7 +836,7 @@ namespace rgw::sal {
     DB::Object::Write obj_op(&op_target);
 
     /* Create meta object */
-    obj_op.meta.owner = owner.id;
+    obj_op.meta.owner = to_string(owner.id);
     obj_op.meta.category = RGWObjCategory::MultiMeta;
     obj_op.meta.flags = PUT_OBJ_CREATE_EXCL;
     obj_op.meta.mtime = &mtime;
@@ -1013,7 +1015,7 @@ namespace rgw::sal {
     DB::Object::Write obj_op(&op_target);
     ret = obj_op.prepare(dpp);
 
-    obj_op.meta.owner = owner.id;
+    obj_op.meta.owner = to_string(owner.id);
     obj_op.meta.flags = PUT_OBJ_CREATE;
     obj_op.meta.category = RGWObjCategory::Main;
     obj_op.meta.modify_tail = true;
index aa971d1cdf08b1189d86e4061b0b448a2874dc60..8df568e3c9d1434ed46e9c33d75a834e861fc954 100644 (file)
@@ -158,11 +158,11 @@ protected:
           std::string *max_marker = nullptr,
           bool *syncstopped = nullptr) override;
       virtual int read_stats_async(const DoutPrefixProvider *dpp, const bucket_index_layout_generation& idx_layout, int shard_id, boost::intrusive_ptr<ReadStatsCB> ctx) override;
-      int sync_user_stats(const DoutPrefixProvider *dpp, optional_yield y,
-                          RGWBucketEnt* ent) override;
+      int sync_owner_stats(const DoutPrefixProvider *dpp, optional_yield y,
+                           RGWBucketEnt* ent) override;
       int check_bucket_shards(const DoutPrefixProvider *dpp,
                               uint64_t num_objs, optional_yield y) override;
-      virtual int chown(const DoutPrefixProvider *dpp, const rgw_user& new_owner, optional_yield y) override;
+      virtual int chown(const DoutPrefixProvider *dpp, const rgw_owner& new_owner, optional_yield y) override;
       virtual int put_info(const DoutPrefixProvider *dpp, bool exclusive, ceph::real_time mtime, optional_yield y) override;
       virtual int check_empty(const DoutPrefixProvider *dpp, optional_yield y) override;
       virtual int check_quota(const DoutPrefixProvider *dpp, RGWQuota& quota, uint64_t obj_size, optional_yield y, bool check_size_only = false) override;
@@ -547,6 +547,7 @@ protected:
           optional_yield y,
           uint32_t flags) override;
       virtual int copy_object(const ACLOwner& owner,
+          const rgw_user& remote_user,
           req_info* info, const rgw_zone_id& source_zone,
           rgw::sal::Object* dest_object, rgw::sal::Bucket* dest_bucket,
           rgw::sal::Bucket* src_bucket,
@@ -587,9 +588,11 @@ protected:
       virtual int dump_obj_layout(const DoutPrefixProvider *dpp, optional_yield y, Formatter* f) override;
 
       /* Swift versioning */
-      virtual int swift_versioning_restore(const ACLOwner& owner, bool& restored,
+      virtual int swift_versioning_restore(const ACLOwner& owner,
+          const rgw_user& remote_user, bool& restored,
           const DoutPrefixProvider* dpp, optional_yield y) override;
-      virtual int swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
+      virtual int swift_versioning_copy(const ACLOwner& owner,
+          const rgw_user& remote_user, const DoutPrefixProvider* dpp,
           optional_yield y) override;
 
       /* OPs */
index 78dfc9f28aa85d4579f82c5f18c1a3ee3ccb06e3..358f3a9ae38e09249f5d36150d8dadf3690b15f4 100644 (file)
@@ -682,10 +682,10 @@ int FilterBucket::read_stats_async(const DoutPrefixProvider *dpp,
   return next->read_stats_async(dpp, idx_layout, shard_id, ctx);
 }
 
-int FilterBucket::sync_user_stats(const DoutPrefixProvider *dpp, optional_yield y,
-                                  RGWBucketEnt* ent)
+int FilterBucket::sync_owner_stats(const DoutPrefixProvider *dpp, optional_yield y,
+                                   RGWBucketEnt* ent)
 {
-  return next->sync_user_stats(dpp, y, ent);
+  return next->sync_owner_stats(dpp, y, ent);
 }
 
 int FilterBucket::check_bucket_shards(const DoutPrefixProvider* dpp,
@@ -694,7 +694,7 @@ int FilterBucket::check_bucket_shards(const DoutPrefixProvider* dpp,
   return next->check_bucket_shards(dpp, num_objs, y);
 }
 
-int FilterBucket::chown(const DoutPrefixProvider* dpp, const rgw_user& new_owner, optional_yield y)
+int FilterBucket::chown(const DoutPrefixProvider* dpp, const rgw_owner& new_owner, optional_yield y)
 {
   return next->chown(dpp, new_owner, y);
 }
@@ -705,7 +705,7 @@ int FilterBucket::put_info(const DoutPrefixProvider* dpp, bool exclusive,
   return next->put_info(dpp, exclusive, _mtime, y);
 }
 
-const rgw_user& FilterBucket::get_owner() const
+const rgw_owner& FilterBucket::get_owner() const
 {
   return next->get_owner();
 }
@@ -825,6 +825,7 @@ int FilterObject::delete_object(const DoutPrefixProvider* dpp,
 }
 
 int FilterObject::copy_object(const ACLOwner& owner,
+                             const rgw_user& remote_user,
                              req_info* info,
                              const rgw_zone_id& source_zone,
                              rgw::sal::Object* dest_object,
@@ -852,7 +853,7 @@ int FilterObject::copy_object(const ACLOwner& owner,
                              const DoutPrefixProvider* dpp,
                              optional_yield y)
 {
-  return next->copy_object(owner, info, source_zone,
+  return next->copy_object(owner, remote_user, info, source_zone,
                           nextObject(dest_object),
                           nextBucket(dest_bucket),
                           nextBucket(src_bucket),
@@ -957,16 +958,21 @@ void FilterObject::set_bucket(Bucket* b)
   next->set_bucket(nextBucket(b));
 };
 
-int FilterObject::swift_versioning_restore(const ACLOwner& owner, bool& restored,
-                                          const DoutPrefixProvider* dpp, optional_yield y)
+int FilterObject::swift_versioning_restore(const ACLOwner& owner,
+                                           const rgw_user& remote_user,
+                                           bool& restored,
+                                           const DoutPrefixProvider* dpp,
+                                           optional_yield y)
 {
-  return next->swift_versioning_restore(owner, restored, dpp, y);
+  return next->swift_versioning_restore(owner, remote_user, restored, dpp, y);
 }
 
-int FilterObject::swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
-                                       optional_yield y)
+int FilterObject::swift_versioning_copy(const ACLOwner& owner,
+                                        const rgw_user& remote_user,
+                                        const DoutPrefixProvider* dpp,
+                                        optional_yield y)
 {
-  return next->swift_versioning_copy(owner, dpp, y);
+  return next->swift_versioning_copy(owner, remote_user, dpp, y);
 }
 
 std::unique_ptr<Object::ReadOp> FilterObject::get_read_op()
index 5c4e632724560da93b9596a58e355075b4c130ca..d896f9999235d7a9d9ff428118ff7c0d8715d28e 100644 (file)
@@ -486,15 +486,15 @@ public:
   virtual int read_stats_async(const DoutPrefixProvider *dpp,
                               const bucket_index_layout_generation& idx_layout,
                               int shard_id, boost::intrusive_ptr<ReadStatsCB> ctx) override;
-  int sync_user_stats(const DoutPrefixProvider *dpp, optional_yield y,
-                      RGWBucketEnt* ent) override;
+  int sync_owner_stats(const DoutPrefixProvider *dpp, optional_yield y,
+                       RGWBucketEnt* ent) override;
   int check_bucket_shards(const DoutPrefixProvider* dpp,
                           uint64_t num_objs, optional_yield y) override;
-  virtual int chown(const DoutPrefixProvider* dpp, const rgw_user& new_owner,
+  virtual int chown(const DoutPrefixProvider* dpp, const rgw_owner& new_owner,
                    optional_yield y) override;
   virtual int put_info(const DoutPrefixProvider* dpp, bool exclusive,
                       ceph::real_time mtime, optional_yield y) override;
-  virtual const rgw_user& get_owner() const override;
+  virtual const rgw_owner& get_owner() const override;
   virtual int check_empty(const DoutPrefixProvider* dpp, optional_yield y) override;
   virtual int check_quota(const DoutPrefixProvider *dpp, RGWQuota& quota,
                          uint64_t obj_size, optional_yield y,
@@ -625,6 +625,7 @@ public:
                            optional_yield y,
                            uint32_t flags) override;
   virtual int copy_object(const ACLOwner& owner,
+               const rgw_user& remote_user,
                req_info* info, const rgw_zone_id& source_zone,
               rgw::sal::Object* dest_object, rgw::sal::Bucket* dest_bucket,
                rgw::sal::Bucket* src_bucket,
@@ -712,10 +713,15 @@ public:
   virtual bool have_instance(void) override { return next->have_instance(); }
   virtual void clear_instance() override { return next->clear_instance(); }
 
-  virtual int swift_versioning_restore(const ACLOwner& owner, bool& restored,   /* out */
-                                      const DoutPrefixProvider* dpp, optional_yield y) override;
-  virtual int swift_versioning_copy(const ACLOwner& owner, const DoutPrefixProvider* dpp,
-                                   optional_yield y) override;
+  virtual int swift_versioning_restore(const ACLOwner& owner,
+                                       const rgw_user& remote_user,
+                                       bool& restored,
+                                       const DoutPrefixProvider* dpp,
+                                       optional_yield y) override;
+  virtual int swift_versioning_copy(const ACLOwner& owner,
+                                    const rgw_user& remote_user,
+                                    const DoutPrefixProvider* dpp,
+                                    optional_yield y) override;
 
   virtual std::unique_ptr<ReadOp> get_read_op() override;
   virtual std::unique_ptr<DeleteOp> get_delete_op() override;
index 1ba44bc02ec4af18420da094c7b8a1fd2aa68c42..8bfff8025260e4e1b4c0ccf1dcc1027c99d985d4 100644 (file)
@@ -135,7 +135,7 @@ class StoreBucket : public Bucket {
 
     virtual Attrs& get_attrs(void) override { return attrs; }
     virtual int set_attrs(Attrs a) override { attrs = a; return 0; }
-    virtual const rgw_user& get_owner() const override { return info.owner; };
+    virtual const rgw_owner& get_owner() const override { return info.owner; }
     virtual bool empty() const override { return info.bucket.name.empty(); }
     virtual const std::string& get_name() const override { return info.bucket.name; }
     virtual const std::string& get_tenant() const override { return info.bucket.tenant; }
index aa31adc1d0a4563d718efdaecd09159fdc83c927..9edf257b6b80bf2baba66c2f279f88cb4d6a74e2 100644 (file)
@@ -124,11 +124,16 @@ void TempURLEngine::get_owner_info(const DoutPrefixProvider* dpp, const req_stat
     throw ret;
   }
 
+  const rgw_user* uid = std::get_if<rgw_user>(&bucket->get_info().owner);
+  if (!uid) {
+    throw -EPERM;
+  }
+
   ldpp_dout(dpp, 20) << "temp url user (bucket owner): " << bucket->get_info().owner
                  << dendl;
 
   std::unique_ptr<rgw::sal::User> user;
-  user = driver->get_user(bucket->get_info().owner);
+  user = driver->get_user(*uid);
   if (user->load_user(dpp, s->yield) < 0) {
     throw -EPERM;
   }
index 02403e5f342e454511794490e612e72f39657308..d77b50a111737f6e540bd949714d4862734b5352 100644 (file)
@@ -35,7 +35,7 @@ int rgw_user_sync_all_stats(const DoutPrefixProvider *dpp, rgw::sal::Driver* dri
         ldpp_dout(dpp, 0) << "ERROR: could not read bucket info: bucket=" << bucket << " ret=" << ret << dendl;
         continue;
       }
-      ret = bucket->sync_user_stats(dpp, y, &ent);
+      ret = bucket->sync_owner_stats(dpp, y, &ent);
       if (ret < 0) {
         ldpp_dout(dpp, 0) << "ERROR: could not sync bucket stats: ret=" << ret << dendl;
         return ret;
index ed60fb9ec1f445cb59b85eabe49c2f8b6289697d..57bfc08ea3503b310184d7cd482e60fa043734ec 100644 (file)
@@ -367,8 +367,7 @@ TEST(TestRGWLua, Bucket)
   info.bucket.name = "myname";
   info.bucket.marker = "mymarker";
   info.bucket.bucket_id = "myid";
-  info.owner.id = "myuser";
-  info.owner.tenant = "mytenant";
+  info.owner = rgw_user{"mytenant", "myuser"};
   s.bucket.reset(new sal::RadosBucket(nullptr, info));
 
   const auto rc = lua::request::execute(nullptr, nullptr, nullptr, &s, nullptr, script);
@@ -672,8 +671,7 @@ TEST(TestRGWLua, Acl)
     end
 
     assert(Request.UserAcl.Owner.DisplayName == "jack black", Request.UserAcl.Owner.DisplayName)
-    assert(Request.UserAcl.Owner.User.Id == "black", Request.UserAcl.Owner.User.Id)
-    assert(Request.UserAcl.Owner.User.Tenant == "jack", Request.UserAcl.Owner.User.Tenant)
+    assert(Request.UserAcl.Owner.User == "jack$black", Request.UserAcl.Owner.User)
     assert(#Request.UserAcl.Grants == 7)
     print_grant("", Request.UserAcl.Grants[""])
     for k, v in pairs(Request.UserAcl.Grants) do
@@ -735,8 +733,7 @@ TEST(TestRGWLua, UseFunction)
        const std::string script = R"(
                function print_owner(owner)
                print("Owner Display Name: " .. owner.DisplayName)
-               print("Owner Id: " .. owner.User.Id)
-               print("Owner Tenanet: " .. owner.User.Tenant)
+               print("Owner Id: " .. owner.User)
                end
 
                print_owner(Request.ObjectOwner)
@@ -1586,8 +1583,7 @@ TEST(TestRGWLua, DifferentContextUser)
   s.user.reset(new sal::RadosUser(nullptr, rgw_user("tenant1", "user1")));
   RGWBucketInfo info;
   info.bucket.name = "bucket1";
-  info.owner.id = "user2";
-  info.owner.tenant = "tenant2";
+  info.owner = rgw_user{"tenant2", "user2"};
   s.bucket.reset(new sal::RadosBucket(nullptr, info));
 
   const auto rc = lua::request::execute(nullptr, nullptr, nullptr, &s, nullptr, script);