/** * json_parser_load_from_data: * @parser: a #JsonParser * @data: the buffer to parse * @length: the length of the buffer, or -1 * @error: return location for a #GError, or %NULL * * Loads a JSON stream from a buffer and parses it. You can call this function * multiple times with the same #JsonParser object, but the contents of the * parser will be destroyed each time. * * Return value: %TRUE if the buffer was succesfully parser. In case * of error, @error is set accordingly and %FALSE is returned */ gboolean json_parser_load_from_data (JsonParser *parser, const gchar *data, gssize length, GError **error) { JsonParserPrivate *priv; GError *internal_error; gboolean retval = TRUE; g_return_val_if_fail (JSON_IS_PARSER (parser), FALSE); g_return_val_if_fail (data != NULL, FALSE); priv = parser->priv; if (length < 0) length = strlen (data); priv->is_filename = FALSE; g_free (priv->filename); priv->filename = NULL; internal_error = NULL; if (!json_parser_load (parser, data, length, &internal_error)) { g_propagate_error (error, internal_error); retval = FALSE; } return retval; }
static void utc_libjson_json_parser_has_assignment_func_04(void) { JsonParser *parser = NULL; GError *error = NULL; gboolean ret = FALSE; gchar *var = NULL; int i = 0; parser = json_parser_new (); g_assert (JSON_IS_PARSER (parser)); for (i = 0; i < n_test_assignments; i++) { error = NULL; if (!json_parser_load_from_data (parser, test_assignments[i].str, -1, &error)) { g_error_free (error); } else { ret = json_parser_has_assignment (parser, &var); dts_check_eq("json_parser_has_assignment", ret, TRUE); dts_check_ne("json_parser_has_assignment", var, NULL); dts_check_str_eq ("json_parser_has_assignment", var, test_assignments[i].var); } } dts_pass("json_parser_has_assignment", "pass"); g_object_unref (parser); }
/** * json_parser_load_from_stream_async: * @parser: a #JsonParser * @stream: a #GInputStream * @cancellable: (allow-none): a #GCancellable, or %NULL * @callback: a #GAsyncReadyCallback to call when the request is satisfied * @user_data: the data to pass to @callback * * Asynchronously reads the contents of @stream. * * For more details, see json_parser_load_from_stream() which is the * synchronous version of this call. * * When the operation is finished, @callback will be called. You should * then call json_parser_load_from_stream_finish() to get the result * of the operation. * * Since: 0.12 */ void json_parser_load_from_stream_async (JsonParser *parser, GInputStream *stream, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data) { LoadData *data; GTask *task; g_return_if_fail (JSON_IS_PARSER (parser)); g_return_if_fail (G_IS_INPUT_STREAM (stream)); g_return_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable)); data = g_new (LoadData, 1); data->stream = g_object_ref (stream); data->content = g_byte_array_new (); data->pos = 0; task = g_task_new (parser, cancellable, callback, user_data); g_task_set_task_data (task, data, load_data_free); g_task_run_in_thread (task, read_from_stream); g_object_unref (task); }
/** * json_parser_load_from_stream_finish: * @parser: a #JsonParser * @result: a #GAsyncResult * @error: the return location for a #GError or %NULL * * Finishes an asynchronous stream loading started with * json_parser_load_from_stream_async(). * * Return value: %TRUE if the content of the stream was successfully retrieves * and parsed, and %FALSE otherwise. In case of error, the #GError will be * filled accordingly. * * Since: 0.12 */ gboolean json_parser_load_from_stream_finish (JsonParser *parser, GAsyncResult *result, GError **error) { gboolean res; g_return_val_if_fail (JSON_IS_PARSER (parser), FALSE); g_return_val_if_fail (g_task_is_valid (result, parser), FALSE); res = g_task_propagate_boolean (G_TASK (result), error); if (res) { LoadData *data = g_task_get_task_data (G_TASK (result)); GError *internal_error = NULL; /* We need to do this inside the finis() function because JsonParser will emit * signals, and we need to ensure that the signals are emitted in the right * context; it's easier to do that if we just rely on the async callback being * called in the right context, even if it means making the finish() function * necessary to complete the async operation. */ res = json_parser_load (parser, (const gchar *) data->content->data, data->pos, &internal_error); if (internal_error != NULL) g_propagate_error (error, internal_error); } return res; }
static void test_invalid_array (gconstpointer user_data) { const char *json = user_data; GError *error = NULL; JsonParser *parser; gboolean res; parser = json_parser_new (); g_assert (JSON_IS_PARSER (parser)); if (g_test_verbose ()) g_print ("invalid data: '%s'...", json); res = json_parser_load_from_data (parser, json, -1, &error); g_assert (!res); g_assert (error != NULL); if (g_test_verbose ()) g_print ("expected error: %s\n", error->message); g_clear_error (&error); g_object_unref (parser); }
/** * json_parser_load_from_stream_async: * @parser: a #JsonParser * @stream: a #GInputStream * @cancellable: (allow-none): a #GCancellable, or %NULL * @callback: a #GAsyncReadyCallback to call when the request is satisfied * @user_data: the data to pass to @callback * * Asynchronously reads the contents of @stream. * * For more details, see json_parser_load_from_stream() which is the * synchronous version of this call. * * When the operation is finished, @callback will be called. You should * then call json_parser_load_from_stream_finish() to get the result * of the operation. * * Since: 0.12 */ void json_parser_load_from_stream_async (JsonParser *parser, GInputStream *stream, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data) { LoadStreamData *data; g_return_if_fail (JSON_IS_PARSER (parser)); g_return_if_fail (G_IS_INPUT_STREAM (stream)); g_return_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable)); data = g_new0 (LoadStreamData, 1); if (cancellable != NULL) data->cancellable = g_object_ref (cancellable); data->callback = callback; data->user_data = user_data; data->content = g_byte_array_new (); data->parser = g_object_ref (parser); g_byte_array_set_size (data->content, data->pos + GET_DATA_BLOCK_SIZE); g_input_stream_read_async (stream, data->content->data + data->pos, GET_DATA_BLOCK_SIZE, 0, data->cancellable, load_stream_data_read_callback, data); }
/** * json_parser_get_root: * @parser: a #JsonParser * * Retrieves the top level node from the parsed JSON stream. * * Return value: (transfer none): the root #JsonNode . The returned * node is owned by the #JsonParser and should never be modified * or freed. */ JsonNode * json_parser_get_root (JsonParser *parser) { g_return_val_if_fail (JSON_IS_PARSER (parser), NULL); return parser->priv->root; }
/** * json_parser_steal_root: * @parser: a #JsonParser * * Steals the top level node from the parsed JSON stream. * * Returns: (transfer full): the top level #JsonNode * * Since: 1.4 */ JsonNode * json_parser_steal_root (JsonParser *parser) { JsonParserPrivate *priv = json_parser_get_instance_private (parser); g_return_val_if_fail (JSON_IS_PARSER (parser), NULL); return g_steal_pointer (&priv->root); }
/** * @brief Negative test case of ug_init json_parser_new() */ static void utc_libjson_json_parser_new_func_02(void) { JsonParser *parser = NULL; parser = json_parser_new(); dts_check_eq("json_parser_new", JSON_IS_PARSER(parser), TRUE); g_object_unref (parser); }
/** * json_parser_get_current_pos: * @parser: a #JsonParser * * Retrieves the current position inside the current line, starting * from 0. * * This function has defined behaviour only while parsing; calling this * function from outside the signal handlers emitted by #JsonParser will * yield 0. * * Return value: the position in the current line, or 0. */ guint json_parser_get_current_pos (JsonParser *parser) { g_return_val_if_fail (JSON_IS_PARSER (parser), 0); if (parser->priv->scanner != NULL) return parser->priv->scanner->position; return 0; }
/** * json_parser_get_current_pos: * @parser: a #JsonParser * * Retrieves the current position inside the current line, starting * from 0. * * This function has defined behaviour only while parsing; calling this * function from outside the signal handlers emitted by #JsonParser will * yield 0. * * Return value: the position in the current line, or 0. */ guint json_parser_get_current_pos (JsonParser *parser) { g_return_val_if_fail (JSON_IS_PARSER (parser), 0); if (parser->priv->scanner) return json_scanner_cur_line (parser->priv->scanner); return 0; }
/** * json_parser_get_root: * @parser: a #JsonParser * * Retrieves the top level node from the parsed JSON stream. * * Return value: (transfer none): the root #JsonNode . The returned * node is owned by the #JsonParser and should never be modified * or freed. */ JsonNode * json_parser_get_root (JsonParser *parser) { g_return_val_if_fail (JSON_IS_PARSER (parser), NULL); /* Sanity check. */ g_return_val_if_fail (!parser->priv->is_immutable || json_node_is_immutable (parser->priv->root), NULL); return parser->priv->root; }
/** * @brief Negative test case of ug_init json_parser_has_assignment() */ static void utc_libjson_json_parser_has_assignment_func_02(void) { JsonParser *parser = NULL; gboolean ret = FALSE; parser = json_parser_new (); g_assert (JSON_IS_PARSER (parser)); ret = json_parser_has_assignment(parser, NULL); dts_check_eq("json_parser_has_assignment", ret, FALSE); g_object_unref (parser); }
/** * json_parser_load_from_stream: * @parser: a #JsonParser * @stream: an open #GInputStream * @cancellable: (allow-none): a #GCancellable, or %NULL * @error: the return location for a #GError, or %NULL * * Loads the contents of an input stream and parses them. * * If @cancellable is not %NULL, then the operation can be cancelled by * triggering the @cancellable object from another thread. If the * operation was cancelled, the error %G_IO_ERROR_CANCELLED will be set * on the passed @error. * * Return value: %TRUE if the data stream was successfully read and * parsed, and %FALSE otherwise * * Since: 0.12 */ gboolean json_parser_load_from_stream (JsonParser *parser, GInputStream *stream, GCancellable *cancellable, GError **error) { GByteArray *content; gsize pos; gssize res; gboolean retval = FALSE; GError *internal_error; g_return_val_if_fail (JSON_IS_PARSER (parser), FALSE); g_return_val_if_fail (G_IS_INPUT_STREAM (stream), FALSE); g_return_val_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable), FALSE); if (g_cancellable_set_error_if_cancelled (cancellable, error)) return FALSE; content = g_byte_array_new (); pos = 0; g_byte_array_set_size (content, pos + GET_DATA_BLOCK_SIZE + 1); while ((res = g_input_stream_read (stream, content->data + pos, GET_DATA_BLOCK_SIZE, cancellable, error)) > 0) { pos += res; g_byte_array_set_size (content, pos + GET_DATA_BLOCK_SIZE + 1); } if (res < 0) { /* error has already been set */ retval = FALSE; goto out; } /* zero-terminate the content; we allocated an extra byte for this */ content->data[pos] = 0; internal_error = NULL; retval = json_parser_load (parser, (const gchar *) content->data, content->len, &internal_error); if (internal_error != NULL) g_propagate_error (error, internal_error); out: g_byte_array_free (content, TRUE); return retval; }
/** * json_parser_has_assignment: * @parser: a #JsonParser * @variable_name: (out) (allow-none) (transfer none): Return location for the variable * name, or %NULL * * A JSON data stream might sometimes contain an assignment, like: * * |[ * var _json_data = { "member_name" : [ ... * ]| * * even though it would technically constitute a violation of the RFC. * * #JsonParser will ignore the left hand identifier and parse the right * hand value of the assignment. #JsonParser will record, though, the * existence of the assignment in the data stream and the variable name * used. * * Return value: %TRUE if there was an assignment, %FALSE otherwise. If * @variable_name is not %NULL it will be set to the name of the variable * used in the assignment. The string is owned by #JsonParser and should * never be modified or freed. * * Since: 0.4 */ gboolean json_parser_has_assignment (JsonParser *parser, gchar **variable_name) { JsonParserPrivate *priv; g_return_val_if_fail (JSON_IS_PARSER (parser), FALSE); priv = parser->priv; if (priv->has_assignment && variable_name) *variable_name = priv->variable_name; return priv->has_assignment; }
static void gb_project_format_real_open_cb (GObject *object, GAsyncResult *result, gpointer user_data) { GSimpleAsyncResult *simple = user_data; const gchar *directory; JsonParser *parser = (JsonParser *)object; JsonNode *root; GObject *project; GError *error = NULL; ENTRY; g_assert(JSON_IS_PARSER(parser)); g_assert(G_IS_SIMPLE_ASYNC_RESULT(simple)); if (!json_parser_load_from_stream_finish(parser, result, &error)) { g_simple_async_result_take_error(simple, error); GOTO(failure); } root = json_parser_get_root(parser); g_assert(root); if (!(project = json_gobject_deserialize(GB_TYPE_PROJECT, root))) { g_simple_async_result_set_error(simple, GB_PROJECT_FORMAT_ERROR, GB_PROJECT_FORMAT_ERROR_INVALID_JSON, _("Failed to deserialize from JSON.")); GOTO(failure); } directory = g_object_get_data(G_OBJECT(simple), "directory"); g_object_set(project, "directory", directory, NULL); g_simple_async_result_set_op_res_gpointer(simple, project, g_object_unref); failure: g_simple_async_result_complete_in_idle(simple); g_object_unref(simple); EXIT; }
/** * json_parser_load_from_stream_finish: * @parser: a #JsonParser * @result: a #GAsyncResult * @error: the return location for a #GError or %NULL * * Finishes an asynchronous stream loading started with * json_parser_load_from_stream_async(). * * Return value: %TRUE if the content of the stream was successfully retrieves * and parsed, and %FALSE otherwise. In case of error, the #GError will be * filled accordingly. * * Since: 0.12 */ gboolean json_parser_load_from_stream_finish (JsonParser *parser, GAsyncResult *result, GError **error) { GSimpleAsyncResult *simple; GError *internal_error; LoadStreamData *data; gboolean res; g_return_val_if_fail (JSON_IS_PARSER (parser), FALSE); g_return_val_if_fail (G_IS_SIMPLE_ASYNC_RESULT (result), FALSE); simple = G_SIMPLE_ASYNC_RESULT (result); if (g_simple_async_result_propagate_error (simple, error)) return FALSE; g_warn_if_fail (g_simple_async_result_get_source_tag (simple) == json_parser_load_from_stream_async); data = g_simple_async_result_get_op_res_gpointer (simple); if (data->error) { g_propagate_error (error, data->error); data->error = NULL; return FALSE; } g_byte_array_set_size (data->content, data->pos + 1); data->content->data[data->pos] = 0; internal_error = NULL; res = json_parser_load (parser, (const gchar *) data->content->data, data->content->len, &internal_error); if (internal_error != NULL) g_propagate_error (error, internal_error); return res; }
static void utc_libjson_json_parser_has_assignment_func_03(void) { JsonParser *parser = NULL; GError *error = NULL; gboolean ret = FALSE; gchar *var = NULL; ; parser = json_parser_new (); g_assert (JSON_IS_PARSER (parser)); if (!json_parser_load_from_data (parser, test_string, -1, &error)) { g_error_free (error); } else { ret = json_parser_has_assignment (parser, &var); dts_check_eq("json_parser_has_assignment", ret, FALSE); dts_check_eq("json_parser_has_assignment", var, NULL); } g_object_unref (parser); }
/** * json_parser_load_from_file: * @parser: a #JsonParser * @filename: the path for the file to parse * @error: return location for a #GError, or %NULL * * Loads a JSON stream from the content of @filename and parses it. See * json_parser_load_from_data(). * * Return value: %TRUE if the file was successfully loaded and parsed. * In case of error, @error is set accordingly and %FALSE is returned */ gboolean json_parser_load_from_file (JsonParser *parser, const gchar *filename, GError **error) { JsonParserPrivate *priv; GError *internal_error; gchar *data; gsize length; gboolean retval = TRUE; g_return_val_if_fail (JSON_IS_PARSER (parser), FALSE); g_return_val_if_fail (filename != NULL, FALSE); priv = parser->priv; internal_error = NULL; if (!g_file_get_contents (filename, &data, &length, &internal_error)) { g_propagate_error (error, internal_error); return FALSE; } g_free (priv->filename); priv->is_filename = TRUE; priv->filename = g_strdup (filename); if (!json_parser_load (parser, data, length, &internal_error)) { g_propagate_error (error, internal_error); retval = FALSE; } g_free (data); return retval; }