[email protected] | 15f08dd | 2012-01-27 07:29:48 | [diff] [blame] | 1 | // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 | // Use of this source code is governed by a BSD-style license that can be |
| 3 | // found in the LICENSE file. |
| 4 | |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 5 | #ifndef TOOLS_JSON_SCHEMA_COMPILER_UTIL_H_ |
| 6 | #define TOOLS_JSON_SCHEMA_COMPILER_UTIL_H_ |
[email protected] | 15f08dd | 2012-01-27 07:29:48 | [diff] [blame] | 7 | |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 8 | #include <memory> |
[email protected] | 15f08dd | 2012-01-27 07:29:48 | [diff] [blame] | 9 | #include <string> |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 10 | #include <utility> |
[email protected] | 15f08dd | 2012-01-27 07:29:48 | [diff] [blame] | 11 | #include <vector> |
| 12 | |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 13 | #include "base/values.h" |
[email protected] | 15f08dd | 2012-01-27 07:29:48 | [diff] [blame] | 14 | |
| 15 | namespace json_schema_compiler { |
[email protected] | feba21e | 2012-03-02 15:05:27 | [diff] [blame] | 16 | |
[email protected] | 15f08dd | 2012-01-27 07:29:48 | [diff] [blame] | 17 | namespace util { |
| 18 | |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 19 | // Populates the item |out| from the value |from|. These are used by template |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 20 | // specializations of |Get(Optional)ArrayFromList|. |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 21 | bool PopulateItem(const base::Value& from, std::unique_ptr<base::Value>* out); |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 22 | |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 23 | bool PopulateItem(const base::Value& from, int* out); |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 24 | bool PopulateItem(const base::Value& from, int* out, base::string16* error); |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 25 | bool PopulateItem(const base::Value& from, bool* out); |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 26 | bool PopulateItem(const base::Value& from, bool* out, base::string16* error); |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 27 | bool PopulateItem(const base::Value& from, double* out); |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 28 | bool PopulateItem(const base::Value& from, double* out, base::string16* error); |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 29 | bool PopulateItem(const base::Value& from, std::string* out); |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 30 | bool PopulateItem(const base::Value& from, |
| 31 | std::string* out, |
| 32 | base::string16* error); |
jdoerrie | 9970f20e | 2018-07-20 21:41:18 | [diff] [blame] | 33 | bool PopulateItem(const base::Value& from, std::vector<uint8_t>* out); |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 34 | bool PopulateItem(const base::Value& from, |
jdoerrie | 9970f20e | 2018-07-20 21:41:18 | [diff] [blame] | 35 | std::vector<uint8_t>* out, |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 36 | base::string16* error); |
| 37 | bool PopulateItem(const base::Value& from, |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 38 | std::unique_ptr<base::Value>* out, |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 39 | base::string16* error); |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 40 | bool PopulateItem(const base::Value& from, std::unique_ptr<base::Value>* out); |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 41 | |
| 42 | // This template is used for types generated by tools/json_schema_compiler. |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 43 | template <class T> |
rdevlin.cronin | 63ef43c0 | 2016-03-22 22:11:00 | [diff] [blame] | 44 | bool PopulateItem(const base::Value& from, T* out) { |
| 45 | const base::DictionaryValue* dict = nullptr; |
| 46 | if (!from.GetAsDictionary(&dict)) |
| 47 | return false; |
| 48 | T obj; |
| 49 | if (!T::Populate(*dict, &obj)) |
| 50 | return false; |
| 51 | *out = std::move(obj); |
| 52 | return true; |
| 53 | } |
| 54 | |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 55 | // This template is used for types generated by tools/json_schema_compiler with |
| 56 | // error generation enabled. |
| 57 | template <class T> |
rdevlin.cronin | 8b7c710 | 2016-03-29 20:27:54 | [diff] [blame] | 58 | bool PopulateItem(const base::Value& from, T* out, base::string16* error) { |
rdevlin.cronin | 8b7c710 | 2016-03-29 20:27:54 | [diff] [blame] | 59 | T obj; |
Utkarsh Patankar | 96f049d | 2020-07-25 03:12:07 | [diff] [blame] | 60 | if (!T::Populate(from, &obj, error)) |
rdevlin.cronin | 8b7c710 | 2016-03-29 20:27:54 | [diff] [blame] | 61 | return false; |
| 62 | *out = std::move(obj); |
| 63 | return true; |
| 64 | } |
| 65 | |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 66 | // Populates |out| with |list|. Returns false if there is no list at the |
| 67 | // specified key or if the list has anything other than |T|. |
| 68 | template <class T> |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 69 | bool PopulateArrayFromList(const base::ListValue& list, std::vector<T>* out) { |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 70 | out->clear(); |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 71 | T item; |
dcheng | cb60e70 | 2016-05-25 18:30:47 | [diff] [blame] | 72 | for (const auto& value : list) { |
jdoerrie | a5676c6 | 2017-04-11 18:09:14 | [diff] [blame] | 73 | if (!PopulateItem(value, &item)) |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 74 | return false; |
rdevlin.cronin | 63ef43c0 | 2016-03-22 22:11:00 | [diff] [blame] | 75 | // T might not be movable, but in that case it should be copyable, and this |
| 76 | // will still work. |
| 77 | out->push_back(std::move(item)); |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 78 | } |
| 79 | |
| 80 | return true; |
| 81 | } |
| 82 | |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 83 | // Populates |out| with |list|. Returns false and sets |error| if there is no |
| 84 | // list at the specified key or if the list has anything other than |T|. |
| 85 | template <class T> |
| 86 | bool PopulateArrayFromList(const base::ListValue& list, |
| 87 | std::vector<T>* out, |
| 88 | base::string16* error) { |
| 89 | out->clear(); |
| 90 | T item; |
dcheng | cb60e70 | 2016-05-25 18:30:47 | [diff] [blame] | 91 | for (const auto& value : list) { |
jdoerrie | a5676c6 | 2017-04-11 18:09:14 | [diff] [blame] | 92 | if (!PopulateItem(value, &item, error)) |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 93 | return false; |
rdevlin.cronin | 8b7c710 | 2016-03-29 20:27:54 | [diff] [blame] | 94 | out->push_back(std::move(item)); |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 95 | } |
| 96 | |
| 97 | return true; |
| 98 | } |
| 99 | |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 100 | // Creates a new vector containing |list| at |out|. Returns |
[email protected] | 15f08dd | 2012-01-27 07:29:48 | [diff] [blame] | 101 | // true on success or if there is nothing at the specified key. Returns false |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 102 | // if anything other than a list of |T| is at the specified key. |
| 103 | template <class T> |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 104 | bool PopulateOptionalArrayFromList(const base::ListValue& list, |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 105 | std::unique_ptr<std::vector<T>>* out) { |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 106 | out->reset(new std::vector<T>()); |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 107 | if (!PopulateArrayFromList(list, out->get())) { |
| 108 | out->reset(); |
| 109 | return false; |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 110 | } |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 111 | return true; |
| 112 | } |
| 113 | |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 114 | template <class T> |
| 115 | bool PopulateOptionalArrayFromList(const base::ListValue& list, |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 116 | std::unique_ptr<std::vector<T>>* out, |
reillyg | 89a17f7 | 2015-05-06 02:34:27 | [diff] [blame] | 117 | base::string16* error) { |
| 118 | out->reset(new std::vector<T>()); |
| 119 | if (!PopulateArrayFromList(list, out->get(), error)) { |
| 120 | out->reset(); |
| 121 | return false; |
| 122 | } |
| 123 | return true; |
| 124 | } |
| 125 | |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 126 | // Appends a Value newly created from |from| to |out|. These used by template |
| 127 | // specializations of |Set(Optional)ArrayToList|. |
| 128 | void AddItemToList(const int from, base::ListValue* out); |
| 129 | void AddItemToList(const bool from, base::ListValue* out); |
| 130 | void AddItemToList(const double from, base::ListValue* out); |
| 131 | void AddItemToList(const std::string& from, base::ListValue* out); |
jdoerrie | 9970f20e | 2018-07-20 21:41:18 | [diff] [blame] | 132 | void AddItemToList(const std::vector<uint8_t>& from, base::ListValue* out); |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 133 | void AddItemToList(const std::unique_ptr<base::Value>& from, |
| 134 | base::ListValue* out); |
| 135 | void AddItemToList(const std::unique_ptr<base::DictionaryValue>& from, |
[email protected] | 242d5e7a | 2013-01-17 06:50:31 | [diff] [blame] | 136 | base::ListValue* out); |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 137 | |
| 138 | // This template is used for types generated by tools/json_schema_compiler. |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 139 | template <class T> |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 140 | void AddItemToList(const std::unique_ptr<T>& from, base::ListValue* out) { |
rdevlin.cronin | 3d8ce9c | 2016-04-04 21:14:16 | [diff] [blame] | 141 | out->Append(from->ToValue()); |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 142 | } |
| 143 | |
rdevlin.cronin | 63ef43c0 | 2016-03-22 22:11:00 | [diff] [blame] | 144 | // This template is used for types generated by tools/json_schema_compiler. |
| 145 | template <class T> |
| 146 | void AddItemToList(const T& from, base::ListValue* out) { |
| 147 | out->Append(from.ToValue()); |
| 148 | } |
| 149 | |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 150 | // Set |out| to the the contents of |from|. Requires PopulateItem to be |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 151 | // implemented for |T|. |
| 152 | template <class T> |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 153 | void PopulateListFromArray(const std::vector<T>& from, base::ListValue* out) { |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 154 | out->Clear(); |
rdevlin.cronin | 63ef43c0 | 2016-03-22 22:11:00 | [diff] [blame] | 155 | for (const T& item : from) |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 156 | AddItemToList(item, out); |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 157 | } |
| 158 | |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 159 | // Set |out| to the the contents of |from| if |from| is not null. Requires |
| 160 | // PopulateItem to be implemented for |T|. |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 161 | template <class T> |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 162 | void PopulateListFromOptionalArray(const std::unique_ptr<std::vector<T>>& from, |
pneubeck | de496d5 | 2015-01-19 08:49:53 | [diff] [blame] | 163 | base::ListValue* out) { |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 164 | if (from) |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 165 | PopulateListFromArray(*from, out); |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 166 | } |
| 167 | |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 168 | template <class T> |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 169 | std::unique_ptr<base::Value> CreateValueFromArray(const std::vector<T>& from) { |
| 170 | std::unique_ptr<base::ListValue> list(new base::ListValue()); |
| 171 | PopulateListFromArray(from, list.get()); |
| 172 | return std::move(list); |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 173 | } |
| 174 | |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 175 | template <class T> |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 176 | std::unique_ptr<base::Value> CreateValueFromOptionalArray( |
| 177 | const std::unique_ptr<std::vector<T>>& from) { |
thestig | e7615d6c | 2016-07-19 19:43:46 | [diff] [blame] | 178 | return from ? CreateValueFromArray(*from) : nullptr; |
[email protected] | cfe48490 | 2012-02-15 14:52:32 | [diff] [blame] | 179 | } |
| 180 | |
[email protected] | feba21e | 2012-03-02 15:05:27 | [diff] [blame] | 181 | } // namespace util |
| 182 | } // namespace json_schema_compiler |
[email protected] | 15f08dd | 2012-01-27 07:29:48 | [diff] [blame] | 183 | |
dcheng | a500b69 | 2016-04-08 19:55:42 | [diff] [blame] | 184 | #endif // TOOLS_JSON_SCHEMA_COMPILER_UTIL_H_ |