Austin Schuh | f417eaf | 2019-09-16 21:58:36 -0700 | [diff] [blame] | 1 | #include <jsont.h> |
| 2 | #include <stdio.h> |
| 3 | #include <string.h> |
| 4 | #include <assert.h> |
| 5 | #include <math.h> |
| 6 | |
| 7 | #define JSONT_ASSERT_FIELD_NAME(fieldName) do { \ |
| 8 | assert(jsont_current(S) == JSONT_FIELD_NAME); \ |
| 9 | assert(jsont_data_equals(S, (const uint8_t*)fieldName, \ |
| 10 | strlen(fieldName)) == true); \ |
| 11 | } while(0) |
| 12 | |
| 13 | int main(int argc, const char** argv) { |
| 14 | // Create a new reusable tokenizer |
| 15 | jsont_ctx_t* S = jsont_create(0); |
| 16 | |
| 17 | const char* inbuf = "{ " |
| 18 | "\"\\\"fo\\\"o\": \"Foo\"," // "\"fo\"o": "Foo" |
| 19 | "\"1\" : \"\\u2192\"," |
| 20 | "\"n\":1234," |
| 21 | "\"x\" : \t 12.34," |
| 22 | "\"overflow\" : \t 9999999999999999999999999999999999," |
| 23 | "\"b\\/a\\/r\":[" |
| 24 | "null," |
| 25 | "true," |
| 26 | "false," |
| 27 | "{" |
| 28 | "\"x\":12.3" |
| 29 | "}," |
| 30 | "\n123," |
| 31 | "\"456\"," |
| 32 | "\"a\\\"b\\\"\"," |
| 33 | "\"a\\u0000b\"," |
| 34 | "\"a\\bb\"," |
| 35 | "\"a\\fb\"," |
| 36 | "\"a\\nb\"," |
| 37 | "\"a\\rb\"," |
| 38 | "\"a\\tb\"," |
| 39 | "\"\"," |
| 40 | "\" \"" |
| 41 | "]" |
| 42 | "}"; |
| 43 | |
| 44 | jsont_reset(S, (const uint8_t*)inbuf, strlen(inbuf)); |
| 45 | jsont_tok_t tok; |
| 46 | |
| 47 | tok = jsont_next(S); |
| 48 | assert(tok == JSONT_OBJECT_START); |
| 49 | assert(jsont_current(S) == JSONT_OBJECT_START); |
| 50 | |
| 51 | tok = jsont_next(S); |
| 52 | assert(tok == JSONT_FIELD_NAME); |
| 53 | |
| 54 | // Expect current data to be the bytes '"fo"o' |
| 55 | const char* expectedData = "\"fo\"o"; |
| 56 | const uint8_t* bytes; |
| 57 | size_t size = jsont_data_value(S, &bytes); |
| 58 | size_t expectedSize = strlen(expectedData); |
| 59 | // printf("expectedData: '%s'\n", expectedData); |
| 60 | // printf("currentData: '%.*s'\n", (int)size, (const char*)bytes); |
| 61 | assert(size == expectedSize); |
| 62 | int d = memcmp((const void*)expectedData, bytes, size); |
| 63 | assert(d == 0); |
| 64 | |
| 65 | // Expect a string value "Foo" |
| 66 | tok = jsont_next(S); |
| 67 | assert(tok == JSONT_STRING); |
| 68 | char* str = jsont_strcpy_value(S); |
| 69 | assert(str != 0); |
| 70 | assert(strcmp(str, "Foo") == 0); |
| 71 | free(str); str = 0; |
| 72 | |
| 73 | // Expect field name "1". Also tests the integrity of jsont_data_equals |
| 74 | tok = jsont_next(S); |
| 75 | assert(jsont_data_equals(S, (const uint8_t*)"1", 1) == true); |
| 76 | assert(jsont_str_equals(S, "1") == true); |
| 77 | size = jsont_data_value(S, &bytes); |
| 78 | assert(size == 1); |
| 79 | assert(memcmp((const void*)"1", (const void*)bytes, 1) == 0); |
| 80 | |
| 81 | // Expect the string '\u2192' (RIGHTWARDS ARROW, UTF8: E2,86,92) |
| 82 | assert(jsont_next(S) == JSONT_STRING); |
| 83 | assert(jsont_str_equals(S, "\xe2\x86\x92") == true); |
| 84 | |
| 85 | // Expect a field name 'n' |
| 86 | jsont_next(S); |
| 87 | JSONT_ASSERT_FIELD_NAME("n"); |
| 88 | |
| 89 | // Expect a number value '1234' |
| 90 | assert(jsont_next(S) == JSONT_NUMBER_INT); |
| 91 | //printf("int: %lld (str: '%s')\n", jsont_int_value(S), jsont_strcpy_value(S)); |
| 92 | assert(jsont_int_value(S) == 1234LL); |
| 93 | assert(jsont_float_value(S) == 1234.0); |
| 94 | |
| 95 | // Expect a field name 'x' |
| 96 | jsont_next(S); |
| 97 | JSONT_ASSERT_FIELD_NAME("x"); |
| 98 | |
| 99 | // Expect a number value '12.34' |
| 100 | assert(jsont_next(S) == JSONT_NUMBER_FLOAT); |
| 101 | assert(jsont_float_value(S) == 12.34); |
| 102 | assert(jsont_int_value(S) == 12LL); // partial expected |
| 103 | |
| 104 | jsont_next(S); |
| 105 | JSONT_ASSERT_FIELD_NAME("overflow"); |
| 106 | |
| 107 | // Expect a cut-off integer value of INT64_MAX |
| 108 | assert(jsont_next(S) == JSONT_NUMBER_INT); |
| 109 | assert(jsont_int_value(S) == INT64_MAX); |
| 110 | |
| 111 | // Expect a valid floating point value (although it will have less-than |
| 112 | // perfect precision) |
| 113 | assert(!isnan(jsont_float_value(S))); |
| 114 | |
| 115 | // Expect a field name 'bar' |
| 116 | jsont_next(S); |
| 117 | JSONT_ASSERT_FIELD_NAME("b/a/r"); |
| 118 | |
| 119 | // Expect start of array |
| 120 | assert(jsont_next(S) == JSONT_ARRAY_START); |
| 121 | |
| 122 | // Expect null, true and false |
| 123 | assert(jsont_next(S) == JSONT_NULL); |
| 124 | assert(jsont_next(S) == JSONT_TRUE); |
| 125 | assert(jsont_next(S) == JSONT_FALSE); |
| 126 | |
| 127 | // { "x": 12.3 } |
| 128 | assert(jsont_next(S) == JSONT_OBJECT_START); |
| 129 | jsont_next(S); |
| 130 | JSONT_ASSERT_FIELD_NAME("x"); |
| 131 | assert(jsont_next(S) == JSONT_NUMBER_FLOAT); |
| 132 | assert(jsont_float_value(S) == 12.3); |
| 133 | assert(jsont_next(S) == JSONT_OBJECT_END); |
| 134 | |
| 135 | // 123, "456", "a\"b\"" |
| 136 | assert(jsont_next(S) == JSONT_NUMBER_INT); |
| 137 | assert(jsont_int_value(S) == 123); |
| 138 | |
| 139 | assert(jsont_next(S) == JSONT_STRING); |
| 140 | assert(jsont_str_equals(S, "456") == true); |
| 141 | |
| 142 | assert(jsont_next(S) == JSONT_STRING); |
| 143 | assert(jsont_str_equals(S, "a\"b\"") == true); |
| 144 | |
| 145 | // "a\u0000b" |
| 146 | assert(jsont_next(S) == JSONT_STRING); |
| 147 | const uint8_t b3[] = {'a',0,'b'}; |
| 148 | assert(jsont_data_equals(S, b3, sizeof(b3)) == true); |
| 149 | |
| 150 | // "a\{b,f,n,r,t}b" |
| 151 | assert(jsont_next(S) == JSONT_STRING); |
| 152 | assert(jsont_str_equals(S, "a\bb") == true); |
| 153 | assert(jsont_next(S) == JSONT_STRING); |
| 154 | assert(jsont_str_equals(S, "a\fb") == true); |
| 155 | assert(jsont_next(S) == JSONT_STRING); |
| 156 | assert(jsont_str_equals(S, "a\nb") == true); |
| 157 | assert(jsont_next(S) == JSONT_STRING); |
| 158 | assert(jsont_str_equals(S, "a\rb") == true); |
| 159 | assert(jsont_next(S) == JSONT_STRING); |
| 160 | assert(jsont_str_equals(S, "a\tb") == true); |
| 161 | |
| 162 | // "" |
| 163 | assert(jsont_next(S) == JSONT_STRING); |
| 164 | assert(jsont_str_equals(S, "") == true); |
| 165 | assert(jsont_str_equals(S, " ") == false); |
| 166 | |
| 167 | // " " |
| 168 | assert(jsont_next(S) == JSONT_STRING); |
| 169 | assert(jsont_str_equals(S, " ") == true); |
| 170 | assert(jsont_str_equals(S, "") == false); |
| 171 | |
| 172 | // ] } |
| 173 | assert(jsont_next(S) == JSONT_ARRAY_END); |
| 174 | assert(jsont_next(S) == JSONT_OBJECT_END); |
| 175 | |
| 176 | |
| 177 | jsont_destroy(S); |
| 178 | printf("PASS\n"); |
| 179 | return 0; |
| 180 | } |