summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCarlos Garnacho <carlosg@gnome.org>2020-11-28 18:44:07 +0100
committerCarlos Garnacho <carlosg@gnome.org>2020-12-01 13:07:12 +0100
commit9a89c7c6b92bec114a85621dabe86605729f665e (patch)
tree1c8d156e151f8053eaafe0074df4bc95b1aa8bbb
parent2ad29dc2c516205a1f53d29c8e132ab61a4f0194 (diff)
downloadtracker-9a89c7c6b92bec114a85621dabe86605729f665e.tar.gz
libtracker-data: Inverse expectations when inserting a resource
Before this change we would first query the ID, and then insert it if non existent. Apply the "better to ask for forgiveness than permission" principle here, and try to always insert the resource. Only resort to queries if there is a constraint violation (meaning the URI already exists). This optimizes insertions over lookups of existing resource IDs, but we have other caching layers for the latter.
-rw-r--r--src/libtracker-data/tracker-data-update.c61
1 files changed, 40 insertions, 21 deletions
diff --git a/src/libtracker-data/tracker-data-update.c b/src/libtracker-data/tracker-data-update.c
index 378f434bc..a18bcff1c 100644
--- a/src/libtracker-data/tracker-data-update.c
+++ b/src/libtracker-data/tracker-data-update.c
@@ -785,38 +785,57 @@ ensure_resource_id (TrackerData *data,
GError *error = NULL;
gint id;
- id = query_resource_id (data, uri);
+ id = GPOINTER_TO_INT (g_hash_table_lookup (data->update_buffer.resource_cache, uri));
- if (create) {
- *create = (id == 0);
+ if (id != 0) {
+ if (create)
+ *create = FALSE;
+ return id;
}
- if (id == 0) {
- iface = tracker_data_manager_get_writable_db_interface (data->manager);
+ iface = tracker_data_manager_get_writable_db_interface (data->manager);
- id = tracker_data_update_get_new_service_id (data, &error);
+ id = tracker_data_update_get_new_service_id (data, &error);
- if (id > 0) {
- stmt = tracker_db_interface_create_statement (iface, TRACKER_DB_STATEMENT_CACHE_TYPE_UPDATE, &error,
- "INSERT INTO Resource (ID, Uri, BlankNode) VALUES (?, ?, ?)");
- }
+ if (id > 0) {
+ stmt = tracker_db_interface_create_statement (iface, TRACKER_DB_STATEMENT_CACHE_TYPE_UPDATE, &error,
+ "INSERT INTO Resource (ID, Uri, BlankNode) VALUES (?, ?, ?)");
+ }
- if (stmt) {
- tracker_db_statement_bind_int (stmt, 0, id);
- tracker_db_statement_bind_text (stmt, 1, uri);
- tracker_db_statement_bind_int (stmt, 2, g_str_has_prefix (uri, "urn:bnode:"));
- tracker_db_statement_execute (stmt, &error);
- g_object_unref (stmt);
- }
+ if (stmt) {
+ tracker_db_statement_bind_int (stmt, 0, id);
+ tracker_db_statement_bind_text (stmt, 1, uri);
+ tracker_db_statement_bind_int (stmt, 2, g_str_has_prefix (uri, "urn:bnode:"));
+ tracker_db_statement_execute (stmt, &error);
+ g_object_unref (stmt);
+ }
- if (error) {
- g_error ("Could not ensure resource existence: %s", error->message);
- g_error_free (error);
+ if (error) {
+ if (g_error_matches (error,
+ TRACKER_DB_INTERFACE_ERROR,
+ TRACKER_DB_CONSTRAINT)) {
+ id = query_resource_id (data, uri);
+
+ if (id != 0) {
+ if (create)
+ *create = FALSE;
+
+ g_hash_table_insert (data->update_buffer.resource_cache, g_strdup (uri), GINT_TO_POINTER (id));
+ g_error_free (error);
+ return id;
+ }
}
- g_hash_table_insert (data->update_buffer.resource_cache, g_strdup (uri), GINT_TO_POINTER (id));
+ g_error ("Could not ensure resource existence: %s", error->message);
+ g_error_free (error);
}
+ if (create)
+ *create = TRUE;
+
+ id = tracker_db_interface_sqlite_get_last_insert_id (iface);
+ g_hash_table_insert (data->update_buffer.resource_cache, g_strdup (uri), GINT_TO_POINTER (id));
+
return id;
}