[gnome-software/wip/hughsie/gs_app_set_priority] Add gs_app_set_priority() to allow plugins be better than others
- From: Richard Hughes <rhughes src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-software/wip/hughsie/gs_app_set_priority] Add gs_app_set_priority() to allow plugins be better than others
- Date: Wed, 8 Jun 2016 20:14:57 +0000 (UTC)
commit 8f38b2fc44464305176c8a50d985b1a973514225
Author: Richard Hughes <richard hughsie com>
Date: Wed Jun 8 21:11:53 2016 +0100
Add gs_app_set_priority() to allow plugins be better than others
src/gs-app-private.h | 4 +
src/gs-app.c | 33 ++++++++++
src/gs-plugin-loader.c | 104 ++++++++++++++++++++++++++------
src/gs-plugin-private.h | 3 +
src/gs-plugin.c | 32 ++++++++++
src/gs-plugin.h | 2 +
src/plugins/gs-plugin-flatpak-system.c | 3 +
src/plugins/gs-plugin-flatpak-user.c | 3 +
8 files changed, 165 insertions(+), 19 deletions(-)
---
diff --git a/src/gs-app-private.h b/src/gs-app-private.h
index 6d41284..53e168c 100644
--- a/src/gs-app-private.h
+++ b/src/gs-app-private.h
@@ -29,6 +29,10 @@ G_BEGIN_DECLS
GError *gs_app_get_last_error (GsApp *app);
void gs_app_set_last_error (GsApp *app,
GError *error);
+void gs_app_set_priority (GsApp *app,
+ guint priority);
+guint gs_app_get_priority (GsApp *app);
+
G_END_DECLS
#endif /* __GS_APP_PRIVATE_H */
diff --git a/src/gs-app.c b/src/gs-app.c
index e2ba06f..4f5eeed 100644
--- a/src/gs-app.c
+++ b/src/gs-app.c
@@ -89,6 +89,7 @@ struct _GsApp
AsUrgencyKind update_urgency;
gchar *management_plugin;
guint match_value;
+ guint priority;
gint rating;
GArray *review_ratings;
GPtrArray *reviews; /* of GsReview */
@@ -309,6 +310,8 @@ gs_app_to_string (GsApp *app)
}
if (app->match_value != 0)
gs_app_kv_printf (str, "match-value", "%05x", app->match_value);
+ if (app->priority != 0)
+ gs_app_kv_printf (str, "priority", "%i", app->priority);
if (app->version != NULL)
gs_app_kv_lpad (str, "version", app->version);
if (app->version_ui != NULL)
@@ -2608,6 +2611,36 @@ gs_app_get_match_value (GsApp *app)
}
/**
+ * gs_app_set_priority:
+ * @app: a #GsApp
+ * @priority: a value
+ *
+ * Set a priority value.
+ **/
+void
+gs_app_set_priority (GsApp *app, guint priority)
+{
+ g_return_if_fail (GS_IS_APP (app));
+ app->priority = priority;
+}
+
+/**
+ * gs_app_get_priority:
+ * @app: a #GsApp
+ *
+ * Get a priority value, where higher values will be chosen where
+ * multiple #GsApp's match a specific rule.
+ *
+ * Returns: a value, where higher is better
+ **/
+guint
+gs_app_get_priority (GsApp *app)
+{
+ g_return_val_if_fail (GS_IS_APP (app), 0);
+ return app->priority;
+}
+
+/**
* gs_app_get_last_error:
* @app: a #GsApp
*
diff --git a/src/gs-plugin-loader.c b/src/gs-plugin-loader.c
index 28e384e..8789625 100644
--- a/src/gs-plugin-loader.c
+++ b/src/gs-plugin-loader.c
@@ -169,6 +169,22 @@ gs_plugin_loader_app_sort_cb (GsApp *app1, GsApp *app2, gpointer user_data)
gs_app_get_name (app2));
}
+static GsPlugin *
+gs_plugin_loader_find_plugin (GsPluginLoader *plugin_loader,
+ const gchar *plugin_name)
+{
+ GsPluginLoaderPrivate *priv = gs_plugin_loader_get_instance_private (plugin_loader);
+ GsPlugin *plugin;
+ guint i;
+
+ for (i = 0; i < priv->plugins->len; i++) {
+ plugin = g_ptr_array_index (priv->plugins, i);
+ if (g_strcmp0 (gs_plugin_get_name (plugin), plugin_name) == 0)
+ return plugin;
+ }
+ return NULL;
+}
+
/**
* gs_plugin_loader_action_start:
**/
@@ -622,6 +638,24 @@ gs_plugin_loader_get_app_str (GsApp *app)
return "<invalid>";
}
+static gboolean
+gs_plugin_loader_app_set_prio (GsApp *app, gpointer user_data)
+{
+ GsPluginLoader *plugin_loader = GS_PLUGIN_LOADER (user_data);
+ GsPlugin *plugin;
+ const gchar *tmp;
+
+ /* if set, copy the priority */
+ tmp = gs_app_get_management_plugin (app);
+ if (tmp == NULL)
+ return TRUE;
+ plugin = gs_plugin_loader_find_plugin (plugin_loader, tmp);
+ if (plugin == NULL)
+ return TRUE;
+ gs_app_set_priority (app, gs_plugin_get_priority (plugin));
+ return TRUE;
+}
+
/**
* gs_plugin_loader_app_is_valid_installed:
**/
@@ -1011,6 +1045,7 @@ gs_plugin_loader_get_updates_thread_cb (GTask *task,
/* remove any packages that are not proper applications or
* OS updates */
gs_app_list_filter (state->list, gs_plugin_loader_app_is_valid, state);
+ gs_app_list_filter (state->list, gs_plugin_loader_app_set_prio, plugin_loader);
/* success */
g_task_return_pointer (task, g_object_ref (state->list), (GDestroyNotify) g_object_unref);
@@ -1348,6 +1383,7 @@ gs_plugin_loader_get_installed_thread_cb (GTask *task,
/* filter package list */
gs_app_list_filter (state->list, gs_plugin_loader_app_is_valid, state);
gs_app_list_filter (state->list, gs_plugin_loader_app_is_valid_installed, state);
+ gs_app_list_filter (state->list, gs_plugin_loader_app_set_prio, plugin_loader);
/* success */
g_task_return_pointer (task, g_object_ref (state->list), (GDestroyNotify) g_object_unref);
@@ -1463,6 +1499,7 @@ gs_plugin_loader_get_popular_thread_cb (GTask *task,
gs_app_list_filter (state->list, gs_plugin_loader_app_is_valid, state);
gs_app_list_filter (state->list, gs_plugin_loader_filter_qt_for_gtk, NULL);
gs_app_list_filter (state->list, gs_plugin_loader_get_app_is_compatible, plugin_loader);
+ gs_app_list_filter (state->list, gs_plugin_loader_app_set_prio, plugin_loader);
/* success */
g_task_return_pointer (task, g_object_ref (state->list), (GDestroyNotify) g_object_unref);
@@ -1557,6 +1594,7 @@ gs_plugin_loader_get_featured_thread_cb (GTask *task,
gs_app_list_filter (state->list, gs_plugin_loader_app_is_valid, state);
gs_app_list_filter (state->list, gs_plugin_loader_get_app_is_compatible, plugin_loader);
}
+ gs_app_list_filter (state->list, gs_plugin_loader_app_set_prio, plugin_loader);
/* success */
g_task_return_pointer (task, g_object_ref (state->list), (GDestroyNotify) g_object_unref);
@@ -1778,6 +1816,7 @@ gs_plugin_loader_search_thread_cb (GTask *task,
gs_app_list_filter (state->list, gs_plugin_loader_app_is_valid, state);
gs_app_list_filter (state->list, gs_plugin_loader_filter_qt_for_gtk, NULL);
gs_app_list_filter (state->list, gs_plugin_loader_get_app_is_compatible, plugin_loader);
+ gs_app_list_filter (state->list, gs_plugin_loader_app_set_prio, plugin_loader);
if (gs_app_list_length (state->list) > 500) {
g_task_return_new_error (task,
GS_PLUGIN_ERROR,
@@ -1941,6 +1980,7 @@ gs_plugin_loader_search_files_thread_cb (GTask *task,
gs_app_list_filter (state->list, gs_plugin_loader_app_is_non_installed, NULL);
gs_app_list_filter (state->list, gs_plugin_loader_filter_qt_for_gtk, NULL);
gs_app_list_filter (state->list, gs_plugin_loader_get_app_is_compatible, plugin_loader);
+ gs_app_list_filter (state->list, gs_plugin_loader_app_set_prio, plugin_loader);
if (gs_app_list_length (state->list) > 500) {
g_task_return_new_error (task,
GS_PLUGIN_ERROR,
@@ -2104,6 +2144,7 @@ gs_plugin_loader_search_what_provides_thread_cb (GTask *task,
gs_app_list_filter (state->list, gs_plugin_loader_app_is_non_installed, NULL);
gs_app_list_filter (state->list, gs_plugin_loader_filter_qt_for_gtk, NULL);
gs_app_list_filter (state->list, gs_plugin_loader_get_app_is_compatible, plugin_loader);
+ gs_app_list_filter (state->list, gs_plugin_loader_app_set_prio, plugin_loader);
if (gs_app_list_length (state->list) > 500) {
g_task_return_new_error (task,
GS_PLUGIN_ERROR,
@@ -2446,6 +2487,7 @@ gs_plugin_loader_get_category_apps_thread_cb (GTask *task,
gs_app_list_filter (state->list, gs_plugin_loader_app_is_valid, state);
gs_app_list_filter (state->list, gs_plugin_loader_filter_qt_for_gtk, NULL);
gs_app_list_filter (state->list, gs_plugin_loader_get_app_is_compatible, plugin_loader);
+ gs_app_list_filter (state->list, gs_plugin_loader_app_set_prio, plugin_loader);
/* sort, just in case the UI doesn't do this */
gs_app_list_sort (state->list, gs_plugin_loader_app_sort_cb, NULL);
@@ -3150,25 +3192,6 @@ gs_plugin_loader_run (GsPluginLoader *plugin_loader, const gchar *function_name)
}
/**
- * gs_plugin_loader_find_plugin:
- */
-static GsPlugin *
-gs_plugin_loader_find_plugin (GsPluginLoader *plugin_loader,
- const gchar *plugin_name)
-{
- GsPluginLoaderPrivate *priv = gs_plugin_loader_get_instance_private (plugin_loader);
- GsPlugin *plugin;
- guint i;
-
- for (i = 0; i < priv->plugins->len; i++) {
- plugin = g_ptr_array_index (priv->plugins, i);
- if (g_strcmp0 (gs_plugin_get_name (plugin), plugin_name) == 0)
- return plugin;
- }
- return NULL;
-}
-
-/**
* gs_plugin_loader_get_enabled:
*/
gboolean
@@ -3527,6 +3550,49 @@ gs_plugin_loader_setup (GsPluginLoader *plugin_loader,
g_ptr_array_sort (priv->plugins,
gs_plugin_loader_plugin_sort_fn);
+ /* assign priority values */
+ do {
+ changes = FALSE;
+ for (i = 0; i < priv->plugins->len; i++) {
+ plugin = g_ptr_array_index (priv->plugins, i);
+ deps = gs_plugin_get_rules (plugin, GS_PLUGIN_RULE_BETTER_THAN);
+ for (j = 0; j < deps->len && !changes; j++) {
+ plugin_name = g_ptr_array_index (deps, j);
+ dep = gs_plugin_loader_find_plugin (plugin_loader,
+ plugin_name);
+ if (dep == NULL) {
+ g_debug ("cannot find plugin '%s' "
+ "requested by '%s'",
+ plugin_name,
+ gs_plugin_get_name (plugin));
+ continue;
+ }
+ if (!gs_plugin_get_enabled (dep))
+ continue;
+ if (gs_plugin_get_priority (plugin) <= gs_plugin_get_priority (dep)) {
+ g_debug ("%s [%i] is better than %s [%i] "
+ "so promoting to [%i]",
+ gs_plugin_get_name (plugin),
+ gs_plugin_get_priority (plugin),
+ gs_plugin_get_name (dep),
+ gs_plugin_get_priority (dep),
+ gs_plugin_get_priority (dep) + 1);
+ gs_plugin_set_priority (plugin, gs_plugin_get_priority (dep) + 1);
+ changes = TRUE;
+ }
+ }
+ }
+
+ /* check we're not stuck */
+ if (dep_loop_check++ > 100) {
+ g_set_error (error,
+ GS_PLUGIN_ERROR,
+ GS_PLUGIN_ERROR_FAILED,
+ "got stuck in priority loop");
+ return FALSE;
+ }
+ } while (changes);
+
/* run setup */
for (i = 0; i < priv->plugins->len; i++) {
GsPluginSetupFunc plugin_func = NULL;
diff --git a/src/gs-plugin-private.h b/src/gs-plugin-private.h
index ea318f2..ec66ef0 100644
--- a/src/gs-plugin-private.h
+++ b/src/gs-plugin-private.h
@@ -43,6 +43,9 @@ void gs_plugin_set_scale (GsPlugin *plugin,
guint gs_plugin_get_order (GsPlugin *plugin);
void gs_plugin_set_order (GsPlugin *plugin,
guint order);
+guint gs_plugin_get_priority (GsPlugin *plugin);
+void gs_plugin_set_priority (GsPlugin *plugin,
+ guint priority);
void gs_plugin_set_locale (GsPlugin *plugin,
const gchar *locale);
void gs_plugin_set_profile (GsPlugin *plugin,
diff --git a/src/gs-plugin.c b/src/gs-plugin.c
index 4a19832..e456e9a 100644
--- a/src/gs-plugin.c
+++ b/src/gs-plugin.c
@@ -68,6 +68,7 @@ typedef struct
gchar *name;
gint scale;
guint order;
+ guint priority;
guint timer_id;
GMutex timer_mutex;
} GsPluginPrivate;
@@ -422,6 +423,37 @@ gs_plugin_set_order (GsPlugin *plugin, guint order)
}
/**
+ * gs_plugin_get_priority:
+ * @plugin: a #GsPlugin
+ *
+ * Gets the plugin priority, where higher values will be chosen where
+ * multiple #GsApp's match a specific rule.
+ *
+ * Returns: the integer value
+ **/
+guint
+gs_plugin_get_priority (GsPlugin *plugin)
+{
+ GsPluginPrivate *priv = gs_plugin_get_instance_private (plugin);
+ return priv->priority;
+}
+
+/**
+ * gs_plugin_set_priority:
+ * @plugin: a #GsPlugin
+ * @priority: a integer value
+ *
+ * Sets the plugin priority, where higher values will be chosen where
+ * multiple #GsApp's match a specific rule.
+ **/
+void
+gs_plugin_set_priority (GsPlugin *plugin, guint priority)
+{
+ GsPluginPrivate *priv = gs_plugin_get_instance_private (plugin);
+ priv->priority = priority;
+}
+
+/**
* gs_plugin_get_locale:
* @plugin: a #GsPlugin
*
diff --git a/src/gs-plugin.h b/src/gs-plugin.h
index 230c4a1..bb9626c 100644
--- a/src/gs-plugin.h
+++ b/src/gs-plugin.h
@@ -204,6 +204,7 @@ typedef enum {
* @GS_PLUGIN_RULE_CONFLICTS: The plugin conflicts with another
* @GS_PLUGIN_RULE_RUN_AFTER: Order the plugin after another
* @GS_PLUGIN_RULE_RUN_BEFORE: Order the plugin before another
+ * @GS_PLUGIN_RULE_BETTER_THAN: Results are better than another
*
* The rules used for ordering plugins.
* Plugins are expected to add rules in gs_plugin_initialize().
@@ -212,6 +213,7 @@ typedef enum {
GS_PLUGIN_RULE_CONFLICTS,
GS_PLUGIN_RULE_RUN_AFTER,
GS_PLUGIN_RULE_RUN_BEFORE,
+ GS_PLUGIN_RULE_BETTER_THAN,
/*< private >*/
GS_PLUGIN_RULE_LAST
} GsPluginRule;
diff --git a/src/plugins/gs-plugin-flatpak-system.c b/src/plugins/gs-plugin-flatpak-system.c
index 7fe08ca..715eb44 100644
--- a/src/plugins/gs-plugin-flatpak-system.c
+++ b/src/plugins/gs-plugin-flatpak-system.c
@@ -48,6 +48,9 @@ gs_plugin_initialize (GsPlugin *plugin)
/* getting app properties from appstream is quicker */
gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_RUN_AFTER, "appstream");
+
+ /* prioritize over packages */
+ gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_BETTER_THAN, "packagekit");
}
void
diff --git a/src/plugins/gs-plugin-flatpak-user.c b/src/plugins/gs-plugin-flatpak-user.c
index 0700918..7334373 100644
--- a/src/plugins/gs-plugin-flatpak-user.c
+++ b/src/plugins/gs-plugin-flatpak-user.c
@@ -48,6 +48,9 @@ gs_plugin_initialize (GsPlugin *plugin)
/* getting app properties from appstream is quicker */
gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_RUN_AFTER, "appstream");
+
+ /* prioritize over packages */
+ gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_BETTER_THAN, "packagekit");
}
void
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]