123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290 |
- #pragma once
- #include <library/cpp/json/common/defs.h>
- #include <util/generic/string.h>
- #include <util/generic/hash.h>
- #include <util/generic/vector.h>
- #include <util/generic/deque.h>
- #include <util/generic/utility.h>
- #include <util/generic/yexception.h>
- namespace NJson {
- enum EJsonValueType {
- JSON_UNDEFINED /* "Undefined" */,
- JSON_NULL /* "Null" */,
- JSON_BOOLEAN /* "Boolean" */,
- JSON_INTEGER /* "Integer" */,
- JSON_DOUBLE /* "Double" */,
- JSON_STRING /* "String" */,
- JSON_MAP /* "Map" */,
- JSON_ARRAY /* "Array" */,
- JSON_UINTEGER /* "UInteger" */
- };
- class TJsonValue;
- class IScanCallback {
- public:
- virtual ~IScanCallback() = default;
- virtual bool Do(const TString& path, TJsonValue* parent, TJsonValue& value) = 0;
- };
- class TJsonValue {
- void Clear() noexcept;
- public:
- typedef THashMap<TString, TJsonValue> TMapType;
- typedef TDeque<TJsonValue> TArray;
- TJsonValue() noexcept = default;
- TJsonValue(EJsonValueType type);
- TJsonValue(bool value) noexcept;
- TJsonValue(int value) noexcept;
- TJsonValue(unsigned int value) noexcept;
- TJsonValue(long value) noexcept;
- TJsonValue(unsigned long value) noexcept;
- TJsonValue(long long value) noexcept;
- TJsonValue(unsigned long long value) noexcept;
- TJsonValue(double value) noexcept;
- TJsonValue(TString value);
- TJsonValue(const char* value);
- template <class T>
- TJsonValue(const T*) = delete;
- TJsonValue(TStringBuf value);
- TJsonValue(const std::string& s)
- : TJsonValue(TStringBuf(s))
- {
- }
- TJsonValue(const TJsonValue& vval);
- TJsonValue(TJsonValue&& vval) noexcept;
- TJsonValue& operator=(const TJsonValue& val);
- TJsonValue& operator=(TJsonValue&& val) noexcept;
- ~TJsonValue() {
- Clear();
- }
- EJsonValueType GetType() const noexcept;
- TJsonValue& SetType(EJsonValueType type);
- TJsonValue& SetValue(const TJsonValue& value);
- TJsonValue& SetValue(TJsonValue&& value);
- // for Map
- TJsonValue& InsertValue(const TString& key, const TJsonValue& value);
- TJsonValue& InsertValue(TStringBuf key, const TJsonValue& value);
- TJsonValue& InsertValue(const char* key, const TJsonValue& value);
- TJsonValue& InsertValue(const TString& key, TJsonValue&& value);
- TJsonValue& InsertValue(TStringBuf key, TJsonValue&& value);
- TJsonValue& InsertValue(const char* key, TJsonValue&& value);
- // for Array
- TJsonValue& AppendValue(const TJsonValue& value);
- TJsonValue& AppendValue(TJsonValue&& value);
- TJsonValue& Back();
- const TJsonValue& Back() const;
- bool GetValueByPath(TStringBuf path, TJsonValue& result, char delimiter = '.') const;
- bool SetValueByPath(TStringBuf path, const TJsonValue& value, char delimiter = '.');
- bool SetValueByPath(TStringBuf path, TJsonValue&& value, char delimiter = '.');
- // returns NULL on failure
- const TJsonValue* GetValueByPath(TStringBuf path, char delimiter = '.') const noexcept;
- TJsonValue* GetValueByPath(TStringBuf path, char delimiter = '.') noexcept;
- void EraseValue(TStringBuf key);
- void EraseValue(size_t index);
- TJsonValue& operator[](size_t idx);
- TJsonValue& operator[](const TStringBuf& key);
- const TJsonValue& operator[](size_t idx) const noexcept;
- const TJsonValue& operator[](const TStringBuf& key) const noexcept;
- bool GetBoolean() const;
- long long GetInteger() const;
- unsigned long long GetUInteger() const;
- double GetDouble() const;
- const TString& GetString() const;
- const TMapType& GetMap() const;
- const TArray& GetArray() const;
- //throwing TJsonException possible
- bool GetBooleanSafe() const;
- long long GetIntegerSafe() const;
- unsigned long long GetUIntegerSafe() const;
- double GetDoubleSafe() const;
- const TString& GetStringSafe() const;
- const TMapType& GetMapSafe() const;
- TMapType& GetMapSafe();
- const TArray& GetArraySafe() const;
- TArray& GetArraySafe();
- bool GetBooleanSafe(bool defaultValue) const;
- long long GetIntegerSafe(long long defaultValue) const;
- unsigned long long GetUIntegerSafe(unsigned long long defaultValue) const;
- double GetDoubleSafe(double defaultValue) const;
- TString GetStringSafe(const TString& defaultValue) const;
- bool GetBooleanRobust() const noexcept;
- long long GetIntegerRobust() const noexcept;
- unsigned long long GetUIntegerRobust() const noexcept;
- double GetDoubleRobust() const noexcept;
- TString GetStringRobust() const;
- // Exception-free accessors
- bool GetBoolean(bool* value) const noexcept;
- bool GetInteger(long long* value) const noexcept;
- bool GetUInteger(unsigned long long* value) const noexcept;
- bool GetDouble(double* value) const noexcept;
- bool GetMapPointer(const TMapType** value) const noexcept;
- bool GetArrayPointer(const TArray** value) const noexcept;
- bool GetString(TString* value) const;
- bool GetMap(TMapType* value) const;
- bool GetArray(TArray* value) const;
- bool GetValue(size_t index, TJsonValue* value) const;
- bool GetValue(TStringBuf key, TJsonValue* value) const;
- bool GetValuePointer(size_t index, const TJsonValue** value) const noexcept;
- bool GetValuePointer(TStringBuf key, const TJsonValue** value) const noexcept;
- bool GetValuePointer(TStringBuf key, TJsonValue** value) noexcept;
- // Checking for defined non-null value
- bool IsDefined() const noexcept {
- return Type != JSON_UNDEFINED && Type != JSON_NULL;
- }
- bool IsNull() const noexcept;
- bool IsBoolean() const noexcept;
- bool IsDouble() const noexcept;
- bool IsString() const noexcept;
- bool IsMap() const noexcept;
- bool IsArray() const noexcept;
- /// @return true if JSON_INTEGER or (JSON_UINTEGER and Value <= Max<long long>)
- bool IsInteger() const noexcept;
- /// @return true if JSON_UINTEGER or (JSON_INTEGER and Value >= 0)
- bool IsUInteger() const noexcept;
- bool Has(const TStringBuf& key) const noexcept;
- bool Has(size_t key) const noexcept;
- void Scan(IScanCallback& callback);
- /// Non-robust comparison.
- bool operator==(const TJsonValue& rhs) const;
- void Swap(TJsonValue& rhs) noexcept;
- // save using util/ysaveload.h serialization (not to JSON stream)
- void Save(IOutputStream* s) const;
- // load using util/ysaveload.h serialization (not as JSON stream)
- void Load(IInputStream* s);
- static const TJsonValue UNDEFINED;
- private:
- EJsonValueType Type = JSON_UNDEFINED;
- union TValueUnion {
- bool Boolean;
- long long Integer;
- unsigned long long UInteger;
- double Double;
- TString String;
- TMapType* Map;
- TArray* Array;
- TValueUnion() noexcept {
- Zero(*this);
- }
- ~TValueUnion() noexcept {
- }
- };
- TValueUnion Value;
- void DoScan(const TString& path, TJsonValue* parent, IScanCallback& callback);
- void SwapWithUndefined(TJsonValue& output) noexcept;
- /**
- @throw yexception if Back shouldn't be called on the object.
- */
- void BackChecks() const;
- };
- inline bool GetBoolean(const TJsonValue& jv, size_t index, bool* value) noexcept {
- return jv[index].GetBoolean(value);
- }
- inline bool GetInteger(const TJsonValue& jv, size_t index, long long* value) noexcept {
- return jv[index].GetInteger(value);
- }
- inline bool GetUInteger(const TJsonValue& jv, size_t index, unsigned long long* value) noexcept {
- return jv[index].GetUInteger(value);
- }
- inline bool GetDouble(const TJsonValue& jv, size_t index, double* value) noexcept {
- return jv[index].GetDouble(value);
- }
- inline bool GetString(const TJsonValue& jv, size_t index, TString* value) {
- return jv[index].GetString(value);
- }
- bool GetMapPointer(const TJsonValue& jv, size_t index, const TJsonValue::TMapType** value);
- bool GetArrayPointer(const TJsonValue& jv, size_t index, const TJsonValue::TArray** value);
- inline bool GetBoolean(const TJsonValue& jv, TStringBuf key, bool* value) noexcept {
- return jv[key].GetBoolean(value);
- }
- inline bool GetInteger(const TJsonValue& jv, TStringBuf key, long long* value) noexcept {
- return jv[key].GetInteger(value);
- }
- inline bool GetUInteger(const TJsonValue& jv, TStringBuf key, unsigned long long* value) noexcept {
- return jv[key].GetUInteger(value);
- }
- inline bool GetDouble(const TJsonValue& jv, TStringBuf key, double* value) noexcept {
- return jv[key].GetDouble(value);
- }
- inline bool GetString(const TJsonValue& jv, TStringBuf key, TString* value) {
- return jv[key].GetString(value);
- }
- bool GetMapPointer(const TJsonValue& jv, const TStringBuf key, const TJsonValue::TMapType** value);
- bool GetArrayPointer(const TJsonValue& jv, const TStringBuf key, const TJsonValue::TArray** value);
- class TJsonMap: public TJsonValue {
- public:
- TJsonMap()
- : TJsonValue(NJson::JSON_MAP)
- {}
- TJsonMap(const std::initializer_list<std::pair<TString, TJsonValue>>& list)
- : TJsonValue(NJson::JSON_MAP)
- {
- GetMapSafe() = THashMap<TString, TJsonValue>(list);
- }
- };
- class TJsonArray: public TJsonValue {
- public:
- TJsonArray()
- : TJsonValue(NJson::JSON_ARRAY)
- {}
- TJsonArray(const std::initializer_list<TJsonValue>& list)
- : TJsonValue(NJson::JSON_ARRAY)
- {
- GetArraySafe() = TJsonValue::TArray(list);
- }
- };
- }
|