• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2025 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  * http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "json_object.h"
17 
18 namespace OHOS {
19 namespace DistributedHardware {
20 
ToJson(JsonItemObject & itemObject,const std::string & value)21 void ToJson(JsonItemObject &itemObject, const std::string &value)
22 {
23     if (itemObject.item_ != nullptr) {
24         cJSON_Delete(itemObject.item_);
25     }
26     itemObject.item_ = cJSON_CreateString(value.c_str());
27 }
28 
ToJson(JsonItemObject & itemObject,const char * value)29 void ToJson(JsonItemObject &itemObject, const char *value)
30 {
31     if (itemObject.item_ != nullptr) {
32         cJSON_Delete(itemObject.item_);
33     }
34     itemObject.item_ = cJSON_CreateString(value);
35 }
36 
ToJson(JsonItemObject & itemObject,const double & value)37 void ToJson(JsonItemObject &itemObject, const double &value)
38 {
39     if (itemObject.item_ != nullptr) {
40         cJSON_Delete(itemObject.item_);
41     }
42     itemObject.item_ = cJSON_CreateNumber(value);
43 }
44 
ToJson(JsonItemObject & itemObject,const bool & value)45 void ToJson(JsonItemObject &itemObject, const bool &value)
46 {
47     if (itemObject.item_ != nullptr) {
48         cJSON_Delete(itemObject.item_);
49     }
50     itemObject.item_ = value ? cJSON_CreateTrue() : cJSON_CreateFalse();
51 }
52 
ToJson(JsonItemObject & itemObject,const uint8_t & value)53 void ToJson(JsonItemObject &itemObject, const uint8_t &value)
54 {
55     if (itemObject.item_ != nullptr) {
56         cJSON_Delete(itemObject.item_);
57     }
58     itemObject.item_ = cJSON_CreateNumber(value);
59 }
60 
ToJson(JsonItemObject & itemObject,const int16_t & value)61 void ToJson(JsonItemObject &itemObject, const int16_t &value)
62 {
63     if (itemObject.item_ != nullptr) {
64         cJSON_Delete(itemObject.item_);
65     }
66     itemObject.item_ = cJSON_CreateNumber(value);
67 }
68 
ToJson(JsonItemObject & itemObject,const uint16_t & value)69 void ToJson(JsonItemObject &itemObject, const uint16_t &value)
70 {
71     if (itemObject.item_ != nullptr) {
72         cJSON_Delete(itemObject.item_);
73     }
74     itemObject.item_ = cJSON_CreateNumber(value);
75 }
76 
ToJson(JsonItemObject & itemObject,const int32_t & value)77 void ToJson(JsonItemObject &itemObject, const int32_t &value)
78 {
79     if (itemObject.item_ != nullptr) {
80         cJSON_Delete(itemObject.item_);
81     }
82     itemObject.item_ = cJSON_CreateNumber(value);
83 }
84 
ToJson(JsonItemObject & itemObject,const uint32_t & value)85 void ToJson(JsonItemObject &itemObject, const uint32_t &value)
86 {
87     if (itemObject.item_ != nullptr) {
88         cJSON_Delete(itemObject.item_);
89     }
90     itemObject.item_ = cJSON_CreateNumber(value);
91 }
92 
ToJson(JsonItemObject & itemObject,const int64_t & value)93 void ToJson(JsonItemObject &itemObject, const int64_t &value)
94 {
95     if (itemObject.item_ != nullptr) {
96         cJSON_Delete(itemObject.item_);
97     }
98     itemObject.item_ = cJSON_CreateNumber(value);
99 }
100 
ToJson(JsonItemObject & itemObject,const uint64_t & value)101 void ToJson(JsonItemObject &itemObject, const uint64_t &value)
102 {
103     if (itemObject.item_ != nullptr) {
104         cJSON_Delete(itemObject.item_);
105     }
106     itemObject.item_ = cJSON_CreateNumber(value);
107 }
108 
FromJson(const JsonItemObject & itemObject,std::string & value)109 void FromJson(const JsonItemObject &itemObject, std::string &value)
110 {
111     itemObject.GetTo(value);
112 }
113 
FromJson(const JsonItemObject & itemObject,double & value)114 void FromJson(const JsonItemObject &itemObject, double &value)
115 {
116     itemObject.GetTo(value);
117 }
118 
FromJson(const JsonItemObject & itemObject,bool & value)119 void FromJson(const JsonItemObject &itemObject, bool &value)
120 {
121     itemObject.GetTo(value);
122 }
123 
FromJson(const JsonItemObject & itemObject,uint8_t & value)124 void FromJson(const JsonItemObject &itemObject, uint8_t &value)
125 {
126     int32_t tmpValue = 0;
127     itemObject.GetTo(tmpValue);
128     value = static_cast<uint8_t>(tmpValue);
129 }
130 
FromJson(const JsonItemObject & itemObject,int16_t & value)131 void FromJson(const JsonItemObject &itemObject, int16_t &value)
132 {
133     int32_t tmpValue = 0;
134     itemObject.GetTo(tmpValue);
135     value = static_cast<int16_t>(tmpValue);
136 }
137 
FromJson(const JsonItemObject & itemObject,uint16_t & value)138 void FromJson(const JsonItemObject &itemObject, uint16_t &value)
139 {
140     int32_t tmpValue = 0;
141     itemObject.GetTo(tmpValue);
142     value = static_cast<uint16_t>(tmpValue);
143 }
144 
FromJson(const JsonItemObject & itemObject,int32_t & value)145 void FromJson(const JsonItemObject &itemObject, int32_t &value)
146 {
147     itemObject.GetTo(value);
148 }
149 
FromJson(const JsonItemObject & itemObject,uint32_t & value)150 void FromJson(const JsonItemObject &itemObject, uint32_t &value)
151 {
152     int32_t tmpValue = 0;
153     itemObject.GetTo(tmpValue);
154     value = static_cast<uint32_t>(tmpValue);
155 }
156 
FromJson(const JsonItemObject & itemObject,int64_t & value)157 void FromJson(const JsonItemObject &itemObject, int64_t &value)
158 {
159     itemObject.GetTo(value);
160 }
161 
FromJson(const JsonItemObject & itemObject,uint64_t & value)162 void FromJson(const JsonItemObject &itemObject, uint64_t &value)
163 {
164     int64_t tmpValue = 0;
165     itemObject.GetTo(tmpValue);
166     value = static_cast<uint64_t>(tmpValue);
167 }
168 
ToString(const JsonItemObject & jsonItem)169 std::string ToString(const JsonItemObject &jsonItem)
170 {
171     return jsonItem.Dump();
172 }
173 
JsonItemObject()174 JsonItemObject::JsonItemObject()
175 {}
176 
JsonItemObject(const JsonItemObject & object)177 JsonItemObject::JsonItemObject(const JsonItemObject &object)
178 {
179     item_ = object.item_;
180     parent_ = object.parent_;
181     itemName_ = object.itemName_;
182     needDeleteItem_ = object.needDeleteItem_;
183     if (object.needDeleteItem_) {
184         item_ = cJSON_Duplicate(object.item_, cJSON_True);
185     }
186 }
187 
~JsonItemObject()188 JsonItemObject::~JsonItemObject()
189 {
190     Delete();
191 }
192 
Delete()193 void JsonItemObject::Delete()
194 {
195     if (needDeleteItem_ && item_ != nullptr) {
196         cJSON_Delete(item_);
197     }
198     item_ = nullptr;
199 }
200 
IsString() const201 bool JsonItemObject::IsString() const
202 {
203     if (item_ == nullptr) {
204         return false;
205     }
206     return cJSON_IsString(item_);
207 }
208 
IsNumber() const209 bool JsonItemObject::IsNumber() const
210 {
211     if (item_ == nullptr) {
212         return false;
213     }
214     return cJSON_IsNumber(item_);
215 }
216 
IsNumberInteger() const217 bool JsonItemObject::IsNumberInteger() const
218 {
219     if (!IsNumber()) {
220         return false;
221     }
222     double value = 0.0;
223     GetTo(value);
224     return ((value - static_cast<int64_t>(value)) == 0);
225 }
226 
IsArray() const227 bool JsonItemObject::IsArray() const
228 {
229     if (item_ == nullptr) {
230         return false;
231     }
232     return cJSON_IsArray(item_);
233 }
234 
IsBoolean() const235 bool JsonItemObject::IsBoolean() const
236 {
237     if (item_ == nullptr) {
238         return false;
239     }
240     return cJSON_IsBool(item_);
241 }
242 
IsObject() const243 bool JsonItemObject::IsObject() const
244 {
245     if (item_ == nullptr) {
246         return false;
247     }
248     return cJSON_IsObject(item_);
249 }
250 
Insert(const std::string & key,const JsonItemObject & object)251 void JsonItemObject::Insert(const std::string &key, const JsonItemObject &object)
252 {
253     if (item_ == nullptr || object.item_ == nullptr) {
254         LOGE("invalid item or object item");
255         return;
256     }
257     cJSON *newItem = cJSON_Duplicate(object.item_, cJSON_True);
258     if (newItem == nullptr) {
259         LOGE("copy item fail");
260         return;
261     }
262     if (cJSON_GetObjectItemCaseSensitive(item_, key.c_str()) != nullptr) {
263         cJSON_DeleteItemFromObjectCaseSensitive(item_, key.c_str());
264     }
265     if (!cJSON_AddItemToObject(item_, key.c_str(), newItem)) {
266         LOGE("add new item to object fail");
267         cJSON_Delete(newItem);
268     }
269 }
270 
operator =(const JsonItemObject & object)271 JsonItemObject& JsonItemObject::operator=(const JsonItemObject &object)
272 {
273     item_ = object.item_;
274     parent_ = object.parent_;
275     itemName_ = object.itemName_;
276     needDeleteItem_ = object.needDeleteItem_;
277     if (object.needDeleteItem_) {
278         item_ = cJSON_Duplicate(object.item_, cJSON_True);
279     }
280     return *this;
281 }
282 
DumpFormated() const283 std::string JsonItemObject::DumpFormated() const
284 {
285     return Dump(true);
286 }
287 
Dump() const288 std::string JsonItemObject::Dump() const
289 {
290     return Dump(false);
291 }
292 
Dump(bool formatFlag) const293 std::string JsonItemObject::Dump(bool formatFlag) const
294 {
295     if (item_ == nullptr) {
296         LOGE("item_ is nullptr");
297         return "";
298     }
299     char* jsonString = formatFlag ? cJSON_Print(item_) : cJSON_PrintUnformatted(item_);
300     if (jsonString == nullptr) {
301         return "";
302     }
303     std::string out(jsonString);
304     cJSON_free(jsonString);
305     return out;
306 }
307 
operator [](const std::string & key)308 JsonItemObject JsonItemObject::operator[](const std::string &key)
309 {
310     JsonItemObject itemObject = At(key);
311     if (itemObject.item_ == nullptr) {
312         itemObject.item_ = cJSON_CreateNull();
313         if (itemObject.item_ == nullptr) {
314             return itemObject;
315         }
316         if (!cJSON_AddItemToObject(item_, key.c_str(), itemObject.item_)) {
317             LOGE("add item to object fail");
318             cJSON_Delete(itemObject.item_);
319             itemObject.item_ = nullptr;
320         } else {
321             itemObject.beValid_ = true;
322         }
323     }
324     return itemObject;
325 }
326 
operator [](const std::string & key) const327 const JsonItemObject JsonItemObject::operator[](const std::string &key) const
328 {
329     return At(key);
330 }
331 
Contains(const std::string & key) const332 bool JsonItemObject::Contains(const std::string &key) const
333 {
334     if (item_ == nullptr) {
335         LOGE("item_ is nullptr");
336         return false;
337     }
338     cJSON* item = cJSON_GetObjectItemCaseSensitive(item_, key.c_str());
339     return (item != nullptr);
340 }
341 
IsDiscarded() const342 bool JsonItemObject::IsDiscarded() const
343 {
344     return (item_ == nullptr);
345 }
346 
PushBack(const std::string & strValue)347 bool JsonItemObject::PushBack(const std::string &strValue)
348 {
349     if (item_ == nullptr) {
350         LOGE("item_ is nullptr");
351         return false;
352     }
353     if (item_->type != cJSON_Array) {
354         LOGE("item_ type is not array");
355         return false;
356     }
357     cJSON *newItem = cJSON_CreateString(strValue.c_str());
358     return AddToArray(newItem);
359 }
360 
PushBack(const double & value)361 bool JsonItemObject::PushBack(const double &value)
362 {
363     if (item_ == nullptr) {
364         LOGE("item_ is nullptr");
365         return false;
366     }
367     if (item_->type != cJSON_Array) {
368         LOGE("item_ type is not array");
369         return false;
370     }
371     cJSON *newItem = cJSON_CreateNumber(value);
372     return AddToArray(newItem);
373 }
374 
PushBack(const JsonItemObject & item)375 bool JsonItemObject::PushBack(const JsonItemObject &item)
376 {
377     if (item_ == nullptr) {
378         LOGE("item_ is nullptr");
379         return false;
380     }
381     if (!item.beValid_ || !beValid_) {
382         return false;
383     }
384     if (item_->type != cJSON_Array) {
385         LOGE("item_ type is not array");
386         return false;
387     }
388     cJSON* newItem = cJSON_Duplicate(item.item_, cJSON_True);
389     return AddToArray(newItem);
390 }
391 
AddToArray(cJSON * newItem)392 bool JsonItemObject::AddToArray(cJSON *newItem)
393 {
394     if (item_ == nullptr) {
395         LOGE("item_ is nullptr");
396         return false;
397     }
398     if (!cJSON_AddItemToArray(item_, newItem)) {
399         LOGE("add item to array fail");
400         cJSON_Delete(newItem);
401         return false;
402     }
403     return true;
404 }
405 
Key() const406 std::string JsonItemObject::Key() const
407 {
408     if (item_ != nullptr) {
409         return std::string(item_->string);
410     }
411     return itemName_;
412 }
413 
At(const std::string & key) const414 JsonItemObject JsonItemObject::At(const std::string &key) const
415 {
416     JsonItemObject operationItem;
417     operationItem.item_ = cJSON_GetObjectItemCaseSensitive(item_, key.c_str());
418     if (operationItem.item_ != nullptr) {
419         operationItem.beValid_ = true;
420     }
421     operationItem.parent_ = item_;
422     operationItem.itemName_ = key;
423     return operationItem;
424 }
425 
GetTo(std::string & value) const426 void JsonItemObject::GetTo(std::string &value) const
427 {
428     value = "";
429     if (item_ == nullptr) {
430         LOGE("value item is null");
431         return;
432     }
433     if (!IsString()) {
434         return;
435     }
436     const char* strValue = cJSON_GetStringValue(item_);
437     if (strValue == nullptr) {
438         return;
439     }
440     value = std::string(strValue);
441 }
442 
GetTo(double & value) const443 void JsonItemObject::GetTo(double &value) const
444 {
445     value = 0.0;
446     if (item_ == nullptr) {
447         LOGE("value item is null");
448         return;
449     }
450     if (!IsNumber()) {
451         return;
452     }
453     value = cJSON_GetNumberValue(item_);
454 }
455 
GetTo(int32_t & value) const456 void JsonItemObject::GetTo(int32_t &value) const
457 {
458     double tmpValue = 0.0;
459     GetTo(tmpValue);
460     value = static_cast<int32_t>(tmpValue);
461 }
462 
GetTo(uint32_t & value) const463 void JsonItemObject::GetTo(uint32_t &value) const
464 {
465     double tmpValue = 0.0;
466     GetTo(tmpValue);
467     value = static_cast<uint32_t>(tmpValue);
468 }
469 
GetTo(int64_t & value) const470 void JsonItemObject::GetTo(int64_t &value) const
471 {
472     double tmpValue = 0.0;
473     GetTo(tmpValue);
474     value = static_cast<int64_t>(tmpValue);
475 }
476 
GetTo(bool & value) const477 void JsonItemObject::GetTo(bool &value) const
478 {
479     value = false;
480     if (item_ == nullptr) {
481         LOGE("value item is null");
482         return;
483     }
484     if (!IsBoolean()) {
485         return;
486     }
487     value = cJSON_IsTrue(item_) ? true : false;
488 }
489 
Items() const490 std::vector<JsonItemObject> JsonItemObject::Items() const
491 {
492     std::vector<JsonItemObject> items;
493     if (item_ == nullptr) {
494         return items;
495     }
496     cJSON *current = nullptr;
497     if (item_->type == cJSON_Object || item_->type == cJSON_Array) {
498         cJSON_ArrayForEach(current, item_) {
499             JsonItemObject child;
500             child.item_ = current;
501             child.parent_ = item_;
502             items.push_back(child);
503         }
504     }
505     return items;
506 }
507 
InitItem(JsonItemObject & item)508 bool JsonItemObject::InitItem(JsonItemObject &item)
509 {
510     if (!beValid_) {
511         LOGE("invalid item");
512         return false;
513     }
514     item.item_ = cJSON_CreateObject();
515     if (item.item_ == nullptr) {
516         LOGE("create new object item fail");
517         return false;
518     }
519     item.parent_ = parent_;
520     item.beValid_ = true;
521     item.itemName_ = itemName_;
522     item.itemIndex_ = itemIndex_;
523     return true;
524 }
525 
InitArray()526 bool JsonItemObject::InitArray()
527 {
528     if (!beValid_) {
529         return false;
530     }
531     cJSON *newItem = cJSON_CreateArray();
532     if (newItem == nullptr) {
533         return false;
534     }
535     if (!ReplaceItem(newItem)) {
536         cJSON_Delete(newItem);
537         return false;
538     }
539     return true;
540 }
541 
ReplaceItem(cJSON * newItem)542 bool JsonItemObject::ReplaceItem(cJSON *newItem)
543 {
544     if (parent_ != nullptr) {
545         if (cJSON_IsObject(parent_)) {
546             if (!cJSON_ReplaceItemInObjectCaseSensitive(parent_, itemName_.c_str(), newItem)) {
547                 LOGE("replace item in object fail, itemName:%{public}s", itemName_.c_str());
548                 return false;
549             }
550         } else if (cJSON_IsArray(parent_) && itemIndex_ >= 0 && itemIndex_ < cJSON_GetArraySize(parent_)) {
551             if (!cJSON_ReplaceItemInArray(parent_, itemIndex_, newItem)) {
552                 LOGE("replace item in array fail, itemIndex:%{public}d", itemIndex_);
553                 return false;
554             }
555         }
556     } else {
557         cJSON_Delete(item_);
558     }
559     item_ = newItem;
560     return true;
561 }
562 
Erase(const std::string & key)563 void JsonItemObject::Erase(const std::string &key)
564 {
565     if (item_ == nullptr) {
566         return;
567     }
568     if (IsObject()) {
569         cJSON_DeleteItemFromObjectCaseSensitive(item_, key.c_str());
570     }
571 }
572 
573 
JsonObject(JsonCreateType type)574 JsonObject::JsonObject(JsonCreateType type)
575 {
576     needDeleteItem_ = true;
577     beValid_ = true;
578     if (type == JsonCreateType::JSON_CREATE_TYPE_OBJECT) {
579         item_ = cJSON_CreateObject();
580     } else {
581         item_ = cJSON_CreateArray();
582     }
583 }
584 
JsonObject(const std::string & strJson)585 JsonObject::JsonObject(const std::string &strJson)
586 {
587     needDeleteItem_ = true;
588     beValid_ = true;
589     Parse(strJson);
590 }
591 
~JsonObject()592 JsonObject::~JsonObject()
593 {
594     Delete();
595 }
596 
Parse(const std::string & strJson)597 bool JsonObject::Parse(const std::string &strJson)
598 {
599     Delete();
600     if (!strJson.empty()) {
601         item_ = cJSON_Parse(strJson.c_str());
602         return true;
603     }
604     LOGE("strJson is empty");
605     return false;
606 }
607 
Duplicate(const JsonObject & object)608 void JsonObject::Duplicate(const JsonObject &object)
609 {
610     Delete();
611     item_ = cJSON_Duplicate(object.item_, cJSON_True);
612 }
613 
614 } // namespace DistributedHardware
615 } // namespace OHOS