diff --git a/docs/changes.md b/docs/changes.md index d18fc076a..dcc0c23e6 100644 --- a/docs/changes.md +++ b/docs/changes.md @@ -1,4 +1,6 @@ # 最新动态 +2023/05/04 + * 完善tk\_object\_to\_json对不同数据类型和数组的处理。 2023/04/28 * 修复由于未初始化预留空间而导致的bsvg打包频繁更新问题(感谢高源提供补丁)。 diff --git a/src/tkc/object.c b/src/tkc/object.c index 11d0cfa86..f72fd6c18 100644 --- a/src/tkc/object.c +++ b/src/tkc/object.c @@ -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); } - str_append_json_str(s, nv->name); - str_append(s, ": "); + 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; } diff --git a/tests/object_default_test.cc b/tests/object_default_test.cc index 05e51c93e..fca13e7b2 100644 --- a/tests/object_default_test.cc +++ b/tests/object_default_test.cc @@ -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); +}