[nautilus/wip/antoniof/update-starred-uris: 2/3] tag-manager: Erase starred URIs on trash & delete




commit c41f9b2045f642290082b393471cdd0fbfb0b861
Author: António Fernandes <antoniof gnome org>
Date:   Sun Sep 13 14:56:59 2020 +0100

    tag-manager: Erase starred URIs on trash & delete
    
    If a starred item was deleted or trashed, it's no longer displayed in
    the Starred view, which ignores broken URIs in the database. Erasing the
    broken URI in the database is not necessary for this.
    
    However, if we keep the broken URI in the database and later a different
    file appears at the same URI, it's going to be treated as if it starred
    was starred, which is wrong.
    
    In order to avoid this, delete URIs from the database when the item they
    point to is deleted/trashed by this application.
    
    This has an undesirable side effect: when restoring previously starred
    items from the trash, they don't get their star restored. This needs to
    be addressed by the undo machinery.

 src/nautilus-file-operations.c |  6 +++
 src/nautilus-tag-manager.c     | 90 ++++++++++++++++++++++++++++++++++++++++++
 src/nautilus-tag-manager.h     |  2 +
 3 files changed, 98 insertions(+)
---
diff --git a/src/nautilus-file-operations.c b/src/nautilus-file-operations.c
index c80d7ee6b..6506183a1 100644
--- a/src/nautilus-file-operations.c
+++ b/src/nautilus-file-operations.c
@@ -2013,7 +2013,10 @@ file_deleted_callback (GFile    *file,
 
     if (error == NULL)
     {
+        g_autoptr (NautilusTagManager) tag_manager = nautilus_tag_manager_get ();
+
         nautilus_file_changes_queue_file_removed (file);
+        nautilus_tag_manager_update_removed_uris (tag_manager, file);
         report_delete_progress (data->job, data->source_info, data->transfer_info);
 
         return;
@@ -2321,8 +2324,11 @@ trash_file (CommonJob     *job,
 
     if (g_file_trash (file, job->cancellable, &error))
     {
+        g_autoptr (NautilusTagManager) tag_manager = nautilus_tag_manager_get ();
+
         transfer_info->num_files++;
         nautilus_file_changes_queue_file_removed (file);
+        nautilus_tag_manager_update_removed_uris (tag_manager, file);
 
         if (job->undo_info != NULL)
         {
diff --git a/src/nautilus-tag-manager.c b/src/nautilus-tag-manager.c
index 5eac8bc30..9c71e731e 100644
--- a/src/nautilus-tag-manager.c
+++ b/src/nautilus-tag-manager.c
@@ -830,6 +830,96 @@ nautilus_tag_manager_update_moved_uris (NautilusTagManager *self,
                                             g_steal_pointer (&new_uris));
 }
 
+static void
+update_removed_uris_callback (GObject      *object,
+                              GAsyncResult *result,
+                              gpointer      user_data)
+{
+    g_autoptr (GError) error = NULL;
+
+    tracker_sparql_connection_update_finish (TRACKER_SPARQL_CONNECTION (object),
+                                             result,
+                                             &error);
+
+    if (error != NULL && error->code != G_IO_ERROR_CANCELLED)
+    {
+        g_warning ("Error removing deleted/trashed starred uris: %s", error->message);
+    }
+    else
+    {
+        g_autoptr (NautilusTagManager) tag_manager = nautilus_tag_manager_get ();
+
+        g_signal_emit_by_name (tag_manager, "starred-changed", NULL);
+    }
+}
+
+/**
+ * nautilus_tag_manager_update_removed_uris:
+ * @self: The tag manager singleton
+ * @src: The deleted/trashed location as a #GFile
+ *
+ * Checks whether the deleted/trashed item @src was starred or contained starred
+ * items, and erases the respective URIs from the database.
+ */
+void
+nautilus_tag_manager_update_removed_uris (NautilusTagManager *self,
+                                          GFile              *src)
+{
+    GHashTableIter starred_iter;
+    gchar *starred_uri;
+    g_autoptr (GPtrArray) broken_starred_uris = NULL;
+    g_autoptr (GString) query = NULL;
+
+    if (!self->database_ok)
+    {
+        g_message ("nautilus-tag-manager: No Tracker connection");
+        return;
+    }
+
+    broken_starred_uris = g_ptr_array_new ();
+
+    g_hash_table_iter_init (&starred_iter, self->starred_file_uris);
+    while (g_hash_table_iter_next (&starred_iter, (gpointer *) &starred_uri, NULL))
+    {
+        g_autoptr (GFile) starred_location = NULL;
+
+        starred_location = g_file_new_for_uri (starred_uri);
+
+        if (g_file_equal (starred_location, src)
+            || g_file_has_prefix (starred_location, src))
+        {
+            g_ptr_array_add (broken_starred_uris, starred_uri);
+        }
+    }
+
+    if (broken_starred_uris->len == 0)
+    {
+        /* No starred files are affected by this move/rename */
+        return;
+    }
+
+    DEBUG ("Erasing %i deleted/trashed starred files from database", broken_starred_uris->len);
+
+    query = g_string_new ("DELETE DATA {");
+
+    for (guint i = 0; i < broken_starred_uris->len; i++)
+    {
+        gchar *old_uri = g_ptr_array_index (broken_starred_uris, i);
+        g_string_append_printf (query,
+                                "    <%s> a nautilus:File ; "
+                                "        nautilus:starred true . ",
+                                old_uri);
+    }
+
+    g_string_append (query, "}");
+
+    tracker_sparql_connection_update_async (self->db,
+                                            query->str,
+                                            self->cancellable,
+                                            update_removed_uris_callback,
+                                            NULL);
+}
+
 static void
 process_tracker2_data_cb (GObject      *source_object,
                           GAsyncResult *res,
diff --git a/src/nautilus-tag-manager.h b/src/nautilus-tag-manager.h
index 1ba8a48dd..dfc1e2d49 100644
--- a/src/nautilus-tag-manager.h
+++ b/src/nautilus-tag-manager.h
@@ -56,6 +56,8 @@ gboolean            nautilus_tag_manager_can_star_contents (NautilusTagManager *
 void                nautilus_tag_manager_update_moved_uris  (NautilusTagManager *tag_manager,
                                                              GFile              *src,
                                                              GFile              *dest);
+void                nautilus_tag_manager_update_removed_uris  (NautilusTagManager *tag_manager,
+                                                               GFile              *src);
 
 void                nautilus_tag_manager_maybe_migrate_tracker2_data (NautilusTagManager *self);
 


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]