static void php_jq_exec(zval **return_value, char *str, int str_len, char *filter, int filter_len, long flags TSRMLS_DC) { jq_state *jq = php_jq_init(); jv json, result; if (!jq) { PHP_JQ_EXCEPTION(0, "jq object has not been correctly initialized " "by its constructor"); ZVAL_BOOL(*return_value, 0); return; } json = jv_parse_sized(str, str_len); if (!jv_is_valid(json)) { jv_free(json); jq_teardown(&jq); if (PHP_JQ_G(display_errors)) { PHP_JQ_ERR(E_WARNING, "load json parse error"); } ZVAL_BOOL(*return_value, 0); return; } filter[filter_len] = 0; if (!jq_compile(jq, filter)) { jv_free(json); jq_teardown(&jq); if (PHP_JQ_G(display_errors)) { PHP_JQ_ERR(E_WARNING, "filter compile error"); } ZVAL_BOOL(*return_value, 0); return; } php_jq_filter(return_value, jq, json, flags TSRMLS_CC); jv_free(json); jq_teardown(&jq); }
static void run_jq_tests(jv lib_dirs, FILE *testdata) { char prog[4096]; char buf[4096]; struct err_data err_msg; int tests = 0, passed = 0, invalid = 0; unsigned int lineno = 0; int must_fail = 0; int check_msg = 0; jq_state *jq = NULL; jq = jq_init(); assert(jq); if (jv_get_kind(lib_dirs) == JV_KIND_NULL) lib_dirs = jv_array(); jq_set_attr(jq, jv_string("JQ_LIBRARY_PATH"), lib_dirs); while (1) { if (!fgets(prog, sizeof(prog), testdata)) break; lineno++; if (skipline(prog)) continue; if (checkfail(prog)) { must_fail = 1; check_msg = checkerrormsg(prog); jq_set_error_cb(jq, test_err_cb, &err_msg); continue; } if (prog[strlen(prog)-1] == '\n') prog[strlen(prog)-1] = 0; printf("Testing '%s' at line number %u\n", prog, lineno); int pass = 1; tests++; int compiled = jq_compile(jq, prog); if (must_fail) { jq_set_error_cb(jq, NULL, NULL); must_fail = 0; check_msg = 0; if (!fgets(buf, sizeof(buf), testdata)) { invalid++; break; } lineno++; if (buf[strlen(buf)-1] == '\n') buf[strlen(buf)-1] = 0; if (compiled) { printf("*** Test program compiled that should not have at line %u: %s\n", lineno, prog); invalid++; continue; } if (check_msg && strcmp(buf, err_msg.buf) != 0) { printf("*** Erroneous test program failed with wrong message (%s) at line %u: %s\n", err_msg.buf, lineno, prog); invalid++; } else { passed++; } continue; } if (!compiled) { printf("*** Test program failed to compile at line %u: %s\n", lineno, prog); invalid++; // skip past test data while (fgets(buf, sizeof(buf), testdata)) { lineno++; if (buf[0] == '\n' || (buf[0] == '\r' && buf[1] == '\n')) break; } continue; } printf("Disassembly:\n"); jq_dump_disassembly(jq, 2); printf("\n"); if (!fgets(buf, sizeof(buf), testdata)) { invalid++; break; } lineno++; jv input = jv_parse(buf); if (!jv_is_valid(input)){ invalid++; continue; } jq_start(jq, input, JQ_DEBUG_TRACE); while (fgets(buf, sizeof(buf), testdata)) { lineno++; if (skipline(buf)) break; jv expected = jv_parse(buf); if (!jv_is_valid(expected)){ invalid++; continue; } jv actual = jq_next(jq); if (!jv_is_valid(actual)) { jv_free(actual); printf("*** Insufficient results for test at line number %u: %s\n", lineno, prog); pass = 0; break; } else if (!jv_equal(jv_copy(expected), jv_copy(actual))) { printf("*** Expected "); jv_dump(jv_copy(expected), 0); printf(", but got "); jv_dump(jv_copy(actual), 0); printf(" for test at line number %u: %s\n", lineno, prog); pass = 0; } jv as_string = jv_dump_string(jv_copy(expected), rand() & ~(JV_PRINT_COLOUR|JV_PRINT_REFCOUNT)); jv reparsed = jv_parse_sized(jv_string_value(as_string), jv_string_length_bytes(jv_copy(as_string))); assert(jv_equal(jv_copy(expected), jv_copy(reparsed))); jv_free(as_string); jv_free(reparsed); jv_free(expected); jv_free(actual); } if (pass) { jv extra = jq_next(jq); if (jv_is_valid(extra)) { printf("*** Superfluous result: "); jv_dump(extra, 0); printf(" for test at line number %u, %s\n", lineno, prog); pass = 0; } else { jv_free(extra); } } passed+=pass; } jq_teardown(&jq); printf("%d of %d tests passed (%d malformed)\n", passed,tests,invalid); if (passed != tests) exit(1); }
virtual jq_value parse(const std::string& source) const { jq_value x(new jv, [] (jv* p) { jv_free(*p); delete p; }); *x = jv_parse_sized(source.c_str(), source.size()); return x; }
jv jv_parse(const char* string) { return jv_parse_sized(string, strlen(string)); }
static void run_jq_tests(FILE *testdata) { char buf[4096]; int tests = 0, passed = 0, invalid = 0; jq_state *jq = NULL; while (1) { if (!fgets(buf, sizeof(buf), testdata)) break; if (skipline(buf)) continue; if (buf[strlen(buf)-1] == '\n') buf[strlen(buf)-1] = 0; printf("Testing %s\n", buf); int pass = 1; tests++; struct bytecode* bc = jq_compile(buf); if (!bc) {invalid++; continue;} printf("Disassembly:\n"); dump_disassembly(2, bc); printf("\n"); fgets(buf, sizeof(buf), testdata); jv input = jv_parse(buf); if (!jv_is_valid(input)){ invalid++; continue; } jq_init(bc, input, &jq, JQ_DEBUG_TRACE); while (fgets(buf, sizeof(buf), testdata)) { if (skipline(buf)) break; jv expected = jv_parse(buf); if (!jv_is_valid(expected)){ invalid++; continue; } jv actual = jq_next(jq); if (!jv_is_valid(actual)) { jv_free(actual); printf("*** Insufficient results\n"); pass = 0; break; } else if (!jv_equal(jv_copy(expected), jv_copy(actual))) { printf("*** Expected "); jv_dump(jv_copy(expected), 0); printf(", but got "); jv_dump(jv_copy(actual), 0); printf("\n"); pass = 0; } jv as_string = jv_dump_string(jv_copy(expected), rand() & ~JV_PRINT_COLOUR); jv reparsed = jv_parse_sized(jv_string_value(as_string), jv_string_length_bytes(jv_copy(as_string))); assert(jv_equal(jv_copy(expected), jv_copy(reparsed))); jv_free(as_string); jv_free(reparsed); jv_free(expected); jv_free(actual); } if (pass) { jv extra = jq_next(jq); if (jv_is_valid(extra)) { printf("*** Superfluous result: "); jv_dump(extra, 0); printf("\n"); pass = 0; } else { jv_free(extra); } } jq_teardown(&jq); bytecode_free(bc); passed+=pass; } printf("%d of %d tests passed (%d malformed)\n", passed,tests,invalid); if (passed != tests) exit(1); }