cJSON

mirror of Dave's cJSON
git clone git://git.thc420.xyz/cJSON
Log | Files | Refs | README | LICENSE

commit 03ba72faec115160d1f3aea5582d9b6af5d3e473
parent 569aa060c6319fb24ab21bbf699aad2c40f454c1
Author: Max Bruckner <max@maxbruckner.de>
Date:   Tue, 13 Jun 2017 08:48:41 +0200

cJSON_Compare: Fix comparison of objects

It did consider two arrays equal if one is a subset of te other one,
which is incorrect.

See #180

Diffstat:
McJSON.c | 19++++++++++++++++++-
Mtests/compare_tests.c | 9+++++++++
2 files changed, 27 insertions(+), 1 deletion(-)

diff --git a/cJSON.c b/cJSON.c @@ -2605,10 +2605,11 @@ CJSON_PUBLIC(cJSON_bool) cJSON_Compare(const cJSON * const a, const cJSON * cons case cJSON_Object: { cJSON *a_element = NULL; + cJSON *b_element = NULL; cJSON_ArrayForEach(a_element, a) { /* TODO This has O(n^2) runtime, which is horrible! */ - cJSON *b_element = get_object_item(b, a_element->string, case_sensitive); + b_element = get_object_item(b, a_element->string, case_sensitive); if (b_element == NULL) { return false; @@ -2620,6 +2621,22 @@ CJSON_PUBLIC(cJSON_bool) cJSON_Compare(const cJSON * const a, const cJSON * cons } } + /* doing this twice, once on a and b to prevent true comparison if a subset of b + * TODO: Do this the proper way, this is just a fix for now */ + cJSON_ArrayForEach(b_element, b) + { + a_element = get_object_item(a, b_element->string, case_sensitive); + if (a_element == NULL) + { + return false; + } + + if (!cJSON_Compare(b_element, a_element, case_sensitive)) + { + return false; + } + } + return true; } diff --git a/tests/compare_tests.c b/tests/compare_tests.c @@ -175,6 +175,15 @@ static void cjson_compare_should_compare_objects(void) "{\"Flse\": false, \"true\": true, \"null\": null, \"number\": 42, \"string\": \"string\", \"array\": [], \"object\": {}}", "{\"true\": true, \"false\": false, \"null\": null, \"number\": 42, \"string\": \"string\", \"array\": [], \"object\": {}}", false)); + /* test objects that are a subset of each other */ + TEST_ASSERT_FALSE(compare_from_string( + "{\"one\": 1, \"two\": 2}", + "{\"one\": 1, \"two\": 2, \"three\": 3}", + true)) + TEST_ASSERT_FALSE(compare_from_string( + "{\"one\": 1, \"two\": 2}", + "{\"one\": 1, \"two\": 2, \"three\": 3}", + false)) } int main(void)