]> git-server-git.apps.pok.os.sepia.ceph.com Git - ceph.git/commitdiff
src/tools/rbd: add group info command to output group id 57759/head
authorjunxiang Mu <1948535941@qq.com>
Wed, 29 May 2024 08:15:20 +0000 (04:15 -0400)
committerjunxiang Mu <1948535941@qq.com>
Thu, 6 Jun 2024 08:39:24 +0000 (16:39 +0800)
Fixes: https://tracker.ceph.com/issues/66010
Signed-off-by: junxiang Mu <1948535941@qq.com>
12 files changed:
src/include/rbd/librbd.h
src/include/rbd/librbd.hpp
src/librbd/api/Group.cc
src/librbd/api/Group.h
src/librbd/librbd.cc
src/pybind/rbd/c_rbd.pxd
src/pybind/rbd/mock_rbd.pxi
src/pybind/rbd/rbd.pyx
src/test/cli/rbd/help.t
src/test/librbd/test_Groups.cc
src/test/pybind/test_rbd.py
src/tools/rbd/action/Group.cc

index 4a7e108e73f58053ade2fd77e40b135194bdb5cc..e94a72a719b34eca7044cef983976b68c3ff2979 100644 (file)
@@ -1377,6 +1377,8 @@ CEPH_RBD_API int rbd_aio_mirror_image_create_snapshot(rbd_image_t image,
 CEPH_RBD_API int rbd_group_create(rados_ioctx_t p, const char *name);
 CEPH_RBD_API int rbd_group_remove(rados_ioctx_t p, const char *name);
 CEPH_RBD_API int rbd_group_list(rados_ioctx_t p, char *names, size_t *size);
+CEPH_RBD_API int rbd_group_get_id(rados_ioctx_t p, const char *group_name,
+                                  char *group_id, size_t *size);
 CEPH_RBD_API int rbd_group_rename(rados_ioctx_t p, const char *src_name,
                                   const char *dest_name);
 CEPH_RBD_API int rbd_group_info_cleanup(rbd_group_info_t *group_info,
index 6d97d1087adf6fc4cd5063323f0f60111508c92f..9224c850c55951545e6a0fe6fd5c09dd338f0932 100644 (file)
@@ -410,6 +410,8 @@ public:
   int group_create(IoCtx& io_ctx, const char *group_name);
   int group_remove(IoCtx& io_ctx, const char *group_name);
   int group_list(IoCtx& io_ctx, std::vector<std::string> *names);
+  int group_get_id(IoCtx& io_ctx, const char *group_name,
+                   std::string *group_id);
   int group_rename(IoCtx& io_ctx, const char *src_group_name,
                    const char *dest_group_name);
 
index 06d38fe85007354afb67bc8f0ce12b321e400755..afa5b0aff032b495a3dc1edfc84ae0ea50d8ce0a 100644 (file)
@@ -648,6 +648,24 @@ int Group<I>::list(IoCtx& io_ctx, vector<string> *names)
   return 0;
 }
 
+template <typename I>
+int Group<I>::get_id(IoCtx& io_ctx, const char *group_name,
+                     std::string *group_id)
+{
+  CephContext *cct = (CephContext *)io_ctx.cct();
+  ldout(cct, 20) << "io_ctx=" << &io_ctx << dendl;
+
+  int r = cls_client::dir_get_id(&io_ctx, RBD_GROUP_DIRECTORY, group_name,
+                                 group_id);
+  if (r < 0) {
+    lderr(cct) << "error reading group id object: "
+              << cpp_strerror(r) << dendl;
+    return r;
+  }
+
+  return 0;
+}
+
 template <typename I>
 int Group<I>::image_add(librados::IoCtx& group_ioctx, const char *group_name,
                        librados::IoCtx& image_ioctx, const char *image_name)
index 9d3abcc59e832f8846a162b29d7f60ec23870a28..98833eb506f541fb3d6744bc9007dede5faf6b84 100644 (file)
@@ -21,6 +21,8 @@ struct Group {
   static int create(librados::IoCtx& io_ctx, const char *group_name);
   static int remove(librados::IoCtx& io_ctx, const char *group_name);
   static int list(librados::IoCtx& io_ctx, std::vector<std::string> *names);
+  static int get_id(librados::IoCtx& io_ctx, const char *group_name,
+                    std::string *group_id);
   static int rename(librados::IoCtx& io_ctx, const char *src_group_name,
                     const char *dest_group_name);
 
index 8749a04d2d5edfbd930ea5505795ee5e6c462d04..2fccdf5abb46afd31e1c254d1afecafa823bb351 100644 (file)
@@ -1292,6 +1292,11 @@ namespace librbd {
     return r;
   }
 
+  int RBD::group_get_id(IoCtx& io_ctx, const char *group_name, std::string *group_id)
+  {
+    return librbd::api::Group<>::get_id(io_ctx, group_name, group_id);
+  }
+
   int RBD::group_rename(IoCtx& io_ctx, const char *src_name,
                         const char *dest_name)
   {
@@ -6923,6 +6928,31 @@ extern "C" int rbd_group_rename(rados_ioctx_t p, const char *src_name,
   return r;
 }
 
+extern "C" int rbd_group_get_id(rados_ioctx_t p,
+                                const char *group_name,
+                                char *group_id,
+                                size_t *size)
+{
+  librados::IoCtx io_ctx;
+  librados::IoCtx::from_rados_ioctx_t(p, io_ctx);
+
+  std::string cpp_id;
+  int r = librbd::api::Group<>::get_id(io_ctx, group_name, &cpp_id);
+  if (r < 0) {
+    return r;
+  }
+
+  auto total_len = cpp_id.size() + 1;
+  if (*size < total_len) {
+    *size = total_len;
+    return -ERANGE;
+  }
+  *size = total_len;
+
+  strcpy(group_id, cpp_id.c_str());
+  return 0;
+}
+
 extern "C" int rbd_group_image_add(rados_ioctx_t group_p,
                                    const char *group_name,
                                    rados_ioctx_t image_p,
index c451baac58eef62ca4252eb16e42f6a0e3a93e67..e7d1958bf31cf3c5a0b5eeedd640c70a084f009f 100644 (file)
@@ -662,6 +662,8 @@ cdef extern from "rbd/librbd.h" nogil:
     int rbd_group_create(rados_ioctx_t p, const char *name)
     int rbd_group_remove(rados_ioctx_t p, const char *name)
     int rbd_group_list(rados_ioctx_t p, char *names, size_t *size)
+    int rbd_group_get_id(rados_ioctx_t p, const char *group_name,
+                         char *group_id, size_t *size)
     int rbd_group_rename(rados_ioctx_t p, const char *src, const char *dest)
     void rbd_group_info_cleanup(rbd_group_info_t *group_info,
                                 size_t group_info_size)
index 15f2c78e3b1bd9bd776c9265d7f2de03d9597160..dc0d499664e1567cfa3fb1ff0c0ea4619c24ae70 100644 (file)
@@ -841,6 +841,9 @@ cdef nogil:
         pass
     int rbd_group_list(rados_ioctx_t p, char *names, size_t *size):
         pass
+    int rbd_group_get_id(rados_ioctx_t p, const char *group_name,
+                         char *group_id, size_t *size):
+        pass
     int rbd_group_rename(rados_ioctx_t p, const char *src, const char *dest):
         pass
     void rbd_group_info_cleanup(rbd_group_info_t *group_info,
index df176a410a940058cc5b95dab4280995ec2fe25e..7d33e1ed62bef711bc8e9031873f2f826cdd5207 100644 (file)
@@ -2642,6 +2642,29 @@ cdef class Group(object):
 
     def __exit__(self, type_, value, traceback):
         return False
+    
+    def id(self):
+        """
+        Get group's id.
+
+        :returns: str - group id
+        """
+        cdef:
+            size_t size = 32
+            char *id = NULL
+        try:
+            while True:
+                id = <char *>realloc_chk(id, size)
+                with nogil:
+                    ret = rbd_group_get_id(self._ioctx, self._name, id, &size)
+                if ret >= 0:
+                    break
+                elif ret != -errno.ERANGE:
+                    raise make_ex(ret, 'error getting id for group %s' % self._name,
+                                  group_errno_to_exception)
+            return decode_cstr(id)
+        finally:
+            free(id)
 
     def add_image(self, image_ioctx, image_name):
         """
index 866bd8f11c85fd538c82a224475ea67603ef2523..69060b0af12f3ee0596d0b6202ab2074d3bb18af 100644 (file)
@@ -48,6 +48,7 @@
       group image add                   Add an image to a group.
       group image list (... ls)         List images in a group.
       group image remove (... rm)       Remove an image from a group.
+      group info                        Show information about a group.
       group list (group ls)             List rbd groups.
       group remove (group rm)           Delete a group.
       group rename                      Rename a group within pool.
     -p [ --pool ] arg     pool name unless overridden
     --image-id arg        image id
   
+  rbd help group info
+  usage: rbd group info [--pool <pool>] [--namespace <namespace>] 
+                        [--group <group>] [--format <format>] [--pretty-format] 
+                        <group-spec> 
+  
+  Show information about a group.
+  
+  Positional arguments
+    <group-spec>         group specification
+                         (example: [<pool-name>/[<namespace>/]]<group-name>)
+  
+  Optional arguments
+    -p [ --pool ] arg    pool name
+    --namespace arg      namespace name
+    --group arg          group name
+    --format arg         output format (plain, json, or xml) [default: plain]
+    --pretty-format      pretty formatting (json and xml)
+  
   rbd help group list
   usage: rbd group list [--pool <pool>] [--namespace <namespace>] 
                         [--format <format>] [--pretty-format] 
index 88b19146f161ea4e9cd018cf1f6ca262154a000a..5172dac316740796ca04f87878fe2c021fd07504 100644 (file)
@@ -70,6 +70,42 @@ TEST_F(TestGroup, group_createPP)
   ASSERT_EQ(0U, groups.size());
 }
 
+TEST_F(TestGroup, group_get_id)
+{
+  rados_ioctx_t ioctx;
+  rados_ioctx_create(_cluster, _pool_name.c_str(), &ioctx);
+  BOOST_SCOPE_EXIT(ioctx) {
+    rados_ioctx_destroy(ioctx);
+  } BOOST_SCOPE_EXIT_END;
+
+  ASSERT_EQ(0, rbd_group_create(ioctx, "group_get_id"));
+  
+  size_t size = 0;
+  ASSERT_EQ(-ERANGE, rbd_group_get_id(ioctx, "group_get_id", NULL, &size));
+  ASSERT_GT(size, 0);
+
+  char group_id[32];
+  ASSERT_EQ(0, rbd_group_get_id(ioctx, "group_get_id", group_id, &size));
+  ASSERT_EQ(strlen(group_id) + 1, size);
+
+  ASSERT_EQ(0, rbd_group_remove(ioctx, "group_get_id"));
+}
+
+TEST_F(TestGroup, group_get_idPP)
+{
+  librados::IoCtx ioctx;
+  ASSERT_EQ(0, _rados.ioctx_create(_pool_name.c_str(), ioctx));
+
+  librbd::RBD rbd;
+  ASSERT_EQ(0, rbd.group_create(ioctx, "group_get_idPP"));
+
+  std::string group_id;
+  ASSERT_EQ(0, rbd.group_get_id(ioctx, "group_get_idPP", &group_id));
+  ASSERT_FALSE(group_id.empty());
+
+  ASSERT_EQ(0, rbd.group_remove(ioctx, "group_get_idPP"));
+}
+
 TEST_F(TestGroup, add_image)
 {
   REQUIRE_FORMAT_V2();
index 0040d1e67e5b82e00f7aacbe011634e02c0105bd..94e2bc1c74762e9704d02317edf7a299bf7271b8 100644 (file)
@@ -2769,6 +2769,11 @@ class TestGroups(object):
         eq([], list(self.group.list_images()))
         RBD().trash_restore(ioctx, image_id, image_name)
 
+    def test_group_get_id(self):
+        id = self.group.id()
+        assert isinstance(id, str)
+        assert len(id) > 0
+
     def test_group_image_many_images(self):
         eq([], list(self.group.list_images()))
         self.group.add_image(ioctx, image_name)
index 5c2232a6fc68f960cee6d0dd0a5e00e662e8b6e2..e8cc66ca6797e8d92c758c06425688b406390819 100644 (file)
@@ -261,6 +261,58 @@ int execute_rename(const po::variables_map &vm,
   return 0;
 }
 
+int execute_info(const po::variables_map &vm,
+                   const std::vector<std::string> &ceph_global_init_args) {
+  size_t arg_index = 0;
+
+  std::string pool_name;
+  std::string namespace_name;
+  std::string group_name;
+
+  int r = utils::get_pool_generic_snapshot_names(
+    vm, at::ARGUMENT_MODIFIER_NONE, &arg_index, at::POOL_NAME, &pool_name,
+    &namespace_name, GROUP_NAME, "group", &group_name, nullptr, true,
+    utils::SNAPSHOT_PRESENCE_NONE, utils::SPEC_VALIDATION_FULL);
+  if (r < 0) {
+    return r;
+  }
+
+  at::Format::Formatter formatter;
+  r = utils::get_formatter(vm, &formatter);
+  if (r < 0) {
+    return r;
+  }
+  Formatter *f = formatter.get();
+
+  librados::Rados rados;
+  librados::IoCtx io_ctx;
+
+  r = utils::init(pool_name, namespace_name, &rados, &io_ctx);
+  if (r < 0) {
+    return r;
+  }
+
+  librbd::RBD rbd;
+  std::string group_id;
+  r = rbd.group_get_id(io_ctx, group_name.c_str(), &group_id);
+  if (r < 0) {
+    return r;
+  }
+
+  if (f) {
+    f->open_object_section("group");
+    f->dump_string("group_name", group_name);
+    f->dump_string("group_id", group_id);
+    f->close_section();
+    f->flush(std::cout);
+  } else {
+    std::cout << "rbd group '" << group_name << "':\n"
+              << "\t" << "id: " << group_id << std::endl;
+  }
+
+  return 0;
+}
+
 int execute_add(const po::variables_map &vm,
                 const std::vector<std::string> &ceph_global_init_args) {
   size_t arg_index = 0;
@@ -771,6 +823,13 @@ void get_rename_arguments(po::options_description *positional,
                          false);
 }
 
+void get_info_arguments(po::options_description *positional,
+                          po::options_description *options) {
+  add_group_spec_options(positional, options, at::ARGUMENT_MODIFIER_NONE,
+                         false);
+  at::add_format_options(options);
+}
+
 void get_add_arguments(po::options_description *positional,
                        po::options_description *options) {
   positional->add_options()
@@ -877,6 +936,9 @@ Shell::Action action_list(
 Shell::Action action_rename(
   {"group", "rename"}, {}, "Rename a group within pool.",
   "", &get_rename_arguments, &execute_rename);
+Shell::Action action_info(
+  {"group", "info"}, {}, "Show information about a group.",
+  "", &get_info_arguments, &execute_info);
 Shell::Action action_add(
   {"group", "image", "add"}, {}, "Add an image to a group.",
   "", &get_add_arguments, &execute_add);