1 // -*- mode:C++; tab-width:8; c-basic-offset:2; indent-tabs-mode:t -*-
2 // vim: ts=8 sw=2 smarttab ft=cpp
4 #ifndef CEPH_RGW_ZONE_H
5 #define CEPH_RGW_ZONE_H
7 #include "rgw_common.h"
8 #include "rgw_sync_policy.h"
10 namespace rgw_zone_defaults
{
12 extern std::string zone_names_oid_prefix
;
13 extern std::string region_info_oid_prefix
;
14 extern std::string realm_names_oid_prefix
;
15 extern std::string zone_group_info_oid_prefix
;
16 extern std::string realm_info_oid_prefix
;
17 extern std::string default_region_info_oid
;
18 extern std::string default_zone_group_info_oid
;
19 extern std::string region_map_oid
;
20 extern std::string default_realm_info_oid
;
21 extern std::string default_zonegroup_name
;
22 extern std::string default_zone_name
;
23 extern std::string zonegroup_names_oid_prefix
;
24 extern std::string RGW_DEFAULT_ZONE_ROOT_POOL
;
25 extern std::string RGW_DEFAULT_ZONEGROUP_ROOT_POOL
;
26 extern std::string RGW_DEFAULT_REALM_ROOT_POOL
;
27 extern std::string RGW_DEFAULT_PERIOD_ROOT_POOL
;
28 extern std::string avail_pools
;
29 extern std::string default_storage_pool_suffix
;
34 class RGWSyncModulesManager
;
40 void encode(bufferlist
& bl
) const {
41 ENCODE_START(1, 1, bl
);
46 void decode(bufferlist::const_iterator
& bl
) {
52 void dump(Formatter
*f
) const;
53 void decode_json(JSONObj
*obj
);
55 WRITE_CLASS_ENCODER(RGWNameToId
)
57 struct RGWDefaultSystemMetaObjInfo
{
58 std::string default_id
;
60 void encode(bufferlist
& bl
) const {
61 ENCODE_START(1, 1, bl
);
62 encode(default_id
, bl
);
66 void decode(bufferlist::const_iterator
& bl
) {
68 decode(default_id
, bl
);
72 void dump(Formatter
*f
) const;
73 void decode_json(JSONObj
*obj
);
75 WRITE_CLASS_ENCODER(RGWDefaultSystemMetaObjInfo
)
80 class RGWSystemMetaObj
{
85 CephContext
*cct
{nullptr};
86 RGWSI_SysObj
*sysobj_svc
{nullptr};
87 RGWSI_Zone
*zone_svc
{nullptr};
89 int store_name(bool exclusive
);
90 int store_info(bool exclusive
);
91 int read_info(const std::string
& obj_id
, bool old_format
= false);
92 int read_id(const std::string
& obj_name
, std::string
& obj_id
);
93 int read_default(RGWDefaultSystemMetaObjInfo
& default_info
,
94 const std::string
& oid
);
95 /* read and use default id */
96 int use_default(bool old_format
= false);
100 RGWSystemMetaObj(const std::string
& _name
): name(_name
) {}
101 RGWSystemMetaObj(const std::string
& _id
, const std::string
& _name
) : id(_id
), name(_name
) {}
102 RGWSystemMetaObj(CephContext
*_cct
, RGWSI_SysObj
*_sysobj_svc
) {
103 reinit_instance(_cct
, _sysobj_svc
);
105 RGWSystemMetaObj(const std::string
& _name
, CephContext
*_cct
, RGWSI_SysObj
*_sysobj_svc
): name(_name
) {
106 reinit_instance(_cct
, _sysobj_svc
);
109 const std::string
& get_name() const { return name
; }
110 const std::string
& get_id() const { return id
; }
112 void set_name(const std::string
& _name
) { name
= _name
;}
113 void set_id(const std::string
& _id
) { id
= _id
;}
114 void clear_id() { id
.clear(); }
116 virtual ~RGWSystemMetaObj() {}
118 virtual void encode(bufferlist
& bl
) const {
119 ENCODE_START(1, 1, bl
);
125 virtual void decode(bufferlist::const_iterator
& bl
) {
132 void reinit_instance(CephContext
*_cct
, RGWSI_SysObj
*_sysobj_svc
);
133 int init(CephContext
*_cct
, RGWSI_SysObj
*_sysobj_svc
, bool setup_obj
= true, bool old_format
= false);
134 virtual int read_default_id(std::string
& default_id
, bool old_format
= false);
135 virtual int set_as_default(bool exclusive
= false);
136 int delete_default();
137 virtual int create(bool exclusive
= true);
138 int delete_obj(bool old_format
= false);
139 int rename(const std::string
& new_name
);
140 int update() { return store_info(false);}
141 int update_name() { return store_name(false);}
143 int write(bool exclusive
);
145 virtual rgw_pool
get_pool(CephContext
*cct
) const = 0;
146 virtual const std::string
get_default_oid(bool old_format
= false) const = 0;
147 virtual const std::string
& get_names_oid_prefix() const = 0;
148 virtual const std::string
& get_info_oid_prefix(bool old_format
= false) const = 0;
149 virtual const std::string
& get_predefined_name(CephContext
*cct
) const = 0;
151 void dump(Formatter
*f
) const;
152 void decode_json(JSONObj
*obj
);
154 WRITE_CLASS_ENCODER(RGWSystemMetaObj
)
156 struct RGWZoneStorageClass
{
157 boost::optional
<rgw_pool
> data_pool
;
158 boost::optional
<std::string
> compression_type
;
160 void encode(bufferlist
& bl
) const {
161 ENCODE_START(1, 1, bl
);
162 encode(data_pool
, bl
);
163 encode(compression_type
, bl
);
167 void decode(bufferlist::const_iterator
& bl
) {
169 decode(data_pool
, bl
);
170 decode(compression_type
, bl
);
174 void dump(Formatter
*f
) const;
175 void decode_json(JSONObj
*obj
);
177 WRITE_CLASS_ENCODER(RGWZoneStorageClass
)
180 class RGWZoneStorageClasses
{
181 map
<string
, RGWZoneStorageClass
> m
;
184 RGWZoneStorageClass
*standard_class
;
187 RGWZoneStorageClasses() {
188 standard_class
= &m
[RGW_STORAGE_CLASS_STANDARD
];
190 RGWZoneStorageClasses(const RGWZoneStorageClasses
& rhs
) {
192 standard_class
= &m
[RGW_STORAGE_CLASS_STANDARD
];
194 RGWZoneStorageClasses
& operator=(const RGWZoneStorageClasses
& rhs
) {
196 standard_class
= &m
[RGW_STORAGE_CLASS_STANDARD
];
200 const RGWZoneStorageClass
& get_standard() const {
201 return *standard_class
;
204 bool find(const string
& sc
, const RGWZoneStorageClass
**pstorage_class
) const {
205 auto iter
= m
.find(sc
);
206 if (iter
== m
.end()) {
209 *pstorage_class
= &iter
->second
;
213 bool exists(const string
& sc
) const {
217 auto iter
= m
.find(sc
);
218 return (iter
!= m
.end());
221 const map
<string
, RGWZoneStorageClass
>& get_all() const {
225 map
<string
, RGWZoneStorageClass
>& get_all() {
229 void set_storage_class(const string
& sc
, const rgw_pool
*data_pool
, const string
*compression_type
) {
230 const string
*psc
= &sc
;
232 psc
= &RGW_STORAGE_CLASS_STANDARD
;
234 RGWZoneStorageClass
& storage_class
= m
[*psc
];
236 storage_class
.data_pool
= *data_pool
;
238 if (compression_type
) {
239 storage_class
.compression_type
= *compression_type
;
243 void remove_storage_class(const string
& sc
) {
249 void encode(bufferlist
& bl
) const {
250 ENCODE_START(1, 1, bl
);
255 void decode(bufferlist::const_iterator
& bl
) {
258 standard_class
= &m
[RGW_STORAGE_CLASS_STANDARD
];
262 void dump(Formatter
*f
) const;
263 void decode_json(JSONObj
*obj
);
265 WRITE_CLASS_ENCODER(RGWZoneStorageClasses
)
267 struct RGWZonePlacementInfo
{
269 rgw_pool data_extra_pool
; /* if not set we should use data_pool */
270 RGWZoneStorageClasses storage_classes
;
271 RGWBucketIndexType index_type
;
273 RGWZonePlacementInfo() : index_type(RGWBIType_Normal
) {}
275 void encode(bufferlist
& bl
) const {
276 ENCODE_START(7, 1, bl
);
277 encode(index_pool
.to_str(), bl
);
278 rgw_pool standard_data_pool
= get_data_pool(RGW_STORAGE_CLASS_STANDARD
);
279 encode(standard_data_pool
.to_str(), bl
);
280 encode(data_extra_pool
.to_str(), bl
);
281 encode((uint32_t)index_type
, bl
);
282 string standard_compression_type
= get_compression_type(RGW_STORAGE_CLASS_STANDARD
);
283 encode(standard_compression_type
, bl
);
284 encode(storage_classes
, bl
);
288 void decode(bufferlist::const_iterator
& bl
) {
290 string index_pool_str
;
291 string data_pool_str
;
292 decode(index_pool_str
, bl
);
293 index_pool
= rgw_pool(index_pool_str
);
294 decode(data_pool_str
, bl
);
295 rgw_pool
standard_data_pool(data_pool_str
);
297 string data_extra_pool_str
;
298 decode(data_extra_pool_str
, bl
);
299 data_extra_pool
= rgw_pool(data_extra_pool_str
);
304 index_type
= (RGWBucketIndexType
)it
;
306 string standard_compression_type
;
308 decode(standard_compression_type
, bl
);
311 decode(storage_classes
, bl
);
313 storage_classes
.set_storage_class(RGW_STORAGE_CLASS_STANDARD
, &standard_data_pool
,
314 (!standard_compression_type
.empty() ? &standard_compression_type
: nullptr));
318 const rgw_pool
& get_data_extra_pool() const {
319 static rgw_pool no_pool
;
320 if (data_extra_pool
.empty()) {
321 return storage_classes
.get_standard().data_pool
.get_value_or(no_pool
);
323 return data_extra_pool
;
325 const rgw_pool
& get_data_pool(const string
& sc
) const {
326 const RGWZoneStorageClass
*storage_class
;
327 static rgw_pool no_pool
;
329 if (!storage_classes
.find(sc
, &storage_class
)) {
330 return storage_classes
.get_standard().data_pool
.get_value_or(no_pool
);
333 return storage_class
->data_pool
.get_value_or(no_pool
);
335 const rgw_pool
& get_standard_data_pool() const {
336 return get_data_pool(RGW_STORAGE_CLASS_STANDARD
);
339 const string
& get_compression_type(const string
& sc
) const {
340 const RGWZoneStorageClass
*storage_class
;
341 static string no_compression
;
343 if (!storage_classes
.find(sc
, &storage_class
)) {
344 return no_compression
;
346 return storage_class
->compression_type
.get_value_or(no_compression
);
349 bool storage_class_exists(const string
& sc
) const {
350 return storage_classes
.exists(sc
);
353 void dump(Formatter
*f
) const;
354 void decode_json(JSONObj
*obj
);
357 WRITE_CLASS_ENCODER(RGWZonePlacementInfo
)
359 struct RGWZoneParams
: RGWSystemMetaObj
{
360 rgw_pool domain_root
;
361 rgw_pool control_pool
;
365 rgw_pool intent_log_pool
;
366 rgw_pool usage_log_pool
;
368 rgw_pool user_keys_pool
;
369 rgw_pool user_email_pool
;
370 rgw_pool user_swift_pool
;
371 rgw_pool user_uid_pool
;
373 rgw_pool reshard_pool
;
377 RGWAccessKey system_key
;
379 map
<std::string
, RGWZonePlacementInfo
> placement_pools
;
381 std::string realm_id
;
383 JSONFormattable tier_config
;
385 RGWZoneParams() : RGWSystemMetaObj() {}
386 explicit RGWZoneParams(const std::string
& name
) : RGWSystemMetaObj(name
){}
387 RGWZoneParams(const rgw_zone_id
& id
, const std::string
& name
) : RGWSystemMetaObj(id
.id
, name
) {}
388 RGWZoneParams(const rgw_zone_id
& id
, const std::string
& name
, const std::string
& _realm_id
)
389 : RGWSystemMetaObj(id
.id
, name
), realm_id(_realm_id
) {}
391 rgw_pool
get_pool(CephContext
*cct
) const override
;
392 const std::string
get_default_oid(bool old_format
= false) const override
;
393 const std::string
& get_names_oid_prefix() const override
;
394 const std::string
& get_info_oid_prefix(bool old_format
= false) const override
;
395 const std::string
& get_predefined_name(CephContext
*cct
) const override
;
397 int init(CephContext
*_cct
, RGWSI_SysObj
*_sysobj_svc
, bool setup_obj
= true,
398 bool old_format
= false);
399 using RGWSystemMetaObj::init
;
400 int read_default_id(std::string
& default_id
, bool old_format
= false) override
;
401 int set_as_default(bool exclusive
= false) override
;
402 int create_default(bool old_format
= false);
403 int create(bool exclusive
= true) override
;
404 int fix_pool_names();
406 const string
& get_compression_type(const rgw_placement_rule
& placement_rule
) const;
408 void encode(bufferlist
& bl
) const override
{
409 ENCODE_START(13, 1, bl
);
410 encode(domain_root
, bl
);
411 encode(control_pool
, bl
);
413 encode(log_pool
, bl
);
414 encode(intent_log_pool
, bl
);
415 encode(usage_log_pool
, bl
);
416 encode(user_keys_pool
, bl
);
417 encode(user_email_pool
, bl
);
418 encode(user_swift_pool
, bl
);
419 encode(user_uid_pool
, bl
);
420 RGWSystemMetaObj::encode(bl
);
421 encode(system_key
, bl
);
422 encode(placement_pools
, bl
);
423 rgw_pool unused_metadata_heap
;
424 encode(unused_metadata_heap
, bl
);
425 encode(realm_id
, bl
);
427 map
<std::string
, std::string
, ltstr_nocase
> old_tier_config
;
428 encode(old_tier_config
, bl
);
429 encode(roles_pool
, bl
);
430 encode(reshard_pool
, bl
);
431 encode(otp_pool
, bl
);
432 encode(tier_config
, bl
);
433 encode(oidc_pool
, bl
);
437 void decode(bufferlist::const_iterator
& bl
) override
{
438 DECODE_START(13, bl
);
439 decode(domain_root
, bl
);
440 decode(control_pool
, bl
);
442 decode(log_pool
, bl
);
443 decode(intent_log_pool
, bl
);
444 decode(usage_log_pool
, bl
);
445 decode(user_keys_pool
, bl
);
446 decode(user_email_pool
, bl
);
447 decode(user_swift_pool
, bl
);
448 decode(user_uid_pool
, bl
);
450 RGWSystemMetaObj::decode(bl
);
451 } else if (struct_v
>= 2) {
456 decode(system_key
, bl
);
458 decode(placement_pools
, bl
);
460 rgw_pool unused_metadata_heap
;
461 decode(unused_metadata_heap
, bl
);
464 decode(realm_id
, bl
);
469 lc_pool
= log_pool
.name
+ ":lc";
471 map
<std::string
, std::string
, ltstr_nocase
> old_tier_config
;
473 decode(old_tier_config
, bl
);
476 decode(roles_pool
, bl
);
478 roles_pool
= name
+ ".rgw.meta:roles";
480 if (struct_v
>= 10) {
481 decode(reshard_pool
, bl
);
483 reshard_pool
= log_pool
.name
+ ":reshard";
485 if (struct_v
>= 11) {
486 ::decode(otp_pool
, bl
);
488 otp_pool
= name
+ ".rgw.otp";
490 if (struct_v
>= 12) {
491 ::decode(tier_config
, bl
);
493 for (auto& kv
: old_tier_config
) {
494 tier_config
.set(kv
.first
, kv
.second
);
497 if (struct_v
>= 13) {
498 ::decode(oidc_pool
, bl
);
500 oidc_pool
= name
+ ".rgw.meta:oidc";
504 void dump(Formatter
*f
) const;
505 void decode_json(JSONObj
*obj
);
506 static void generate_test_instances(list
<RGWZoneParams
*>& o
);
508 bool get_placement(const std::string
& placement_id
, RGWZonePlacementInfo
*placement
) const {
509 auto iter
= placement_pools
.find(placement_id
);
510 if (iter
== placement_pools
.end()) {
513 *placement
= iter
->second
;
518 * return data pool of the head object
520 bool get_head_data_pool(const rgw_placement_rule
& placement_rule
, const rgw_obj
& obj
, rgw_pool
*pool
) const {
521 const rgw_data_placement_target
& explicit_placement
= obj
.bucket
.explicit_placement
;
522 if (!explicit_placement
.data_pool
.empty()) {
523 if (!obj
.in_extra_data
) {
524 *pool
= explicit_placement
.data_pool
;
526 *pool
= explicit_placement
.get_data_extra_pool();
530 if (placement_rule
.empty()) {
533 auto iter
= placement_pools
.find(placement_rule
.name
);
534 if (iter
== placement_pools
.end()) {
537 if (!obj
.in_extra_data
) {
538 *pool
= iter
->second
.get_data_pool(placement_rule
.storage_class
);
540 *pool
= iter
->second
.get_data_extra_pool();
545 bool valid_placement(const rgw_placement_rule
& rule
) const {
546 auto iter
= placement_pools
.find(rule
.name
);
547 if (iter
== placement_pools
.end()) {
550 return iter
->second
.storage_class_exists(rule
.storage_class
);
553 WRITE_CLASS_ENCODER(RGWZoneParams
)
558 list
<std::string
> endpoints
;
562 std::string tier_type
;
564 std::string redirect_zone
;
567 * Represents the number of shards for the bucket index object, a value of zero
568 * indicates there is no sharding. By default (no sharding, the name of the object
569 * is '.dir.{marker}', with sharding, the name is '.dir.{marker}.{sharding_id}',
570 * sharding_id is zero-based value. It is not recommended to set a too large value
571 * (e.g. thousand) as it increases the cost for bucket listing.
573 uint32_t bucket_index_max_shards
;
575 // pre-shard buckets on creation to enable some write-parallism by default,
576 // delay the need to reshard as the bucket grows, and (in multisite) get some
577 // bucket index sharding where dynamic resharding is not supported
578 static constexpr uint32_t default_bucket_index_max_shards
= 11;
581 set
<std::string
> sync_from
; /* list of zones to sync from */
584 : log_meta(false), log_data(false), read_only(false),
585 bucket_index_max_shards(default_bucket_index_max_shards
),
586 sync_from_all(true) {}
588 void encode(bufferlist
& bl
) const {
589 ENCODE_START(7, 1, bl
);
591 encode(endpoints
, bl
);
592 encode(log_meta
, bl
);
593 encode(log_data
, bl
);
594 encode(bucket_index_max_shards
, bl
);
596 encode(read_only
, bl
);
597 encode(tier_type
, bl
);
598 encode(sync_from_all
, bl
);
599 encode(sync_from
, bl
);
600 encode(redirect_zone
, bl
);
604 void decode(bufferlist::const_iterator
& bl
) {
610 decode(endpoints
, bl
);
612 decode(log_meta
, bl
);
613 decode(log_data
, bl
);
616 decode(bucket_index_max_shards
, bl
);
620 decode(read_only
, bl
);
623 decode(tier_type
, bl
);
626 decode(sync_from_all
, bl
);
627 decode(sync_from
, bl
);
630 decode(redirect_zone
, bl
);
634 void dump(Formatter
*f
) const;
635 void decode_json(JSONObj
*obj
);
636 static void generate_test_instances(list
<RGWZone
*>& o
);
638 bool is_read_only() const { return read_only
; }
640 bool syncs_from(const std::string
& zone_name
) const {
641 return (sync_from_all
|| sync_from
.find(zone_name
) != sync_from
.end());
644 WRITE_CLASS_ENCODER(RGWZone
)
646 struct RGWDefaultZoneGroupInfo
{
647 std::string default_zonegroup
;
649 void encode(bufferlist
& bl
) const {
650 ENCODE_START(1, 1, bl
);
651 encode(default_zonegroup
, bl
);
655 void decode(bufferlist::const_iterator
& bl
) {
657 decode(default_zonegroup
, bl
);
660 void dump(Formatter
*f
) const;
661 void decode_json(JSONObj
*obj
);
662 //todo: implement ceph-dencoder
664 WRITE_CLASS_ENCODER(RGWDefaultZoneGroupInfo
)
666 struct RGWZoneGroupPlacementTarget
{
668 set
<std::string
> tags
;
669 set
<std::string
> storage_classes
;
671 bool user_permitted(const list
<std::string
>& user_tags
) const {
675 for (auto& rule
: user_tags
) {
676 if (tags
.find(rule
) != tags
.end()) {
683 void encode(bufferlist
& bl
) const {
684 ENCODE_START(2, 1, bl
);
687 encode(storage_classes
, bl
);
691 void decode(bufferlist::const_iterator
& bl
) {
696 decode(storage_classes
, bl
);
698 if (storage_classes
.empty()) {
699 storage_classes
.insert(RGW_STORAGE_CLASS_STANDARD
);
703 void dump(Formatter
*f
) const;
704 void decode_json(JSONObj
*obj
);
706 WRITE_CLASS_ENCODER(RGWZoneGroupPlacementTarget
)
708 struct RGWZoneGroup
: public RGWSystemMetaObj
{
709 std::string api_name
;
710 list
<std::string
> endpoints
;
711 bool is_master
= false;
713 rgw_zone_id master_zone
;
714 map
<rgw_zone_id
, RGWZone
> zones
;
716 map
<std::string
, RGWZoneGroupPlacementTarget
> placement_targets
;
717 rgw_placement_rule default_placement
;
719 list
<std::string
> hostnames
;
720 list
<std::string
> hostnames_s3website
;
721 // TODO: Maybe convert hostnames to a map<std::string,list<std::string>> for
722 // endpoint_type->hostnames
724 20:05 < _robbat21irssi> maybe I do someting like: if (hostname_map.empty()) { populate all map keys from hostnames; };
725 20:05 < _robbat21irssi> but that's a later compatability migration planning bit
726 20:06 < yehudasa> more like if (!hostnames.empty()) {
727 20:06 < yehudasa> for (list<std::string>::iterator iter = hostnames.begin(); iter != hostnames.end(); ++iter) {
728 20:06 < yehudasa> hostname_map["s3"].append(iter->second);
729 20:07 < yehudasa> hostname_map["s3website"].append(iter->second);
730 20:07 < yehudasa> s/append/push_back/g
731 20:08 < _robbat21irssi> inner loop over APIs
732 20:08 < yehudasa> yeah, probably
733 20:08 < _robbat21irssi> s3, s3website, swift, swith_auth, swift_website
735 map
<std::string
, list
<std::string
> > api_hostname_map
;
736 map
<std::string
, list
<std::string
> > api_endpoints_map
;
738 std::string realm_id
;
740 rgw_sync_policy_info sync_policy
;
742 RGWZoneGroup(): is_master(false){}
743 RGWZoneGroup(const std::string
&id
, const std::string
&name
):RGWSystemMetaObj(id
, name
) {}
744 explicit RGWZoneGroup(const std::string
&_name
):RGWSystemMetaObj(_name
) {}
745 RGWZoneGroup(const std::string
&_name
, bool _is_master
, CephContext
*cct
, RGWSI_SysObj
* sysobj_svc
,
746 const std::string
& _realm_id
, const list
<std::string
>& _endpoints
)
747 : RGWSystemMetaObj(_name
, cct
, sysobj_svc
), endpoints(_endpoints
), is_master(_is_master
),
748 realm_id(_realm_id
) {}
750 bool is_master_zonegroup() const { return is_master
;}
751 void update_master(bool _is_master
) {
752 is_master
= _is_master
;
753 post_process_params();
755 void post_process_params();
757 void encode(bufferlist
& bl
) const override
{
758 ENCODE_START(5, 1, bl
);
760 encode(api_name
, bl
);
761 encode(is_master
, bl
);
762 encode(endpoints
, bl
);
763 encode(master_zone
, bl
);
765 encode(placement_targets
, bl
);
766 encode(default_placement
, bl
);
767 encode(hostnames
, bl
);
768 encode(hostnames_s3website
, bl
);
769 RGWSystemMetaObj::encode(bl
);
770 encode(realm_id
, bl
);
771 encode(sync_policy
, bl
);
775 void decode(bufferlist::const_iterator
& bl
) override
{
778 decode(api_name
, bl
);
779 decode(is_master
, bl
);
780 decode(endpoints
, bl
);
781 decode(master_zone
, bl
);
783 decode(placement_targets
, bl
);
784 decode(default_placement
, bl
);
786 decode(hostnames
, bl
);
789 decode(hostnames_s3website
, bl
);
792 RGWSystemMetaObj::decode(bl
);
793 decode(realm_id
, bl
);
798 decode(sync_policy
, bl
);
803 int read_default_id(std::string
& default_id
, bool old_format
= false) override
;
804 int set_as_default(bool exclusive
= false) override
;
805 int create_default(bool old_format
= false);
806 int equals(const std::string
& other_zonegroup
) const;
807 int add_zone(const RGWZoneParams
& zone_params
, bool *is_master
, bool *read_only
,
808 const list
<std::string
>& endpoints
, const std::string
*ptier_type
,
809 bool *psync_from_all
, list
<std::string
>& sync_from
,
810 list
<std::string
>& sync_from_rm
, std::string
*predirect_zone
,
811 std::optional
<int> bucket_index_max_shards
, RGWSyncModulesManager
*sync_mgr
);
812 int remove_zone(const std::string
& zone_id
);
813 int rename_zone(const RGWZoneParams
& zone_params
);
814 rgw_pool
get_pool(CephContext
*cct
) const override
;
815 const std::string
get_default_oid(bool old_region_format
= false) const override
;
816 const std::string
& get_info_oid_prefix(bool old_region_format
= false) const override
;
817 const std::string
& get_names_oid_prefix() const override
;
818 const std::string
& get_predefined_name(CephContext
*cct
) const override
;
820 void dump(Formatter
*f
) const;
821 void decode_json(JSONObj
*obj
);
822 static void generate_test_instances(list
<RGWZoneGroup
*>& o
);
824 WRITE_CLASS_ENCODER(RGWZoneGroup
)
829 map
<std::string
, RGWZoneGroup
> zonegroups
;
830 map
<std::string
, RGWZoneGroup
> zonegroups_by_api
;
831 map
<std::string
, uint32_t> short_zone_ids
;
833 std::string master_zonegroup
;
835 void encode(bufferlist
& bl
) const;
836 void decode(bufferlist::const_iterator
& bl
);
838 int update(const RGWZoneGroup
& zonegroup
, CephContext
*cct
);
840 void dump(Formatter
*f
) const;
841 void decode_json(JSONObj
*obj
);
845 zonegroups_by_api
.clear();
846 master_zonegroup
.clear();
849 uint32_t get_zone_short_id(const std::string
& zone_id
) const;
851 WRITE_CLASS_ENCODER(RGWPeriodMap
)
853 struct RGWPeriodConfig
855 RGWQuotaInfo bucket_quota
;
856 RGWQuotaInfo user_quota
;
858 void encode(bufferlist
& bl
) const {
859 ENCODE_START(1, 1, bl
);
860 encode(bucket_quota
, bl
);
861 encode(user_quota
, bl
);
865 void decode(bufferlist::const_iterator
& bl
) {
867 decode(bucket_quota
, bl
);
868 decode(user_quota
, bl
);
872 void dump(Formatter
*f
) const;
873 void decode_json(JSONObj
*obj
);
875 // the period config must be stored in a local object outside of the period,
876 // so that it can be used in a default configuration where no realm/period
878 int read(RGWSI_SysObj
*sysobj_svc
, const std::string
& realm_id
);
879 int write(RGWSI_SysObj
*sysobj_svc
, const std::string
& realm_id
);
881 static std::string
get_oid(const std::string
& realm_id
);
882 static rgw_pool
get_pool(CephContext
*cct
);
884 WRITE_CLASS_ENCODER(RGWPeriodConfig
)
886 /* for backward comaptability */
887 struct RGWRegionMap
{
889 map
<std::string
, RGWZoneGroup
> regions
;
891 std::string master_region
;
893 RGWQuotaInfo bucket_quota
;
894 RGWQuotaInfo user_quota
;
896 void encode(bufferlist
& bl
) const;
897 void decode(bufferlist::const_iterator
& bl
);
899 void dump(Formatter
*f
) const;
900 void decode_json(JSONObj
*obj
);
902 WRITE_CLASS_ENCODER(RGWRegionMap
)
904 struct RGWZoneGroupMap
{
906 map
<std::string
, RGWZoneGroup
> zonegroups
;
907 map
<std::string
, RGWZoneGroup
> zonegroups_by_api
;
909 std::string master_zonegroup
;
911 RGWQuotaInfo bucket_quota
;
912 RGWQuotaInfo user_quota
;
914 /* construct the map */
915 int read(CephContext
*cct
, RGWSI_SysObj
*sysobj_svc
);
917 void encode(bufferlist
& bl
) const;
918 void decode(bufferlist::const_iterator
& bl
);
920 void dump(Formatter
*f
) const;
921 void decode_json(JSONObj
*obj
);
923 WRITE_CLASS_ENCODER(RGWZoneGroupMap
)
928 class RGWRealm
: public RGWSystemMetaObj
930 std::string current_period
;
931 epoch_t epoch
{0}; //< realm epoch, incremented for each new period
933 int create_control(bool exclusive
);
934 int delete_control();
937 RGWRealm(const std::string
& _id
, const std::string
& _name
= "") : RGWSystemMetaObj(_id
, _name
) {}
938 RGWRealm(CephContext
*_cct
, RGWSI_SysObj
*_sysobj_svc
): RGWSystemMetaObj(_cct
, _sysobj_svc
) {}
939 RGWRealm(const std::string
& _name
, CephContext
*_cct
, RGWSI_SysObj
*_sysobj_svc
): RGWSystemMetaObj(_name
, _cct
, _sysobj_svc
){}
941 void encode(bufferlist
& bl
) const override
{
942 ENCODE_START(1, 1, bl
);
943 RGWSystemMetaObj::encode(bl
);
944 encode(current_period
, bl
);
949 void decode(bufferlist::const_iterator
& bl
) override
{
951 RGWSystemMetaObj::decode(bl
);
952 decode(current_period
, bl
);
957 int create(bool exclusive
= true) override
;
959 rgw_pool
get_pool(CephContext
*cct
) const override
;
960 const std::string
get_default_oid(bool old_format
= false) const override
;
961 const std::string
& get_names_oid_prefix() const override
;
962 const std::string
& get_info_oid_prefix(bool old_format
= false) const override
;
963 const std::string
& get_predefined_name(CephContext
*cct
) const override
;
965 using RGWSystemMetaObj::read_id
; // expose as public for radosgw-admin
967 void dump(Formatter
*f
) const;
968 void decode_json(JSONObj
*obj
);
969 static void generate_test_instances(list
<RGWRealm
*>& o
);
971 const std::string
& get_current_period() const {
972 return current_period
;
974 int set_current_period(RGWPeriod
& period
);
975 void clear_current_period_and_epoch() {
976 current_period
.clear();
979 epoch_t
get_epoch() const { return epoch
; }
981 std::string
get_control_oid() const;
982 /// send a notify on the realm control object
983 int notify_zone(bufferlist
& bl
);
984 /// notify the zone of a new period
985 int notify_new_period(const RGWPeriod
& period
);
987 WRITE_CLASS_ENCODER(RGWRealm
)
989 struct RGWPeriodLatestEpochInfo
{
992 void encode(bufferlist
& bl
) const {
993 ENCODE_START(1, 1, bl
);
998 void decode(bufferlist::const_iterator
& bl
) {
1004 void dump(Formatter
*f
) const;
1005 void decode_json(JSONObj
*obj
);
1006 static void generate_test_instances(list
<RGWPeriodLatestEpochInfo
*>& o
);
1008 WRITE_CLASS_ENCODER(RGWPeriodLatestEpochInfo
)
1012 * The RGWPeriod object contains the entire configuration of a
1013 * RGWRealm, including its RGWZoneGroups and RGWZones. Consistency of
1014 * this configuration is maintained across all zones by passing around
1015 * the RGWPeriod object in its JSON representation.
1017 * If a new configuration changes which zone is the metadata master
1018 * zone (i.e., master zone of the master zonegroup), then a new
1019 * RGWPeriod::id (a uuid) is generated, its RGWPeriod::realm_epoch is
1020 * incremented, and the RGWRealm object is updated to reflect that new
1021 * current_period id and epoch. If the configuration changes BUT which
1022 * zone is the metadata master does NOT change, then only the
1023 * RGWPeriod::epoch is incremented (and the RGWPeriod::id remains the
1026 * When a new RGWPeriod is created with a new RGWPeriod::id (uuid), it
1027 * is linked back to its predecessor RGWPeriod through the
1028 * RGWPeriod::predecessor_uuid field, thus creating a "linked
1029 * list"-like structure of RGWPeriods back to the cluster's creation.
1033 std::string id
; //< a uuid
1035 std::string predecessor_uuid
;
1036 std::vector
<std::string
> sync_status
;
1037 RGWPeriodMap period_map
;
1038 RGWPeriodConfig period_config
;
1039 std::string master_zonegroup
;
1040 rgw_zone_id master_zone
;
1042 std::string realm_id
;
1043 std::string realm_name
;
1044 epoch_t realm_epoch
{1}; //< realm epoch when period was made current
1046 CephContext
*cct
{nullptr};
1047 RGWSI_SysObj
*sysobj_svc
{nullptr};
1050 int read_latest_epoch(RGWPeriodLatestEpochInfo
& epoch_info
,
1051 RGWObjVersionTracker
*objv
= nullptr);
1052 int use_latest_epoch();
1053 int use_current_period();
1055 const std::string
get_period_oid() const;
1056 const std::string
get_period_oid_prefix() const;
1058 // gather the metadata sync status for each shard; only for use on master zone
1059 int update_sync_status(rgw::sal::RGWRadosStore
*store
,
1060 const RGWPeriod
¤t_period
,
1061 std::ostream
& error_stream
, bool force_if_stale
);
1066 explicit RGWPeriod(const std::string
& period_id
, epoch_t _epoch
= 0)
1067 : id(period_id
), epoch(_epoch
) {}
1069 const std::string
& get_id() const { return id
; }
1070 epoch_t
get_epoch() const { return epoch
; }
1071 epoch_t
get_realm_epoch() const { return realm_epoch
; }
1072 const std::string
& get_predecessor() const { return predecessor_uuid
; }
1073 const rgw_zone_id
& get_master_zone() const { return master_zone
; }
1074 const std::string
& get_master_zonegroup() const { return master_zonegroup
; }
1075 const std::string
& get_realm() const { return realm_id
; }
1076 const RGWPeriodMap
& get_map() const { return period_map
; }
1077 RGWPeriodConfig
& get_config() { return period_config
; }
1078 const RGWPeriodConfig
& get_config() const { return period_config
; }
1079 const std::vector
<std::string
>& get_sync_status() const { return sync_status
; }
1080 rgw_pool
get_pool(CephContext
*cct
) const;
1081 const std::string
& get_latest_epoch_oid() const;
1082 const std::string
& get_info_oid_prefix() const;
1084 void set_user_quota(RGWQuotaInfo
& user_quota
) {
1085 period_config
.user_quota
= user_quota
;
1088 void set_bucket_quota(RGWQuotaInfo
& bucket_quota
) {
1089 period_config
.bucket_quota
= bucket_quota
;
1092 void set_id(const string
& _id
) {
1094 period_map
.id
= _id
;
1096 void set_epoch(epoch_t epoch
) { this->epoch
= epoch
; }
1097 void set_realm_epoch(epoch_t epoch
) { realm_epoch
= epoch
; }
1099 void set_predecessor(const std::string
& predecessor
)
1101 predecessor_uuid
= predecessor
;
1104 void set_realm_id(const std::string
& _realm_id
) {
1105 realm_id
= _realm_id
;
1110 int get_zonegroup(RGWZoneGroup
& zonegroup
,
1111 const std::string
& zonegroup_id
) const;
1113 bool is_single_zonegroup() const
1115 return (period_map
.zonegroups
.size() <= 1);
1119 returns true if there are several zone groups with a least one zone
1121 bool is_multi_zonegroups_with_zones() const
1124 for (const auto& zg
: period_map
.zonegroups
) {
1125 if (zg
.second
.zones
.size() > 0) {
1134 int get_latest_epoch(epoch_t
& epoch
);
1135 int set_latest_epoch(epoch_t epoch
, bool exclusive
= false,
1136 RGWObjVersionTracker
*objv
= nullptr);
1137 // update latest_epoch if the given epoch is higher, else return -EEXIST
1138 int update_latest_epoch(epoch_t epoch
);
1140 int init(CephContext
*_cct
, RGWSI_SysObj
*_sysobj_svc
, const std::string
&period_realm_id
, const std::string
&period_realm_name
= "",
1141 bool setup_obj
= true);
1142 int init(CephContext
*_cct
, RGWSI_SysObj
*_sysobj_svc
, bool setup_obj
= true);
1144 int create(bool exclusive
= true);
1146 int store_info(bool exclusive
);
1147 int add_zonegroup(const RGWZoneGroup
& zonegroup
);
1152 // commit a staging period; only for use on master zone
1153 int commit(rgw::sal::RGWRadosStore
*store
,
1154 RGWRealm
& realm
, const RGWPeriod
¤t_period
,
1155 std::ostream
& error_stream
, bool force_if_stale
= false);
1157 void encode(bufferlist
& bl
) const {
1158 ENCODE_START(1, 1, bl
);
1161 encode(realm_epoch
, bl
);
1162 encode(predecessor_uuid
, bl
);
1163 encode(sync_status
, bl
);
1164 encode(period_map
, bl
);
1165 encode(master_zone
, bl
);
1166 encode(master_zonegroup
, bl
);
1167 encode(period_config
, bl
);
1168 encode(realm_id
, bl
);
1169 encode(realm_name
, bl
);
1173 void decode(bufferlist::const_iterator
& bl
) {
1174 DECODE_START(1, bl
);
1177 decode(realm_epoch
, bl
);
1178 decode(predecessor_uuid
, bl
);
1179 decode(sync_status
, bl
);
1180 decode(period_map
, bl
);
1181 decode(master_zone
, bl
);
1182 decode(master_zonegroup
, bl
);
1183 decode(period_config
, bl
);
1184 decode(realm_id
, bl
);
1185 decode(realm_name
, bl
);
1188 void dump(Formatter
*f
) const;
1189 void decode_json(JSONObj
*obj
);
1190 static void generate_test_instances(list
<RGWPeriod
*>& o
);
1192 static std::string
get_staging_id(const std::string
& realm_id
) {
1193 return realm_id
+ ":staging";
1196 WRITE_CLASS_ENCODER(RGWPeriod
)