improve tk_object_to_json

This commit is contained in:
lixianjing 2023-05-04 18:39:41 +08:00
parent d9b75a7893
commit 4519f239cc
3 changed files with 60 additions and 10 deletions

View File

@ -1,4 +1,6 @@
# 最新动态
2023/05/04
* 完善tk\_object\_to\_json对不同数据类型和数组的处理。
2023/04/28
* 修复由于未初始化预留空间而导致的bsvg打包频繁更新问题(感谢高源提供补丁)。

View File

@ -855,9 +855,11 @@ typedef struct _json_info_t {
uint32_t level;
bool_t oneline;
uint32_t index;
bool_t is_array;
} json_info_t;
static ret_t to_json(void* ctx, const void* data) {
char buff[64] = {0};
json_info_t* info = (json_info_t*)ctx;
named_value_t* nv = (named_value_t*)data;
str_t* s = info->json;
@ -878,8 +880,10 @@ static ret_t to_json(void* ctx, const void* data) {
str_append_n_chars(s, ' ', info->indent * info->level);
}
if (!info->is_array) {
str_append_json_str(s, nv->name);
str_append(s, ": ");
}
switch (v->type) {
case VALUE_TYPE_STRING: {
@ -890,8 +894,22 @@ static ret_t to_json(void* ctx, const void* data) {
tk_object_to_json(value_object(v), s, info->indent + 1, info->level, oneline);
break;
}
case VALUE_TYPE_INT8:
case VALUE_TYPE_BOOL:
case VALUE_TYPE_INT16:
case VALUE_TYPE_INT32:
case VALUE_TYPE_INT64:
case VALUE_TYPE_UINT8:
case VALUE_TYPE_UINT16:
case VALUE_TYPE_UINT32:
case VALUE_TYPE_UINT64:
case VALUE_TYPE_FLOAT:
case VALUE_TYPE_FLOAT32:
case VALUE_TYPE_DOUBLE: {
str_append(s, value_str_ex(v, buff, sizeof(buff)));
break;
}
default: {
char buff[64] = {0};
str_append_json_str(s, value_str_ex(v, buff, sizeof(buff)));
break;
}
@ -902,6 +920,7 @@ static ret_t to_json(void* ctx, const void* data) {
ret_t tk_object_to_json(tk_object_t* obj, str_t* json, uint32_t indent, uint32_t level,
bool_t oneline) {
bool_t is_array = FALSE;
json_info_t info = {json, indent, level, oneline, 0};
return_value_if_fail(obj != NULL && json != NULL, RET_BAD_PARAMS);
@ -909,7 +928,9 @@ ret_t tk_object_to_json(tk_object_t* obj, str_t* json, uint32_t indent, uint32_t
str_append_n_chars(json, ' ', indent * level);
}
str_append(json, "{");
is_array = tk_str_eq(obj->vt->type, "object_array");
info.is_array = is_array;
str_append(json, is_array ? "[" : "{");
info.level++;
tk_object_foreach_prop(obj, to_json, &info);
if (!oneline) {
@ -919,7 +940,7 @@ ret_t tk_object_to_json(tk_object_t* obj, str_t* json, uint32_t indent, uint32_t
if (!oneline) {
str_append_n_chars(json, ' ', indent * level);
}
str_append(json, "}");
str_append(json, is_array ? "]" : "}");
return RET_OK;
}

View File

@ -673,19 +673,19 @@ TEST(ObjectDefault, to_json1) {
tk_object_set_prop_int(obj, "age", 100);
str_clear(&str);
tk_object_to_json(obj, &str, 2, 0, TRUE);
ASSERT_STREQ(str.str, "{\"age\": \"100\",\"name\": \"jim\"}");
ASSERT_STREQ(str.str, "{\"age\": 100,\"name\": \"jim\"}");
str_clear(&str);
tk_object_to_json(obj, &str, 1, 0, FALSE);
ASSERT_STREQ(str.str, "{\n \"age\": \"100\",\n \"name\": \"jim\"\n}");
ASSERT_STREQ(str.str, "{\n \"age\": 100,\n \"name\": \"jim\"\n}");
str_clear(&str);
tk_object_to_json(obj, &str, 2, 0, FALSE);
ASSERT_STREQ(str.str, "{\n \"age\": \"100\",\n \"name\": \"jim\"\n}");
ASSERT_STREQ(str.str, "{\n \"age\": 100,\n \"name\": \"jim\"\n}");
str_clear(&str);
tk_object_to_json(obj, &str, 2, 1, FALSE);
ASSERT_STREQ(str.str, " {\n \"age\": \"100\",\n \"name\": \"jim\"\n }");
ASSERT_STREQ(str.str, " {\n \"age\": 100,\n \"name\": \"jim\"\n }");
tk_object_t* detail = object_default_create();
tk_object_set_prop_str(detail, "city", "sz");
@ -694,10 +694,37 @@ TEST(ObjectDefault, to_json1) {
str_clear(&str);
tk_object_to_json(obj, &str, 2, 0, FALSE);
ASSERT_STREQ(str.str,
"{\n \"age\": \"100\",\n \"detail\": {\n \"city\": \"sz\"\n },\n "
"{\n \"age\": 100,\n \"detail\": {\n \"city\": \"sz\"\n },\n "
"\"name\": \"jim\"\n}");
str_reset(&str);
TK_OBJECT_UNREF(obj);
TK_OBJECT_UNREF(detail);
}
#include "tkc/object_array.h"
TEST(ObjectDefault, to_json2) {
str_t str;
value_t v;
tk_object_t* obj = object_default_create();
tk_object_t* detail = object_array_create();
str_init(&str, 100);
tk_object_set_prop_str(obj, "name", "awtk");
tk_object_set_prop_bool(obj, "light", FALSE);
tk_object_set_prop_int(obj, "age", 100);
tk_object_set_prop_float(obj, "weight", 60);
tk_object_set_prop_object(obj, "detail", detail);
object_array_push(detail, value_set_int(&v, 1));
object_array_push(detail, value_set_uint32(&v, 2));
object_array_push(detail, value_set_str(&v, "3"));
object_array_push(detail, value_set_str(&v, "4"));
tk_object_to_json(obj, &str, 0, 0, TRUE);
ASSERT_STREQ(str.str, "{\"age\": 100,\"detail\": [1,2,\"3\",\"4\"],\"light\": false,\"name\": \"awtk\",\"weight\": 60.000000}");
TK_OBJECT_UNREF(obj);
TK_OBJECT_UNREF(detail);
}