]> git.apps.os.sepia.ceph.com Git - ceph.git/commitdiff
rgw: set keys from from master zone on admin api user modify 48731/head
authorAli Maredia <amaredia@redhat.com>
Tue, 29 Nov 2022 22:31:25 +0000 (17:31 -0500)
committerAli Maredia <amaredia@redhat.com>
Tue, 24 Jan 2023 21:01:34 +0000 (16:01 -0500)
When users were being modified via the admin_api
to generate keys on a secondary zone, the keys
returned in the json output are not correct.

This commit ensures the proper keys are set to be
returned to the user via the json output.

fixes: https://tracker.ceph.com/issues/57724

Signed-off-by: Ali Maredia <amaredia@redhat.com>
src/rgw/driver/rados/rgw_rest_user.cc
src/rgw/driver/rados/rgw_user.cc
src/rgw/driver/rados/rgw_user.h

index 0befc1ee43a64b1b199187cc5b389d5ab48a6d3e..361ceb0f70fcb54e4b0817aad196344d2d6ab1ee 100644 (file)
 
 using namespace std;
 
+int fetch_access_keys_from_master(const DoutPrefixProvider *dpp, rgw::sal::Driver* driver, RGWUserAdminOpState &op_state, req_state *s, optional_yield y) {
+    bufferlist data;
+    JSONParser jp;
+    RGWUserInfo ui;
+    int op_ret = driver->forward_request_to_master(s, s->user.get(), nullptr, data, &jp, s->info, y);
+    if (op_ret < 0) {
+      ldpp_dout(dpp, 0) << "forward_request_to_master returned ret=" << op_ret << dendl;
+      return op_ret;
+    }
+    ui.decode_json(&jp);
+    op_state.op_access_keys = std::move(ui.access_keys);
+
+    return 0;
+}
+
 class RGWOp_User_List : public RGWRESTOp {
 
 public:
@@ -223,28 +238,22 @@ void RGWOp_User_Create::execute(optional_yield y)
     op_state.set_placement_tags(placement_tags_list);
   }
 
-  if(!(store->is_meta_master())) {
-    bufferlist data;
-    JSONParser jp;
-    RGWUserInfo ui;
-    op_ret = store->forward_request_to_master(s, s->user.get(), nullptr, data, &jp, s->info, y);
-    if (op_ret < 0) {
-      ldpp_dout(this, 0) << "forward_request_to_master returned ret=" << op_ret << dendl;
+  if(!(driver->is_meta_master())) {
+    op_ret = fetch_access_keys_from_master(this, driver, op_state, s, y);
+
+    if(op_ret < 0) {
       return;
+    } else {
+      // set_generate_key() is not set if keys have already been fetched from master zone
+      gen_key = false;
     }
-    ui.decode_json(&jp);
-    std::map<std::string, RGWAccessKey> keys = ui.access_keys;
-    auto keys_itr = keys.begin();
-    RGWAccessKey first_key = keys_itr->second;
-    op_state.id = first_key.id;
-    op_state.key = first_key.key;
   }
 
   if (gen_key) {
     op_state.set_generate_key();
   }
 
-  op_ret = RGWUserAdminOp_User::create(s, store, op_state, flusher, y);
+  op_ret = RGWUserAdminOp_User::create(s, driver, op_state, flusher, y);
 }
 
 class RGWOp_User_Modify : public RGWRESTOp {
@@ -320,8 +329,6 @@ void RGWOp_User_Modify::execute(optional_yield y)
     }
     op_state.set_max_buckets(max_buckets);
   }
-  if (gen_key)
-    op_state.set_generate_key();
 
   if (!key_type_str.empty()) {
     int32_t key_type = KEY_TYPE_UNDEFINED;
@@ -377,12 +384,21 @@ void RGWOp_User_Modify::execute(optional_yield y)
     op_state.set_placement_tags(placement_tags_list);
   }
   
-  bufferlist data;
-  op_ret = driver->forward_request_to_master(s, s->user.get(), nullptr, data, nullptr, s->info, y);
-  if (op_ret < 0) {
-    ldpp_dout(this, 0) << "forward_request_to_master returned ret=" << op_ret << dendl;
-    return;
+  if(!(driver->is_meta_master())) {
+    op_ret = fetch_access_keys_from_master(this, driver, op_state, s, y);
+
+    if(op_ret < 0) {
+      return;
+    } else {
+      // set_generate_key() is not set if keys have already been fetched from master zone
+      gen_key = false;
+    }
+  }
+
+  if (gen_key) {
+    op_state.set_generate_key();
   }
+
   op_ret = RGWUserAdminOp_User::modify(s, driver, op_state, flusher, y);
 }
 
index 7aefcfd5ddaee329f3e8b7e5950b0c49e866e28e..51b38c0829d1c53933d39fe39dab066e2b37af4c 100644 (file)
@@ -1439,6 +1439,12 @@ int RGWUser::update(const DoutPrefixProvider *dpp, RGWUserAdminOpState& op_state
     return -EINVAL;
   }
 
+  // if op_state.op_access_keys is not empty most recent keys have been fetched from master zone
+  if(!op_state.op_access_keys.empty()) {
+    auto user_access_keys = op_state.get_access_keys();
+    *(user_access_keys) = op_state.op_access_keys;
+  }
+
   RGWUserInfo *pold_info = (is_populated() ? &old_info : nullptr);
 
   ret = user->store_user(dpp, y, false, pold_info);
index 83e3720f71bd29805bc2b466cdae1bc3600d6a6a..ea05de8063df7a73625862e35d3cad8fa58b23b4 100644 (file)
@@ -125,6 +125,8 @@ struct RGWUserAdminOpState {
   // key_attributes
   std::string id; // access key
   std::string key; // secret key
+  // access keys fetched for a user in the middle of an op
+  std::map<std::string, RGWAccessKey> op_access_keys;
   int32_t key_type{-1};
   bool access_key_exist = false;