6 #include <include/types.h>
7 #include <boost/container/flat_map.hpp>
8 #include <boost/container/flat_set.hpp>
9 #include <include/ceph_fs.h>
10 #include "common/ceph_time.h"
12 #include "json_spirit/json_spirit.h"
14 #include "Formatter.h"
21 typedef std::map
<std::string
, JSONObj
*>::iterator map_iter_t
;
28 void set(const JSONObjIter::map_iter_t
&_cur
, const JSONObjIter::map_iter_t
&_end
);
46 void set(std::string_view s
, bool q
) {
52 std::string name
; // corresponds to obj_type in XMLObj
53 json_spirit::Value data
;
55 bool data_quoted
{false};
56 std::multimap
<std::string
, JSONObj
*> children
;
57 std::map
<std::string
, data_val
> attr_map
;
58 void handle_value(json_spirit::Value v
);
62 JSONObj() : parent(NULL
){}
66 void init(JSONObj
*p
, json_spirit::Value v
, std::string n
);
68 std::string
& get_name() { return name
; }
69 data_val
& get_data_val() { return val
; }
70 const std::string
& get_data() { return val
.str
; }
71 bool get_data(const std::string
& key
, data_val
*dest
);
72 JSONObj
*get_parent();
73 void add_child(std::string el
, JSONObj
*child
);
74 bool get_attr(std::string name
, data_val
& attr
);
75 JSONObjIter
find(const std::string
& name
);
76 JSONObjIter
find_first();
77 JSONObjIter
find_first(const std::string
& name
);
78 JSONObj
*find_obj(const std::string
& name
);
80 friend std::ostream
& operator<<(std::ostream
&out
,
81 const JSONObj
&obj
); // does not work, FIXME
85 std::vector
<std::string
> get_array_elements();
88 inline std::ostream
& operator<<(std::ostream
&out
, const JSONObj::data_val
& dv
) {
89 const char *q
= (dv
.quoted
? "\"" : "");
90 out
<< q
<< dv
.str
<< q
;
94 class JSONParser
: public JSONObj
97 std::string json_buffer
;
101 ~JSONParser() override
;
102 void handle_data(const char *s
, int len
);
104 bool parse(const char *buf_
, int len
);
107 bool parse(const char *file_name
);
109 const char *get_json() { return json_buffer
.c_str(); }
110 void set_failure() { success
= false; }
113 void encode_json(const char *name
, const JSONObj::data_val
& v
, ceph::Formatter
*f
);
117 struct err
: std::runtime_error
{
118 using runtime_error::runtime_error
;
123 JSONDecoder(ceph::buffer::list
& bl
) {
124 if (!parser
.parse(bl
.c_str(), bl
.length())) {
125 std::cout
<< "JSONDecoder::err()" << std::endl
;
126 throw JSONDecoder::err("failed to parse JSON input");
131 static bool decode_json(const char *name
, T
& val
, JSONObj
*obj
, bool mandatory
= false);
134 static bool decode_json(const char *name
, C
& container
, void (*cb
)(C
&, JSONObj
*obj
), JSONObj
*obj
, bool mandatory
= false);
137 static void decode_json(const char *name
, T
& val
, const T
& default_val
, JSONObj
*obj
);
140 static bool decode_json(const char *name
, boost::optional
<T
>& val
, JSONObj
*obj
, bool mandatory
= false);
143 static bool decode_json(const char *name
, std::optional
<T
>& val
, JSONObj
*obj
, bool mandatory
= false);
148 void decode_json_obj(T
& val
, JSONObj
*obj
)
150 val
.decode_json(obj
);
153 inline void decode_json_obj(std::string
& val
, JSONObj
*obj
)
155 val
= obj
->get_data();
158 static inline void decode_json_obj(JSONObj::data_val
& val
, JSONObj
*obj
)
160 val
= obj
->get_data_val();
163 void decode_json_obj(unsigned long long& val
, JSONObj
*obj
);
164 void decode_json_obj(long long& val
, JSONObj
*obj
);
165 void decode_json_obj(unsigned long& val
, JSONObj
*obj
);
166 void decode_json_obj(long& val
, JSONObj
*obj
);
167 void decode_json_obj(unsigned& val
, JSONObj
*obj
);
168 void decode_json_obj(int& val
, JSONObj
*obj
);
169 void decode_json_obj(bool& val
, JSONObj
*obj
);
170 void decode_json_obj(ceph::buffer::list
& val
, JSONObj
*obj
);
172 void decode_json_obj(utime_t
& val
, JSONObj
*obj
);
173 void decode_json_obj(ceph_dir_layout
& i
, JSONObj
*obj
);
175 void decode_json_obj(ceph::real_time
& val
, JSONObj
*obj
);
176 void decode_json_obj(ceph::coarse_real_time
& val
, JSONObj
*obj
);
179 void decode_json_obj(std::list
<T
>& l
, JSONObj
*obj
)
183 JSONObjIter iter
= obj
->find_first();
185 for (; !iter
.end(); ++iter
) {
188 decode_json_obj(val
, o
);
194 void decode_json_obj(std::deque
<T
>& l
, JSONObj
*obj
)
198 JSONObjIter iter
= obj
->find_first();
200 for (; !iter
.end(); ++iter
) {
203 decode_json_obj(val
, o
);
209 void decode_json_obj(std::set
<T
>& l
, JSONObj
*obj
)
213 JSONObjIter iter
= obj
->find_first();
215 for (; !iter
.end(); ++iter
) {
218 decode_json_obj(val
, o
);
223 template<class T
, class Compare
, class Alloc
>
224 void decode_json_obj(boost::container::flat_set
<T
, Compare
, Alloc
>& l
, JSONObj
*obj
)
228 JSONObjIter iter
= obj
->find_first();
230 for (; !iter
.end(); ++iter
) {
233 decode_json_obj(val
, o
);
239 void decode_json_obj(std::vector
<T
>& l
, JSONObj
*obj
)
243 JSONObjIter iter
= obj
->find_first();
245 for (; !iter
.end(); ++iter
) {
248 decode_json_obj(val
, o
);
253 template<class K
, class V
, class C
= std::less
<K
> >
254 void decode_json_obj(std::map
<K
, V
, C
>& m
, JSONObj
*obj
)
258 JSONObjIter iter
= obj
->find_first();
260 for (; !iter
.end(); ++iter
) {
264 JSONDecoder::decode_json("key", key
, o
);
265 JSONDecoder::decode_json("val", val
, o
);
270 template<class K
, class V
, class C
= std::less
<K
> >
271 void decode_json_obj(boost::container::flat_map
<K
, V
, C
>& m
, JSONObj
*obj
)
275 JSONObjIter iter
= obj
->find_first();
277 for (; !iter
.end(); ++iter
) {
281 JSONDecoder::decode_json("key", key
, o
);
282 JSONDecoder::decode_json("val", val
, o
);
287 template<class K
, class V
>
288 void decode_json_obj(std::multimap
<K
, V
>& m
, JSONObj
*obj
)
292 JSONObjIter iter
= obj
->find_first();
294 for (; !iter
.end(); ++iter
) {
298 JSONDecoder::decode_json("key", key
, o
);
299 JSONDecoder::decode_json("val", val
, o
);
300 m
.insert(make_pair(key
, val
));
304 template<class K
, class V
>
305 void decode_json_obj(boost::container::flat_map
<K
, V
>& m
, JSONObj
*obj
)
309 JSONObjIter iter
= obj
->find_first();
311 for (; !iter
.end(); ++iter
) {
315 JSONDecoder::decode_json("key", key
, o
);
316 JSONDecoder::decode_json("val", val
, o
);
321 void decode_json_obj(C
& container
, void (*cb
)(C
&, JSONObj
*obj
), JSONObj
*obj
)
325 JSONObjIter iter
= obj
->find_first();
327 for (; !iter
.end(); ++iter
) {
334 bool JSONDecoder::decode_json(const char *name
, T
& val
, JSONObj
*obj
, bool mandatory
)
336 JSONObjIter iter
= obj
->find_first(name
);
339 std::string s
= "missing mandatory field " + std::string(name
);
342 if constexpr (std::is_default_constructible_v
<T
>) {
349 decode_json_obj(val
, *iter
);
350 } catch (const err
& e
) {
351 std::string s
= std::string(name
) + ": ";
360 bool JSONDecoder::decode_json(const char *name
, C
& container
, void (*cb
)(C
&, JSONObj
*), JSONObj
*obj
, bool mandatory
)
364 JSONObjIter iter
= obj
->find_first(name
);
367 std::string s
= "missing mandatory field " + std::string(name
);
374 decode_json_obj(container
, cb
, *iter
);
375 } catch (const err
& e
) {
376 std::string s
= std::string(name
) + ": ";
385 void JSONDecoder::decode_json(const char *name
, T
& val
, const T
& default_val
, JSONObj
*obj
)
387 JSONObjIter iter
= obj
->find_first(name
);
394 decode_json_obj(val
, *iter
);
395 } catch (const err
& e
) {
397 std::string s
= std::string(name
) + ": ";
404 bool JSONDecoder::decode_json(const char *name
, boost::optional
<T
>& val
, JSONObj
*obj
, bool mandatory
)
406 JSONObjIter iter
= obj
->find_first(name
);
409 std::string s
= "missing mandatory field " + std::string(name
);
418 decode_json_obj(val
.get(), *iter
);
419 } catch (const err
& e
) {
421 std::string s
= std::string(name
) + ": ";
430 bool JSONDecoder::decode_json(const char *name
, std::optional
<T
>& val
, JSONObj
*obj
, bool mandatory
)
432 JSONObjIter iter
= obj
->find_first(name
);
435 std::string s
= "missing mandatory field " + std::string(name
);
444 decode_json_obj(*val
, *iter
);
445 } catch (const err
& e
) {
447 std::string s
= std::string(name
) + ": ";
455 class JSONEncodeFilter
460 virtual ~HandlerBase() {}
462 virtual std::type_index
get_type() = 0;
463 virtual void encode_json(const char *name
, const void *pval
, ceph::Formatter
*) const = 0;
467 class Handler
: public HandlerBase
{
469 virtual ~Handler() {}
471 std::type_index
get_type() override
{
472 return std::type_index(typeid(const T
&));
477 std::map
<std::type_index
, HandlerBase
*> handlers
;
480 void register_type(HandlerBase
*h
) {
481 handlers
[h
->get_type()] = h
;
485 bool encode_json(const char *name
, const T
& val
, ceph::Formatter
*f
) {
486 auto iter
= handlers
.find(std::type_index(typeid(val
)));
487 if (iter
== handlers
.end()) {
491 iter
->second
->encode_json(name
, (const void *)&val
, f
);
497 static void encode_json_impl(const char *name
, const T
& val
, ceph::Formatter
*f
)
499 f
->open_object_section(name
);
505 static void encode_json(const char *name
, const T
& val
, ceph::Formatter
*f
)
507 JSONEncodeFilter
*filter
= static_cast<JSONEncodeFilter
*>(f
->get_external_feature_handler("JSONEncodeFilter"));
510 !filter
->encode_json(name
, val
, f
)) {
511 encode_json_impl(name
, val
, f
);
517 void encode_json(const char *name
, std::string_view val
, ceph::Formatter
*f
);
518 void encode_json(const char *name
, const std::string
& val
, ceph::Formatter
*f
);
519 void encode_json(const char *name
, const char *val
, ceph::Formatter
*f
);
520 void encode_json(const char *name
, bool val
, ceph::Formatter
*f
);
521 void encode_json(const char *name
, int val
, ceph::Formatter
*f
);
522 void encode_json(const char *name
, unsigned val
, ceph::Formatter
*f
);
523 void encode_json(const char *name
, long val
, ceph::Formatter
*f
);
524 void encode_json(const char *name
, unsigned long val
, ceph::Formatter
*f
);
525 void encode_json(const char *name
, long long val
, ceph::Formatter
*f
);
526 void encode_json(const char *name
, const utime_t
& val
, ceph::Formatter
*f
);
527 void encode_json(const char *name
, const ceph::buffer::list
& bl
, ceph::Formatter
*f
);
528 void encode_json(const char *name
, long long unsigned val
, ceph::Formatter
*f
);
530 void encode_json(const char *name
, const ceph::real_time
& val
, ceph::Formatter
*f
);
531 void encode_json(const char *name
, const ceph::coarse_real_time
& val
, ceph::Formatter
*f
);
534 static void encode_json(const char *name
, const std::list
<T
>& l
, ceph::Formatter
*f
)
536 f
->open_array_section(name
);
537 for (auto iter
= l
.cbegin(); iter
!= l
.cend(); ++iter
) {
538 encode_json("obj", *iter
, f
);
544 static void encode_json(const char *name
, const std::deque
<T
>& l
, ceph::Formatter
*f
)
546 f
->open_array_section(name
);
547 for (auto iter
= l
.cbegin(); iter
!= l
.cend(); ++iter
) {
548 encode_json("obj", *iter
, f
);
553 template<class T
, class Compare
= std::less
<T
> >
554 static void encode_json(const char *name
, const std::set
<T
, Compare
>& l
, ceph::Formatter
*f
)
556 f
->open_array_section(name
);
557 for (auto iter
= l
.cbegin(); iter
!= l
.cend(); ++iter
) {
558 encode_json("obj", *iter
, f
);
563 template<class T
, class Compare
, class Alloc
>
564 static void encode_json(const char *name
,
565 const boost::container::flat_set
<T
, Compare
, Alloc
>& l
,
568 f
->open_array_section(name
);
569 for (auto iter
= l
.cbegin(); iter
!= l
.cend(); ++iter
) {
570 encode_json("obj", *iter
, f
);
576 static void encode_json(const char *name
, const std::vector
<T
>& l
, ceph::Formatter
*f
)
578 f
->open_array_section(name
);
579 for (auto iter
= l
.cbegin(); iter
!= l
.cend(); ++iter
) {
580 encode_json("obj", *iter
, f
);
585 template<class K
, class V
, class C
= std::less
<K
>>
586 static void encode_json(const char *name
, const std::map
<K
, V
, C
>& m
, ceph::Formatter
*f
)
588 f
->open_array_section(name
);
589 for (auto i
= m
.cbegin(); i
!= m
.cend(); ++i
) {
590 f
->open_object_section("entry");
591 encode_json("key", i
->first
, f
);
592 encode_json("val", i
->second
, f
);
598 template<class K
, class V
, class C
= std::less
<K
> >
599 static void encode_json(const char *name
, const boost::container::flat_map
<K
, V
, C
>& m
, ceph::Formatter
*f
)
601 f
->open_array_section(name
);
602 for (auto i
= m
.cbegin(); i
!= m
.cend(); ++i
) {
603 f
->open_object_section("entry");
604 encode_json("key", i
->first
, f
);
605 encode_json("val", i
->second
, f
);
611 template<class K
, class V
>
612 static void encode_json(const char *name
, const std::multimap
<K
, V
>& m
, ceph::Formatter
*f
)
614 f
->open_array_section(name
);
615 for (auto i
= m
.begin(); i
!= m
.end(); ++i
) {
616 f
->open_object_section("entry");
617 encode_json("key", i
->first
, f
);
618 encode_json("val", i
->second
, f
);
624 template<class K
, class V
>
625 static void encode_json(const char *name
, const boost::container::flat_map
<K
, V
>& m
, ceph::Formatter
*f
)
627 f
->open_array_section(name
);
628 for (auto i
= m
.begin(); i
!= m
.end(); ++i
) {
629 f
->open_object_section("entry");
630 encode_json("key", i
->first
, f
);
631 encode_json("val", i
->second
, f
);
637 template<class K
, class V
>
638 void encode_json_map(const char *name
, const std::map
<K
, V
>& m
, ceph::Formatter
*f
)
640 f
->open_array_section(name
);
641 for (auto iter
= m
.cbegin(); iter
!= m
.cend(); ++iter
) {
642 encode_json("obj", iter
->second
, f
);
648 template<class K
, class V
>
649 void encode_json_map(const char *name
, const char *index_name
,
650 const char *object_name
, const char *value_name
,
651 void (*cb
)(const char *, const V
&, ceph::Formatter
*, void *), void *parent
,
652 const std::map
<K
, V
>& m
, ceph::Formatter
*f
)
654 f
->open_array_section(name
);
655 for (auto iter
= m
.cbegin(); iter
!= m
.cend(); ++iter
) {
657 f
->open_object_section("key_value");
658 f
->dump_string(index_name
, iter
->first
);
662 f
->open_object_section(object_name
);
666 cb(value_name
, iter
->second
, f
, parent
);
668 encode_json(value_name
, iter
->second
, f
);
681 template<class K
, class V
>
682 void encode_json_map(const char *name
, const char *index_name
,
683 const char *object_name
, const char *value_name
,
684 const std::map
<K
, V
>& m
, ceph::Formatter
*f
)
686 encode_json_map
<K
, V
>(name
, index_name
, object_name
, value_name
, NULL
, NULL
, m
, f
);
689 template<class K
, class V
>
690 void encode_json_map(const char *name
, const char *index_name
, const char *value_name
,
691 const std::map
<K
, V
>& m
, ceph::Formatter
*f
)
693 encode_json_map
<K
, V
>(name
, index_name
, NULL
, value_name
, NULL
, NULL
, m
, f
);
697 static void encode_json(const char *name
, const std::optional
<T
>& o
, ceph::Formatter
*f
)
702 encode_json(name
, *o
, f
);
706 template<class K
, class V
>
707 void encode_json_map(const char *name
, const boost::container::flat_map
<K
, V
>& m
, ceph::Formatter
*f
)
709 f
->open_array_section(name
);
710 for (auto iter
= m
.cbegin(); iter
!= m
.cend(); ++iter
) {
711 encode_json("obj", iter
->second
, f
);
717 template<class K
, class V
>
718 void encode_json_map(const char *name
, const char *index_name
,
719 const char *object_name
, const char *value_name
,
720 void (*cb
)(const char *, const V
&, ceph::Formatter
*, void *), void *parent
,
721 const boost::container::flat_map
<K
, V
>& m
, ceph::Formatter
*f
)
723 f
->open_array_section(name
);
724 for (auto iter
= m
.cbegin(); iter
!= m
.cend(); ++iter
) {
726 f
->open_object_section("key_value");
727 f
->dump_string(index_name
, iter
->first
);
731 f
->open_object_section(object_name
);
735 cb(value_name
, iter
->second
, f
, parent
);
737 encode_json(value_name
, iter
->second
, f
);
750 template<class K
, class V
>
751 void encode_json_map(const char *name
, const char *index_name
,
752 const char *object_name
, const char *value_name
,
753 const boost::container::flat_map
<K
, V
>& m
, ceph::Formatter
*f
)
755 encode_json_map
<K
, V
>(name
, index_name
, object_name
, value_name
, NULL
, NULL
, m
, f
);
758 template<class K
, class V
>
759 void encode_json_map(const char *name
, const char *index_name
, const char *value_name
,
760 const boost::container::flat_map
<K
, V
>& m
, ceph::Formatter
*f
)
762 encode_json_map
<K
, V
>(name
, index_name
, NULL
, value_name
, NULL
, NULL
, m
, f
);
766 class JSONFormattable
: public ceph::JSONFormatter
{
767 JSONObj::data_val value
;
768 std::vector
<JSONFormattable
> arr
;
769 std::map
<std::string
, JSONFormattable
> obj
;
771 std::vector
<JSONFormattable
*> enc_stack
;
772 JSONFormattable
*cur_enc
;
775 bool handle_value(std::string_view name
, std::string_view s
, bool quoted
) override
;
776 bool handle_open_section(std::string_view name
, const char *ns
, bool section_is_array
) override
;
777 bool handle_close_section() override
;
780 JSONFormattable(bool p
= false) : JSONFormatter(p
) {
782 enc_stack
.push_back(cur_enc
);
792 void set_type(Type t
) {
796 void decode_json(JSONObj
*jo
) {
797 if (jo
->is_array()) {
798 set_type(JSONFormattable::FMT_ARRAY
);
799 decode_json_obj(arr
, jo
);
800 } else if (jo
->is_object()) {
801 set_type(JSONFormattable::FMT_OBJ
);
802 auto iter
= jo
->find_first();
803 for (;!iter
.end(); ++iter
) {
804 JSONObj
*field
= *iter
;
805 decode_json_obj(obj
[field
->get_name()], field
);
808 set_type(JSONFormattable::FMT_VALUE
);
809 decode_json_obj(value
, jo
);
813 void encode(ceph::buffer::list
& bl
) const {
814 ENCODE_START(2, 1, bl
);
815 encode((uint8_t)type
, bl
);
816 encode(value
.str
, bl
);
819 encode(value
.quoted
, bl
);
823 void decode(ceph::buffer::list::const_iterator
& bl
) {
828 decode(value
.str
, bl
);
832 decode(value
.quoted
, bl
);
839 const std::string
& val() const {
844 long val_long() const;
845 long long val_long_long() const;
846 bool val_bool() const;
848 const std::map
<std::string
, JSONFormattable
> object() const {
852 const std::vector
<JSONFormattable
>& array() const {
856 const JSONFormattable
& operator[](const std::string
& name
) const;
857 const JSONFormattable
& operator[](size_t index
) const;
859 JSONFormattable
& operator[](const std::string
& name
);
860 JSONFormattable
& operator[](size_t index
);
862 operator std::string() const {
866 explicit operator int() const {
870 explicit operator long() const {
874 explicit operator long long() const {
875 return val_long_long();
878 explicit operator bool() const {
883 T
operator[](const std::string
& name
) const {
884 return this->operator[](name
)(T());
888 T
operator[](const std::string
& name
) {
889 return this->operator[](name
)(T());
892 std::string
operator ()(const char *def_val
) const {
893 return def(std::string(def_val
));
896 int operator()(int def_val
) const {
900 bool operator()(bool def_val
) const {
904 bool exists(const std::string
& name
) const;
905 bool exists(size_t index
) const;
907 std::string
def(const std::string
& def_val
) const;
908 int def(int def_val
) const;
909 bool def(bool def_val
) const;
911 bool find(const std::string
& name
, std::string
*val
) const;
913 std::string
get(const std::string
& name
, const std::string
& def_val
) const;
915 int get_int(const std::string
& name
, int def_val
) const;
916 bool get_bool(const std::string
& name
, bool def_val
) const;
918 int set(const std::string
& name
, const std::string
& val
);
919 int erase(const std::string
& name
);
921 void derive_from(const JSONFormattable
& jf
);
923 void encode_json(const char *name
, ceph::Formatter
*f
) const;
925 bool is_array() const {
926 return (type
== FMT_ARRAY
);
929 WRITE_CLASS_ENCODER(JSONFormattable
)
931 void encode_json(const char *name
, const JSONFormattable
& v
, ceph::Formatter
*f
);