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_BASIC_TYPES_H
5 #define CEPH_RGW_BASIC_TYPES_H
9 #include "include/types.h"
12 class cls_user_bucket
;
20 explicit rgw_user(const std::string
& s
) {
23 rgw_user(const std::string
& tenant
, const std::string
& id
, const std::string
& ns
="")
28 rgw_user(std::string
&& tenant
, std::string
&& id
, std::string
&& ns
="")
29 : tenant(std::move(tenant
)),
34 void encode(ceph::buffer::list
& bl
) const {
35 ENCODE_START(2, 1, bl
);
41 void decode(ceph::buffer::list::const_iterator
& bl
) {
51 void to_str(std::string
& str
) const {
52 if (!tenant
.empty()) {
54 str
= tenant
+ '$' + ns
+ '$' + id
;
56 str
= tenant
+ '$' + id
;
58 } else if (!ns
.empty()) {
59 str
= '$' + ns
+ '$' + id
;
75 std::string
to_str() const {
81 void from_str(const std::string
& str
) {
82 size_t pos
= str
.find('$');
83 if (pos
!= std::string::npos
) {
84 tenant
= str
.substr(0, pos
);
85 std::string_view sv
= str
;
86 std::string_view ns_id
= sv
.substr(pos
+ 1);
87 size_t ns_pos
= ns_id
.find('$');
88 if (ns_pos
!= std::string::npos
) {
89 ns
= std::string(ns_id
.substr(0, ns_pos
));
90 id
= std::string(ns_id
.substr(ns_pos
+ 1));
93 id
= std::string(ns_id
);
102 rgw_user
& operator=(const std::string
& str
) {
107 int compare(const rgw_user
& u
) const {
108 int r
= tenant
.compare(u
.tenant
);
111 r
= ns
.compare(u
.ns
);
115 return id
.compare(u
.id
);
117 int compare(const std::string
& str
) const {
122 bool operator!=(const rgw_user
& rhs
) const {
123 return (compare(rhs
) != 0);
125 bool operator==(const rgw_user
& rhs
) const {
126 return (compare(rhs
) == 0);
128 bool operator<(const rgw_user
& rhs
) const {
129 if (tenant
< rhs
.tenant
) {
131 } else if (tenant
> rhs
.tenant
) {
136 } else if (ns
> rhs
.ns
) {
139 return (id
< rhs
.id
);
141 void dump(ceph::Formatter
*f
) const;
142 static void generate_test_instances(std::list
<rgw_user
*>& o
);
144 WRITE_CLASS_ENCODER(rgw_user
)
150 rgw_pool() = default;
151 rgw_pool(const rgw_pool
& _p
) : name(_p
.name
), ns(_p
.ns
) {}
152 rgw_pool(rgw_pool
&&) = default;
153 rgw_pool(const std::string
& _s
) {
156 rgw_pool(const std::string
& _name
, const std::string
& _ns
) : name(_name
), ns(_ns
) {}
158 std::string
to_str() const;
159 void from_str(const std::string
& s
);
161 void init(const std::string
& _s
) {
169 int compare(const rgw_pool
& p
) const {
170 int r
= name
.compare(p
.name
);
174 return ns
.compare(p
.ns
);
177 void encode(ceph::buffer::list
& bl
) const {
178 ENCODE_START(10, 10, bl
);
184 void decode_from_bucket(ceph::buffer::list::const_iterator
& bl
);
186 void decode(ceph::buffer::list::const_iterator
& bl
) {
187 DECODE_START_LEGACY_COMPAT_LEN(10, 3, 3, bl
);
194 * note that rgw_pool can be used where rgw_bucket was used before
195 * therefore we inherit rgw_bucket's old versions. However, we only
196 * need the first field from rgw_bucket. unless we add more fields
197 * in which case we'll need to look at struct_v, and check the actual
198 * version. Anything older than 10 needs to be treated as old rgw_bucket
208 rgw_pool
& operator=(const rgw_pool
&) = default;
210 bool operator==(const rgw_pool
& p
) const {
211 return (compare(p
) == 0);
213 bool operator!=(const rgw_pool
& p
) const {
214 return !(*this == p
);
216 bool operator<(const rgw_pool
& p
) const {
217 int r
= name
.compare(p
.name
);
219 return (ns
.compare(p
.ns
) < 0);
224 WRITE_CLASS_ENCODER(rgw_pool
)
226 inline std::ostream
& operator<<(std::ostream
& out
, const rgw_pool
& p
) {
231 struct rgw_data_placement_target
{
233 rgw_pool data_extra_pool
;
236 rgw_data_placement_target() = default;
237 rgw_data_placement_target(const rgw_data_placement_target
&) = default;
238 rgw_data_placement_target(rgw_data_placement_target
&&) = default;
240 rgw_data_placement_target(const rgw_pool
& data_pool
,
241 const rgw_pool
& data_extra_pool
,
242 const rgw_pool
& index_pool
)
243 : data_pool(data_pool
),
244 data_extra_pool(data_extra_pool
),
245 index_pool(index_pool
) {
248 rgw_data_placement_target
&
249 operator=(const rgw_data_placement_target
&) = default;
251 const rgw_pool
& get_data_extra_pool() const {
252 if (data_extra_pool
.empty()) {
255 return data_extra_pool
;
258 int compare(const rgw_data_placement_target
& t
) {
259 int c
= data_pool
.compare(t
.data_pool
);
263 c
= data_extra_pool
.compare(t
.data_extra_pool
);
267 return index_pool
.compare(t
.index_pool
);
270 void dump(ceph::Formatter
*f
) const;
271 void decode_json(JSONObj
*obj
);
274 struct rgw_bucket_key
{
277 std::string bucket_id
;
279 rgw_bucket_key(const std::string
& _tenant
,
280 const std::string
& _name
,
281 const std::string
& _bucket_id
) : tenant(_tenant
),
283 bucket_id(_bucket_id
) {}
284 rgw_bucket_key(const std::string
& _tenant
,
285 const std::string
& _name
) : tenant(_tenant
),
293 std::string bucket_id
;
294 rgw_data_placement_target explicit_placement
;
297 // cppcheck-suppress noExplicitConstructor
298 explicit rgw_bucket(const rgw_user
& u
, const cls_user_bucket
& b
);
300 rgw_bucket(const std::string
& _tenant
,
301 const std::string
& _name
,
302 const std::string
& _bucket_id
) : tenant(_tenant
),
304 bucket_id(_bucket_id
) {}
305 rgw_bucket(const rgw_bucket_key
& bk
) : tenant(bk
.tenant
),
307 bucket_id(bk
.bucket_id
) {}
308 rgw_bucket(const rgw_bucket
&) = default;
309 rgw_bucket(rgw_bucket
&&) = default;
311 bool match(const rgw_bucket
& b
) const {
312 return (tenant
== b
.tenant
&&
314 (bucket_id
== b
.bucket_id
||
316 b
.bucket_id
.empty()));
319 void convert(cls_user_bucket
*b
) const;
321 void encode(ceph::buffer::list
& bl
) const {
322 ENCODE_START(10, 10, bl
);
325 encode(bucket_id
, bl
);
327 bool encode_explicit
= !explicit_placement
.data_pool
.empty();
328 encode(encode_explicit
, bl
);
329 if (encode_explicit
) {
330 encode(explicit_placement
.data_pool
, bl
);
331 encode(explicit_placement
.data_extra_pool
, bl
);
332 encode(explicit_placement
.index_pool
, bl
);
336 void decode(ceph::buffer::list::const_iterator
& bl
) {
337 DECODE_START_LEGACY_COMPAT_LEN(10, 3, 3, bl
);
340 decode(explicit_placement
.data_pool
.name
, bl
);
348 snprintf(buf
, sizeof(buf
), "%" PRIu64
, id
);
351 decode(bucket_id
, bl
);
356 decode(explicit_placement
.index_pool
.name
, bl
);
358 explicit_placement
.index_pool
= explicit_placement
.data_pool
;
361 decode(explicit_placement
.data_extra_pool
.name
, bl
);
367 if (struct_v
>= 10) {
368 bool decode_explicit
= !explicit_placement
.data_pool
.empty();
369 decode(decode_explicit
, bl
);
370 if (decode_explicit
) {
371 decode(explicit_placement
.data_pool
, bl
);
372 decode(explicit_placement
.data_extra_pool
, bl
);
373 decode(explicit_placement
.index_pool
, bl
);
379 void update_bucket_id(const std::string
& new_bucket_id
) {
380 bucket_id
= new_bucket_id
;
383 // format a key for the bucket/instance. pass delim=0 to skip a field
384 std::string
get_key(char tenant_delim
= '/',
386 size_t reserve
= 0) const;
388 const rgw_pool
& get_data_extra_pool() const {
389 return explicit_placement
.get_data_extra_pool();
392 void dump(ceph::Formatter
*f
) const;
393 void decode_json(JSONObj
*obj
);
394 static void generate_test_instances(std::list
<rgw_bucket
*>& o
);
396 rgw_bucket
& operator=(const rgw_bucket
&) = default;
398 bool operator<(const rgw_bucket
& b
) const {
399 if (tenant
< b
.tenant
) {
401 } else if (tenant
> b
.tenant
) {
407 } else if (name
> b
.name
) {
411 return (bucket_id
< b
.bucket_id
);
414 bool operator==(const rgw_bucket
& b
) const {
415 return (tenant
== b
.tenant
) && (name
== b
.name
) && \
416 (bucket_id
== b
.bucket_id
);
418 bool operator!=(const rgw_bucket
& b
) const {
419 return (tenant
!= b
.tenant
) || (name
!= b
.name
) ||
420 (bucket_id
!= b
.bucket_id
);
423 WRITE_CLASS_ENCODER(rgw_bucket
)
425 inline std::ostream
& operator<<(std::ostream
& out
, const rgw_bucket
&b
) {
426 out
<< b
.tenant
<< ":" << b
.name
<< "[" << b
.bucket_id
<< "])";
430 struct rgw_bucket_shard
{
434 rgw_bucket_shard() : shard_id(-1) {}
435 rgw_bucket_shard(const rgw_bucket
& _b
, int _sid
) : bucket(_b
), shard_id(_sid
) {}
437 std::string
get_key(char tenant_delim
= '/', char id_delim
= ':',
438 char shard_delim
= ':') const;
440 bool operator<(const rgw_bucket_shard
& b
) const {
441 if (bucket
< b
.bucket
) {
444 if (b
.bucket
< bucket
) {
447 return shard_id
< b
.shard_id
;
450 bool operator==(const rgw_bucket_shard
& b
) const {
451 return (bucket
== b
.bucket
&&
452 shard_id
== b
.shard_id
);
456 inline std::ostream
& operator<<(std::ostream
& out
, const rgw_bucket_shard
& bs
) {
457 if (bs
.shard_id
<= 0) {
458 return out
<< bs
.bucket
;
461 return out
<< bs
.bucket
<< ":" << bs
.shard_id
;
469 rgw_zone_id(const std::string
& _id
) : id(_id
) {}
470 rgw_zone_id(std::string
&& _id
) : id(std::move(_id
)) {}
472 void encode(ceph::buffer::list
& bl
) const {
473 /* backward compatiblity, not using ENCODE_{START,END} macros */
474 ceph::encode(id
, bl
);
477 void decode(ceph::buffer::list::const_iterator
& bl
) {
478 /* backward compatiblity, not using DECODE_{START,END} macros */
479 ceph::decode(id
, bl
);
486 bool operator==(const std::string
& _id
) const {
489 bool operator==(const rgw_zone_id
& zid
) const {
490 return (id
== zid
.id
);
492 bool operator!=(const rgw_zone_id
& zid
) const {
493 return (id
!= zid
.id
);
495 bool operator<(const rgw_zone_id
& zid
) const {
496 return (id
< zid
.id
);
498 bool operator>(const rgw_zone_id
& zid
) const {
499 return (id
> zid
.id
);
506 WRITE_CLASS_ENCODER(rgw_zone_id
)
508 inline std::ostream
& operator<<(std::ostream
& os
, const rgw_zone_id
& zid
) {
514 struct rgw_placement_rule
;
518 extern void encode_json(const char *name
, const obj_version
& v
, Formatter
*f
);
519 extern void encode_json(const char *name
, const RGWUserCaps
& val
, Formatter
*f
);
520 extern void encode_json(const char *name
, const rgw_pool
& pool
, Formatter
*f
);
521 extern void encode_json(const char *name
, const rgw_placement_rule
& r
, Formatter
*f
);
522 extern void encode_json_impl(const char *name
, const rgw_zone_id
& zid
, ceph::Formatter
*f
);
523 extern void encode_json_plain(const char *name
, const RGWAccessKey
& val
, Formatter
*f
);
525 extern void decode_json_obj(obj_version
& v
, JSONObj
*obj
);
526 extern void decode_json_obj(rgw_zone_id
& zid
, JSONObj
*obj
);
527 extern void decode_json_obj(rgw_pool
& pool
, JSONObj
*obj
);
528 extern void decode_json_obj(rgw_placement_rule
& v
, JSONObj
*obj
);
530 // Represents an identity. This is more wide-ranging than a
531 // 'User'. Its purposes is to be matched against by an
532 // IdentityApplier. The internal representation will doubtless change as
533 // more types are added. We may want to expose the type enum and make
534 // the member public so people can switch/case on it.
539 enum types
{ User
, Role
, Tenant
, Wildcard
, OidcProvider
, AssumedRole
};
544 explicit Principal(types t
)
547 Principal(types t
, std::string
&& n
, std::string i
)
548 : t(t
), u(std::move(n
), std::move(i
)) {}
550 Principal(std::string
&& idp_url
)
551 : t(OidcProvider
), idp_url(std::move(idp_url
)) {}
555 static Principal
wildcard() {
556 return Principal(Wildcard
);
559 static Principal
user(std::string
&& t
, std::string
&& u
) {
560 return Principal(User
, std::move(t
), std::move(u
));
563 static Principal
role(std::string
&& t
, std::string
&& u
) {
564 return Principal(Role
, std::move(t
), std::move(u
));
567 static Principal
tenant(std::string
&& t
) {
568 return Principal(Tenant
, std::move(t
), {});
571 static Principal
oidc_provider(std::string
&& idp_url
) {
572 return Principal(std::move(idp_url
));
575 static Principal
assumed_role(std::string
&& t
, std::string
&& u
) {
576 return Principal(AssumedRole
, std::move(t
), std::move(u
));
579 bool is_wildcard() const {
580 return t
== Wildcard
;
583 bool is_user() const {
587 bool is_role() const {
591 bool is_tenant() const {
595 bool is_oidc_provider() const {
596 return t
== OidcProvider
;
599 bool is_assumed_role() const {
600 return t
== AssumedRole
;
603 const std::string
& get_tenant() const {
607 const std::string
& get_id() const {
611 const std::string
& get_idp_url() const {
615 const std::string
& get_role_session() const {
619 const std::string
& get_role() const {
623 bool operator ==(const Principal
& o
) const {
624 return (t
== o
.t
) && (u
== o
.u
);
627 bool operator <(const Principal
& o
) const {
628 return (t
< o
.t
) || ((t
== o
.t
) && (u
< o
.u
));
632 std::ostream
& operator <<(std::ostream
& m
, const Principal
& p
);
638 void decode_json_obj(rgw_user
& val
, JSONObj
*obj
);
639 void encode_json(const char *name
, const rgw_user
& val
, ceph::Formatter
*f
);
640 void encode_xml(const char *name
, const rgw_user
& val
, ceph::Formatter
*f
);
642 inline std::ostream
& operator<<(std::ostream
& out
, const rgw_user
&u
) {