test-json-parser.c revision 4e8e7a93628b4ed60aaaa47c6f72c1433f21e81d
c25356d5978632df6203437e1953bcb29e0c736fTimo Sirainen/* Copyright (c) 2012 Dovecot authors, see the included COPYING file */
c25356d5978632df6203437e1953bcb29e0c736fTimo Sirainen
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen#include "test-lib.h"
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen#include "str.h"
d9076f5939edf5d20a261494b1a861dcbb0d32e2Timo Sirainen#include "istream-private.h"
d9fdacd5fb3e07997e5c389739d2054f0c8441d8Timo Sirainen#include "json-parser.h"
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen
5666a3d6a7ea89362b8d9e8b39b15424cd9d6388Timo Sirainenstatic const char json_input[] =
a64adf62fa33f2463a86f990217b0c9078531a40Timo Sirainen "{\n"
146f9076cd456ea1e9b3f8536456d9d3c962fadbStephan Bosch "\t\"key\"\t:\t\t\"string\","
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen " \"key2\" : 1234, \n"
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen "\"key3\":true,"
8c909e451d14075c05d90382cf8eebc4e354f569Timo Sirainen "\"key4\":false,"
8c909e451d14075c05d90382cf8eebc4e354f569Timo Sirainen "\"key5\":null,"
8c909e451d14075c05d90382cf8eebc4e354f569Timo Sirainen "\"key6\": {},"
573f0491a5733fe21fa062a455acb4790b4e0499Timo Sirainen "\"key7\": {"
573f0491a5733fe21fa062a455acb4790b4e0499Timo Sirainen " \"sub1\":\"value\""
573f0491a5733fe21fa062a455acb4790b4e0499Timo Sirainen "},"
3ed2d0f6b5e67e2663d44489d9da3176823789a8Timo Sirainen "\"key8\": {"
65f8fb656051f1059f7b5a2da9c5555adcc30439Timo Sirainen " \"sub2\":-12.456,\n"
1a5573ebc32fae2fe576ec544e1781323c1db609Timo Sirainen " \"sub3\":12.456e9,\n"
1a5573ebc32fae2fe576ec544e1781323c1db609Timo Sirainen " \"sub4\":0.456e-789"
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen "},"
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen "\"key9\": \"\\\\\\\"\\b\\f\\n\\r\\t\\u0001\uffff\""
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen "}\n";
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainenstatic struct {
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen enum json_type type;
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen const char *value;
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen} json_output[] = {
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen { JSON_TYPE_OBJECT_KEY, "key" },
a64adf62fa33f2463a86f990217b0c9078531a40Timo Sirainen { JSON_TYPE_STRING, "string" },
a64adf62fa33f2463a86f990217b0c9078531a40Timo Sirainen { JSON_TYPE_OBJECT_KEY, "key2" },
f7539a17ea306191b53b8f5e752e228937df9ec3Timo Sirainen { JSON_TYPE_NUMBER, "1234" },
2615df45a8027948a474abe5e817b34b0499c171Timo Sirainen { JSON_TYPE_OBJECT_KEY, "key3" },
2dd39e478269d6fb0bb26d12b394aa30ee965e38Timo Sirainen { JSON_TYPE_TRUE, "true" },
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen { JSON_TYPE_OBJECT_KEY, "key4" },
563273bdac80393af63b9520cbf4d24cc0efd028Timo Sirainen { JSON_TYPE_FALSE, "false" },
563273bdac80393af63b9520cbf4d24cc0efd028Timo Sirainen { JSON_TYPE_OBJECT_KEY, "key5" },
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen { JSON_TYPE_NULL, NULL },
2615df45a8027948a474abe5e817b34b0499c171Timo Sirainen { JSON_TYPE_OBJECT_KEY, "key6" },
2615df45a8027948a474abe5e817b34b0499c171Timo Sirainen { JSON_TYPE_OBJECT, NULL },
2615df45a8027948a474abe5e817b34b0499c171Timo Sirainen { JSON_TYPE_OBJECT_END, NULL },
2615df45a8027948a474abe5e817b34b0499c171Timo Sirainen { JSON_TYPE_OBJECT_KEY, "key7" },
0cb2e8eb55e70f8ebe1e8349bdf49e4cbe5d8834Timo Sirainen { JSON_TYPE_OBJECT, NULL },
1d2b188f0eedc3cab6e27ceac5425a037f38042eTimo Sirainen { JSON_TYPE_OBJECT_KEY, "sub1" },
1d2b188f0eedc3cab6e27ceac5425a037f38042eTimo Sirainen { JSON_TYPE_STRING, "value" },
c0a87e5f3316a57e6f915882fa1951d0fbb74a61Timo Sirainen { JSON_TYPE_OBJECT_END, NULL },
1d2b188f0eedc3cab6e27ceac5425a037f38042eTimo Sirainen { JSON_TYPE_OBJECT_KEY, "key8" },
3e564425db51f3921ce4de11859777135fdedd15Timo Sirainen { JSON_TYPE_OBJECT, NULL },
857c471c13ca215f4be9dd4b336b742b8d434e31Timo Sirainen { JSON_TYPE_OBJECT_KEY, "sub2" },
857c471c13ca215f4be9dd4b336b742b8d434e31Timo Sirainen { JSON_TYPE_NUMBER, "-12.456" },
857c471c13ca215f4be9dd4b336b742b8d434e31Timo Sirainen { JSON_TYPE_OBJECT_KEY, "sub3" },
857c471c13ca215f4be9dd4b336b742b8d434e31Timo Sirainen { JSON_TYPE_NUMBER, "12.456e9" },
857c471c13ca215f4be9dd4b336b742b8d434e31Timo Sirainen { JSON_TYPE_OBJECT_KEY, "sub4" },
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen { JSON_TYPE_NUMBER, "0.456e-789" },
fdc557286bc9f92c5f3bb49096ff6e2bcec0ea79Timo Sirainen { JSON_TYPE_OBJECT_END, NULL },
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen { JSON_TYPE_OBJECT_KEY, "key9" },
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen { JSON_TYPE_STRING, "\\\"\b\f\n\r\t\001\xef\xbf\xbf" }
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen};
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainen
8e371a3ce32bd64288786855b8ce0cb63f19f7d1Timo Sirainenstatic void test_json_parser_success(bool full_size)
563273bdac80393af63b9520cbf4d24cc0efd028Timo Sirainen{
563273bdac80393af63b9520cbf4d24cc0efd028Timo Sirainen struct json_parser *parser;
563273bdac80393af63b9520cbf4d24cc0efd028Timo Sirainen struct istream *input;
563273bdac80393af63b9520cbf4d24cc0efd028Timo Sirainen enum json_type type;
e5fd6dfd0a492e4708d4dbb7971d7fc5d7b8fd85Timo Sirainen const char *value, *error;
e5fd6dfd0a492e4708d4dbb7971d7fc5d7b8fd85Timo Sirainen unsigned int i, pos, json_input_len = strlen(json_input);
4ba9a1d3facc515b3feb5238a16bcf91f76fac61Timo Sirainen int ret = 0;
4ba9a1d3facc515b3feb5238a16bcf91f76fac61Timo Sirainen
dfaefeabae939803ceb8c503101e86b5496541d1Timo Sirainen test_begin("json parser");
dfaefeabae939803ceb8c503101e86b5496541d1Timo Sirainen input = test_istream_create_data(json_input, json_input_len);
e15b305e90c9834734ccf35ed78f0ad29d570ee9Timo Sirainen test_istream_set_allow_eof(input, FALSE);
e15b305e90c9834734ccf35ed78f0ad29d570ee9Timo Sirainen parser = json_parser_init(input);
8b31f966d9688e07672ef1958dcbdb7686523c04Timo Sirainen
8b31f966d9688e07672ef1958dcbdb7686523c04Timo Sirainen i = full_size ? json_input_len : 0;
9847ec56efa15fa063eea9988eee2d4ed9ec7d58Timo Sirainen for (pos = 0; i <= json_input_len; i++) {
9847ec56efa15fa063eea9988eee2d4ed9ec7d58Timo Sirainen test_istream_set_size(input, i);
9847ec56efa15fa063eea9988eee2d4ed9ec7d58Timo Sirainen
d46a1e3f999dda802dc5137e883adcd7a6629cd3Timo Sirainen while ((ret = json_parse_next(parser, &type, &value)) > 0) {
d46a1e3f999dda802dc5137e883adcd7a6629cd3Timo Sirainen i_assert(pos < N_ELEMENTS(json_output));
d46a1e3f999dda802dc5137e883adcd7a6629cd3Timo Sirainen test_assert(json_output[pos].type == type);
d1e843e77f4760e303c53d9fce10123fc8d230a1Timo Sirainen test_assert(null_strcmp(json_output[pos].value, value) == 0);
d1e843e77f4760e303c53d9fce10123fc8d230a1Timo Sirainen pos++;
d1e843e77f4760e303c53d9fce10123fc8d230a1Timo Sirainen }
291ce16fffca75e8598a8c9dceb08613413dcb07Timo Sirainen test_assert(ret == 0);
291ce16fffca75e8598a8c9dceb08613413dcb07Timo Sirainen }
291ce16fffca75e8598a8c9dceb08613413dcb07Timo Sirainen test_assert(pos == N_ELEMENTS(json_output));
08e9fd42eb8007e1f9db62c088eef74f906114a5Josef 'Jeff' Sipek test_istream_set_allow_eof(input, TRUE);
08e9fd42eb8007e1f9db62c088eef74f906114a5Josef 'Jeff' Sipek test_assert(json_parse_next(parser, &type, &value) == -1);
08e9fd42eb8007e1f9db62c088eef74f906114a5Josef 'Jeff' Sipek
563273bdac80393af63b9520cbf4d24cc0efd028Timo Sirainen i_stream_unref(&input);
563273bdac80393af63b9520cbf4d24cc0efd028Timo Sirainen test_assert(json_parser_deinit(&parser, &error) == 0);
306b3f41b05da642d87e7ca7a1496efce9f5902fTimo Sirainen test_end();
306b3f41b05da642d87e7ca7a1496efce9f5902fTimo Sirainen}
306b3f41b05da642d87e7ca7a1496efce9f5902fTimo Sirainen
306b3f41b05da642d87e7ca7a1496efce9f5902fTimo Sirainenvoid test_json_parser(void)
306b3f41b05da642d87e7ca7a1496efce9f5902fTimo Sirainen{
306b3f41b05da642d87e7ca7a1496efce9f5902fTimo Sirainen test_json_parser_success(FALSE);
306b3f41b05da642d87e7ca7a1496efce9f5902fTimo Sirainen test_json_parser_success(TRUE);
306b3f41b05da642d87e7ca7a1496efce9f5902fTimo Sirainen}
306b3f41b05da642d87e7ca7a1496efce9f5902fTimo Sirainen