From: Yehuda Sadeh Date: Fri, 22 Jun 2018 02:25:15 +0000 (-0700) Subject: rgw: more storage class data structure changes X-Git-Tag: v14.1.0~314^2~56 X-Git-Url: http://git-server-git.apps.pok.os.sepia.ceph.com/?a=commitdiff_plain;h=708d3396634722b4e6c6c67828f05840fd27ba5e;p=ceph.git rgw: more storage class data structure changes storage class also handles compression info Signed-off-by: Yehuda Sadeh --- diff --git a/src/common/ceph_json.h b/src/common/ceph_json.h index 02b70758be5..ba841d269da 100644 --- a/src/common/ceph_json.h +++ b/src/common/ceph_json.h @@ -142,6 +142,10 @@ public: template static void decode_json(const char *name, T& val, const T& default_val, JSONObj *obj); + + template + static bool decode_json(const char *name, boost::optional& val, JSONObj *obj, bool mandatory = false); + }; template @@ -346,6 +350,32 @@ void JSONDecoder::decode_json(const char *name, T& val, const T& default_val, JS } } +template +bool JSONDecoder::decode_json(const char *name, boost::optional& val, JSONObj *obj, bool mandatory) +{ + JSONObjIter iter = obj->find_first(name); + if (iter.end()) { + if (mandatory) { + string s = "missing mandatory field " + string(name); + throw err(s); + } + val = boost::none; + return false; + } + + try { + val.reset(T()); + decode_json_obj(val.get(), *iter); + } catch (err& e) { + val.reset(); + string s = string(name) + ": "; + s.append(e.message); + throw err(s); + } + + return true; +} + template static void encode_json(const char *name, const T& val, ceph::Formatter *f) { @@ -574,6 +604,10 @@ public: long long val_long_long() const; bool val_bool() const; + const map object() const { + return obj; + } + const vector& array() const { return arr; } diff --git a/src/rgw/rgw_admin.cc b/src/rgw/rgw_admin.cc index d056c028701..7470e5cb5db 100644 --- a/src/rgw/rgw_admin.cc +++ b/src/rgw/rgw_admin.cc @@ -4780,20 +4780,15 @@ int main(int argc, const char **argv) RGWZonePlacementInfo& info = zone.placement_pools[placement_id]; info.index_pool = *index_pool; - if (storage_class.empty()) { - info.data_pools[RGW_STORAGE_CLASS_STANDARD] = *data_pool; - } else { - info.data_pools[storage_class] = *data_pool; - } + rgw_pool dp = data_pool.get(); + info.storage_classes.set_storage_class(storage_class, &dp, compression_type.get_ptr()); + if (data_extra_pool) { info.data_extra_pool = *data_extra_pool; } if (index_type_specified) { info.index_type = placement_index_type; } - if (compression_type) { - info.compression_type = *compression_type; - } ret = check_pool_support_omap(info.get_data_extra_pool()); if (ret < 0) { @@ -4812,22 +4807,15 @@ int main(int argc, const char **argv) if (index_pool && !index_pool->empty()) { info.index_pool = *index_pool; } - if (data_pool && !data_pool->empty()) { - if (storage_class.empty()) { - info.data_pools[RGW_STORAGE_CLASS_STANDARD] = *data_pool; - } else { - info.data_pools[storage_class] = *data_pool; - } - } + rgw_pool dp = data_pool.get(); + info.storage_classes.set_storage_class(storage_class, &dp, compression_type.get_ptr()); + if (data_extra_pool) { info.data_extra_pool = *data_extra_pool; } if (index_type_specified) { info.index_type = placement_index_type; } - if (compression_type) { - info.compression_type = *compression_type; - } ret = check_pool_support_omap(info.get_data_extra_pool()); if (ret < 0) { diff --git a/src/rgw/rgw_json_enc.cc b/src/rgw/rgw_json_enc.cc index 448e6012f1f..ff54299ce3e 100644 --- a/src/rgw/rgw_json_enc.cc +++ b/src/rgw/rgw_json_enc.cc @@ -964,32 +964,76 @@ void RGWZoneParams::dump(Formatter *f) const encode_json("realm_id", realm_id, f); } +void RGWZoneStorageClass::dump(Formatter *f) const +{ + if (data_pool) { + encode_json("data_pool", data_pool.get(), f); + } + if (compression_type) { + encode_json("compression_type", compression_type.get(), f); + } +} + +void RGWZoneStorageClass::decode_json(JSONObj *obj) +{ + JSONDecoder::decode_json("data_pool", data_pool, obj); + JSONDecoder::decode_json("compression_type", compression_type, obj); +} + +void RGWZoneStorageClasses::dump(Formatter *f) const +{ + for (auto& i : m) { + encode_json(i.first.c_str(), i.second, f); + } +} + +void RGWZoneStorageClasses::decode_json(JSONObj *obj) +{ + JSONFormattable f; + decode_json_obj(f, obj); + + for (auto& field : f.object()) { + JSONObj *field_obj = obj->find_obj(field.first); + assert(field_obj); + + decode_json_obj(m[field.first], field_obj); + } +} + void RGWZonePlacementInfo::dump(Formatter *f) const { encode_json("index_pool", index_pool, f); - encode_json("data_pools", data_pools, f); + encode_json("storage_classes", storage_classes, f); encode_json("data_extra_pool", data_extra_pool, f); encode_json("index_type", (uint32_t)index_type, f); - encode_json("compression", compression_type, f); + + /* no real need for backward compatibility of compression_type and data_pool in here, + * rather not clutter the output */ } void RGWZonePlacementInfo::decode_json(JSONObj *obj) { JSONDecoder::decode_json("index_pool", index_pool, obj); - JSONDecoder::decode_json("data_pools", data_pools, obj); - if (JSONDecoder::decode_json("data_pool", standard_data_pool, obj)) { - data_pools[RGW_STORAGE_CLASS_STANDARD] = standard_data_pool; - } else { - auto iter = data_pools.find(RGW_STORAGE_CLASS_STANDARD); - if (iter != data_pools.end()) { - standard_data_pool = iter->second; - } - } + JSONDecoder::decode_json("storage_classes", storage_classes, obj); JSONDecoder::decode_json("data_extra_pool", data_extra_pool, obj); uint32_t it; JSONDecoder::decode_json("index_type", it, obj); index_type = (RGWBucketIndexType)it; - JSONDecoder::decode_json("compression", compression_type, obj); + + /* backward compatibility, these are now defined in storage_classes */ + string standard_compression_type; + string *pcompression = nullptr; + if (JSONDecoder::decode_json("compression", standard_compression_type, obj)) { + pcompression = &standard_compression_type; + } + rgw_pool standard_data_pool; + rgw_pool *ppool = nullptr; + if (JSONDecoder::decode_json("data_pool", standard_data_pool, obj)) { + ppool = &standard_data_pool; + } + if (ppool || pcompression) { + storage_classes.set_storage_class(RGW_STORAGE_CLASS_STANDARD, ppool, pcompression); + } } void RGWZoneParams::decode_json(JSONObj *obj) diff --git a/src/rgw/rgw_op.cc b/src/rgw/rgw_op.cc index 6a7d0599524..5a0476a737e 100644 --- a/src/rgw/rgw_op.cc +++ b/src/rgw/rgw_op.cc @@ -3865,7 +3865,7 @@ void RGWPostObj::execute() filter = encrypt.get(); } else { const auto& compression_type = store->svc.zone->get_zone_params().get_compression_type( - s->bucket_info.placement_rule.name); + s->bucket_info.placement_rule); if (compression_type != "none") { plugin = Compressor::create(s->cct, compression_type); if (!plugin) { @@ -6586,9 +6586,8 @@ int RGWBulkUploadOp::handle_file(const boost::string_ref path, /* No filters by default. */ DataProcessor *filter = &processor; -#warning add storage_class compression const auto& compression_type = store->svc.zone->get_zone_params().get_compression_type( - binfo.placement_rule.name); + binfo.placement_rule); CompressorRef plugin; boost::optional compressor; if (compression_type != "none") { diff --git a/src/rgw/rgw_rados.cc b/src/rgw/rgw_rados.cc index 984c026d2a3..79967948102 100644 --- a/src/rgw/rgw_rados.cc +++ b/src/rgw/rgw_rados.cc @@ -2891,7 +2891,7 @@ int RGWRados::create_bucket(const RGWUserInfo& owner, rgw_bucket& bucket, return -ENOENT; } -bool RGWRados::get_obj_data_pool(const string& placement_rule, const rgw_obj& obj, rgw_pool *pool) +bool RGWRados::get_obj_data_pool(const rgw_placement_rule& placement_rule, const rgw_obj& obj, rgw_pool *pool) { return rgw_get_obj_data_pool(svc.zone->get_zonegroup(), svc.zone->get_zone_params(), placement_rule, obj, pool); } @@ -4260,9 +4260,8 @@ int RGWRados::fetch_remote_obj(RGWObjectCtx& obj_ctx, boost::optional compressor; CompressorRef plugin; -#warning compression type const auto& compression_type = svc.zone->get_zone_params().get_compression_type( - dest_bucket_info.placement_rule.name); + dest_bucket_info.placement_rule); if (compression_type != "none") { plugin = Compressor::create(cct, compression_type); if (!plugin) { diff --git a/src/rgw/rgw_zone.cc b/src/rgw/rgw_zone.cc index e8acf307807..7c9f414ca17 100644 --- a/src/rgw/rgw_zone.cc +++ b/src/rgw/rgw_zone.cc @@ -1547,8 +1547,10 @@ int get_zones_pool_set(CephContext* cct, pool_names.insert(zone.reshard_pool); for(auto& iter : zone.placement_pools) { pool_names.insert(iter.second.index_pool); - for (auto& pi : iter.second.data_pools) { - pool_names.insert(pi.second); + for (auto& pi : iter.second.storage_classes.get_all()) { + if (pi.second.data_pool) { + pool_names.insert(pi.second.data_pool.get()); + } } pool_names.insert(iter.second.data_extra_pool); } @@ -1623,9 +1625,12 @@ int RGWZoneParams::fix_pool_names() for(auto& iter : placement_pools) { iter.second.index_pool = fix_zone_pool_dup(pools, name, "." + default_bucket_index_pool_suffix, iter.second.index_pool); - for (auto& pi : iter.second.data_pools) { - pi.second = fix_zone_pool_dup(pools, name, "." + default_storage_pool_suffix, - pi.second); + for (auto& pi : iter.second.storage_classes.get_all()) { + if (pi.second.data_pool) { + rgw_pool& pool = pi.second.data_pool.get(); + pool = fix_zone_pool_dup(pools, name, "." + default_storage_pool_suffix, + pool); + } } iter.second.data_extra_pool= fix_zone_pool_dup(pools, name, "." + default_storage_extra_pool_suffix, iter.second.data_extra_pool); @@ -1646,7 +1651,8 @@ int RGWZoneParams::create(bool exclusive) /* a new system, let's set new placement info */ RGWZonePlacementInfo default_placement; default_placement.index_pool = name + "." + default_bucket_index_pool_suffix; - default_placement.data_pools[RGW_STORAGE_CLASS_STANDARD] = name + "." + default_storage_pool_suffix; + rgw_pool pool = name + "." + default_storage_pool_suffix; + default_placement.storage_classes.set_storage_class(RGW_STORAGE_CLASS_STANDARD, &pool, nullptr); default_placement.data_extra_pool = name + "." + default_storage_extra_pool_suffix; placement_pools["default-placement"] = default_placement; } @@ -1746,14 +1752,14 @@ int RGWZoneParams::set_as_default(bool exclusive) return RGWSystemMetaObj::set_as_default(exclusive); } -const string& RGWZoneParams::get_compression_type(const string& placement_rule) const +const string& RGWZoneParams::get_compression_type(const rgw_placement_rule& placement_rule) const { static const std::string NONE{"none"}; - auto p = placement_pools.find(placement_rule); + auto p = placement_pools.find(placement_rule.name); if (p == placement_pools.end()) { return NONE; } - const auto& type = p->second.compression_type; + const auto& type = p->second.get_compression_type(placement_rule.storage_class); return !type.empty() ? type : NONE; } diff --git a/src/rgw/rgw_zone.h b/src/rgw/rgw_zone.h index d50e69dcb71..3b4a4d0b668 100644 --- a/src/rgw/rgw_zone.h +++ b/src/rgw/rgw_zone.h @@ -151,36 +151,131 @@ public: }; WRITE_CLASS_ENCODER(RGWSystemMetaObj) +struct RGWZoneStorageClass { + boost::optional data_pool; + boost::optional compression_type; + + void encode(bufferlist& bl) const { + ENCODE_START(1, 1, bl); + encode(data_pool, bl); + encode(compression_type, bl); + ENCODE_FINISH(bl); + } + + void decode(bufferlist::const_iterator& bl) { + DECODE_START(1, bl); + decode(data_pool, bl); + decode(compression_type, bl); + DECODE_FINISH(bl); + } + + void dump(Formatter *f) const; + void decode_json(JSONObj *obj); +}; +WRITE_CLASS_ENCODER(RGWZoneStorageClass) + + +class RGWZoneStorageClasses { + map m; + + /* in memory only */ + RGWZoneStorageClass *standard_class{&m[RGW_STORAGE_CLASS_STANDARD]}; + +public: + RGWZoneStorageClasses() {} + RGWZoneStorageClasses(const RGWZoneStorageClasses& rhs) { + m = rhs.m; + standard_class = &m[RGW_STORAGE_CLASS_STANDARD]; + } + RGWZoneStorageClasses& operator=(const RGWZoneStorageClasses& rhs) { + m = rhs.m; + standard_class = &m[RGW_STORAGE_CLASS_STANDARD]; + return *this; + } + + const RGWZoneStorageClass& get_standard() const { + return *standard_class; + } + + bool find(const string& sc, const RGWZoneStorageClass **pstorage_class) const { + auto iter = m.find(sc); + if (iter == m.end()) { + return false; + } + *pstorage_class = &iter->second; + return true; + } + + const map& get_all() const { + return m; + } + + map& get_all() { + return m; + } + + void set_storage_class(const string& sc, const rgw_pool *data_pool, const string *compression_type) { + const string *psc = ≻ + if (sc.empty()) { + psc = &RGW_STORAGE_CLASS_STANDARD; + } + RGWZoneStorageClass& storage_class = m[*psc]; + if (data_pool) { + storage_class.data_pool = *data_pool; + } + if (compression_type) { + storage_class.compression_type = *compression_type; + } + } + + void encode(bufferlist& bl) const { + ENCODE_START(1, 1, bl); + encode(m, bl); + ENCODE_FINISH(bl); + } + + void decode(bufferlist::const_iterator& bl) { + DECODE_START(1, bl); + decode(m, bl); + DECODE_FINISH(bl); + } + + void dump(Formatter *f) const; + void decode_json(JSONObj *obj); +}; +WRITE_CLASS_ENCODER(RGWZoneStorageClasses) + struct RGWZonePlacementInfo { rgw_pool index_pool; - rgw_pool standard_data_pool; rgw_pool data_extra_pool; /* if not set we should use data_pool */ - map data_pools; + RGWZoneStorageClasses storage_classes; RGWBucketIndexType index_type; - std::string compression_type; RGWZonePlacementInfo() : index_type(RGWBIType_Normal) {} void encode(bufferlist& bl) const { ENCODE_START(7, 1, bl); encode(index_pool.to_str(), bl); - encode(data_pool.to_str(), bl); + rgw_pool standard_data_pool = get_data_pool(RGW_STORAGE_CLASS_STANDARD); + encode(standard_data_pool.to_str(), bl); encode(data_extra_pool.to_str(), bl); encode((uint32_t)index_type, bl); - encode(compression_type, bl); + string standard_compression_type = get_compression_type(RGW_STORAGE_CLASS_STANDARD); + encode(standard_compression_type, bl); + encode(storage_classes, bl); ENCODE_FINISH(bl); } void decode(bufferlist::const_iterator& bl) { - DECODE_START(6, bl); - std::string index_pool_str; - std::string data_pool_str; + DECODE_START(7, bl); + string index_pool_str; + string data_pool_str; decode(index_pool_str, bl); index_pool = rgw_pool(index_pool_str); decode(data_pool_str, bl); - data_pool = rgw_pool(data_pool_str); + rgw_pool standard_data_pool(data_pool_str); if (struct_v >= 4) { - std::string data_extra_pool_str; + string data_extra_pool_str; decode(data_extra_pool_str, bl); data_extra_pool = rgw_pool(data_extra_pool_str); } @@ -189,19 +284,49 @@ struct RGWZonePlacementInfo { decode(it, bl); index_type = (RGWBucketIndexType)it; } + string standard_compression_type; if (struct_v >= 6) { - decode(compression_type, bl); + decode(standard_compression_type, bl); + } + if (struct_v >= 7) { + decode(storage_classes, bl); + } else { + storage_classes.set_storage_class(RGW_STORAGE_CLASS_STANDARD, &standard_data_pool, + (!standard_compression_type.empty() ? &standard_compression_type : nullptr)); } DECODE_FINISH(bl); } const rgw_pool& get_data_extra_pool() const { + static rgw_pool no_pool; if (data_extra_pool.empty()) { - return data_pool; + return storage_classes.get_standard().data_pool.get_value_or(no_pool); } return data_extra_pool; } + const rgw_pool& get_data_pool(const string& sc) const { + const RGWZoneStorageClass *storage_class; + static rgw_pool no_pool; + + if (!storage_classes.find(sc, &storage_class)) { + return storage_classes.get_standard().data_pool.get_value_or(no_pool); + } + + return storage_class->data_pool.get_value_or(no_pool); + } + + const string& get_compression_type(const string& sc) const { + const RGWZoneStorageClass *storage_class; + static string no_compression; + + if (!storage_classes.find(sc, &storage_class)) { + return no_compression; + } + return storage_class->compression_type.get_value_or(no_compression); + } + void dump(Formatter *f) const; void decode_json(JSONObj *obj); + }; WRITE_CLASS_ENCODER(RGWZonePlacementInfo) @@ -252,7 +377,7 @@ struct RGWZoneParams : RGWSystemMetaObj { int create(bool exclusive = true) override; int fix_pool_names(); - const std::string& get_compression_type(const std::string& placement_rule) const; + const string& get_compression_type(const rgw_placement_rule& placement_rule) const; void encode(bufferlist& bl) const override { ENCODE_START(12, 1, bl); diff --git a/src/rgw/services/svc_zone.cc b/src/rgw/services/svc_zone.cc index d6717ef08f7..aa3d7458084 100644 --- a/src/rgw/services/svc_zone.cc +++ b/src/rgw/services/svc_zone.cc @@ -1132,7 +1132,9 @@ read_omap: } pool_name = miter->first; - rule_info->data_pools[RGW_STORAGE_CLASS_STANDARD] = pool_name; + rgw_pool pool = pool_name; + + rule_info->storage_classes.set_storage_class(RGW_STORAGE_CLASS_STANDARD, &pool, nullptr); rule_info->data_extra_pool = pool_name; rule_info->index_pool = pool_name; rule_info->index_type = RGWBIType_Normal;