From d14944ca6d8f422a1a1cf5e74bdf91c2d2d2d82f Mon Sep 17 00:00:00 2001 From: Richard Hughes Date: Fri, 21 Feb 2020 16:16:26 +0000 Subject: [PATCH 001/163] Backport a patch to fix a crash when looking at the application details --- ...ash-when-viewing-application-details.patch | 146 ++++++++++++++++++ gnome-software.spec | 8 +- 2 files changed, 153 insertions(+), 1 deletion(-) create mode 100644 0001-Fix-crash-when-viewing-application-details.patch diff --git a/0001-Fix-crash-when-viewing-application-details.patch b/0001-Fix-crash-when-viewing-application-details.patch new file mode 100644 index 0000000..ec3962c --- /dev/null +++ b/0001-Fix-crash-when-viewing-application-details.patch @@ -0,0 +1,146 @@ +From 236a05e16c5880e47b1e52a3ece2f9d77b628b49 Mon Sep 17 00:00:00 2001 +From: Richard Hughes +Date: Fri, 21 Feb 2020 13:42:55 +0000 +Subject: [PATCH] Fix crash when viewing application details + +The code was creating an array of guint32 and reading back an array of gint +which caused a crazy histogram and an invalid read in some circumstances. + +Standardize to reading and writing a guint32 everywhere and make the code +somewhat simpler. + +Fixes https://gitlab.gnome.org/GNOME/gnome-software/issues/928 +--- + lib/gs-app.c | 8 +++--- + src/gs-details-page.c | 4 +-- + src/gs-review-histogram.c | 53 +++++++++++++++++++++------------------ + 3 files changed, 35 insertions(+), 30 deletions(-) + +diff --git a/lib/gs-app.c b/lib/gs-app.c +index b7830009..5bc93fd1 100644 +--- a/lib/gs-app.c ++++ b/lib/gs-app.c +@@ -580,8 +580,8 @@ gs_app_to_string_append (GsApp *app, GString *str) + gs_app_kv_printf (str, "rating", "%i", priv->rating); + if (priv->review_ratings != NULL) { + for (i = 0; i < priv->review_ratings->len; i++) { +- gint rat = g_array_index (priv->review_ratings, gint, i); +- gs_app_kv_printf (str, "review-rating", "[%u:%i]", ++ guint32 rat = g_array_index (priv->review_ratings, guint32, i); ++ gs_app_kv_printf (str, "review-rating", "[%u:%u]", + i, rat); + } + } +@@ -2881,7 +2881,7 @@ gs_app_set_rating (GsApp *app, gint rating) + * + * Gets the review ratings. + * +- * Returns: (element-type gint) (transfer none): a list ++ * Returns: (element-type guint32) (transfer none): a list + * + * Since: 3.22 + **/ +@@ -2896,7 +2896,7 @@ gs_app_get_review_ratings (GsApp *app) + /** + * gs_app_set_review_ratings: + * @app: a #GsApp +- * @review_ratings: (element-type gint): a list ++ * @review_ratings: (element-type guint32): a list + * + * Sets the review ratings. + * +diff --git a/src/gs-details-page.c b/src/gs-details-page.c +index 4dd88a1e..8eb07bd3 100644 +--- a/src/gs-details-page.c ++++ b/src/gs-details-page.c +@@ -1565,7 +1565,7 @@ gs_details_page_refresh_reviews (GsDetailsPage *self) + } + if (review_ratings != NULL) { + for (i = 0; i < review_ratings->len; i++) +- n_reviews += (guint) g_array_index (review_ratings, gint, i); ++ n_reviews += (guint) g_array_index (review_ratings, guint32, i); + } else if (gs_app_get_reviews (self->app) != NULL) { + n_reviews = gs_app_get_reviews (self->app)->len; + } +@@ -1574,7 +1574,7 @@ gs_details_page_refresh_reviews (GsDetailsPage *self) + /* enable appropriate widgets */ + gtk_widget_set_visible (self->star, show_reviews); + gtk_widget_set_visible (self->box_reviews, show_reviews); +- gtk_widget_set_visible (self->histogram, review_ratings != NULL); ++ gtk_widget_set_visible (self->histogram, review_ratings != NULL && review_ratings->len > 0); + gtk_widget_set_visible (self->label_review_count, n_reviews > 0); + + /* update the review label next to the star widget */ +diff --git a/src/gs-review-histogram.c b/src/gs-review-histogram.c +index bbd297c8..21455f55 100644 +--- a/src/gs-review-histogram.c ++++ b/src/gs-review-histogram.c +@@ -39,36 +39,41 @@ void + gs_review_histogram_set_ratings (GsReviewHistogram *histogram, + GArray *review_ratings) + { +- GsReviewHistogramPrivate *priv; +- gdouble max; +- gint count[5] = { 0, 0, 0, 0, 0 }; +- guint i; ++ GsReviewHistogramPrivate *priv = gs_review_histogram_get_instance_private (histogram); ++ gdouble fraction[6] = { 0.0f }; ++ guint32 max = 0; ++ guint32 total = 0; + + g_return_if_fail (GS_IS_REVIEW_HISTOGRAM (histogram)); +- priv = gs_review_histogram_get_instance_private (histogram); + +- /* Scale to maximum value */ +- for (max = 0, i = 0; i < review_ratings->len; i++) { +- gint c; ++ /* sanity check */ ++ if (review_ratings->len != 6) { ++ g_warning ("ratings data incorrect expected 012345"); ++ return; ++ } + +- c = g_array_index (review_ratings, gint, i); +- if (c > max) +- max = c; +- if (i > 0 && i < 6) +- count[i - 1] = c; ++ /* idx 0 is '0 stars' which we don't support in the UI */ ++ for (guint i = 1; i < review_ratings->len; i++) { ++ guint32 c = g_array_index (review_ratings, guint32, i); ++ max = MAX (c, max); ++ } ++ for (guint i = 1; i < review_ratings->len; i++) { ++ guint32 c = g_array_index (review_ratings, guint32, i); ++ fraction[i] = max > 0 ? (gdouble) c / (gdouble) max : 0.f; ++ total += c; + } + +- gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar5), count[4] / max); +- set_label (priv->label_count5, count[4]); +- gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar4), count[3] / max); +- set_label (priv->label_count4, count[3]); +- gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar3), count[2] / max); +- set_label (priv->label_count3, count[2]); +- gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar2), count[1] / max); +- set_label (priv->label_count2, count[1]); +- gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar1), count[0] / max); +- set_label (priv->label_count1, count[0]); +- set_label (priv->label_total, count[0] + count[1] + count[2] + count[3] + count[4]); ++ gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar5), fraction[5]); ++ set_label (priv->label_count5, g_array_index (review_ratings, guint, 5)); ++ gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar4), fraction[4]); ++ set_label (priv->label_count4, g_array_index (review_ratings, guint, 4)); ++ gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar3), fraction[3]); ++ set_label (priv->label_count3, g_array_index (review_ratings, guint, 3)); ++ gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar2), fraction[2]); ++ set_label (priv->label_count2, g_array_index (review_ratings, guint, 2)); ++ gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar1), fraction[1]); ++ set_label (priv->label_count1, g_array_index (review_ratings, guint, 1)); ++ set_label (priv->label_total, total); + } + + static void +-- +2.24.1 + diff --git a/gnome-software.spec b/gnome-software.spec index 827161b..e409132 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,13 +12,16 @@ Name: gnome-software Version: 3.35.91 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/3.35/%{name}-%{version}.tar.xz +# already upstream +Patch0: 0001-Fix-crash-when-viewing-application-details.patch + BuildRequires: gcc BuildRequires: gettext BuildRequires: libxslt @@ -203,6 +206,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri Feb 21 2020 Richard Hughes - 3.35.91-2 +- Backport a patch to fix a crash when looking at the application details. + * Wed Feb 19 2020 Richard Hughes - 3.35.91-1 - Update to 3.35.91. From 3ec52c4ecb4642a8d5eef6c9b83e73a6880df5d3 Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Wed, 4 Mar 2020 15:23:46 +0100 Subject: [PATCH 002/163] Update to 3.35.92 --- .gitignore | 1 + ...ash-when-viewing-application-details.patch | 146 ------------------ gnome-software.spec | 10 +- sources | 2 +- 4 files changed, 7 insertions(+), 152 deletions(-) delete mode 100644 0001-Fix-crash-when-viewing-application-details.patch diff --git a/.gitignore b/.gitignore index d4bab8a..441ea94 100644 --- a/.gitignore +++ b/.gitignore @@ -108,3 +108,4 @@ /gnome-software-3.34.1.tar.xz /gnome-software-3.35.2.tar.xz /gnome-software-3.35.91.tar.xz +/gnome-software-3.35.92.tar.xz diff --git a/0001-Fix-crash-when-viewing-application-details.patch b/0001-Fix-crash-when-viewing-application-details.patch deleted file mode 100644 index ec3962c..0000000 --- a/0001-Fix-crash-when-viewing-application-details.patch +++ /dev/null @@ -1,146 +0,0 @@ -From 236a05e16c5880e47b1e52a3ece2f9d77b628b49 Mon Sep 17 00:00:00 2001 -From: Richard Hughes -Date: Fri, 21 Feb 2020 13:42:55 +0000 -Subject: [PATCH] Fix crash when viewing application details - -The code was creating an array of guint32 and reading back an array of gint -which caused a crazy histogram and an invalid read in some circumstances. - -Standardize to reading and writing a guint32 everywhere and make the code -somewhat simpler. - -Fixes https://gitlab.gnome.org/GNOME/gnome-software/issues/928 ---- - lib/gs-app.c | 8 +++--- - src/gs-details-page.c | 4 +-- - src/gs-review-histogram.c | 53 +++++++++++++++++++++------------------ - 3 files changed, 35 insertions(+), 30 deletions(-) - -diff --git a/lib/gs-app.c b/lib/gs-app.c -index b7830009..5bc93fd1 100644 ---- a/lib/gs-app.c -+++ b/lib/gs-app.c -@@ -580,8 +580,8 @@ gs_app_to_string_append (GsApp *app, GString *str) - gs_app_kv_printf (str, "rating", "%i", priv->rating); - if (priv->review_ratings != NULL) { - for (i = 0; i < priv->review_ratings->len; i++) { -- gint rat = g_array_index (priv->review_ratings, gint, i); -- gs_app_kv_printf (str, "review-rating", "[%u:%i]", -+ guint32 rat = g_array_index (priv->review_ratings, guint32, i); -+ gs_app_kv_printf (str, "review-rating", "[%u:%u]", - i, rat); - } - } -@@ -2881,7 +2881,7 @@ gs_app_set_rating (GsApp *app, gint rating) - * - * Gets the review ratings. - * -- * Returns: (element-type gint) (transfer none): a list -+ * Returns: (element-type guint32) (transfer none): a list - * - * Since: 3.22 - **/ -@@ -2896,7 +2896,7 @@ gs_app_get_review_ratings (GsApp *app) - /** - * gs_app_set_review_ratings: - * @app: a #GsApp -- * @review_ratings: (element-type gint): a list -+ * @review_ratings: (element-type guint32): a list - * - * Sets the review ratings. - * -diff --git a/src/gs-details-page.c b/src/gs-details-page.c -index 4dd88a1e..8eb07bd3 100644 ---- a/src/gs-details-page.c -+++ b/src/gs-details-page.c -@@ -1565,7 +1565,7 @@ gs_details_page_refresh_reviews (GsDetailsPage *self) - } - if (review_ratings != NULL) { - for (i = 0; i < review_ratings->len; i++) -- n_reviews += (guint) g_array_index (review_ratings, gint, i); -+ n_reviews += (guint) g_array_index (review_ratings, guint32, i); - } else if (gs_app_get_reviews (self->app) != NULL) { - n_reviews = gs_app_get_reviews (self->app)->len; - } -@@ -1574,7 +1574,7 @@ gs_details_page_refresh_reviews (GsDetailsPage *self) - /* enable appropriate widgets */ - gtk_widget_set_visible (self->star, show_reviews); - gtk_widget_set_visible (self->box_reviews, show_reviews); -- gtk_widget_set_visible (self->histogram, review_ratings != NULL); -+ gtk_widget_set_visible (self->histogram, review_ratings != NULL && review_ratings->len > 0); - gtk_widget_set_visible (self->label_review_count, n_reviews > 0); - - /* update the review label next to the star widget */ -diff --git a/src/gs-review-histogram.c b/src/gs-review-histogram.c -index bbd297c8..21455f55 100644 ---- a/src/gs-review-histogram.c -+++ b/src/gs-review-histogram.c -@@ -39,36 +39,41 @@ void - gs_review_histogram_set_ratings (GsReviewHistogram *histogram, - GArray *review_ratings) - { -- GsReviewHistogramPrivate *priv; -- gdouble max; -- gint count[5] = { 0, 0, 0, 0, 0 }; -- guint i; -+ GsReviewHistogramPrivate *priv = gs_review_histogram_get_instance_private (histogram); -+ gdouble fraction[6] = { 0.0f }; -+ guint32 max = 0; -+ guint32 total = 0; - - g_return_if_fail (GS_IS_REVIEW_HISTOGRAM (histogram)); -- priv = gs_review_histogram_get_instance_private (histogram); - -- /* Scale to maximum value */ -- for (max = 0, i = 0; i < review_ratings->len; i++) { -- gint c; -+ /* sanity check */ -+ if (review_ratings->len != 6) { -+ g_warning ("ratings data incorrect expected 012345"); -+ return; -+ } - -- c = g_array_index (review_ratings, gint, i); -- if (c > max) -- max = c; -- if (i > 0 && i < 6) -- count[i - 1] = c; -+ /* idx 0 is '0 stars' which we don't support in the UI */ -+ for (guint i = 1; i < review_ratings->len; i++) { -+ guint32 c = g_array_index (review_ratings, guint32, i); -+ max = MAX (c, max); -+ } -+ for (guint i = 1; i < review_ratings->len; i++) { -+ guint32 c = g_array_index (review_ratings, guint32, i); -+ fraction[i] = max > 0 ? (gdouble) c / (gdouble) max : 0.f; -+ total += c; - } - -- gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar5), count[4] / max); -- set_label (priv->label_count5, count[4]); -- gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar4), count[3] / max); -- set_label (priv->label_count4, count[3]); -- gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar3), count[2] / max); -- set_label (priv->label_count3, count[2]); -- gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar2), count[1] / max); -- set_label (priv->label_count2, count[1]); -- gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar1), count[0] / max); -- set_label (priv->label_count1, count[0]); -- set_label (priv->label_total, count[0] + count[1] + count[2] + count[3] + count[4]); -+ gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar5), fraction[5]); -+ set_label (priv->label_count5, g_array_index (review_ratings, guint, 5)); -+ gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar4), fraction[4]); -+ set_label (priv->label_count4, g_array_index (review_ratings, guint, 4)); -+ gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar3), fraction[3]); -+ set_label (priv->label_count3, g_array_index (review_ratings, guint, 3)); -+ gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar2), fraction[2]); -+ set_label (priv->label_count2, g_array_index (review_ratings, guint, 2)); -+ gs_review_bar_set_fraction (GS_REVIEW_BAR (priv->bar1), fraction[1]); -+ set_label (priv->label_count1, g_array_index (review_ratings, guint, 1)); -+ set_label (priv->label_total, total); - } - - static void --- -2.24.1 - diff --git a/gnome-software.spec b/gnome-software.spec index e409132..d2e0331 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,17 +11,14 @@ %global libxmlb_version 0.1.7 Name: gnome-software -Version: 3.35.91 -Release: 2%{?dist} +Version: 3.35.92 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/3.35/%{name}-%{version}.tar.xz -# already upstream -Patch0: 0001-Fix-crash-when-viewing-application-details.patch - BuildRequires: gcc BuildRequires: gettext BuildRequires: libxslt @@ -206,6 +203,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Wed Mar 04 2020 Kalev Lember - 3.35.92-1 +- Update to 3.35.92 + * Fri Feb 21 2020 Richard Hughes - 3.35.91-2 - Backport a patch to fix a crash when looking at the application details. diff --git a/sources b/sources index 21ab9a7..077f7c1 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-3.35.91.tar.xz) = 2329e3aafa896442ad61f76e72325632a98dc2913e2874e96bad91ea2b52f759730d729acd7d3ba93c07c3a89817c4e5c29133cc9082f6a54a675cb23f9f28ca +SHA512 (gnome-software-3.35.92.tar.xz) = 1846fa10b19daa48fce9d05e3f95cfabbef90bbe3f4ddbfd31b82cbe59ce8dc742630bc8d441965b724750a344902ffe6447d984041349ae836b73c010d30ff8 From fb614f17e4fc3934805dafd410d93cb3b758631e Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Wed, 11 Mar 2020 13:58:51 +0100 Subject: [PATCH 003/163] Update to 3.36.0 --- .gitignore | 1 + gnome-software.spec | 7 +++++-- sources | 2 +- 3 files changed, 7 insertions(+), 3 deletions(-) diff --git a/.gitignore b/.gitignore index 441ea94..8c0c6a8 100644 --- a/.gitignore +++ b/.gitignore @@ -109,3 +109,4 @@ /gnome-software-3.35.2.tar.xz /gnome-software-3.35.91.tar.xz /gnome-software-3.35.92.tar.xz +/gnome-software-3.36.0.tar.xz diff --git a/gnome-software.spec b/gnome-software.spec index d2e0331..f2e55b7 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,13 +11,13 @@ %global libxmlb_version 0.1.7 Name: gnome-software -Version: 3.35.92 +Version: 3.36.0 Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software -Source0: https://download.gnome.org/sources/gnome-software/3.35/%{name}-%{version}.tar.xz +Source0: https://download.gnome.org/sources/gnome-software/3.36/%{name}-%{version}.tar.xz BuildRequires: gcc BuildRequires: gettext @@ -203,6 +203,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Wed Mar 11 2020 Kalev Lember - 3.36.0-1 +- Update to 3.36.0 + * Wed Mar 04 2020 Kalev Lember - 3.35.92-1 - Update to 3.35.92 diff --git a/sources b/sources index 077f7c1..ebac2ec 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-3.35.92.tar.xz) = 1846fa10b19daa48fce9d05e3f95cfabbef90bbe3f4ddbfd31b82cbe59ce8dc742630bc8d441965b724750a344902ffe6447d984041349ae836b73c010d30ff8 +SHA512 (gnome-software-3.36.0.tar.xz) = 3727b738b0f669018b4b9b2af11dd86a1af6d8da7632b88c6ac47ef97b97299abb0aec47a6de2dc7e6afa33ee153f9df30e63e5dc83652a5402d6444389024c9 From 122d8ac6032e942f632d10ada11f30d0207df4d3 Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Tue, 12 May 2020 20:25:53 +0200 Subject: [PATCH 004/163] Backport various rpm-ostree backend fixes --- ...issing-locking-when-creating-DnfCont.patch | 27 +++++ ...ctly-mark-layered-local-packages-as-.patch | 64 +++++++++++ ...up-the-progress-info-required-for-th.patch | 106 ++++++++++++++++++ gnome-software.spec | 9 +- 4 files changed, 205 insertions(+), 1 deletion(-) create mode 100644 0001-rpm-ostree-Add-missing-locking-when-creating-DnfCont.patch create mode 100644 0002-rpm-ostree-Correctly-mark-layered-local-packages-as-.patch create mode 100644 0003-rpm-ostree-Hook-up-the-progress-info-required-for-th.patch diff --git a/0001-rpm-ostree-Add-missing-locking-when-creating-DnfCont.patch b/0001-rpm-ostree-Add-missing-locking-when-creating-DnfCont.patch new file mode 100644 index 0000000..7729d39 --- /dev/null +++ b/0001-rpm-ostree-Add-missing-locking-when-creating-DnfCont.patch @@ -0,0 +1,27 @@ +From 33c980fb6fc0b0ad8206ffd39cf789447831518a Mon Sep 17 00:00:00 2001 +From: Kalev Lember +Date: Tue, 12 May 2020 10:18:43 +0200 +Subject: [PATCH 1/3] rpm-ostree: Add missing locking when creating DnfContext + +Fixes https://gitlab.gnome.org/GNOME/gnome-software/issues/983 +--- + plugins/rpm-ostree/gs-plugin-rpm-ostree.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +index 3811f935..f2c33484 100644 +--- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c ++++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +@@ -657,6 +657,9 @@ gs_plugin_refresh (GsPlugin *plugin, + GError **error) + { + GsPluginData *priv = gs_plugin_get_data (plugin); ++ g_autoptr(GMutexLocker) locker = NULL; ++ ++ locker = g_mutex_locker_new (&priv->mutex); + + if (!ensure_rpmostree_dnf_context (plugin, cancellable, error)) + return FALSE; +-- +2.26.2 + diff --git a/0002-rpm-ostree-Correctly-mark-layered-local-packages-as-.patch b/0002-rpm-ostree-Correctly-mark-layered-local-packages-as-.patch new file mode 100644 index 0000000..5efd58f --- /dev/null +++ b/0002-rpm-ostree-Correctly-mark-layered-local-packages-as-.patch @@ -0,0 +1,64 @@ +From 1d74bd249459f5a6768ce0642538f2ff395543c8 Mon Sep 17 00:00:00 2001 +From: Kalev Lember +Date: Tue, 12 May 2020 15:13:41 +0200 +Subject: [PATCH 2/3] rpm-ostree: Correctly mark layered local packages as + removable + +Fixes https://gitlab.gnome.org/GNOME/gnome-software/issues/984 +--- + plugins/rpm-ostree/gs-plugin-rpm-ostree.c | 11 +++++++++-- + 1 file changed, 9 insertions(+), 2 deletions(-) + +diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +index f2c33484..e3824df1 100644 +--- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c ++++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +@@ -1251,6 +1251,7 @@ static gboolean + resolve_installed_packages_app (GsPlugin *plugin, + GPtrArray *pkglist, + gchar **layered_packages, ++ gchar **layered_local_packages, + GsApp *app) + { + for (guint i = 0; i < pkglist->len; i++) { +@@ -1260,7 +1261,9 @@ resolve_installed_packages_app (GsPlugin *plugin, + if (gs_app_get_state (app) == AS_APP_STATE_UNKNOWN) + gs_app_set_state (app, AS_APP_STATE_INSTALLED); + if (g_strv_contains ((const gchar * const *) layered_packages, +- rpm_ostree_package_get_name (pkg))) { ++ rpm_ostree_package_get_name (pkg)) || ++ g_strv_contains ((const gchar * const *) layered_local_packages, ++ rpm_ostree_package_get_nevra (pkg))) { + /* layered packages can always be removed */ + gs_app_remove_quirk (app, GS_APP_QUIRK_COMPULSORY); + } else { +@@ -1389,6 +1392,7 @@ gs_plugin_refine (GsPlugin *plugin, + g_autoptr(GPtrArray) pkglist = NULL; + g_autoptr(GVariant) default_deployment = NULL; + g_auto(GStrv) layered_packages = NULL; ++ g_auto(GStrv) layered_local_packages = NULL; + g_autofree gchar *checksum = NULL; + + locker = g_mutex_locker_new (&priv->mutex); +@@ -1403,6 +1407,9 @@ gs_plugin_refine (GsPlugin *plugin, + g_assert (g_variant_lookup (default_deployment, + "packages", "^as", + &layered_packages)); ++ g_assert (g_variant_lookup (default_deployment, ++ "requested-local-packages", "^as", ++ &layered_local_packages)); + g_assert (g_variant_lookup (default_deployment, + "checksum", "s", + &checksum)); +@@ -1442,7 +1449,7 @@ gs_plugin_refine (GsPlugin *plugin, + continue; + + /* first try to resolve from installed packages */ +- found = resolve_installed_packages_app (plugin, pkglist, layered_packages, app); ++ found = resolve_installed_packages_app (plugin, pkglist, layered_packages, layered_local_packages, app); + + /* if we didn't find anything, try resolving from available packages */ + if (!found && priv->dnf_context != NULL) +-- +2.26.2 + diff --git a/0003-rpm-ostree-Hook-up-the-progress-info-required-for-th.patch b/0003-rpm-ostree-Hook-up-the-progress-info-required-for-th.patch new file mode 100644 index 0000000..42a7781 --- /dev/null +++ b/0003-rpm-ostree-Hook-up-the-progress-info-required-for-th.patch @@ -0,0 +1,106 @@ +From 73c6118c15cdcbc33828dc2b470f2e652f4a64ac Mon Sep 17 00:00:00 2001 +From: Kalev Lember +Date: Tue, 12 May 2020 16:53:20 +0200 +Subject: [PATCH 3/3] rpm-ostree: Hook up the progress info required for the + loading page + +--- + plugins/rpm-ostree/gs-plugin-rpm-ostree.c | 34 ++++++++++++++++++++++- + 1 file changed, 33 insertions(+), 1 deletion(-) + +diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +index e3824df1..96531759 100644 +--- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c ++++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +@@ -255,8 +255,9 @@ transaction_progress_new (void) + static void + transaction_progress_free (TransactionProgress *self) + { +- g_main_loop_unref (self->loop); ++ g_clear_object (&self->plugin); + g_clear_error (&self->error); ++ g_main_loop_unref (self->loop); + g_clear_object (&self->app); + g_slice_free (TransactionProgress, self); + } +@@ -281,11 +282,30 @@ on_transaction_progress (GDBusProxy *proxy, + if (g_strcmp0 (signal_name, "PercentProgress") == 0) { + const gchar *message = NULL; + guint32 percentage; ++ + g_variant_get_child (parameters, 0, "&s", &message); + g_variant_get_child (parameters, 1, "u", &percentage); + g_debug ("PercentProgress: %u, %s\n", percentage, message); ++ + if (tp->app != NULL) + gs_app_set_progress (tp->app, (guint) percentage); ++ ++ if (tp->app != NULL && tp->plugin != NULL) { ++ GsPluginStatus plugin_status; ++ ++ switch (gs_app_get_state (tp->app)) { ++ case AS_APP_STATE_INSTALLING: ++ plugin_status = GS_PLUGIN_STATUS_INSTALLING; ++ break; ++ case AS_APP_STATE_REMOVING: ++ plugin_status = GS_PLUGIN_STATUS_REMOVING; ++ break; ++ default: ++ plugin_status = GS_PLUGIN_STATUS_DOWNLOADING; ++ break; ++ } ++ gs_plugin_status_update (tp->plugin, tp->app, plugin_status); ++ } + } else if (g_strcmp0 (signal_name, "Finished") == 0) { + if (tp->error == NULL) { + g_autofree gchar *error_message = NULL; +@@ -603,6 +623,7 @@ ensure_rpmostree_dnf_context (GsPlugin *plugin, GCancellable *cancellable, GErro + { + GsPluginData *priv = gs_plugin_get_data (plugin); + g_autofree gchar *transaction_address = NULL; ++ g_autoptr(GsApp) progress_app = gs_app_new (gs_plugin_get_name (plugin)); + g_autoptr(DnfContext) context = dnf_context_new (); + g_autoptr(DnfState) state = dnf_state_new (); + g_autoptr(GVariant) options = NULL; +@@ -611,6 +632,9 @@ ensure_rpmostree_dnf_context (GsPlugin *plugin, GCancellable *cancellable, GErro + if (priv->dnf_context != NULL) + return TRUE; + ++ tp->app = g_object_ref (progress_app); ++ tp->plugin = g_object_ref (plugin); ++ + dnf_context_set_repo_dir (context, "/etc/yum.repos.d"); + dnf_context_set_cache_dir (context, RPMOSTREE_CORE_CACHEDIR RPMOSTREE_DIR_CACHE_REPOMD); + dnf_context_set_solv_dir (context, RPMOSTREE_CORE_CACHEDIR RPMOSTREE_DIR_CACHE_SOLV); +@@ -669,9 +693,13 @@ gs_plugin_refresh (GsPlugin *plugin, + + { + g_autofree gchar *transaction_address = NULL; ++ g_autoptr(GsApp) progress_app = gs_app_new (gs_plugin_get_name (plugin)); + g_autoptr(GVariant) options = NULL; + g_autoptr(TransactionProgress) tp = transaction_progress_new (); + ++ tp->app = g_object_ref (progress_app); ++ tp->plugin = g_object_ref (plugin); ++ + options = make_rpmostree_options_variant (FALSE, /* reboot */ + FALSE, /* allow-downgrade */ + FALSE, /* cache-only */ +@@ -703,10 +731,14 @@ gs_plugin_refresh (GsPlugin *plugin, + + { + g_autofree gchar *transaction_address = NULL; ++ g_autoptr(GsApp) progress_app = gs_app_new (gs_plugin_get_name (plugin)); + g_autoptr(GVariant) options = NULL; + GVariantDict dict; + g_autoptr(TransactionProgress) tp = transaction_progress_new (); + ++ tp->app = g_object_ref (progress_app); ++ tp->plugin = g_object_ref (plugin); ++ + g_variant_dict_init (&dict, NULL); + g_variant_dict_insert (&dict, "mode", "s", "check"); + options = g_variant_ref_sink (g_variant_dict_end (&dict)); +-- +2.26.2 + diff --git a/gnome-software.spec b/gnome-software.spec index f2e55b7..347044c 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,13 +12,17 @@ Name: gnome-software Version: 3.36.0 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/3.36/%{name}-%{version}.tar.xz +Patch1: 0001-rpm-ostree-Add-missing-locking-when-creating-DnfCont.patch +Patch2: 0002-rpm-ostree-Correctly-mark-layered-local-packages-as-.patch +Patch3: 0003-rpm-ostree-Hook-up-the-progress-info-required-for-th.patch + BuildRequires: gcc BuildRequires: gettext BuildRequires: libxslt @@ -203,6 +207,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Tue May 12 2020 Kalev Lember - 3.36.0-2 +- Backport various rpm-ostree backend fixes + * Wed Mar 11 2020 Kalev Lember - 3.36.0-1 - Update to 3.36.0 From 63583454c0b169814f67661beae5979898ca5f35 Mon Sep 17 00:00:00 2001 From: Richard Hughes Date: Fri, 22 May 2020 17:00:53 +0100 Subject: [PATCH 005/163] Update to 3.36.1 --- .gitignore | 1 + ...issing-locking-when-creating-DnfCont.patch | 27 ----- ...ctly-mark-layered-local-packages-as-.patch | 64 ----------- ...up-the-progress-info-required-for-th.patch | 106 ------------------ gnome-software.spec | 11 +- sources | 2 +- 6 files changed, 7 insertions(+), 204 deletions(-) delete mode 100644 0001-rpm-ostree-Add-missing-locking-when-creating-DnfCont.patch delete mode 100644 0002-rpm-ostree-Correctly-mark-layered-local-packages-as-.patch delete mode 100644 0003-rpm-ostree-Hook-up-the-progress-info-required-for-th.patch diff --git a/.gitignore b/.gitignore index 8c0c6a8..376e4ca 100644 --- a/.gitignore +++ b/.gitignore @@ -110,3 +110,4 @@ /gnome-software-3.35.91.tar.xz /gnome-software-3.35.92.tar.xz /gnome-software-3.36.0.tar.xz +/gnome-software-3.36.1.tar.xz diff --git a/0001-rpm-ostree-Add-missing-locking-when-creating-DnfCont.patch b/0001-rpm-ostree-Add-missing-locking-when-creating-DnfCont.patch deleted file mode 100644 index 7729d39..0000000 --- a/0001-rpm-ostree-Add-missing-locking-when-creating-DnfCont.patch +++ /dev/null @@ -1,27 +0,0 @@ -From 33c980fb6fc0b0ad8206ffd39cf789447831518a Mon Sep 17 00:00:00 2001 -From: Kalev Lember -Date: Tue, 12 May 2020 10:18:43 +0200 -Subject: [PATCH 1/3] rpm-ostree: Add missing locking when creating DnfContext - -Fixes https://gitlab.gnome.org/GNOME/gnome-software/issues/983 ---- - plugins/rpm-ostree/gs-plugin-rpm-ostree.c | 3 +++ - 1 file changed, 3 insertions(+) - -diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -index 3811f935..f2c33484 100644 ---- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -+++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -@@ -657,6 +657,9 @@ gs_plugin_refresh (GsPlugin *plugin, - GError **error) - { - GsPluginData *priv = gs_plugin_get_data (plugin); -+ g_autoptr(GMutexLocker) locker = NULL; -+ -+ locker = g_mutex_locker_new (&priv->mutex); - - if (!ensure_rpmostree_dnf_context (plugin, cancellable, error)) - return FALSE; --- -2.26.2 - diff --git a/0002-rpm-ostree-Correctly-mark-layered-local-packages-as-.patch b/0002-rpm-ostree-Correctly-mark-layered-local-packages-as-.patch deleted file mode 100644 index 5efd58f..0000000 --- a/0002-rpm-ostree-Correctly-mark-layered-local-packages-as-.patch +++ /dev/null @@ -1,64 +0,0 @@ -From 1d74bd249459f5a6768ce0642538f2ff395543c8 Mon Sep 17 00:00:00 2001 -From: Kalev Lember -Date: Tue, 12 May 2020 15:13:41 +0200 -Subject: [PATCH 2/3] rpm-ostree: Correctly mark layered local packages as - removable - -Fixes https://gitlab.gnome.org/GNOME/gnome-software/issues/984 ---- - plugins/rpm-ostree/gs-plugin-rpm-ostree.c | 11 +++++++++-- - 1 file changed, 9 insertions(+), 2 deletions(-) - -diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -index f2c33484..e3824df1 100644 ---- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -+++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -@@ -1251,6 +1251,7 @@ static gboolean - resolve_installed_packages_app (GsPlugin *plugin, - GPtrArray *pkglist, - gchar **layered_packages, -+ gchar **layered_local_packages, - GsApp *app) - { - for (guint i = 0; i < pkglist->len; i++) { -@@ -1260,7 +1261,9 @@ resolve_installed_packages_app (GsPlugin *plugin, - if (gs_app_get_state (app) == AS_APP_STATE_UNKNOWN) - gs_app_set_state (app, AS_APP_STATE_INSTALLED); - if (g_strv_contains ((const gchar * const *) layered_packages, -- rpm_ostree_package_get_name (pkg))) { -+ rpm_ostree_package_get_name (pkg)) || -+ g_strv_contains ((const gchar * const *) layered_local_packages, -+ rpm_ostree_package_get_nevra (pkg))) { - /* layered packages can always be removed */ - gs_app_remove_quirk (app, GS_APP_QUIRK_COMPULSORY); - } else { -@@ -1389,6 +1392,7 @@ gs_plugin_refine (GsPlugin *plugin, - g_autoptr(GPtrArray) pkglist = NULL; - g_autoptr(GVariant) default_deployment = NULL; - g_auto(GStrv) layered_packages = NULL; -+ g_auto(GStrv) layered_local_packages = NULL; - g_autofree gchar *checksum = NULL; - - locker = g_mutex_locker_new (&priv->mutex); -@@ -1403,6 +1407,9 @@ gs_plugin_refine (GsPlugin *plugin, - g_assert (g_variant_lookup (default_deployment, - "packages", "^as", - &layered_packages)); -+ g_assert (g_variant_lookup (default_deployment, -+ "requested-local-packages", "^as", -+ &layered_local_packages)); - g_assert (g_variant_lookup (default_deployment, - "checksum", "s", - &checksum)); -@@ -1442,7 +1449,7 @@ gs_plugin_refine (GsPlugin *plugin, - continue; - - /* first try to resolve from installed packages */ -- found = resolve_installed_packages_app (plugin, pkglist, layered_packages, app); -+ found = resolve_installed_packages_app (plugin, pkglist, layered_packages, layered_local_packages, app); - - /* if we didn't find anything, try resolving from available packages */ - if (!found && priv->dnf_context != NULL) --- -2.26.2 - diff --git a/0003-rpm-ostree-Hook-up-the-progress-info-required-for-th.patch b/0003-rpm-ostree-Hook-up-the-progress-info-required-for-th.patch deleted file mode 100644 index 42a7781..0000000 --- a/0003-rpm-ostree-Hook-up-the-progress-info-required-for-th.patch +++ /dev/null @@ -1,106 +0,0 @@ -From 73c6118c15cdcbc33828dc2b470f2e652f4a64ac Mon Sep 17 00:00:00 2001 -From: Kalev Lember -Date: Tue, 12 May 2020 16:53:20 +0200 -Subject: [PATCH 3/3] rpm-ostree: Hook up the progress info required for the - loading page - ---- - plugins/rpm-ostree/gs-plugin-rpm-ostree.c | 34 ++++++++++++++++++++++- - 1 file changed, 33 insertions(+), 1 deletion(-) - -diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -index e3824df1..96531759 100644 ---- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -+++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -@@ -255,8 +255,9 @@ transaction_progress_new (void) - static void - transaction_progress_free (TransactionProgress *self) - { -- g_main_loop_unref (self->loop); -+ g_clear_object (&self->plugin); - g_clear_error (&self->error); -+ g_main_loop_unref (self->loop); - g_clear_object (&self->app); - g_slice_free (TransactionProgress, self); - } -@@ -281,11 +282,30 @@ on_transaction_progress (GDBusProxy *proxy, - if (g_strcmp0 (signal_name, "PercentProgress") == 0) { - const gchar *message = NULL; - guint32 percentage; -+ - g_variant_get_child (parameters, 0, "&s", &message); - g_variant_get_child (parameters, 1, "u", &percentage); - g_debug ("PercentProgress: %u, %s\n", percentage, message); -+ - if (tp->app != NULL) - gs_app_set_progress (tp->app, (guint) percentage); -+ -+ if (tp->app != NULL && tp->plugin != NULL) { -+ GsPluginStatus plugin_status; -+ -+ switch (gs_app_get_state (tp->app)) { -+ case AS_APP_STATE_INSTALLING: -+ plugin_status = GS_PLUGIN_STATUS_INSTALLING; -+ break; -+ case AS_APP_STATE_REMOVING: -+ plugin_status = GS_PLUGIN_STATUS_REMOVING; -+ break; -+ default: -+ plugin_status = GS_PLUGIN_STATUS_DOWNLOADING; -+ break; -+ } -+ gs_plugin_status_update (tp->plugin, tp->app, plugin_status); -+ } - } else if (g_strcmp0 (signal_name, "Finished") == 0) { - if (tp->error == NULL) { - g_autofree gchar *error_message = NULL; -@@ -603,6 +623,7 @@ ensure_rpmostree_dnf_context (GsPlugin *plugin, GCancellable *cancellable, GErro - { - GsPluginData *priv = gs_plugin_get_data (plugin); - g_autofree gchar *transaction_address = NULL; -+ g_autoptr(GsApp) progress_app = gs_app_new (gs_plugin_get_name (plugin)); - g_autoptr(DnfContext) context = dnf_context_new (); - g_autoptr(DnfState) state = dnf_state_new (); - g_autoptr(GVariant) options = NULL; -@@ -611,6 +632,9 @@ ensure_rpmostree_dnf_context (GsPlugin *plugin, GCancellable *cancellable, GErro - if (priv->dnf_context != NULL) - return TRUE; - -+ tp->app = g_object_ref (progress_app); -+ tp->plugin = g_object_ref (plugin); -+ - dnf_context_set_repo_dir (context, "/etc/yum.repos.d"); - dnf_context_set_cache_dir (context, RPMOSTREE_CORE_CACHEDIR RPMOSTREE_DIR_CACHE_REPOMD); - dnf_context_set_solv_dir (context, RPMOSTREE_CORE_CACHEDIR RPMOSTREE_DIR_CACHE_SOLV); -@@ -669,9 +693,13 @@ gs_plugin_refresh (GsPlugin *plugin, - - { - g_autofree gchar *transaction_address = NULL; -+ g_autoptr(GsApp) progress_app = gs_app_new (gs_plugin_get_name (plugin)); - g_autoptr(GVariant) options = NULL; - g_autoptr(TransactionProgress) tp = transaction_progress_new (); - -+ tp->app = g_object_ref (progress_app); -+ tp->plugin = g_object_ref (plugin); -+ - options = make_rpmostree_options_variant (FALSE, /* reboot */ - FALSE, /* allow-downgrade */ - FALSE, /* cache-only */ -@@ -703,10 +731,14 @@ gs_plugin_refresh (GsPlugin *plugin, - - { - g_autofree gchar *transaction_address = NULL; -+ g_autoptr(GsApp) progress_app = gs_app_new (gs_plugin_get_name (plugin)); - g_autoptr(GVariant) options = NULL; - GVariantDict dict; - g_autoptr(TransactionProgress) tp = transaction_progress_new (); - -+ tp->app = g_object_ref (progress_app); -+ tp->plugin = g_object_ref (plugin); -+ - g_variant_dict_init (&dict, NULL); - g_variant_dict_insert (&dict, "mode", "s", "check"); - options = g_variant_ref_sink (g_variant_dict_end (&dict)); --- -2.26.2 - diff --git a/gnome-software.spec b/gnome-software.spec index 347044c..9a1a5a8 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,18 +11,14 @@ %global libxmlb_version 0.1.7 Name: gnome-software -Version: 3.36.0 -Release: 2%{?dist} +Version: 3.36.1 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/3.36/%{name}-%{version}.tar.xz -Patch1: 0001-rpm-ostree-Add-missing-locking-when-creating-DnfCont.patch -Patch2: 0002-rpm-ostree-Correctly-mark-layered-local-packages-as-.patch -Patch3: 0003-rpm-ostree-Hook-up-the-progress-info-required-for-th.patch - BuildRequires: gcc BuildRequires: gettext BuildRequires: libxslt @@ -207,6 +203,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri May 22 2020 Richard Hughes - 3.36.1-1 +- Update to 3.36.1 + * Tue May 12 2020 Kalev Lember - 3.36.0-2 - Backport various rpm-ostree backend fixes diff --git a/sources b/sources index ebac2ec..27810b5 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-3.36.0.tar.xz) = 3727b738b0f669018b4b9b2af11dd86a1af6d8da7632b88c6ac47ef97b97299abb0aec47a6de2dc7e6afa33ee153f9df30e63e5dc83652a5402d6444389024c9 +SHA512 (gnome-software-3.36.1.tar.xz) = 7d0e8c16192bbbc8f166db137dbd2e6ff9e85f7d3d37f63f41211ba3838e392bd87a8d9bf09d31b43f6d21e1a099ecdeff9114ae27fae40d563671f0bcbe50d4 From a05211def898e0ccb5172fb2695f6ff34d1067cf Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Mon, 27 Jul 2020 20:46:52 +0000 Subject: [PATCH 006/163] - Rebuilt for https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild Signed-off-by: Fedora Release Engineering --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 9a1a5a8..2f723f1 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 3.36.1 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -203,6 +203,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Jul 27 2020 Fedora Release Engineering - 3.36.1-2 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild + * Fri May 22 2020 Richard Hughes - 3.36.1-1 - Update to 3.36.1 From 0b876537d77c157be5ce48934998603c58280d12 Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Sat, 1 Aug 2020 02:20:38 +0000 Subject: [PATCH 007/163] - Second attempt - Rebuilt for https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild Signed-off-by: Fedora Release Engineering --- gnome-software.spec | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 2f723f1..1a95e6b 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 3.36.1 -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -203,6 +203,10 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Sat Aug 01 2020 Fedora Release Engineering - 3.36.1-3 +- Second attempt - Rebuilt for + https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild + * Mon Jul 27 2020 Fedora Release Engineering - 3.36.1-2 - Rebuilt for https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild From 5ddfdf962a7bc8aac9e5916a64052863d9b1f9fc Mon Sep 17 00:00:00 2001 From: Richard Hughes Date: Tue, 18 Aug 2020 16:02:01 +0100 Subject: [PATCH 008/163] Rebuild for the libxmlb API bump --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 1a95e6b..1643345 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 3.36.1 -Release: 3%{?dist} +Release: 4%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -203,6 +203,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Tue Aug 18 2020 Richard Hughes - 3.36.1-4 +- Rebuild for the libxmlb API bump. + * Sat Aug 01 2020 Fedora Release Engineering - 3.36.1-3 - Second attempt - Rebuilt for https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild From 071d487285ef1043bf30e45ff0bf2773fd6b5eca Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Tue, 1 Sep 2020 20:39:46 +0200 Subject: [PATCH 009/163] Update to 3.37.92 --- .gitignore | 1 + gnome-software.spec | 26 ++++++++++++++++---------- sources | 2 +- 3 files changed, 18 insertions(+), 11 deletions(-) diff --git a/.gitignore b/.gitignore index 376e4ca..5aa4663 100644 --- a/.gitignore +++ b/.gitignore @@ -111,3 +111,4 @@ /gnome-software-3.35.92.tar.xz /gnome-software-3.36.0.tar.xz /gnome-software-3.36.1.tar.xz +/gnome-software-3.37.92.tar.xz diff --git a/gnome-software.spec b/gnome-software.spec index 1643345..863eaf3 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -1,23 +1,22 @@ +%global appstream_glib_version 0.7.15 +%global libxmlb_version 0.1.7 %global glib2_version 2.61.1 %global gtk3_version 3.22.4 %global json_glib_version 1.2.0 -%global packagekit_version 1.1.1 -%global appstream_glib_version 0.7.15 %global libsoup_version 2.52.0 -%global gsettings_desktop_schemas_version 3.12.0 %global gnome_desktop_version 3.18.0 +%global packagekit_version 1.1.1 %global fwupd_version 1.3.3 %global flatpak_version 1.5.1 -%global libxmlb_version 0.1.7 Name: gnome-software -Version: 3.36.1 -Release: 4%{?dist} +Version: 3.37.92 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software -Source0: https://download.gnome.org/sources/gnome-software/3.36/%{name}-%{version}.tar.xz +Source0: https://download.gnome.org/sources/gnome-software/3.37/%{name}-%{version}.tar.xz BuildRequires: gcc BuildRequires: gettext @@ -28,7 +27,7 @@ BuildRequires: fwupd-devel >= %{fwupd_version} BuildRequires: glib2-devel >= %{glib2_version} BuildRequires: gnome-desktop3-devel BuildRequires: gnome-online-accounts-devel -BuildRequires: gsettings-desktop-schemas-devel >= %{gsettings_desktop_schemas_version} +BuildRequires: gsettings-desktop-schemas-devel BuildRequires: gspell-devel BuildRequires: gtk3-devel >= %{gtk3_version} BuildRequires: gtk-doc @@ -45,6 +44,7 @@ BuildRequires: ostree-devel BuildRequires: rpm-devel BuildRequires: rpm-ostree-devel BuildRequires: libgudev1-devel +BuildRequires: sysprof-devel BuildRequires: valgrind-devel Requires: appstream-data @@ -55,7 +55,7 @@ Requires: glib2%{?_isa} >= %{glib2_version} Requires: gnome-desktop3%{?_isa} >= %{gnome_desktop_version} # gnome-menus is needed for app folder .directory entries Requires: gnome-menus%{?_isa} -Requires: gsettings-desktop-schemas%{?_isa} >= %{gsettings_desktop_schemas_version} +Requires: gsettings-desktop-schemas%{?_isa} Requires: gtk3%{?_isa} >= %{gtk3_version} Requires: json-glib%{?_isa} >= %{json_glib_version} Requires: iso-codes @@ -117,6 +117,9 @@ This package includes the rpm-ostree backend. # remove unneeded dpkg plugin rm %{buildroot}%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_dpkg.so +# remove unneeded static library +rm %{buildroot}%{_libdir}/libgnomesoftware.a + # make the software center load faster desktop-file-edit %{buildroot}%{_datadir}/applications/org.gnome.Software.desktop \ --set-key=X-AppInstall-Package --set-value=%{name} @@ -160,7 +163,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_flatpak.so %{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_fwupd.so %{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_generic-updates.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-blacklist.so +%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-blocklist.so %{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-popular.so %{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_icons.so %{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_key-colors-metadata.so @@ -203,6 +206,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Tue Sep 01 2020 Kalev Lember - 3.37.92-1 +- Update to 3.37.92 + * Tue Aug 18 2020 Richard Hughes - 3.36.1-4 - Rebuild for the libxmlb API bump. diff --git a/sources b/sources index 27810b5..8cd8f84 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-3.36.1.tar.xz) = 7d0e8c16192bbbc8f166db137dbd2e6ff9e85f7d3d37f63f41211ba3838e392bd87a8d9bf09d31b43f6d21e1a099ecdeff9114ae27fae40d563671f0bcbe50d4 +SHA512 (gnome-software-3.37.92.tar.xz) = 821deaeff4fc9dc6eb4138c740776d284a80acc0197f6dd80643ceadc3df450ff09f605d32f27de18b8d2656511fe9a9912ed4d644b00746d9248d7e9686d6ad From 8653941a77e8bfb0b2e0e316e1ef2b942b9f16be Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Fri, 11 Sep 2020 14:18:53 +0200 Subject: [PATCH 010/163] Update to 3.38.0 --- .gitignore | 1 + gnome-software.spec | 7 +++++-- sources | 2 +- 3 files changed, 7 insertions(+), 3 deletions(-) diff --git a/.gitignore b/.gitignore index 5aa4663..8decd9c 100644 --- a/.gitignore +++ b/.gitignore @@ -112,3 +112,4 @@ /gnome-software-3.36.0.tar.xz /gnome-software-3.36.1.tar.xz /gnome-software-3.37.92.tar.xz +/gnome-software-3.38.0.tar.xz diff --git a/gnome-software.spec b/gnome-software.spec index 863eaf3..f728c07 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -10,13 +10,13 @@ %global flatpak_version 1.5.1 Name: gnome-software -Version: 3.37.92 +Version: 3.38.0 Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software -Source0: https://download.gnome.org/sources/gnome-software/3.37/%{name}-%{version}.tar.xz +Source0: https://download.gnome.org/sources/gnome-software/3.38/%{name}-%{version}.tar.xz BuildRequires: gcc BuildRequires: gettext @@ -206,6 +206,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri Sep 11 2020 Kalev Lember - 3.38.0-1 +- Update to 3.38.0 + * Tue Sep 01 2020 Kalev Lember - 3.37.92-1 - Update to 3.37.92 diff --git a/sources b/sources index 8cd8f84..f74565c 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-3.37.92.tar.xz) = 821deaeff4fc9dc6eb4138c740776d284a80acc0197f6dd80643ceadc3df450ff09f605d32f27de18b8d2656511fe9a9912ed4d644b00746d9248d7e9686d6ad +SHA512 (gnome-software-3.38.0.tar.xz) = 0563f01c23f91047f45e9b0e2e5729065b2703dbf8dd76af105c1bb87654fb40076bdcfc87a8a3922e8a60422d06158a76a3763f52629dec3e15e49a68e68cf2 From d8563228449501002e95ac372856ed8295ecfcd4 Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Mon, 14 Sep 2020 12:12:15 +0200 Subject: [PATCH 011/163] Revert an optimization that broke packagekit updates --- ...t-Avoid-600000-allocations-when-comp.patch | 274 ++++++++++++++++++ gnome-software.spec | 10 +- 2 files changed, 283 insertions(+), 1 deletion(-) create mode 100644 0001-Revert-packagekit-Avoid-600000-allocations-when-comp.patch diff --git a/0001-Revert-packagekit-Avoid-600000-allocations-when-comp.patch b/0001-Revert-packagekit-Avoid-600000-allocations-when-comp.patch new file mode 100644 index 0000000..0d293bb --- /dev/null +++ b/0001-Revert-packagekit-Avoid-600000-allocations-when-comp.patch @@ -0,0 +1,274 @@ +From b3a50ee2d6b93980d1808599ba003e9afc4feae5 Mon Sep 17 00:00:00 2001 +From: Kalev Lember +Date: Mon, 14 Sep 2020 12:07:30 +0200 +Subject: [PATCH] Revert "packagekit: Avoid 600000 allocations when comparing + package IDs" + +This broke packagekit updates. + +https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1061 +https://bodhi.fedoraproject.org/updates/FEDORA-2020-7f57486c95#comment-1621958 + +This reverts commit 955570e4a5d737a9a4f85860fd7e483158e130c4. +--- + .../packagekit/gs-plugin-packagekit-refine.c | 12 +- + .../gs-plugin-packagekit-url-to-app.c | 6 +- + plugins/packagekit/packagekit-common.c | 149 ++++++------------ + plugins/packagekit/packagekit-common.h | 3 +- + 4 files changed, 54 insertions(+), 116 deletions(-) + +diff --git a/plugins/packagekit/gs-plugin-packagekit-refine.c b/plugins/packagekit/gs-plugin-packagekit-refine.c +index 68f7eb64..813390b1 100644 +--- a/plugins/packagekit/gs-plugin-packagekit-refine.c ++++ b/plugins/packagekit/gs-plugin-packagekit-refine.c +@@ -345,7 +345,6 @@ gs_plugin_packagekit_refine_details2 (GsPlugin *plugin, + g_autoptr(GPtrArray) array = NULL; + g_autoptr(GPtrArray) package_ids = NULL; + g_autoptr(PkResults) results = NULL; +- g_autoptr(GHashTable) details_collection = NULL; + + package_ids = g_ptr_array_new_with_free_func (g_free); + for (i = 0; i < gs_app_list_length (list); i++) { +@@ -375,19 +374,12 @@ gs_plugin_packagekit_refine_details2 (GsPlugin *plugin, + return FALSE; + } + +- /* get the results and copy them into a hash table for fast lookups: +- * there are typically 400 to 700 elements in @array, and 100 to 200 +- * elements in @list, each with 1 or 2 source IDs to look up (but +- * sometimes 200) */ +- array = pk_results_get_details_array (results); +- details_collection = gs_plugin_packagekit_details_array_to_hash (array); +- + /* set the update details for the update */ ++ array = pk_results_get_details_array (results); + for (i = 0; i < gs_app_list_length (list); i++) { + app = gs_app_list_index (list, i); +- gs_plugin_packagekit_refine_details_app (plugin, details_collection, app); ++ gs_plugin_packagekit_refine_details_app (plugin, array, app); + } +- + return TRUE; + } + +diff --git a/plugins/packagekit/gs-plugin-packagekit-url-to-app.c b/plugins/packagekit/gs-plugin-packagekit-url-to-app.c +index 04189204..7f566c72 100644 +--- a/plugins/packagekit/gs-plugin-packagekit-url-to-app.c ++++ b/plugins/packagekit/gs-plugin-packagekit-url-to-app.c +@@ -106,15 +106,11 @@ gs_plugin_url_to_app (GsPlugin *plugin, + details = pk_results_get_details_array (results); + + if (packages->len >= 1) { +- g_autoptr(GHashTable) details_collection = NULL; +- + if (gs_app_get_local_file (app) != NULL) + return TRUE; + +- details_collection = gs_plugin_packagekit_details_array_to_hash (details); +- + gs_plugin_packagekit_resolve_packages_app (plugin, packages, app); +- gs_plugin_packagekit_refine_details_app (plugin, details_collection, app); ++ gs_plugin_packagekit_refine_details_app (plugin, details, app); + + gs_app_list_add (list, app); + } else { +diff --git a/plugins/packagekit/packagekit-common.c b/plugins/packagekit/packagekit-common.c +index 495960dd..9367f5bf 100644 +--- a/plugins/packagekit/packagekit-common.c ++++ b/plugins/packagekit/packagekit-common.c +@@ -388,127 +388,78 @@ gs_plugin_packagekit_set_metadata_from_package (GsPlugin *plugin, + pk_package_get_summary (package)); + } + +-/* Hash functions which compare PkPackageIds on NAME, VERSION and ARCH, but not DATA. +- * This is because some backends do not append the origin. ++/* ++ * gs_pk_compare_ids: + * +- * Borrowing some implementation details from pk-package-id.c, a package +- * ID is a semicolon-separated list of NAME;[VERSION];[ARCH];[DATA], +- * so a comparison which ignores DATA is just a strncmp() up to and +- * including the final semicolon. +- * +- * Doing it this way means zero allocations, which allows the hash and +- * equality functions to be fast. This is important when dealing with +- * large refine() package lists. +- * +- * The hash and equality functions assume that the IDs they are passed are +- * valid. */ +-static guint +-package_id_hash (gconstpointer key) +-{ +- const gchar *package_id = key; +- gchar *no_data; +- gsize i, last_semicolon = 0; +- +- /* find the last semicolon, which starts the DATA section */ +- for (i = 0; package_id[i] != '\0'; i++) { +- if (package_id[i] == ';') +- last_semicolon = i; +- } +- +- /* exit early if the DATA section was empty */ +- if (last_semicolon + 1 == i) +- return g_str_hash (package_id); +- +- /* extract up to (and including) the last semicolon into a local string */ +- no_data = g_alloca (last_semicolon + 2); +- memcpy (no_data, package_id, last_semicolon + 1); +- no_data[last_semicolon + 1] = '\0'; +- +- return g_str_hash (no_data); +-} +- ++ * Do not compare the repo. Some backends do not append the origin. ++ */ + static gboolean +-package_id_equal (gconstpointer a, +- gconstpointer b) ++gs_pk_compare_ids (const gchar *package_id1, const gchar *package_id2) + { +- const gchar *package_id_a = a; +- const gchar *package_id_b = b; +- gsize n_semicolons = 0; +- +- /* compare up to and including the last semicolon */ +- for (gsize i = 0; package_id_a[i] != '\0' && package_id_b[i] != '\0'; i++) { +- if (package_id_a[i] != package_id_b[i]) +- return FALSE; +- if (package_id_a[i] == ';') +- n_semicolons++; +- if (n_semicolons == 4) +- return TRUE; +- } ++ gboolean ret; ++ g_auto(GStrv) split1 = NULL; ++ g_auto(GStrv) split2 = NULL; + +- return FALSE; ++ split1 = pk_package_id_split (package_id1); ++ if (split1 == NULL) ++ return FALSE; ++ split2 = pk_package_id_split (package_id2); ++ if (split2 == NULL) ++ return FALSE; ++ ret = (g_strcmp0 (split1[PK_PACKAGE_ID_NAME], ++ split2[PK_PACKAGE_ID_NAME]) == 0 && ++ g_strcmp0 (split1[PK_PACKAGE_ID_VERSION], ++ split2[PK_PACKAGE_ID_VERSION]) == 0 && ++ g_strcmp0 (split1[PK_PACKAGE_ID_ARCH], ++ split2[PK_PACKAGE_ID_ARCH]) == 0); ++ return ret; + } + +-GHashTable * +-gs_plugin_packagekit_details_array_to_hash (GPtrArray *array) +-{ +- g_autoptr(GHashTable) details_collection = NULL; +- +- details_collection = g_hash_table_new_full (package_id_hash, package_id_equal, +- NULL, NULL); +- +- for (gsize i = 0; i < array->len; i++) { +- PkDetails *details = g_ptr_array_index (array, i); +- g_hash_table_insert (details_collection, +- pk_details_get_package_id (details), +- details); +- } +- +- return g_steal_pointer (&details_collection); +-} + + void + gs_plugin_packagekit_refine_details_app (GsPlugin *plugin, +- GHashTable *details_collection, ++ GPtrArray *array, + GsApp *app) + { + GPtrArray *source_ids; + PkDetails *details; + const gchar *package_id; ++ guint i; + guint j; + guint64 size = 0; + +- /* @source_ids can have as many as 200 elements (google-noto); typically +- * it has 1 or 2 +- * +- * @details_collection is typically a large list of apps in the +- * repository, on the order of 400 or 700 apps */ + source_ids = gs_app_get_source_ids (app); + for (j = 0; j < source_ids->len; j++) { + package_id = g_ptr_array_index (source_ids, j); +- details = g_hash_table_lookup (details_collection, package_id); +- if (details == NULL) +- continue; +- +- if (gs_app_get_license (app) == NULL) { +- g_autofree gchar *license_spdx = NULL; +- license_spdx = as_utils_license_to_spdx (pk_details_get_license (details)); +- if (license_spdx != NULL) { +- gs_app_set_license (app, +- GS_APP_QUALITY_LOWEST, +- license_spdx); ++ for (i = 0; i < array->len; i++) { ++ /* right package? */ ++ details = g_ptr_array_index (array, i); ++ if (!gs_pk_compare_ids (package_id, ++ pk_details_get_package_id (details))) { ++ continue; + } ++ if (gs_app_get_license (app) == NULL) { ++ g_autofree gchar *license_spdx = NULL; ++ license_spdx = as_utils_license_to_spdx (pk_details_get_license (details)); ++ if (license_spdx != NULL) { ++ gs_app_set_license (app, ++ GS_APP_QUALITY_LOWEST, ++ license_spdx); ++ } ++ } ++ if (gs_app_get_url (app, AS_URL_KIND_HOMEPAGE) == NULL) { ++ gs_app_set_url (app, ++ AS_URL_KIND_HOMEPAGE, ++ pk_details_get_url (details)); ++ } ++ if (gs_app_get_description (app) == NULL) { ++ gs_app_set_description (app, ++ GS_APP_QUALITY_LOWEST, ++ pk_details_get_description (details)); ++ } ++ size += pk_details_get_size (details); ++ break; + } +- if (gs_app_get_url (app, AS_URL_KIND_HOMEPAGE) == NULL) { +- gs_app_set_url (app, +- AS_URL_KIND_HOMEPAGE, +- pk_details_get_url (details)); +- } +- if (gs_app_get_description (app) == NULL) { +- gs_app_set_description (app, +- GS_APP_QUALITY_LOWEST, +- pk_details_get_description (details)); +- } +- size += pk_details_get_size (details); + } + + /* the size is the size of all sources */ +diff --git a/plugins/packagekit/packagekit-common.h b/plugins/packagekit/packagekit-common.h +index 9f523684..0742ea3a 100644 +--- a/plugins/packagekit/packagekit-common.h ++++ b/plugins/packagekit/packagekit-common.h +@@ -30,9 +30,8 @@ void gs_plugin_packagekit_resolve_packages_app (GsPlugin *plugin, + void gs_plugin_packagekit_set_metadata_from_package (GsPlugin *plugin, + GsApp *app, + PkPackage *package); +-GHashTable * gs_plugin_packagekit_details_array_to_hash (GPtrArray *array); + void gs_plugin_packagekit_refine_details_app (GsPlugin *plugin, +- GHashTable *details_collection, ++ GPtrArray *array, + GsApp *app); + void gs_plugin_packagekit_set_packaging_format (GsPlugin *plugin, + GsApp *app); +-- +2.26.2 + diff --git a/gnome-software.spec b/gnome-software.spec index f728c07..d3ef6d9 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,13 +11,18 @@ Name: gnome-software Version: 3.38.0 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/3.38/%{name}-%{version}.tar.xz +# Revert an optimization that broke packagekit updates +# https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1061 +# https://bodhi.fedoraproject.org/updates/FEDORA-2020-7f57486c95#comment-1621958 +Patch0: 0001-Revert-packagekit-Avoid-600000-allocations-when-comp.patch + BuildRequires: gcc BuildRequires: gettext BuildRequires: libxslt @@ -206,6 +211,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Sep 14 2020 Kalev Lember - 3.38.0-2 +- Revert an optimization that broke packagekit updates + * Fri Sep 11 2020 Kalev Lember - 3.38.0-1 - Update to 3.38.0 From 72021ac9acc7c2974ae4463c2797ef6350b905ae Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Tue, 26 Jan 2021 08:46:52 +0000 Subject: [PATCH 012/163] - Rebuilt for https://fedoraproject.org/wiki/Fedora_34_Mass_Rebuild Signed-off-by: Fedora Release Engineering --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index d3ef6d9..dd5f01e 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,7 +11,7 @@ Name: gnome-software Version: 3.38.0 -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -211,6 +211,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Tue Jan 26 2021 Fedora Release Engineering - 3.38.0-3 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_34_Mass_Rebuild + * Mon Sep 14 2020 Kalev Lember - 3.38.0-2 - Revert an optimization that broke packagekit updates From a7e91182f30c56b46c813558c1683790805558d1 Mon Sep 17 00:00:00 2001 From: Richard Hughes Date: Mon, 8 Feb 2021 10:09:44 +0000 Subject: [PATCH 013/163] New upstream version --- .gitignore | 1 + gnome-software.spec | 14 +++++++------- sources | 2 +- 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/.gitignore b/.gitignore index 8decd9c..81de277 100644 --- a/.gitignore +++ b/.gitignore @@ -113,3 +113,4 @@ /gnome-software-3.36.1.tar.xz /gnome-software-3.37.92.tar.xz /gnome-software-3.38.0.tar.xz +/gnome-software-3.38.1.tar.xz diff --git a/gnome-software.spec b/gnome-software.spec index dd5f01e..b31a5ec 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -10,19 +10,14 @@ %global flatpak_version 1.5.1 Name: gnome-software -Version: 3.38.0 -Release: 3%{?dist} +Version: 3.38.1 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/3.38/%{name}-%{version}.tar.xz -# Revert an optimization that broke packagekit updates -# https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1061 -# https://bodhi.fedoraproject.org/updates/FEDORA-2020-7f57486c95#comment-1621958 -Patch0: 0001-Revert-packagekit-Avoid-600000-allocations-when-comp.patch - BuildRequires: gcc BuildRequires: gettext BuildRequires: libxslt @@ -211,6 +206,11 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Feb 08 2021 Richard Hughes - 3.38.1-1 +- New upstream version +- Fix package details not found for some packages +- Ignore harmless warnings when using unusual fwupd versions + * Tue Jan 26 2021 Fedora Release Engineering - 3.38.0-3 - Rebuilt for https://fedoraproject.org/wiki/Fedora_34_Mass_Rebuild diff --git a/sources b/sources index f74565c..efccce9 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-3.38.0.tar.xz) = 0563f01c23f91047f45e9b0e2e5729065b2703dbf8dd76af105c1bb87654fb40076bdcfc87a8a3922e8a60422d06158a76a3763f52629dec3e15e49a68e68cf2 +SHA512 (gnome-software-3.38.1.tar.xz) = 155f80836a28775a646d0f64713557708039076d7611829b75257ddc7dd471a8135769f953cb147ff4e116723f402fa95a56d3f63c654b4bd0455e6415278341 From 7bc2a78ecdfedf4af42f0d122a0500df1ed149f4 Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Tue, 16 Feb 2021 22:17:05 +0100 Subject: [PATCH 014/163] Update to 40.beta --- .gitignore | 1 + gnome-software.spec | 25 +++++++++++++------------ sources | 2 +- 3 files changed, 15 insertions(+), 13 deletions(-) diff --git a/.gitignore b/.gitignore index 81de277..588cce0 100644 --- a/.gitignore +++ b/.gitignore @@ -114,3 +114,4 @@ /gnome-software-3.37.92.tar.xz /gnome-software-3.38.0.tar.xz /gnome-software-3.38.1.tar.xz +/gnome-software-40.beta.tar.xz diff --git a/gnome-software.spec b/gnome-software.spec index b31a5ec..b4e0ad8 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -1,23 +1,25 @@ -%global appstream_glib_version 0.7.15 +%global appstream_version 0.14.0 %global libxmlb_version 0.1.7 %global glib2_version 2.61.1 %global gtk3_version 3.22.4 %global json_glib_version 1.2.0 %global libsoup_version 2.52.0 -%global gnome_desktop_version 3.18.0 %global packagekit_version 1.1.1 %global fwupd_version 1.3.3 %global flatpak_version 1.5.1 +%global tarball_version %%(echo %{version} | tr '~' '.') + Name: gnome-software -Version: 3.38.1 +Version: 40~beta Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software -Source0: https://download.gnome.org/sources/gnome-software/3.38/%{name}-%{version}.tar.xz +Source0: https://download.gnome.org/sources/gnome-software/40/%{name}-%{tarball_version}.tar.xz +BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc BuildRequires: gettext BuildRequires: libxslt @@ -25,15 +27,14 @@ BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils BuildRequires: fwupd-devel >= %{fwupd_version} BuildRequires: glib2-devel >= %{glib2_version} -BuildRequires: gnome-desktop3-devel BuildRequires: gnome-online-accounts-devel BuildRequires: gsettings-desktop-schemas-devel BuildRequires: gspell-devel BuildRequires: gtk3-devel >= %{gtk3_version} BuildRequires: gtk-doc BuildRequires: json-glib-devel >= %{json_glib_version} -BuildRequires: libappstream-glib-devel >= %{appstream_glib_version} BuildRequires: libdnf-devel +BuildRequires: libhandy1-devel BuildRequires: libsoup-devel BuildRequires: libxmlb-devel >= %{libxmlb_version} BuildRequires: meson @@ -48,18 +49,17 @@ BuildRequires: sysprof-devel BuildRequires: valgrind-devel Requires: appstream-data +Requires: appstream%{?_isa} >= %{appstream_version} Requires: flatpak%{?_isa} >= %{flatpak_version} Requires: flatpak-libs%{?_isa} >= %{flatpak_version} Requires: fwupd%{?_isa} >= %{fwupd_version} Requires: glib2%{?_isa} >= %{glib2_version} -Requires: gnome-desktop3%{?_isa} >= %{gnome_desktop_version} # gnome-menus is needed for app folder .directory entries Requires: gnome-menus%{?_isa} Requires: gsettings-desktop-schemas%{?_isa} Requires: gtk3%{?_isa} >= %{gtk3_version} Requires: json-glib%{?_isa} >= %{json_glib_version} Requires: iso-codes -Requires: libappstream-glib%{?_isa} >= %{appstream_glib_version} # librsvg2 is needed for gdk-pixbuf svg loader Requires: librsvg2%{?_isa} Requires: libsoup%{?_isa} >= %{libsoup_version} @@ -71,7 +71,7 @@ Obsoletes: gnome-software-snap < 3.33.1 Obsoletes: gnome-software-editor < 3.35.1 # this is not a library version -%define gs_plugin_version 13 +%define gs_plugin_version 14 %description gnome-software is an application that makes it easy to add, remove @@ -98,7 +98,7 @@ and update software in the GNOME desktop. This package includes the rpm-ostree backend. %prep -%autosetup -p1 +%autosetup -p1 -n %{name}-%{tarball_version} %build %meson \ @@ -155,8 +155,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/metainfo/org.gnome.Software.Plugin.Odrs.metainfo.xml %dir %{_libdir}/gs-plugins-%{gs_plugin_version} %{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_appstream.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_desktop-categories.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_desktop-menu-path.so %{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_dummy.so %{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so %{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_fedora-pkgdb-collections.so @@ -206,6 +204,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Tue Feb 16 2021 Kalev Lember - 40~beta-1 +- Update to 40.beta + * Mon Feb 08 2021 Richard Hughes - 3.38.1-1 - New upstream version - Fix package details not found for some packages diff --git a/sources b/sources index efccce9..7728ce9 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-3.38.1.tar.xz) = 155f80836a28775a646d0f64713557708039076d7611829b75257ddc7dd471a8135769f953cb147ff4e116723f402fa95a56d3f63c654b4bd0455e6415278341 +SHA512 (gnome-software-40.beta.tar.xz) = 39edf94a3091b8c6e00925cf4e5fab929fbd5166ab35caf247415753bbae8c6ea0df51a80fa2fa7ba35ca64d5b7ce44359b9a451c7f6f3424e1716ed8b493dd4 From 11b7e38d32134481572a994952f2d9d5ef0ded2c Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Wed, 24 Feb 2021 11:36:21 +0100 Subject: [PATCH 015/163] BR sysprof-capture-devel rather than sysprof-devel --- gnome-software.spec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index b4e0ad8..a14ff46 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -45,7 +45,7 @@ BuildRequires: ostree-devel BuildRequires: rpm-devel BuildRequires: rpm-ostree-devel BuildRequires: libgudev1-devel -BuildRequires: sysprof-devel +BuildRequires: sysprof-capture-devel BuildRequires: valgrind-devel Requires: appstream-data From 7a1919c5a53c213faf9011c97b81a0b7dcf03b4a Mon Sep 17 00:00:00 2001 From: Adam Williamson Date: Wed, 10 Mar 2021 10:08:16 -0800 Subject: [PATCH 016/163] Backport MR #643 to fix update notifications on first run (#1930401) --- ...-Reset-online-updates-timestamp-only.patch | 35 +++++++++++++++++++ gnome-software.spec | 9 ++++- 2 files changed, 43 insertions(+), 1 deletion(-) create mode 100644 0001-gs-plugin-loader-Reset-online-updates-timestamp-only.patch diff --git a/0001-gs-plugin-loader-Reset-online-updates-timestamp-only.patch b/0001-gs-plugin-loader-Reset-online-updates-timestamp-only.patch new file mode 100644 index 0000000..94e4b57 --- /dev/null +++ b/0001-gs-plugin-loader-Reset-online-updates-timestamp-only.patch @@ -0,0 +1,35 @@ +From 9a48a04d180f9d3e988efe761cee7bfd9bea79dd Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Fri, 5 Mar 2021 13:34:40 +0100 +Subject: [PATCH] gs-plugin-loader: Reset online-updates-timestamp only when + did the update + +The gs_plugin_loader_generic_update() is used in two cases, when updating +the software and when downloading the software. The former case can reset +the online-updates-timestamp, but the later not, because it did not +update anything. + +This blocks the update notifications from showing up after the first +run of the Software. +--- + lib/gs-plugin-loader.c | 4 +++- + 1 file changed, 3 insertions(+), 1 deletion(-) + +diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c +index 2dad71f86..358cb8439 100644 +--- a/lib/gs-plugin-loader.c ++++ b/lib/gs-plugin-loader.c +@@ -3124,7 +3124,9 @@ gs_plugin_loader_generic_update (GsPluginLoader *plugin_loader, + gs_plugin_status_update (plugin, NULL, GS_PLUGIN_STATUS_FINISHED); + } + +- gs_utils_set_online_updates_timestamp (plugin_loader->settings); ++ if (gs_plugin_job_get_action (helper->plugin_job) == GS_PLUGIN_ACTION_UPDATE) ++ gs_utils_set_online_updates_timestamp (plugin_loader->settings); ++ + return TRUE; + } + +-- +2.30.1 + diff --git a/gnome-software.spec b/gnome-software.spec index a14ff46..8c1496f 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,12 +12,16 @@ Name: gnome-software Version: 40~beta -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/40/%{name}-%{tarball_version}.tar.xz +# Fix update notifications: +# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/643 +# https://bugzilla.redhat.com/show_bug.cgi?id=1930401 +Patch0: 0001-gs-plugin-loader-Reset-online-updates-timestamp-only.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -204,6 +208,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Wed Mar 10 2021 Adam Williamson - 40~beta-2 +- Backport MR #643 to fix update notifications on first run (#1930401) + * Tue Feb 16 2021 Kalev Lember - 40~beta-1 - Update to 40.beta From c68eece936e2cabccd58c7ddac8110317de2c58c Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Mon, 15 Mar 2021 23:06:47 +0100 Subject: [PATCH 017/163] Update to 40.rc --- .gitignore | 1 + ...t-Avoid-600000-allocations-when-comp.patch | 274 ------------------ ...-Reset-online-updates-timestamp-only.patch | 35 --- gnome-software.spec | 85 +++--- sources | 2 +- 5 files changed, 42 insertions(+), 355 deletions(-) delete mode 100644 0001-Revert-packagekit-Avoid-600000-allocations-when-comp.patch delete mode 100644 0001-gs-plugin-loader-Reset-online-updates-timestamp-only.patch diff --git a/.gitignore b/.gitignore index 588cce0..6dba849 100644 --- a/.gitignore +++ b/.gitignore @@ -115,3 +115,4 @@ /gnome-software-3.38.0.tar.xz /gnome-software-3.38.1.tar.xz /gnome-software-40.beta.tar.xz +/gnome-software-40.rc.tar.xz diff --git a/0001-Revert-packagekit-Avoid-600000-allocations-when-comp.patch b/0001-Revert-packagekit-Avoid-600000-allocations-when-comp.patch deleted file mode 100644 index 0d293bb..0000000 --- a/0001-Revert-packagekit-Avoid-600000-allocations-when-comp.patch +++ /dev/null @@ -1,274 +0,0 @@ -From b3a50ee2d6b93980d1808599ba003e9afc4feae5 Mon Sep 17 00:00:00 2001 -From: Kalev Lember -Date: Mon, 14 Sep 2020 12:07:30 +0200 -Subject: [PATCH] Revert "packagekit: Avoid 600000 allocations when comparing - package IDs" - -This broke packagekit updates. - -https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1061 -https://bodhi.fedoraproject.org/updates/FEDORA-2020-7f57486c95#comment-1621958 - -This reverts commit 955570e4a5d737a9a4f85860fd7e483158e130c4. ---- - .../packagekit/gs-plugin-packagekit-refine.c | 12 +- - .../gs-plugin-packagekit-url-to-app.c | 6 +- - plugins/packagekit/packagekit-common.c | 149 ++++++------------ - plugins/packagekit/packagekit-common.h | 3 +- - 4 files changed, 54 insertions(+), 116 deletions(-) - -diff --git a/plugins/packagekit/gs-plugin-packagekit-refine.c b/plugins/packagekit/gs-plugin-packagekit-refine.c -index 68f7eb64..813390b1 100644 ---- a/plugins/packagekit/gs-plugin-packagekit-refine.c -+++ b/plugins/packagekit/gs-plugin-packagekit-refine.c -@@ -345,7 +345,6 @@ gs_plugin_packagekit_refine_details2 (GsPlugin *plugin, - g_autoptr(GPtrArray) array = NULL; - g_autoptr(GPtrArray) package_ids = NULL; - g_autoptr(PkResults) results = NULL; -- g_autoptr(GHashTable) details_collection = NULL; - - package_ids = g_ptr_array_new_with_free_func (g_free); - for (i = 0; i < gs_app_list_length (list); i++) { -@@ -375,19 +374,12 @@ gs_plugin_packagekit_refine_details2 (GsPlugin *plugin, - return FALSE; - } - -- /* get the results and copy them into a hash table for fast lookups: -- * there are typically 400 to 700 elements in @array, and 100 to 200 -- * elements in @list, each with 1 or 2 source IDs to look up (but -- * sometimes 200) */ -- array = pk_results_get_details_array (results); -- details_collection = gs_plugin_packagekit_details_array_to_hash (array); -- - /* set the update details for the update */ -+ array = pk_results_get_details_array (results); - for (i = 0; i < gs_app_list_length (list); i++) { - app = gs_app_list_index (list, i); -- gs_plugin_packagekit_refine_details_app (plugin, details_collection, app); -+ gs_plugin_packagekit_refine_details_app (plugin, array, app); - } -- - return TRUE; - } - -diff --git a/plugins/packagekit/gs-plugin-packagekit-url-to-app.c b/plugins/packagekit/gs-plugin-packagekit-url-to-app.c -index 04189204..7f566c72 100644 ---- a/plugins/packagekit/gs-plugin-packagekit-url-to-app.c -+++ b/plugins/packagekit/gs-plugin-packagekit-url-to-app.c -@@ -106,15 +106,11 @@ gs_plugin_url_to_app (GsPlugin *plugin, - details = pk_results_get_details_array (results); - - if (packages->len >= 1) { -- g_autoptr(GHashTable) details_collection = NULL; -- - if (gs_app_get_local_file (app) != NULL) - return TRUE; - -- details_collection = gs_plugin_packagekit_details_array_to_hash (details); -- - gs_plugin_packagekit_resolve_packages_app (plugin, packages, app); -- gs_plugin_packagekit_refine_details_app (plugin, details_collection, app); -+ gs_plugin_packagekit_refine_details_app (plugin, details, app); - - gs_app_list_add (list, app); - } else { -diff --git a/plugins/packagekit/packagekit-common.c b/plugins/packagekit/packagekit-common.c -index 495960dd..9367f5bf 100644 ---- a/plugins/packagekit/packagekit-common.c -+++ b/plugins/packagekit/packagekit-common.c -@@ -388,127 +388,78 @@ gs_plugin_packagekit_set_metadata_from_package (GsPlugin *plugin, - pk_package_get_summary (package)); - } - --/* Hash functions which compare PkPackageIds on NAME, VERSION and ARCH, but not DATA. -- * This is because some backends do not append the origin. -+/* -+ * gs_pk_compare_ids: - * -- * Borrowing some implementation details from pk-package-id.c, a package -- * ID is a semicolon-separated list of NAME;[VERSION];[ARCH];[DATA], -- * so a comparison which ignores DATA is just a strncmp() up to and -- * including the final semicolon. -- * -- * Doing it this way means zero allocations, which allows the hash and -- * equality functions to be fast. This is important when dealing with -- * large refine() package lists. -- * -- * The hash and equality functions assume that the IDs they are passed are -- * valid. */ --static guint --package_id_hash (gconstpointer key) --{ -- const gchar *package_id = key; -- gchar *no_data; -- gsize i, last_semicolon = 0; -- -- /* find the last semicolon, which starts the DATA section */ -- for (i = 0; package_id[i] != '\0'; i++) { -- if (package_id[i] == ';') -- last_semicolon = i; -- } -- -- /* exit early if the DATA section was empty */ -- if (last_semicolon + 1 == i) -- return g_str_hash (package_id); -- -- /* extract up to (and including) the last semicolon into a local string */ -- no_data = g_alloca (last_semicolon + 2); -- memcpy (no_data, package_id, last_semicolon + 1); -- no_data[last_semicolon + 1] = '\0'; -- -- return g_str_hash (no_data); --} -- -+ * Do not compare the repo. Some backends do not append the origin. -+ */ - static gboolean --package_id_equal (gconstpointer a, -- gconstpointer b) -+gs_pk_compare_ids (const gchar *package_id1, const gchar *package_id2) - { -- const gchar *package_id_a = a; -- const gchar *package_id_b = b; -- gsize n_semicolons = 0; -- -- /* compare up to and including the last semicolon */ -- for (gsize i = 0; package_id_a[i] != '\0' && package_id_b[i] != '\0'; i++) { -- if (package_id_a[i] != package_id_b[i]) -- return FALSE; -- if (package_id_a[i] == ';') -- n_semicolons++; -- if (n_semicolons == 4) -- return TRUE; -- } -+ gboolean ret; -+ g_auto(GStrv) split1 = NULL; -+ g_auto(GStrv) split2 = NULL; - -- return FALSE; -+ split1 = pk_package_id_split (package_id1); -+ if (split1 == NULL) -+ return FALSE; -+ split2 = pk_package_id_split (package_id2); -+ if (split2 == NULL) -+ return FALSE; -+ ret = (g_strcmp0 (split1[PK_PACKAGE_ID_NAME], -+ split2[PK_PACKAGE_ID_NAME]) == 0 && -+ g_strcmp0 (split1[PK_PACKAGE_ID_VERSION], -+ split2[PK_PACKAGE_ID_VERSION]) == 0 && -+ g_strcmp0 (split1[PK_PACKAGE_ID_ARCH], -+ split2[PK_PACKAGE_ID_ARCH]) == 0); -+ return ret; - } - --GHashTable * --gs_plugin_packagekit_details_array_to_hash (GPtrArray *array) --{ -- g_autoptr(GHashTable) details_collection = NULL; -- -- details_collection = g_hash_table_new_full (package_id_hash, package_id_equal, -- NULL, NULL); -- -- for (gsize i = 0; i < array->len; i++) { -- PkDetails *details = g_ptr_array_index (array, i); -- g_hash_table_insert (details_collection, -- pk_details_get_package_id (details), -- details); -- } -- -- return g_steal_pointer (&details_collection); --} - - void - gs_plugin_packagekit_refine_details_app (GsPlugin *plugin, -- GHashTable *details_collection, -+ GPtrArray *array, - GsApp *app) - { - GPtrArray *source_ids; - PkDetails *details; - const gchar *package_id; -+ guint i; - guint j; - guint64 size = 0; - -- /* @source_ids can have as many as 200 elements (google-noto); typically -- * it has 1 or 2 -- * -- * @details_collection is typically a large list of apps in the -- * repository, on the order of 400 or 700 apps */ - source_ids = gs_app_get_source_ids (app); - for (j = 0; j < source_ids->len; j++) { - package_id = g_ptr_array_index (source_ids, j); -- details = g_hash_table_lookup (details_collection, package_id); -- if (details == NULL) -- continue; -- -- if (gs_app_get_license (app) == NULL) { -- g_autofree gchar *license_spdx = NULL; -- license_spdx = as_utils_license_to_spdx (pk_details_get_license (details)); -- if (license_spdx != NULL) { -- gs_app_set_license (app, -- GS_APP_QUALITY_LOWEST, -- license_spdx); -+ for (i = 0; i < array->len; i++) { -+ /* right package? */ -+ details = g_ptr_array_index (array, i); -+ if (!gs_pk_compare_ids (package_id, -+ pk_details_get_package_id (details))) { -+ continue; - } -+ if (gs_app_get_license (app) == NULL) { -+ g_autofree gchar *license_spdx = NULL; -+ license_spdx = as_utils_license_to_spdx (pk_details_get_license (details)); -+ if (license_spdx != NULL) { -+ gs_app_set_license (app, -+ GS_APP_QUALITY_LOWEST, -+ license_spdx); -+ } -+ } -+ if (gs_app_get_url (app, AS_URL_KIND_HOMEPAGE) == NULL) { -+ gs_app_set_url (app, -+ AS_URL_KIND_HOMEPAGE, -+ pk_details_get_url (details)); -+ } -+ if (gs_app_get_description (app) == NULL) { -+ gs_app_set_description (app, -+ GS_APP_QUALITY_LOWEST, -+ pk_details_get_description (details)); -+ } -+ size += pk_details_get_size (details); -+ break; - } -- if (gs_app_get_url (app, AS_URL_KIND_HOMEPAGE) == NULL) { -- gs_app_set_url (app, -- AS_URL_KIND_HOMEPAGE, -- pk_details_get_url (details)); -- } -- if (gs_app_get_description (app) == NULL) { -- gs_app_set_description (app, -- GS_APP_QUALITY_LOWEST, -- pk_details_get_description (details)); -- } -- size += pk_details_get_size (details); - } - - /* the size is the size of all sources */ -diff --git a/plugins/packagekit/packagekit-common.h b/plugins/packagekit/packagekit-common.h -index 9f523684..0742ea3a 100644 ---- a/plugins/packagekit/packagekit-common.h -+++ b/plugins/packagekit/packagekit-common.h -@@ -30,9 +30,8 @@ void gs_plugin_packagekit_resolve_packages_app (GsPlugin *plugin, - void gs_plugin_packagekit_set_metadata_from_package (GsPlugin *plugin, - GsApp *app, - PkPackage *package); --GHashTable * gs_plugin_packagekit_details_array_to_hash (GPtrArray *array); - void gs_plugin_packagekit_refine_details_app (GsPlugin *plugin, -- GHashTable *details_collection, -+ GPtrArray *array, - GsApp *app); - void gs_plugin_packagekit_set_packaging_format (GsPlugin *plugin, - GsApp *app); --- -2.26.2 - diff --git a/0001-gs-plugin-loader-Reset-online-updates-timestamp-only.patch b/0001-gs-plugin-loader-Reset-online-updates-timestamp-only.patch deleted file mode 100644 index 94e4b57..0000000 --- a/0001-gs-plugin-loader-Reset-online-updates-timestamp-only.patch +++ /dev/null @@ -1,35 +0,0 @@ -From 9a48a04d180f9d3e988efe761cee7bfd9bea79dd Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Fri, 5 Mar 2021 13:34:40 +0100 -Subject: [PATCH] gs-plugin-loader: Reset online-updates-timestamp only when - did the update - -The gs_plugin_loader_generic_update() is used in two cases, when updating -the software and when downloading the software. The former case can reset -the online-updates-timestamp, but the later not, because it did not -update anything. - -This blocks the update notifications from showing up after the first -run of the Software. ---- - lib/gs-plugin-loader.c | 4 +++- - 1 file changed, 3 insertions(+), 1 deletion(-) - -diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c -index 2dad71f86..358cb8439 100644 ---- a/lib/gs-plugin-loader.c -+++ b/lib/gs-plugin-loader.c -@@ -3124,7 +3124,9 @@ gs_plugin_loader_generic_update (GsPluginLoader *plugin_loader, - gs_plugin_status_update (plugin, NULL, GS_PLUGIN_STATUS_FINISHED); - } - -- gs_utils_set_online_updates_timestamp (plugin_loader->settings); -+ if (gs_plugin_job_get_action (helper->plugin_job) == GS_PLUGIN_ACTION_UPDATE) -+ gs_utils_set_online_updates_timestamp (plugin_loader->settings); -+ - return TRUE; - } - --- -2.30.1 - diff --git a/gnome-software.spec b/gnome-software.spec index 8c1496f..ed4882c 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,17 +11,13 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 40~beta -Release: 2%{?dist} +Version: 40~rc +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/40/%{name}-%{tarball_version}.tar.xz -# Fix update notifications: -# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/643 -# https://bugzilla.redhat.com/show_bug.cgi?id=1930401 -Patch0: 0001-gs-plugin-loader-Reset-online-updates-timestamp-only.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -75,7 +71,7 @@ Obsoletes: gnome-software-snap < 3.33.1 Obsoletes: gnome-software-editor < 3.35.1 # this is not a library version -%define gs_plugin_version 14 +%define gs_plugin_version 16 %description gnome-software is an application that makes it easy to add, remove @@ -119,10 +115,7 @@ This package includes the rpm-ostree backend. %meson_install # remove unneeded dpkg plugin -rm %{buildroot}%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_dpkg.so - -# remove unneeded static library -rm %{buildroot}%{_libdir}/libgnomesoftware.a +rm %{buildroot}%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dpkg.so # make the software center load faster desktop-file-edit %{buildroot}%{_datadir}/applications/org.gnome.Software.desktop \ @@ -150,44 +143,43 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_mandir}/man1/gnome-software.1.gz %{_datadir}/icons/hicolor/*/apps/org.gnome.Software.svg %{_datadir}/icons/hicolor/symbolic/apps/org.gnome.Software-symbolic.svg +%{_datadir}/icons/hicolor/scalable/actions/carousel-arrow-next-symbolic.svg +%{_datadir}/icons/hicolor/scalable/actions/carousel-arrow-previous-symbolic.svg %{_datadir}/icons/hicolor/scalable/status/software-installed-symbolic.svg -%{_datadir}/gnome-software/featured-*.svg -%{_datadir}/gnome-software/featured-*.jpg %{_datadir}/metainfo/org.gnome.Software.appdata.xml %{_datadir}/metainfo/org.gnome.Software.Plugin.Flatpak.metainfo.xml %{_datadir}/metainfo/org.gnome.Software.Plugin.Fwupd.metainfo.xml %{_datadir}/metainfo/org.gnome.Software.Plugin.Odrs.metainfo.xml -%dir %{_libdir}/gs-plugins-%{gs_plugin_version} -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_appstream.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_dummy.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_fedora-pkgdb-collections.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_flatpak.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_fwupd.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_generic-updates.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-blocklist.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-popular.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_icons.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_key-colors-metadata.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_key-colors.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_modalias.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_odrs.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_os-release.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_packagekit-history.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_packagekit-local.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_packagekit-offline.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_packagekit-proxy.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refine-repos.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refine.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refresh.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_packagekit-upgrade.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_packagekit-url-to-app.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_packagekit.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_provenance-license.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_provenance.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_repos.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_rewrite-resource.so -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_systemd-updates.so +%dir %{_libdir}/gnome-software/plugins-%{gs_plugin_version} +%{_libdir}/gnome-software/libgnomesoftware.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_appstream.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dummy.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-pkgdb-collections.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_flatpak.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fwupd.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_generic-updates.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-blocklist.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-popular.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_icons.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_modalias.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_odrs.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_os-release.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-history.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-local.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-offline.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-proxy.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refine-repos.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refine.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refresh.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-upgrade.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-url-to-app.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance-license.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_repos.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rewrite-resource.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_systemd-updates.so %{_sysconfdir}/xdg/autostart/gnome-software-service.desktop %{_datadir}/app-info/xmls/org.gnome.Software.Featured.xml %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service @@ -199,7 +191,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libexecdir}/gnome-software-restarter %files rpm-ostree -%{_libdir}/gs-plugins-%{gs_plugin_version}/libgs_plugin_rpm-ostree.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rpm-ostree.so %files devel %{_libdir}/pkgconfig/gnome-software.pc @@ -208,6 +200,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Mar 15 2021 Kalev Lember - 40~rc-1 +- Update to 40.rc + * Wed Mar 10 2021 Adam Williamson - 40~beta-2 - Backport MR #643 to fix update notifications on first run (#1930401) diff --git a/sources b/sources index 7728ce9..f95cf36 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-40.beta.tar.xz) = 39edf94a3091b8c6e00925cf4e5fab929fbd5166ab35caf247415753bbae8c6ea0df51a80fa2fa7ba35ca64d5b7ce44359b9a451c7f6f3424e1716ed8b493dd4 +SHA512 (gnome-software-40.rc.tar.xz) = caea26e84641f5db9dbacdec32e9f2039433e60fbb4548f48a33958eb1bd61415ab35e515100b29cb98a655bcf40ee8e2ea3cee4dd80d3777c2a81cf33848f8a From dbac9fa7a31701e5c4e70faa75ee216c66053da5 Mon Sep 17 00:00:00 2001 From: Adam Williamson Date: Thu, 18 Mar 2021 18:25:09 -0700 Subject: [PATCH 018/163] Backport a couple of bug fixes from upstream (icon display, crash bug) --- ...dd-additional-icon-debug-information.patch | 32 ++++++++++ ...-handling-of-icons-where-appdata-doe.patch | 48 +++++++++++++++ ...und-invalid-icon-names-from-some-app.patch | 61 +++++++++++++++++++ ...provider-Fix-crash-in-variant-handli.patch | 29 +++++++++ gnome-software.spec | 16 ++++- 5 files changed, 185 insertions(+), 1 deletion(-) create mode 100644 0001-gs-app-Add-additional-icon-debug-information.patch create mode 100644 0002-gs-appstream-Fix-handling-of-icons-where-appdata-doe.patch create mode 100644 0003-gs-icon-Work-around-invalid-icon-names-from-some-app.patch create mode 100644 0004-gs-shell-search-provider-Fix-crash-in-variant-handli.patch diff --git a/0001-gs-app-Add-additional-icon-debug-information.patch b/0001-gs-app-Add-additional-icon-debug-information.patch new file mode 100644 index 0000000..a881ab0 --- /dev/null +++ b/0001-gs-app-Add-additional-icon-debug-information.patch @@ -0,0 +1,32 @@ +From 81a2e01d407fc903a83b4c1a82749d2591397240 Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Tue, 16 Mar 2021 13:33:40 +0000 +Subject: [PATCH 1/4] gs-app: Add additional icon debug information + +Signed-off-by: Philip Withnall +--- + lib/gs-app.c | 5 +++-- + 1 file changed, 3 insertions(+), 2 deletions(-) + +diff --git a/lib/gs-app.c b/lib/gs-app.c +index 771743330..cb2549d4c 100644 +--- a/lib/gs-app.c ++++ b/lib/gs-app.c +@@ -1828,11 +1828,12 @@ gs_app_get_icon_for_size (GsApp *app, + * lazily created. */ + for (guint i = 0; priv->icons != NULL && i < priv->icons->len; i++) { + GIcon *icon = priv->icons->pdata[i]; ++ g_autofree gchar *icon_str = g_icon_to_string (icon); + guint icon_width = gs_icon_get_width (icon); + guint icon_scale = gs_icon_get_scale (icon); + +- g_debug ("\tConsidering icon of type %s, width %u×%u", +- G_OBJECT_TYPE_NAME (icon), icon_width, icon_scale); ++ g_debug ("\tConsidering icon of type %s (%s), width %u×%u", ++ G_OBJECT_TYPE_NAME (icon), icon_str, icon_width, icon_scale); + + /* Ignore icons with unknown width and skip over ones which + * are too small. */ +-- +2.30.2 + diff --git a/0002-gs-appstream-Fix-handling-of-icons-where-appdata-doe.patch b/0002-gs-appstream-Fix-handling-of-icons-where-appdata-doe.patch new file mode 100644 index 0000000..333baa8 --- /dev/null +++ b/0002-gs-appstream-Fix-handling-of-icons-where-appdata-doe.patch @@ -0,0 +1,48 @@ +From 9a63168893a678f97fe6e3bfde2d6e5debf151c3 Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Tue, 16 Mar 2021 13:34:13 +0000 +Subject: [PATCH 2/4] =?UTF-8?q?gs-appstream:=20Fix=20handling=20of=20icons?= + =?UTF-8?q?=20where=20appdata=20doesn=E2=80=99t=20specify=20width?= +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +If the `` element in the appdata doesn’t specify a `width` +attribute, `xb_node_get_attr_as_uint()` will return `G_MAXUINT64`. +However, its return value was being assigned to `sz`, which is a +`guint`, and hence it was being truncated. This resulted in icons having +their widths set to `G_MAXUINT`, and hence being prioritised for display +when that was not necessarily correct. + +Fix that by explicitly handling the failure response from +`xb_node_get_attr_as_uint()`. + +Signed-off-by: Philip Withnall + +Fixes: #1171 +--- + plugins/core/gs-appstream.c | 8 ++++++-- + 1 file changed, 6 insertions(+), 2 deletions(-) + +diff --git a/plugins/core/gs-appstream.c b/plugins/core/gs-appstream.c +index a9cf97270..22fed1154 100644 +--- a/plugins/core/gs-appstream.c ++++ b/plugins/core/gs-appstream.c +@@ -149,8 +149,12 @@ gs_appstream_new_icon (XbNode *component, XbNode *n, AsIconKind icon_kind, guint + default: + as_icon_set_name (icon, xb_node_get_text (n)); + } +- if (sz == 0) +- sz = xb_node_get_attr_as_uint (n, "width"); ++ if (sz == 0) { ++ guint64 width = xb_node_get_attr_as_uint (n, "width"); ++ if (width > 0 && width < G_MAXUINT) ++ sz = width; ++ } ++ + if (sz > 0) { + as_icon_set_width (icon, sz); + as_icon_set_height (icon, sz); +-- +2.30.2 + diff --git a/0003-gs-icon-Work-around-invalid-icon-names-from-some-app.patch b/0003-gs-icon-Work-around-invalid-icon-names-from-some-app.patch new file mode 100644 index 0000000..bca178b --- /dev/null +++ b/0003-gs-icon-Work-around-invalid-icon-names-from-some-app.patch @@ -0,0 +1,61 @@ +From 3e86354cc5ccffc5ef27fa9e5ce2e99e3e60bc8c Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Tue, 16 Mar 2021 13:36:23 +0000 +Subject: [PATCH 3/4] gs-icon: Work around invalid icon names from some + appstream files +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +Cached icons are supposed to provide a name (like `krita.png`), `width` +and `height` attributes, and then gnome-software can build the path to +the cached icon file according to +https://www.freedesktop.org/software/appstream/docs/sect-AppStream-IconCache.html#spec-iconcache-location. + +Due to a bug in appstream-builder in appstream-glib +(https://github.com/hughsie/appstream-glib/pull/390), some appstream +files – for example, rpmfusion-free-33 – had invalid cached icon names, +which resulted in those icons not being loadable, and not appearing for +their applications. + +As it may take a while for the fix in appstream-builder to be merged and +be used to regenerate all the appstream files for different app +repositories, add a workaround in gnome-software. + +Signed-off-by: Philip Withnall + +Helps: #1171 +--- + lib/gs-icon.c | 10 ++++++++++ + 1 file changed, 10 insertions(+) + +diff --git a/lib/gs-icon.c b/lib/gs-icon.c +index a88e62d34..955ab0217 100644 +--- a/lib/gs-icon.c ++++ b/lib/gs-icon.c +@@ -200,12 +200,22 @@ gs_icon_load_cached (AsIcon *icon) + { + const gchar *filename = as_icon_get_filename (icon); + const gchar *name = as_icon_get_name (icon); ++ g_autofree gchar *name_allocated = NULL; + g_autofree gchar *full_filename = NULL; + g_autoptr(GFile) file = NULL; + + if (filename == NULL || name == NULL) + return NULL; + ++ /* FIXME: Work around https://github.com/hughsie/appstream-glib/pull/390 ++ * where appstream files generated with appstream-builder from ++ * appstream-glib, with its hidpi option enabled, will contain an ++ * unnecessary size subdirectory in the icon name. */ ++ if (g_str_has_prefix (name, "64x64/")) ++ name = name_allocated = g_strdup (name + strlen ("64x64/")); ++ else if (g_str_has_prefix (name, "128x128/")) ++ name = name_allocated = g_strdup (name + strlen ("128x128/")); ++ + if (!g_str_has_suffix (filename, name)) { + /* Spec: https://www.freedesktop.org/software/appstream/docs/sect-AppStream-IconCache.html#spec-iconcache-location */ + if (as_icon_get_scale (icon) <= 1) { +-- +2.30.2 + diff --git a/0004-gs-shell-search-provider-Fix-crash-in-variant-handli.patch b/0004-gs-shell-search-provider-Fix-crash-in-variant-handli.patch new file mode 100644 index 0000000..b83d396 --- /dev/null +++ b/0004-gs-shell-search-provider-Fix-crash-in-variant-handli.patch @@ -0,0 +1,29 @@ +From 80834ed7d336f103cfc7199fa96c6f2a860be438 Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Thu, 18 Mar 2021 13:11:36 +0000 +Subject: [PATCH 4/4] gs-shell-search-provider: Fix crash in variant handling + for icons + +Signed-off-by: Philip Withnall + +Fixes: #1179 +--- + src/gs-shell-search-provider.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/src/gs-shell-search-provider.c b/src/gs-shell-search-provider.c +index 8bafc9a8c..27bbb45f7 100644 +--- a/src/gs-shell-search-provider.c ++++ b/src/gs-shell-search-provider.c +@@ -254,7 +254,7 @@ handle_get_result_metas (GsShellSearchProvider2 *skeleton, + if (icon != NULL) { + g_autofree gchar *icon_str = g_icon_to_string (icon); + if (icon_str != NULL) { +- g_variant_builder_add (&meta, "{sv}", "gicon", icon_str); ++ g_variant_builder_add (&meta, "{sv}", "gicon", g_variant_new_string (icon_str)); + } else { + g_autoptr(GVariant) icon_serialized = g_icon_serialize (icon); + g_variant_builder_add (&meta, "{sv}", "icon", icon_serialized); +-- +2.30.2 + diff --git a/gnome-software.spec b/gnome-software.spec index ed4882c..3c13a51 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,13 +12,24 @@ Name: gnome-software Version: 40~rc -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/40/%{name}-%{tarball_version}.tar.xz +# Fix display of icons for packages and snaps +# https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1171 +# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/653 +Patch0001: 0001-gs-app-Add-additional-icon-debug-information.patch +Patch0002: 0002-gs-appstream-Fix-handling-of-icons-where-appdata-doe.patch +Patch0003: 0003-gs-icon-Work-around-invalid-icon-names-from-some-app.patch +# Fix crash that sometimes breaks search provider or stops window appearing +# https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1179 +# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/658 +Patch0004: 0004-gs-shell-search-provider-Fix-crash-in-variant-handli.patch + BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc BuildRequires: gettext @@ -200,6 +211,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Thu Mar 18 2021 Adam Williamson - 40~rc-2 +- Backport a couple of bug fixes from upstream (icon display, crash bug) + * Mon Mar 15 2021 Kalev Lember - 40~rc-1 - Update to 40.rc From 75366111674a11c45528a9e5224aebdf99452a0e Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Mon, 22 Mar 2021 13:49:58 +0100 Subject: [PATCH 019/163] Update to 40.0 --- .gitignore | 1 + ...dd-additional-icon-debug-information.patch | 32 ---------- ...-handling-of-icons-where-appdata-doe.patch | 48 --------------- ...und-invalid-icon-names-from-some-app.patch | 61 ------------------- ...provider-Fix-crash-in-variant-handli.patch | 29 --------- gnome-software.spec | 18 ++---- sources | 2 +- 7 files changed, 7 insertions(+), 184 deletions(-) delete mode 100644 0001-gs-app-Add-additional-icon-debug-information.patch delete mode 100644 0002-gs-appstream-Fix-handling-of-icons-where-appdata-doe.patch delete mode 100644 0003-gs-icon-Work-around-invalid-icon-names-from-some-app.patch delete mode 100644 0004-gs-shell-search-provider-Fix-crash-in-variant-handli.patch diff --git a/.gitignore b/.gitignore index 6dba849..3aae75a 100644 --- a/.gitignore +++ b/.gitignore @@ -116,3 +116,4 @@ /gnome-software-3.38.1.tar.xz /gnome-software-40.beta.tar.xz /gnome-software-40.rc.tar.xz +/gnome-software-40.0.tar.xz diff --git a/0001-gs-app-Add-additional-icon-debug-information.patch b/0001-gs-app-Add-additional-icon-debug-information.patch deleted file mode 100644 index a881ab0..0000000 --- a/0001-gs-app-Add-additional-icon-debug-information.patch +++ /dev/null @@ -1,32 +0,0 @@ -From 81a2e01d407fc903a83b4c1a82749d2591397240 Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Tue, 16 Mar 2021 13:33:40 +0000 -Subject: [PATCH 1/4] gs-app: Add additional icon debug information - -Signed-off-by: Philip Withnall ---- - lib/gs-app.c | 5 +++-- - 1 file changed, 3 insertions(+), 2 deletions(-) - -diff --git a/lib/gs-app.c b/lib/gs-app.c -index 771743330..cb2549d4c 100644 ---- a/lib/gs-app.c -+++ b/lib/gs-app.c -@@ -1828,11 +1828,12 @@ gs_app_get_icon_for_size (GsApp *app, - * lazily created. */ - for (guint i = 0; priv->icons != NULL && i < priv->icons->len; i++) { - GIcon *icon = priv->icons->pdata[i]; -+ g_autofree gchar *icon_str = g_icon_to_string (icon); - guint icon_width = gs_icon_get_width (icon); - guint icon_scale = gs_icon_get_scale (icon); - -- g_debug ("\tConsidering icon of type %s, width %u×%u", -- G_OBJECT_TYPE_NAME (icon), icon_width, icon_scale); -+ g_debug ("\tConsidering icon of type %s (%s), width %u×%u", -+ G_OBJECT_TYPE_NAME (icon), icon_str, icon_width, icon_scale); - - /* Ignore icons with unknown width and skip over ones which - * are too small. */ --- -2.30.2 - diff --git a/0002-gs-appstream-Fix-handling-of-icons-where-appdata-doe.patch b/0002-gs-appstream-Fix-handling-of-icons-where-appdata-doe.patch deleted file mode 100644 index 333baa8..0000000 --- a/0002-gs-appstream-Fix-handling-of-icons-where-appdata-doe.patch +++ /dev/null @@ -1,48 +0,0 @@ -From 9a63168893a678f97fe6e3bfde2d6e5debf151c3 Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Tue, 16 Mar 2021 13:34:13 +0000 -Subject: [PATCH 2/4] =?UTF-8?q?gs-appstream:=20Fix=20handling=20of=20icons?= - =?UTF-8?q?=20where=20appdata=20doesn=E2=80=99t=20specify=20width?= -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -If the `` element in the appdata doesn’t specify a `width` -attribute, `xb_node_get_attr_as_uint()` will return `G_MAXUINT64`. -However, its return value was being assigned to `sz`, which is a -`guint`, and hence it was being truncated. This resulted in icons having -their widths set to `G_MAXUINT`, and hence being prioritised for display -when that was not necessarily correct. - -Fix that by explicitly handling the failure response from -`xb_node_get_attr_as_uint()`. - -Signed-off-by: Philip Withnall - -Fixes: #1171 ---- - plugins/core/gs-appstream.c | 8 ++++++-- - 1 file changed, 6 insertions(+), 2 deletions(-) - -diff --git a/plugins/core/gs-appstream.c b/plugins/core/gs-appstream.c -index a9cf97270..22fed1154 100644 ---- a/plugins/core/gs-appstream.c -+++ b/plugins/core/gs-appstream.c -@@ -149,8 +149,12 @@ gs_appstream_new_icon (XbNode *component, XbNode *n, AsIconKind icon_kind, guint - default: - as_icon_set_name (icon, xb_node_get_text (n)); - } -- if (sz == 0) -- sz = xb_node_get_attr_as_uint (n, "width"); -+ if (sz == 0) { -+ guint64 width = xb_node_get_attr_as_uint (n, "width"); -+ if (width > 0 && width < G_MAXUINT) -+ sz = width; -+ } -+ - if (sz > 0) { - as_icon_set_width (icon, sz); - as_icon_set_height (icon, sz); --- -2.30.2 - diff --git a/0003-gs-icon-Work-around-invalid-icon-names-from-some-app.patch b/0003-gs-icon-Work-around-invalid-icon-names-from-some-app.patch deleted file mode 100644 index bca178b..0000000 --- a/0003-gs-icon-Work-around-invalid-icon-names-from-some-app.patch +++ /dev/null @@ -1,61 +0,0 @@ -From 3e86354cc5ccffc5ef27fa9e5ce2e99e3e60bc8c Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Tue, 16 Mar 2021 13:36:23 +0000 -Subject: [PATCH 3/4] gs-icon: Work around invalid icon names from some - appstream files -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -Cached icons are supposed to provide a name (like `krita.png`), `width` -and `height` attributes, and then gnome-software can build the path to -the cached icon file according to -https://www.freedesktop.org/software/appstream/docs/sect-AppStream-IconCache.html#spec-iconcache-location. - -Due to a bug in appstream-builder in appstream-glib -(https://github.com/hughsie/appstream-glib/pull/390), some appstream -files – for example, rpmfusion-free-33 – had invalid cached icon names, -which resulted in those icons not being loadable, and not appearing for -their applications. - -As it may take a while for the fix in appstream-builder to be merged and -be used to regenerate all the appstream files for different app -repositories, add a workaround in gnome-software. - -Signed-off-by: Philip Withnall - -Helps: #1171 ---- - lib/gs-icon.c | 10 ++++++++++ - 1 file changed, 10 insertions(+) - -diff --git a/lib/gs-icon.c b/lib/gs-icon.c -index a88e62d34..955ab0217 100644 ---- a/lib/gs-icon.c -+++ b/lib/gs-icon.c -@@ -200,12 +200,22 @@ gs_icon_load_cached (AsIcon *icon) - { - const gchar *filename = as_icon_get_filename (icon); - const gchar *name = as_icon_get_name (icon); -+ g_autofree gchar *name_allocated = NULL; - g_autofree gchar *full_filename = NULL; - g_autoptr(GFile) file = NULL; - - if (filename == NULL || name == NULL) - return NULL; - -+ /* FIXME: Work around https://github.com/hughsie/appstream-glib/pull/390 -+ * where appstream files generated with appstream-builder from -+ * appstream-glib, with its hidpi option enabled, will contain an -+ * unnecessary size subdirectory in the icon name. */ -+ if (g_str_has_prefix (name, "64x64/")) -+ name = name_allocated = g_strdup (name + strlen ("64x64/")); -+ else if (g_str_has_prefix (name, "128x128/")) -+ name = name_allocated = g_strdup (name + strlen ("128x128/")); -+ - if (!g_str_has_suffix (filename, name)) { - /* Spec: https://www.freedesktop.org/software/appstream/docs/sect-AppStream-IconCache.html#spec-iconcache-location */ - if (as_icon_get_scale (icon) <= 1) { --- -2.30.2 - diff --git a/0004-gs-shell-search-provider-Fix-crash-in-variant-handli.patch b/0004-gs-shell-search-provider-Fix-crash-in-variant-handli.patch deleted file mode 100644 index b83d396..0000000 --- a/0004-gs-shell-search-provider-Fix-crash-in-variant-handli.patch +++ /dev/null @@ -1,29 +0,0 @@ -From 80834ed7d336f103cfc7199fa96c6f2a860be438 Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Thu, 18 Mar 2021 13:11:36 +0000 -Subject: [PATCH 4/4] gs-shell-search-provider: Fix crash in variant handling - for icons - -Signed-off-by: Philip Withnall - -Fixes: #1179 ---- - src/gs-shell-search-provider.c | 2 +- - 1 file changed, 1 insertion(+), 1 deletion(-) - -diff --git a/src/gs-shell-search-provider.c b/src/gs-shell-search-provider.c -index 8bafc9a8c..27bbb45f7 100644 ---- a/src/gs-shell-search-provider.c -+++ b/src/gs-shell-search-provider.c -@@ -254,7 +254,7 @@ handle_get_result_metas (GsShellSearchProvider2 *skeleton, - if (icon != NULL) { - g_autofree gchar *icon_str = g_icon_to_string (icon); - if (icon_str != NULL) { -- g_variant_builder_add (&meta, "{sv}", "gicon", icon_str); -+ g_variant_builder_add (&meta, "{sv}", "gicon", g_variant_new_string (icon_str)); - } else { - g_autoptr(GVariant) icon_serialized = g_icon_serialize (icon); - g_variant_builder_add (&meta, "{sv}", "icon", icon_serialized); --- -2.30.2 - diff --git a/gnome-software.spec b/gnome-software.spec index 3c13a51..88cedde 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,25 +11,14 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 40~rc -Release: 2%{?dist} +Version: 40.0 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/40/%{name}-%{tarball_version}.tar.xz -# Fix display of icons for packages and snaps -# https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1171 -# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/653 -Patch0001: 0001-gs-app-Add-additional-icon-debug-information.patch -Patch0002: 0002-gs-appstream-Fix-handling-of-icons-where-appdata-doe.patch -Patch0003: 0003-gs-icon-Work-around-invalid-icon-names-from-some-app.patch -# Fix crash that sometimes breaks search provider or stops window appearing -# https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1179 -# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/658 -Patch0004: 0004-gs-shell-search-provider-Fix-crash-in-variant-handli.patch - BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc BuildRequires: gettext @@ -211,6 +200,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Mar 22 2021 Kalev Lember - 40.0-1 +- Update to 40.0 + * Thu Mar 18 2021 Adam Williamson - 40~rc-2 - Backport a couple of bug fixes from upstream (icon display, crash bug) diff --git a/sources b/sources index f95cf36..a8dc968 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-40.rc.tar.xz) = caea26e84641f5db9dbacdec32e9f2039433e60fbb4548f48a33958eb1bd61415ab35e515100b29cb98a655bcf40ee8e2ea3cee4dd80d3777c2a81cf33848f8a +SHA512 (gnome-software-40.0.tar.xz) = 052c520ab25af4257bb978aaa9e1c7a555f8d24dbd782d9f12f3c3def22e65588d3c76d16e4b3dc26f034a762c2ee3e773026b158d468e9e169369dc3d156a2a From 2db091cafb17ce627ee1912f6e447770a015d155 Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Fri, 26 Mar 2021 11:41:06 +0100 Subject: [PATCH 020/163] Rebuild to fix sysprof-capture symbols leaking into libraries consuming it --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 88cedde..7f439c2 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 40.0 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -200,6 +200,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri Mar 26 2021 Kalev Lember - 40.0-2 +- Rebuild to fix sysprof-capture symbols leaking into libraries consuming it + * Mon Mar 22 2021 Kalev Lember - 40.0-1 - Update to 40.0 From 582b519dd9b8fe41d4d54e012527e7040df64822 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 3 May 2021 09:38:10 +0200 Subject: [PATCH 021/163] Update to 40.1 --- .gitignore | 120 +------------------------------------------- gnome-software.spec | 7 ++- sources | 2 +- 3 files changed, 7 insertions(+), 122 deletions(-) diff --git a/.gitignore b/.gitignore index 3aae75a..b4345b1 100644 --- a/.gitignore +++ b/.gitignore @@ -1,119 +1 @@ -/gnome-software-0.1.tar.xz -/gnome-software-3.9.1.tar.xz -/gnome-software-3.9.2.tar.xz -/gnome-software-3.9.3.tar.xz -/fedora-20.xml.gz -/fedora-20-icons.tar.gz -/gnome-software-3.10.0.tar.xz -/gnome-software-3.11.1.tar.xz -/fedora-20-codecs.xml -/web-apps.xml -/gnome-software-3.11.2.tar.xz -/gnome-software-3.11.3.tar.xz -/gnome-software-3.11.4.tar.xz -/fedora-rawhide-icons.tar.gz -/fedora-rawhide.xml.gz -/gnome-software-3.11.5.tar.xz -/gnome-software-3.11.90.tar.xz -/gnome-software-3.11.91.tar.xz -/gnome-software-3.11.92.tar.xz -/gnome-software-3.12.0.tar.xz -/gnome-software-3.12.1.tar.xz -/gnome-software-3.13.1.tar.xz -/fedora-21-icons.tar.gz -/fedora-21.xml.gz -/gnome-software-3.13.2.tar.xz -/gnome-software-3.13.3-7491627.tar.xz -/gnome-software-3.13.3.tar.xz -/gnome-software-3.13.4.tar.xz -/gnome-software-3.13.5-5c89189.tar.xz -/gnome-software-3.13.90.tar.xz -/gnome-software-3.13.91.tar.xz -/gnome-software-3.13.92.tar.xz -/gnome-software-3.14.0.tar.xz -/gnome-software-3.14.1.tar.xz -/gnome-software-3.14.2.tar.xz -/gnome-software-3.15.2.tar.xz -/gnome-software-3.15.4.tar.xz -/gnome-software-3.15.90.tar.xz -/gnome-software-3.15.91.tar.xz -/gnome-software-3.15.92.tar.xz -/gnome-software-3.16.0.tar.xz -/gnome-software-3.16.1.tar.xz -/gnome-software-3.16.2.tar.xz -/gnome-software-3.17.1.tar.xz -/gnome-software-3.17.2.tar.xz -/gnome-software-3.17.3.tar.xz -/gnome-software-3.17.90.tar.xz -/gnome-software-3.17.91.tar.xz -/gnome-software-3.17.92.tar.xz -/gnome-software-3.18.0.tar.xz -/gnome-software-3.18.1.tar.xz -/gnome-software-3.18.2.tar.xz -/gnome-software-3.18.3.tar.xz -/gnome-software-3.19.4.tar.xz -/gnome-software-3.19.90.tar.xz -/gnome-software-3.19.91.tar.xz -/gnome-software-3.19.92.tar.xz -/gnome-software-3.20.0.tar.xz -/gnome-software-3.20.1.tar.xz -/gnome-software-3.20.2.tar.xz -/gnome-software-3.21.1.tar.xz -/gnome-software-3.21.2.tar.xz -/gnome-software-3.21.4.tar.xz -/gnome-software-3.21.90.tar.xz -/gnome-software-3.21.91.tar.xz -/gnome-software-3.21.92.tar.xz -/gnome-software-3.22.0.tar.xz -/gnome-software-3.22.1.tar.xz -/gnome-software-3.22.2.tar.xz -/gnome-software-3.23.2.tar.xz -/gnome-software-3.23.3.tar.xz -/gnome-software-3.23.90.tar.xz -/gnome-software-3.23.91.tar.xz -/gnome-software-3.23.92.tar.xz -/gnome-software-3.24.0.tar.xz -/gnome-software-3.24.1.tar.xz -/gnome-software-3.24.2.tar.xz -/gnome-software-3.24.3.tar.xz -/gnome-software-3.25.3.tar.xz -/gnome-software-3.25.4.tar.xz -/gnome-software-3.25.90.tar.xz -/gnome-software-3.25.91.tar.xz -/gnome-software-3.26.0.tar.xz -/gnome-software-3.26.1.tar.xz -/gnome-software-3.26.2.tar.xz -/gnome-software-3.27.2.tar.xz -/gnome-software-3.27.3.tar.xz -/gnome-software-3.27.4.tar.xz -/gnome-software-3.27.90.tar.xz -/gnome-software-3.27.92.tar.xz -/gnome-software-3.28.0.tar.xz -/gnome-software-3.28.1.tar.xz -/gnome-software-3.29.1.tar.xz -/gnome-software-3.29.92.tar.xz -/gnome-software-3.30.0.tar.xz -/gnome-software-3.30.1.tar.xz -/gnome-software-3.30.2.tar.xz -/gnome-software-3.31.1.tar.xz -/gnome-software-3.31.2.tar.xz -/gnome-software-3.31.90.tar.xz -/gnome-software-3.31.92.tar.xz -/gnome-software-3.32.0.tar.xz -/gnome-software-3.32.1.tar.xz -/gnome-software-3.32.2.tar.xz -/gnome-software-3.32.3.tar.xz -/gnome-software-3.32.4.tar.xz -/gnome-software-3.34.0.tar.xz -/gnome-software-3.34.1.tar.xz -/gnome-software-3.35.2.tar.xz -/gnome-software-3.35.91.tar.xz -/gnome-software-3.35.92.tar.xz -/gnome-software-3.36.0.tar.xz -/gnome-software-3.36.1.tar.xz -/gnome-software-3.37.92.tar.xz -/gnome-software-3.38.0.tar.xz -/gnome-software-3.38.1.tar.xz -/gnome-software-40.beta.tar.xz -/gnome-software-40.rc.tar.xz -/gnome-software-40.0.tar.xz +/gnome-software-*.tar.xz diff --git a/gnome-software.spec b/gnome-software.spec index 7f439c2..afd1597 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,8 +11,8 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 40.0 -Release: 2%{?dist} +Version: 40.1 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -200,6 +200,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon May 03 2021 Milan Crha - 40.1-1 +- Update to 40.1 + * Fri Mar 26 2021 Kalev Lember - 40.0-2 - Rebuild to fix sysprof-capture symbols leaking into libraries consuming it diff --git a/sources b/sources index a8dc968..2342259 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-40.0.tar.xz) = 052c520ab25af4257bb978aaa9e1c7a555f8d24dbd782d9f12f3c3def22e65588d3c76d16e4b3dc26f034a762c2ee3e773026b158d468e9e169369dc3d156a2a +SHA512 (gnome-software-40.1.tar.xz) = ae805d01896d761dd82a21dedbfafba7e8ffd2d98e99da4548d846aafdf07f9a26dfa2e083ac2dda576f8b1db05bb3f26642d3a6558da86921450049870767fe From 752ac96606813285c03810c67791834c9be458a1 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 3 May 2021 12:48:24 +0200 Subject: [PATCH 022/163] Add patch for crash under gs_details_page_refresh_all() (i#1227) --- ...sh-under-gs_details_page_refresh_all.patch | 312 ++++++++++++++++++ gnome-software.spec | 7 +- 2 files changed, 318 insertions(+), 1 deletion(-) create mode 100644 001-i1227-crash-under-gs_details_page_refresh_all.patch diff --git a/001-i1227-crash-under-gs_details_page_refresh_all.patch b/001-i1227-crash-under-gs_details_page_refresh_all.patch new file mode 100644 index 0000000..4fcaaf5 --- /dev/null +++ b/001-i1227-crash-under-gs_details_page_refresh_all.patch @@ -0,0 +1,312 @@ +From 64a0eaa4a1b1402a0e5926d0c274cfa962589149 Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Thu, 29 Apr 2021 15:49:01 +0100 +Subject: [PATCH 1/6] gs-app: Drop requirement for set_version_history() to be + non-NULL + +Signed-off-by: Philip Withnall +--- + lib/gs-app.c | 1 - + 1 file changed, 1 deletion(-) + +diff --git a/lib/gs-app.c b/lib/gs-app.c +index e8eb9d48b..2db3e6251 100644 +--- a/lib/gs-app.c ++++ b/lib/gs-app.c +@@ -5365,7 +5365,6 @@ gs_app_set_version_history (GsApp *app, GPtrArray *version_history) + GsAppPrivate *priv = gs_app_get_instance_private (app); + g_autoptr(GMutexLocker) locker = NULL; + g_return_if_fail (GS_IS_APP (app)); +- g_return_if_fail (version_history != NULL); + locker = g_mutex_locker_new (&priv->mutex); + _g_set_ptr_array (&priv->version_history, version_history); + } +-- +GitLab + + +From 3229d3d66347c5cd317d12db9b456f8eaefad678 Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Thu, 29 Apr 2021 15:45:33 +0100 +Subject: [PATCH 2/6] gs-app: Clarify documentation/annotations for version + history + +This clarifies the documentation for the existing behaviour. + +Signed-off-by: Philip Withnall + +Helps: #1227 +--- + lib/gs-app.c | 9 +++++---- + 1 file changed, 5 insertions(+), 4 deletions(-) + +diff --git a/lib/gs-app.c b/lib/gs-app.c +index 2db3e6251..5ef7e9942 100644 +--- a/lib/gs-app.c ++++ b/lib/gs-app.c +@@ -129,7 +129,7 @@ typedef struct + GsPluginAction pending_action; + GsAppPermissions permissions; + gboolean is_update_downloaded; +- GPtrArray *version_history; /* (element-type AsRelease) */ ++ GPtrArray *version_history; /* (element-type AsRelease) (nullable) (owned) */ + } GsAppPrivate; + + enum { +@@ -5337,7 +5337,8 @@ gs_app_set_update_permissions (GsApp *app, GsAppPermissions update_permissions) + * Gets the list of past releases for an application (including the latest + * one). + * +- * Returns: (element-type AsRelease) (transfer none): a list ++ * Returns: (element-type AsRelease) (transfer none) (nullable): a list, or ++ * %NULL if the version history is not known + * + * Since: 40 + **/ +@@ -5352,8 +5353,8 @@ gs_app_get_version_history (GsApp *app) + /** + * gs_app_set_version_history: + * @app: a #GsApp +- * @version_history: (element-type AsRelease): a set of entries representing +- * the version history ++ * @version_history: (element-type AsRelease) (nullable): a set of entries ++ * representing the version history, or %NULL if none are known + * + * Set the list of past releases for an application (including the latest one). + * +-- +GitLab + + +From 7910276e5116db3f51dc5b088f3eb567e2472f17 Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Thu, 29 Apr 2021 15:46:39 +0100 +Subject: [PATCH 3/6] gs-app: Squash empty arrays to NULL in + gs_app_set_version_history() +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +This should save a little bit of memory. I have not updated the +documentation to guarantee this behaviour because it’s a little unusual; +simpler to allow callers to continue handling `NULL` and empty array +cases explicitly. + +Signed-off-by: Philip Withnall + +Helps: #1227 +--- + lib/gs-app.c | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/lib/gs-app.c b/lib/gs-app.c +index 5ef7e9942..6c6bb6fe6 100644 +--- a/lib/gs-app.c ++++ b/lib/gs-app.c +@@ -5366,6 +5366,10 @@ gs_app_set_version_history (GsApp *app, GPtrArray *version_history) + GsAppPrivate *priv = gs_app_get_instance_private (app); + g_autoptr(GMutexLocker) locker = NULL; + g_return_if_fail (GS_IS_APP (app)); ++ ++ if (version_history != NULL && version_history->len == 0) ++ version_history = NULL; ++ + locker = g_mutex_locker_new (&priv->mutex); + _g_set_ptr_array (&priv->version_history, version_history); + } +-- +GitLab + + +From ff5d189202788ec84bf690b8ddb184240ae68e2d Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Thu, 29 Apr 2021 15:47:40 +0100 +Subject: [PATCH 4/6] gs-app: Fix generic setters to handle NULL arrays +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +The previous implementation of the functions didn’t handle `NULL` +arrays. + +Signed-off-by: Philip Withnall + +Helps: #1227 +--- + lib/gs-app.c | 8 ++++++-- + 1 file changed, 6 insertions(+), 2 deletions(-) + +diff --git a/lib/gs-app.c b/lib/gs-app.c +index 6c6bb6fe6..efbc4756a 100644 +--- a/lib/gs-app.c ++++ b/lib/gs-app.c +@@ -184,9 +184,11 @@ _g_set_ptr_array (GPtrArray **array_ptr, GPtrArray *new_array) + { + if (*array_ptr == new_array) + return FALSE; ++ if (new_array != NULL) ++ g_ptr_array_ref (new_array); + if (*array_ptr != NULL) + g_ptr_array_unref (*array_ptr); +- *array_ptr = g_ptr_array_ref (new_array); ++ *array_ptr = new_array; + return TRUE; + } + +@@ -195,9 +197,11 @@ _g_set_array (GArray **array_ptr, GArray *new_array) + { + if (*array_ptr == new_array) + return FALSE; ++ if (new_array != NULL) ++ g_array_ref (new_array); + if (*array_ptr != NULL) + g_array_unref (*array_ptr); +- *array_ptr = g_array_ref (new_array); ++ *array_ptr = new_array; + return TRUE; + } + +-- +GitLab + + +From a9597a3a9c04e5dd4571c24dba54abd95eb9fa92 Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Thu, 29 Apr 2021 15:50:36 +0100 +Subject: [PATCH 5/6] gs-details-page: Explicitly handle empty version history + array +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +This makes the code a bit more robust. + +It’s not actually needed, as the current behaviour of +gs_app_get_version_history() is to either return `NULL` or a non-empty +array — never an empty array. However, guaranteeing that behaviour would +defy precedent in other APIs, and be confusing to document, so just +handle the case of empty arrays in the callers anyway, to make their +expected behaviour clear. + +Signed-off-by: Philip Withnall +--- + src/gs-app-version-history-dialog.c | 2 +- + src/gs-details-page.c | 2 +- + 2 files changed, 2 insertions(+), 2 deletions(-) + +diff --git a/src/gs-app-version-history-dialog.c b/src/gs-app-version-history-dialog.c +index 94d55cc0c..5262596a2 100644 +--- a/src/gs-app-version-history-dialog.c ++++ b/src/gs-app-version-history-dialog.c +@@ -34,7 +34,7 @@ populate_version_history (GsAppVersionHistoryDialog *dialog, + gs_container_remove_all (GTK_CONTAINER (dialog->listbox)); + + version_history = gs_app_get_version_history (app); +- if (version_history == NULL) { ++ if (version_history == NULL || version_history->len == 0) { + GtkWidget *row; + row = gs_app_version_history_row_new (); + gs_app_version_history_row_set_info (GS_APP_VERSION_HISTORY_ROW (row), +diff --git a/src/gs-details-page.c b/src/gs-details-page.c +index cf9b4b393..22b38e929 100644 +--- a/src/gs-details-page.c ++++ b/src/gs-details-page.c +@@ -1305,7 +1305,7 @@ gs_details_page_refresh_all (GsDetailsPage *self) + + /* set version history */ + version_history = gs_app_get_version_history (self->app); +- if (version_history == NULL) { ++ if (version_history == NULL || version_history->len == 0) { + const char *version = gs_app_get_version (self->app); + if (version == NULL || *version == '\0') + gtk_widget_set_visible (self->box_version_history_frame, FALSE); +-- +GitLab + + +From bb1cc3a52fca7e98b053f4c9751df28bfd505dec Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Thu, 29 Apr 2021 15:52:43 +0100 +Subject: [PATCH 6/6] gs-app: Change gs_app_get_version_history() to return a + ref +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +It seems the version history can be updated from a separate thread while +refreshing. This can cause crashes if the UI thread queries the version +history, then it’s updated from another thread, then the UI thread +starts iterating over the `GPtrArray` it queried — which has since been +freed. + +Fix that by returning a strong ref to the `GPtrArray`, and doing so +under the app’s mutex. + +Signed-off-by: Philip Withnall + +Fixes: #1227 +--- + lib/gs-app.c | 11 ++++++++--- + src/gs-app-version-history-dialog.c | 2 +- + src/gs-details-page.c | 2 +- + 3 files changed, 10 insertions(+), 5 deletions(-) + +diff --git a/lib/gs-app.c b/lib/gs-app.c +index efbc4756a..f165df562 100644 +--- a/lib/gs-app.c ++++ b/lib/gs-app.c +@@ -5341,17 +5341,22 @@ gs_app_set_update_permissions (GsApp *app, GsAppPermissions update_permissions) + * Gets the list of past releases for an application (including the latest + * one). + * +- * Returns: (element-type AsRelease) (transfer none) (nullable): a list, or ++ * Returns: (element-type AsRelease) (transfer container) (nullable): a list, or + * %NULL if the version history is not known + * +- * Since: 40 ++ * Since: 41 + **/ + GPtrArray * + gs_app_get_version_history (GsApp *app) + { + GsAppPrivate *priv = gs_app_get_instance_private (app); ++ g_autoptr(GMutexLocker) locker = NULL; + g_return_val_if_fail (GS_IS_APP (app), NULL); +- return priv->version_history; ++ ++ locker = g_mutex_locker_new (&priv->mutex); ++ if (priv->version_history == NULL) ++ return NULL; ++ return g_ptr_array_ref (priv->version_history); + } + + /** +diff --git a/src/gs-app-version-history-dialog.c b/src/gs-app-version-history-dialog.c +index 5262596a2..8b61b7c2b 100644 +--- a/src/gs-app-version-history-dialog.c ++++ b/src/gs-app-version-history-dialog.c +@@ -28,7 +28,7 @@ static void + populate_version_history (GsAppVersionHistoryDialog *dialog, + GsApp *app) + { +- GPtrArray *version_history; ++ g_autoptr(GPtrArray) version_history = NULL; + + /* remove previous */ + gs_container_remove_all (GTK_CONTAINER (dialog->listbox)); +diff --git a/src/gs-details-page.c b/src/gs-details-page.c +index 22b38e929..c985f3b06 100644 +--- a/src/gs-details-page.c ++++ b/src/gs-details-page.c +@@ -1191,7 +1191,7 @@ gs_details_page_refresh_all (GsDetailsPage *self) + guint64 user_integration_bf; + gboolean show_support_box = FALSE; + g_autofree gchar *origin = NULL; +- GPtrArray *version_history; ++ g_autoptr(GPtrArray) version_history = NULL; + guint icon_size; + + if (!gs_page_is_active (GS_PAGE (self))) +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index afd1597..59003bf 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,13 +12,15 @@ Name: gnome-software Version: 40.1 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/40/%{name}-%{tarball_version}.tar.xz +Patch01: 001-i1227-crash-under-gs_details_page_refresh_all.patch + BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc BuildRequires: gettext @@ -200,6 +202,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon May 03 2021 Milan Crha - 40.1-2 +- Add patch for crash under gs_details_page_refresh_all() (i#1227) + * Mon May 03 2021 Milan Crha - 40.1-1 - Update to 40.1 From b59e1f44fc00755f8b8c2652537e585ad56cd9ae Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 4 Jun 2021 10:32:18 +0200 Subject: [PATCH 023/163] Update to 40.2 --- 0001-crash-with-broken-theme.patch | 48 +++ ...sh-under-gs_details_page_refresh_all.patch | 312 ------------------ gnome-software.spec | 9 +- sources | 2 +- 4 files changed, 55 insertions(+), 316 deletions(-) create mode 100644 0001-crash-with-broken-theme.patch delete mode 100644 001-i1227-crash-under-gs_details_page_refresh_all.patch diff --git a/0001-crash-with-broken-theme.patch b/0001-crash-with-broken-theme.patch new file mode 100644 index 0000000..fd37e80 --- /dev/null +++ b/0001-crash-with-broken-theme.patch @@ -0,0 +1,48 @@ +From 3a644c151f27f439c36170f0958fd21cf1cc54d0 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Thu, 3 Jun 2021 08:33:53 +0200 +Subject: [PATCH] gs-feature-tile: Do not abort when the theme is broken + +Just print a warning when the theme doesn't provide 'theme_fg_color' and +fallback to black color. + +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1228 +--- + src/gs-feature-tile.c | 14 +++++++++++--- + 1 file changed, 11 insertions(+), 3 deletions(-) + +diff --git a/src/gs-feature-tile.c b/src/gs-feature-tile.c +index 1c85083eb..158af1e56 100644 +--- a/src/gs-feature-tile.c ++++ b/src/gs-feature-tile.c +@@ -268,7 +268,6 @@ gs_feature_tile_refresh (GsAppTile *self) + if (key_colors != tile->key_colors_cache) { + g_autoptr(GArray) colors = NULL; + GdkRGBA fg_rgba; +- gboolean fg_rgba_valid; + GsHSBC fg_hsbc; + + /* Look up the foreground colour for the feature tile, +@@ -283,8 +282,17 @@ gs_feature_tile_refresh (GsAppTile *self) + * @min_abs_contrast contrast with the foreground, so + * that the text is legible. + */ +- fg_rgba_valid = gtk_style_context_lookup_color (context, "theme_fg_color", &fg_rgba); +- g_assert (fg_rgba_valid); ++ if (!gtk_style_context_lookup_color (context, "theme_fg_color", &fg_rgba)) { ++ static gboolean i_know = FALSE; ++ if (!i_know) { ++ i_know = TRUE; ++ g_warning ("The theme doesn't provide 'theme_fg_color', fallbacking to black"); ++ } ++ fg_rgba.red = 0.0; ++ fg_rgba.green = 0.0; ++ fg_rgba.blue = 0.0; ++ fg_rgba.alpha = 1.0; ++ } + + gtk_rgb_to_hsv (fg_rgba.red, fg_rgba.green, fg_rgba.blue, + &fg_hsbc.hue, &fg_hsbc.saturation, &fg_hsbc.brightness); +-- +GitLab + diff --git a/001-i1227-crash-under-gs_details_page_refresh_all.patch b/001-i1227-crash-under-gs_details_page_refresh_all.patch deleted file mode 100644 index 4fcaaf5..0000000 --- a/001-i1227-crash-under-gs_details_page_refresh_all.patch +++ /dev/null @@ -1,312 +0,0 @@ -From 64a0eaa4a1b1402a0e5926d0c274cfa962589149 Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Thu, 29 Apr 2021 15:49:01 +0100 -Subject: [PATCH 1/6] gs-app: Drop requirement for set_version_history() to be - non-NULL - -Signed-off-by: Philip Withnall ---- - lib/gs-app.c | 1 - - 1 file changed, 1 deletion(-) - -diff --git a/lib/gs-app.c b/lib/gs-app.c -index e8eb9d48b..2db3e6251 100644 ---- a/lib/gs-app.c -+++ b/lib/gs-app.c -@@ -5365,7 +5365,6 @@ gs_app_set_version_history (GsApp *app, GPtrArray *version_history) - GsAppPrivate *priv = gs_app_get_instance_private (app); - g_autoptr(GMutexLocker) locker = NULL; - g_return_if_fail (GS_IS_APP (app)); -- g_return_if_fail (version_history != NULL); - locker = g_mutex_locker_new (&priv->mutex); - _g_set_ptr_array (&priv->version_history, version_history); - } --- -GitLab - - -From 3229d3d66347c5cd317d12db9b456f8eaefad678 Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Thu, 29 Apr 2021 15:45:33 +0100 -Subject: [PATCH 2/6] gs-app: Clarify documentation/annotations for version - history - -This clarifies the documentation for the existing behaviour. - -Signed-off-by: Philip Withnall - -Helps: #1227 ---- - lib/gs-app.c | 9 +++++---- - 1 file changed, 5 insertions(+), 4 deletions(-) - -diff --git a/lib/gs-app.c b/lib/gs-app.c -index 2db3e6251..5ef7e9942 100644 ---- a/lib/gs-app.c -+++ b/lib/gs-app.c -@@ -129,7 +129,7 @@ typedef struct - GsPluginAction pending_action; - GsAppPermissions permissions; - gboolean is_update_downloaded; -- GPtrArray *version_history; /* (element-type AsRelease) */ -+ GPtrArray *version_history; /* (element-type AsRelease) (nullable) (owned) */ - } GsAppPrivate; - - enum { -@@ -5337,7 +5337,8 @@ gs_app_set_update_permissions (GsApp *app, GsAppPermissions update_permissions) - * Gets the list of past releases for an application (including the latest - * one). - * -- * Returns: (element-type AsRelease) (transfer none): a list -+ * Returns: (element-type AsRelease) (transfer none) (nullable): a list, or -+ * %NULL if the version history is not known - * - * Since: 40 - **/ -@@ -5352,8 +5353,8 @@ gs_app_get_version_history (GsApp *app) - /** - * gs_app_set_version_history: - * @app: a #GsApp -- * @version_history: (element-type AsRelease): a set of entries representing -- * the version history -+ * @version_history: (element-type AsRelease) (nullable): a set of entries -+ * representing the version history, or %NULL if none are known - * - * Set the list of past releases for an application (including the latest one). - * --- -GitLab - - -From 7910276e5116db3f51dc5b088f3eb567e2472f17 Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Thu, 29 Apr 2021 15:46:39 +0100 -Subject: [PATCH 3/6] gs-app: Squash empty arrays to NULL in - gs_app_set_version_history() -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -This should save a little bit of memory. I have not updated the -documentation to guarantee this behaviour because it’s a little unusual; -simpler to allow callers to continue handling `NULL` and empty array -cases explicitly. - -Signed-off-by: Philip Withnall - -Helps: #1227 ---- - lib/gs-app.c | 4 ++++ - 1 file changed, 4 insertions(+) - -diff --git a/lib/gs-app.c b/lib/gs-app.c -index 5ef7e9942..6c6bb6fe6 100644 ---- a/lib/gs-app.c -+++ b/lib/gs-app.c -@@ -5366,6 +5366,10 @@ gs_app_set_version_history (GsApp *app, GPtrArray *version_history) - GsAppPrivate *priv = gs_app_get_instance_private (app); - g_autoptr(GMutexLocker) locker = NULL; - g_return_if_fail (GS_IS_APP (app)); -+ -+ if (version_history != NULL && version_history->len == 0) -+ version_history = NULL; -+ - locker = g_mutex_locker_new (&priv->mutex); - _g_set_ptr_array (&priv->version_history, version_history); - } --- -GitLab - - -From ff5d189202788ec84bf690b8ddb184240ae68e2d Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Thu, 29 Apr 2021 15:47:40 +0100 -Subject: [PATCH 4/6] gs-app: Fix generic setters to handle NULL arrays -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -The previous implementation of the functions didn’t handle `NULL` -arrays. - -Signed-off-by: Philip Withnall - -Helps: #1227 ---- - lib/gs-app.c | 8 ++++++-- - 1 file changed, 6 insertions(+), 2 deletions(-) - -diff --git a/lib/gs-app.c b/lib/gs-app.c -index 6c6bb6fe6..efbc4756a 100644 ---- a/lib/gs-app.c -+++ b/lib/gs-app.c -@@ -184,9 +184,11 @@ _g_set_ptr_array (GPtrArray **array_ptr, GPtrArray *new_array) - { - if (*array_ptr == new_array) - return FALSE; -+ if (new_array != NULL) -+ g_ptr_array_ref (new_array); - if (*array_ptr != NULL) - g_ptr_array_unref (*array_ptr); -- *array_ptr = g_ptr_array_ref (new_array); -+ *array_ptr = new_array; - return TRUE; - } - -@@ -195,9 +197,11 @@ _g_set_array (GArray **array_ptr, GArray *new_array) - { - if (*array_ptr == new_array) - return FALSE; -+ if (new_array != NULL) -+ g_array_ref (new_array); - if (*array_ptr != NULL) - g_array_unref (*array_ptr); -- *array_ptr = g_array_ref (new_array); -+ *array_ptr = new_array; - return TRUE; - } - --- -GitLab - - -From a9597a3a9c04e5dd4571c24dba54abd95eb9fa92 Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Thu, 29 Apr 2021 15:50:36 +0100 -Subject: [PATCH 5/6] gs-details-page: Explicitly handle empty version history - array -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -This makes the code a bit more robust. - -It’s not actually needed, as the current behaviour of -gs_app_get_version_history() is to either return `NULL` or a non-empty -array — never an empty array. However, guaranteeing that behaviour would -defy precedent in other APIs, and be confusing to document, so just -handle the case of empty arrays in the callers anyway, to make their -expected behaviour clear. - -Signed-off-by: Philip Withnall ---- - src/gs-app-version-history-dialog.c | 2 +- - src/gs-details-page.c | 2 +- - 2 files changed, 2 insertions(+), 2 deletions(-) - -diff --git a/src/gs-app-version-history-dialog.c b/src/gs-app-version-history-dialog.c -index 94d55cc0c..5262596a2 100644 ---- a/src/gs-app-version-history-dialog.c -+++ b/src/gs-app-version-history-dialog.c -@@ -34,7 +34,7 @@ populate_version_history (GsAppVersionHistoryDialog *dialog, - gs_container_remove_all (GTK_CONTAINER (dialog->listbox)); - - version_history = gs_app_get_version_history (app); -- if (version_history == NULL) { -+ if (version_history == NULL || version_history->len == 0) { - GtkWidget *row; - row = gs_app_version_history_row_new (); - gs_app_version_history_row_set_info (GS_APP_VERSION_HISTORY_ROW (row), -diff --git a/src/gs-details-page.c b/src/gs-details-page.c -index cf9b4b393..22b38e929 100644 ---- a/src/gs-details-page.c -+++ b/src/gs-details-page.c -@@ -1305,7 +1305,7 @@ gs_details_page_refresh_all (GsDetailsPage *self) - - /* set version history */ - version_history = gs_app_get_version_history (self->app); -- if (version_history == NULL) { -+ if (version_history == NULL || version_history->len == 0) { - const char *version = gs_app_get_version (self->app); - if (version == NULL || *version == '\0') - gtk_widget_set_visible (self->box_version_history_frame, FALSE); --- -GitLab - - -From bb1cc3a52fca7e98b053f4c9751df28bfd505dec Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Thu, 29 Apr 2021 15:52:43 +0100 -Subject: [PATCH 6/6] gs-app: Change gs_app_get_version_history() to return a - ref -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -It seems the version history can be updated from a separate thread while -refreshing. This can cause crashes if the UI thread queries the version -history, then it’s updated from another thread, then the UI thread -starts iterating over the `GPtrArray` it queried — which has since been -freed. - -Fix that by returning a strong ref to the `GPtrArray`, and doing so -under the app’s mutex. - -Signed-off-by: Philip Withnall - -Fixes: #1227 ---- - lib/gs-app.c | 11 ++++++++--- - src/gs-app-version-history-dialog.c | 2 +- - src/gs-details-page.c | 2 +- - 3 files changed, 10 insertions(+), 5 deletions(-) - -diff --git a/lib/gs-app.c b/lib/gs-app.c -index efbc4756a..f165df562 100644 ---- a/lib/gs-app.c -+++ b/lib/gs-app.c -@@ -5341,17 +5341,22 @@ gs_app_set_update_permissions (GsApp *app, GsAppPermissions update_permissions) - * Gets the list of past releases for an application (including the latest - * one). - * -- * Returns: (element-type AsRelease) (transfer none) (nullable): a list, or -+ * Returns: (element-type AsRelease) (transfer container) (nullable): a list, or - * %NULL if the version history is not known - * -- * Since: 40 -+ * Since: 41 - **/ - GPtrArray * - gs_app_get_version_history (GsApp *app) - { - GsAppPrivate *priv = gs_app_get_instance_private (app); -+ g_autoptr(GMutexLocker) locker = NULL; - g_return_val_if_fail (GS_IS_APP (app), NULL); -- return priv->version_history; -+ -+ locker = g_mutex_locker_new (&priv->mutex); -+ if (priv->version_history == NULL) -+ return NULL; -+ return g_ptr_array_ref (priv->version_history); - } - - /** -diff --git a/src/gs-app-version-history-dialog.c b/src/gs-app-version-history-dialog.c -index 5262596a2..8b61b7c2b 100644 ---- a/src/gs-app-version-history-dialog.c -+++ b/src/gs-app-version-history-dialog.c -@@ -28,7 +28,7 @@ static void - populate_version_history (GsAppVersionHistoryDialog *dialog, - GsApp *app) - { -- GPtrArray *version_history; -+ g_autoptr(GPtrArray) version_history = NULL; - - /* remove previous */ - gs_container_remove_all (GTK_CONTAINER (dialog->listbox)); -diff --git a/src/gs-details-page.c b/src/gs-details-page.c -index 22b38e929..c985f3b06 100644 ---- a/src/gs-details-page.c -+++ b/src/gs-details-page.c -@@ -1191,7 +1191,7 @@ gs_details_page_refresh_all (GsDetailsPage *self) - guint64 user_integration_bf; - gboolean show_support_box = FALSE; - g_autofree gchar *origin = NULL; -- GPtrArray *version_history; -+ g_autoptr(GPtrArray) version_history = NULL; - guint icon_size; - - if (!gs_page_is_active (GS_PAGE (self))) --- -GitLab - diff --git a/gnome-software.spec b/gnome-software.spec index 59003bf..347fd29 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,15 +11,15 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 40.1 -Release: 2%{?dist} +Version: 40.2 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/40/%{name}-%{tarball_version}.tar.xz -Patch01: 001-i1227-crash-under-gs_details_page_refresh_all.patch +Patch01: 0001-crash-with-broken-theme.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -202,6 +202,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri Jun 04 2021 Milan Crha - 40.2-1 +- Update to 40.2 + * Mon May 03 2021 Milan Crha - 40.1-2 - Add patch for crash under gs_details_page_refresh_all() (i#1227) diff --git a/sources b/sources index 2342259..e57a641 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-40.1.tar.xz) = ae805d01896d761dd82a21dedbfafba7e8ffd2d98e99da4548d846aafdf07f9a26dfa2e083ac2dda576f8b1db05bb3f26642d3a6558da86921450049870767fe +SHA512 (gnome-software-40.2.tar.xz) = ded29be4c59130a4016d43d3e18a67c8cf3fec4761a7a57c067bf075a6f1da5b7726000172e2303ba129b3b5cb8bd22ebfad8fbf0e3248285a4864350f3a1679 From 0f8fa871373dcae9c702b7f41d80cc4682c27edc Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Wed, 23 Jun 2021 09:15:51 +0200 Subject: [PATCH 024/163] Add patch to automatically install application updates (i#1248) --- ...atically_install_application_updates.patch | 89 +++++++++++++++++++ gnome-software.spec | 6 +- 2 files changed, 94 insertions(+), 1 deletion(-) create mode 100644 0002-gs-update-monitor_automatically_install_application_updates.patch diff --git a/0002-gs-update-monitor_automatically_install_application_updates.patch b/0002-gs-update-monitor_automatically_install_application_updates.patch new file mode 100644 index 0000000..aa98d80 --- /dev/null +++ b/0002-gs-update-monitor_automatically_install_application_updates.patch @@ -0,0 +1,89 @@ +From 69ba099e9d49979a6dacdcd879d98f72744d298a Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 11 May 2021 11:13:52 +0200 +Subject: [PATCH] gs-update-monitor: Automatically install application updates + +The application updates, so called online updates, should be installed immediately +when found, when the user has enabled automatic updates. + +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1248 +--- + src/gs-update-monitor.c | 47 +++++++++++++++++++++++++++++++++++++++-- + 1 file changed, 45 insertions(+), 2 deletions(-) + +diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c +index b3209185d..234c7de95 100644 +--- a/src/gs-update-monitor.c ++++ b/src/gs-update-monitor.c +@@ -475,6 +475,7 @@ get_updates_finished_cb (GObject *object, GAsyncResult *res, gpointer data) + guint64 security_timestamp_old = 0; + g_autoptr(GError) error = NULL; + g_autoptr(GsAppList) apps = NULL; ++ gboolean should_download; + + /* get result */ + apps = gs_plugin_loader_job_process_finish (GS_PLUGIN_LOADER (object), res, &error); +@@ -509,7 +510,9 @@ get_updates_finished_cb (GObject *object, GAsyncResult *res, gpointer data) + + g_debug ("got %u updates", gs_app_list_length (apps)); + +- if (should_download_updates (monitor) && ++ should_download = should_download_updates (monitor); ++ ++ if (should_download && + (security_timestamp_old != security_timestamp || + check_if_timestamp_more_than_days_ago (monitor, "install-timestamp", 14))) { + g_autoptr(GsPluginJob) plugin_job = NULL; +@@ -528,8 +531,48 @@ get_updates_finished_cb (GObject *object, GAsyncResult *res, gpointer data) + download_finished_cb, + monitor); + } else { +- notify_about_pending_updates (monitor, apps); ++ g_autoptr(GsAppList) update_online = NULL; ++ g_autoptr(GsAppList) update_offline = NULL; ++ GsAppList *notify_list; ++ ++ update_online = gs_app_list_new (); ++ update_offline = gs_app_list_new (); ++ for (guint i = 0; i < gs_app_list_length (apps); i++) { ++ GsApp *app = gs_app_list_index (apps, i); ++ if (_should_auto_update (app)) { ++ g_debug ("download for auto-update %s", gs_app_get_unique_id (app)); ++ gs_app_list_add (update_online, app); ++ } else { ++ gs_app_list_add (update_offline, app); ++ } ++ } ++ ++ g_debug ("Received %u apps to update, %u are online and %u offline updates; will%s download online updates", ++ gs_app_list_length (apps), ++ gs_app_list_length (update_online), ++ gs_app_list_length (update_offline), ++ should_download ? "" : " not"); ++ ++ if (should_download && gs_app_list_length (update_online) > 0) { ++ g_autoptr(GsPluginJob) plugin_job = NULL; ++ ++ plugin_job = gs_plugin_job_newv (GS_PLUGIN_ACTION_DOWNLOAD, ++ "list", update_online, ++ NULL); ++ g_debug ("Getting %u online updates", gs_app_list_length (update_online)); ++ gs_plugin_loader_job_process_async (monitor->plugin_loader, ++ plugin_job, ++ monitor->cancellable, ++ download_finished_cb, ++ monitor); ++ } ++ ++ if (should_download) ++ notify_list = update_offline; ++ else ++ notify_list = apps; + ++ notify_about_pending_updates (monitor, notify_list); + reset_update_notification_timestamp (monitor); + } + } +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index 347fd29..9b1865d 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 40.2 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -20,6 +20,7 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/40/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +Patch02: 0002-gs-update-monitor_automatically_install_application_updates.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -202,6 +203,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Wed Jun 23 2021 Milan Crha - 40.2-2 +- Add patch to automatically install application updates (i#1248) + * Fri Jun 04 2021 Milan Crha - 40.2-1 - Update to 40.2 From ad5b2dba08c2908b36d638254062757f7a15d0fc Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 12 Jul 2021 11:52:52 +0200 Subject: [PATCH 025/163] Update to 40.3 --- ...atically_install_application_updates.patch | 89 ------------------- gnome-software.spec | 8 +- sources | 2 +- 3 files changed, 6 insertions(+), 93 deletions(-) delete mode 100644 0002-gs-update-monitor_automatically_install_application_updates.patch diff --git a/0002-gs-update-monitor_automatically_install_application_updates.patch b/0002-gs-update-monitor_automatically_install_application_updates.patch deleted file mode 100644 index aa98d80..0000000 --- a/0002-gs-update-monitor_automatically_install_application_updates.patch +++ /dev/null @@ -1,89 +0,0 @@ -From 69ba099e9d49979a6dacdcd879d98f72744d298a Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 11 May 2021 11:13:52 +0200 -Subject: [PATCH] gs-update-monitor: Automatically install application updates - -The application updates, so called online updates, should be installed immediately -when found, when the user has enabled automatic updates. - -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1248 ---- - src/gs-update-monitor.c | 47 +++++++++++++++++++++++++++++++++++++++-- - 1 file changed, 45 insertions(+), 2 deletions(-) - -diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c -index b3209185d..234c7de95 100644 ---- a/src/gs-update-monitor.c -+++ b/src/gs-update-monitor.c -@@ -475,6 +475,7 @@ get_updates_finished_cb (GObject *object, GAsyncResult *res, gpointer data) - guint64 security_timestamp_old = 0; - g_autoptr(GError) error = NULL; - g_autoptr(GsAppList) apps = NULL; -+ gboolean should_download; - - /* get result */ - apps = gs_plugin_loader_job_process_finish (GS_PLUGIN_LOADER (object), res, &error); -@@ -509,7 +510,9 @@ get_updates_finished_cb (GObject *object, GAsyncResult *res, gpointer data) - - g_debug ("got %u updates", gs_app_list_length (apps)); - -- if (should_download_updates (monitor) && -+ should_download = should_download_updates (monitor); -+ -+ if (should_download && - (security_timestamp_old != security_timestamp || - check_if_timestamp_more_than_days_ago (monitor, "install-timestamp", 14))) { - g_autoptr(GsPluginJob) plugin_job = NULL; -@@ -528,8 +531,48 @@ get_updates_finished_cb (GObject *object, GAsyncResult *res, gpointer data) - download_finished_cb, - monitor); - } else { -- notify_about_pending_updates (monitor, apps); -+ g_autoptr(GsAppList) update_online = NULL; -+ g_autoptr(GsAppList) update_offline = NULL; -+ GsAppList *notify_list; -+ -+ update_online = gs_app_list_new (); -+ update_offline = gs_app_list_new (); -+ for (guint i = 0; i < gs_app_list_length (apps); i++) { -+ GsApp *app = gs_app_list_index (apps, i); -+ if (_should_auto_update (app)) { -+ g_debug ("download for auto-update %s", gs_app_get_unique_id (app)); -+ gs_app_list_add (update_online, app); -+ } else { -+ gs_app_list_add (update_offline, app); -+ } -+ } -+ -+ g_debug ("Received %u apps to update, %u are online and %u offline updates; will%s download online updates", -+ gs_app_list_length (apps), -+ gs_app_list_length (update_online), -+ gs_app_list_length (update_offline), -+ should_download ? "" : " not"); -+ -+ if (should_download && gs_app_list_length (update_online) > 0) { -+ g_autoptr(GsPluginJob) plugin_job = NULL; -+ -+ plugin_job = gs_plugin_job_newv (GS_PLUGIN_ACTION_DOWNLOAD, -+ "list", update_online, -+ NULL); -+ g_debug ("Getting %u online updates", gs_app_list_length (update_online)); -+ gs_plugin_loader_job_process_async (monitor->plugin_loader, -+ plugin_job, -+ monitor->cancellable, -+ download_finished_cb, -+ monitor); -+ } -+ -+ if (should_download) -+ notify_list = update_offline; -+ else -+ notify_list = apps; - -+ notify_about_pending_updates (monitor, notify_list); - reset_update_notification_timestamp (monitor); - } - } --- -GitLab - diff --git a/gnome-software.spec b/gnome-software.spec index 9b1865d..dd54a25 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,8 +11,8 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 40.2 -Release: 2%{?dist} +Version: 40.3 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -20,7 +20,6 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/40/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -Patch02: 0002-gs-update-monitor_automatically_install_application_updates.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -203,6 +202,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Jul 12 2021 Milan Crha - 40.3-1 +- Update to 40.3 + * Wed Jun 23 2021 Milan Crha - 40.2-2 - Add patch to automatically install application updates (i#1248) diff --git a/sources b/sources index e57a641..028dcb3 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-40.2.tar.xz) = ded29be4c59130a4016d43d3e18a67c8cf3fec4761a7a57c067bf075a6f1da5b7726000172e2303ba129b3b5cb8bd22ebfad8fbf0e3248285a4864350f3a1679 +SHA512 (gnome-software-40.3.tar.xz) = 6070f8f59fa9872282a081b6ba4f740616a799cffae43a8a541ebf4e0d7b189710dbdce679b1e5136a3fff5f8da29ec8e1ed9df7289c0a6ed697eb0ad693271f From ac5db513229f1c415c2f352135a3acd9cc69dc65 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 12 Jul 2021 18:32:34 +0200 Subject: [PATCH 026/163] Add rpm-ostree patch to hide packages from the search results; Add patch to implement what-provides search in the Flatpak plugin --- ...e-Hide-only-Web-and-Console-applicat.patch | 29 ++++++++ ...t-gs_plugin_add_search_what_provides.patch | 72 +++++++++++++++++++ gnome-software.spec | 8 ++- 3 files changed, 108 insertions(+), 1 deletion(-) create mode 100644 0002-Revert-rpm-ostree-Hide-only-Web-and-Console-applicat.patch create mode 100644 0003-flatpak-Implement-gs_plugin_add_search_what_provides.patch diff --git a/0002-Revert-rpm-ostree-Hide-only-Web-and-Console-applicat.patch b/0002-Revert-rpm-ostree-Hide-only-Web-and-Console-applicat.patch new file mode 100644 index 0000000..bcec2fd --- /dev/null +++ b/0002-Revert-rpm-ostree-Hide-only-Web-and-Console-applicat.patch @@ -0,0 +1,29 @@ +From 7667bb916408b61c4630837d4483be266bf6a799 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Mon, 12 Jul 2021 14:54:26 +0200 +Subject: [PATCH 1/2] Revert "rpm-ostree: Hide only Web and Console + applications from the search" + +This reverts commit ef67695cb2e20f0cb1cfcd8965173226dd755b09. + +The correct fix for https://gitlab.gnome.org/GNOME/gnome-software/-/issues/613 +is https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1210 +--- + plugins/rpm-ostree/gs-plugin-rpm-ostree.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +index 6b1a1351..541b59f8 100644 +--- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c ++++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +@@ -1598,6 +1598,7 @@ resolve_available_packages_app (GsPlugin *plugin, + /* set hide-from-search quirk for available apps we don't want to show */ + if (!gs_app_is_installed (app)) { + switch (gs_app_get_kind (app)) { ++ case AS_COMPONENT_KIND_DESKTOP_APP: + case AS_COMPONENT_KIND_WEB_APP: + case AS_COMPONENT_KIND_CONSOLE_APP: + gs_app_add_quirk (app, GS_APP_QUIRK_HIDE_FROM_SEARCH); +-- +2.31.1 + diff --git a/0003-flatpak-Implement-gs_plugin_add_search_what_provides.patch b/0003-flatpak-Implement-gs_plugin_add_search_what_provides.patch new file mode 100644 index 0000000..d0b0e8d --- /dev/null +++ b/0003-flatpak-Implement-gs_plugin_add_search_what_provides.patch @@ -0,0 +1,72 @@ +From f148ef7e91716bf6cac069eb61f0ecb370507dc9 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Thu, 15 Apr 2021 18:49:08 +0200 +Subject: [PATCH 2/2] flatpak: Implement gs_plugin_add_search_what_provides() + +Let the Flatpak plugin search for "what provides" as well. It's the same +search, due to the appstream search terms, and it gets more results to +pick from. + +Related https://gitlab.gnome.org/GNOME/gnome-software/-/issues/613 +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1210 +--- + plugins/flatpak/gs-plugin-flatpak.c | 33 +++++++++++++++++++++++------ + 1 file changed, 27 insertions(+), 6 deletions(-) + +diff --git a/plugins/flatpak/gs-plugin-flatpak.c b/plugins/flatpak/gs-plugin-flatpak.c +index 364bc27d..808e1a56 100644 +--- a/plugins/flatpak/gs-plugin-flatpak.c ++++ b/plugins/flatpak/gs-plugin-flatpak.c +@@ -1444,12 +1444,12 @@ gs_plugin_file_to_app (GsPlugin *plugin, + return TRUE; + } + +-gboolean +-gs_plugin_add_search (GsPlugin *plugin, +- gchar **values, +- GsAppList *list, +- GCancellable *cancellable, +- GError **error) ++static gboolean ++gs_plugin_flatpak_do_search (GsPlugin *plugin, ++ gchar **values, ++ GsAppList *list, ++ GCancellable *cancellable, ++ GError **error) + { + GsPluginData *priv = gs_plugin_get_data (plugin); + for (guint i = 0; i < priv->flatpaks->len; i++) { +@@ -1459,9 +1459,30 @@ gs_plugin_add_search (GsPlugin *plugin, + return FALSE; + } + } ++ + return TRUE; + } + ++gboolean ++gs_plugin_add_search (GsPlugin *plugin, ++ gchar **values, ++ GsAppList *list, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ return gs_plugin_flatpak_do_search (plugin, values, list, cancellable, error); ++} ++ ++gboolean ++gs_plugin_add_search_what_provides (GsPlugin *plugin, ++ gchar **search, ++ GsAppList *list, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ return gs_plugin_flatpak_do_search (plugin, search, list, cancellable, error); ++} ++ + gboolean + gs_plugin_add_categories (GsPlugin *plugin, + GPtrArray *list, +-- +2.31.1 + diff --git a/gnome-software.spec b/gnome-software.spec index dd54a25..36737c2 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 40.3 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -20,6 +20,8 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/40/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +Patch02: 0002-Revert-rpm-ostree-Hide-only-Web-and-Console-applicat.patch +Patch03: 0003-flatpak-Implement-gs_plugin_add_search_what_provides.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -202,6 +204,10 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Jul 12 2021 Milan Crha - 40.3-2 +- Add rpm-ostree patch to hide packages from the search results +- Add patch to implement what-provides search in the Flatpak plugin + * Mon Jul 12 2021 Milan Crha - 40.3-1 - Update to 40.3 From c71ea6160d990899e449ccc22ad2253c016e7165 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Wed, 21 Jul 2021 14:16:09 +0200 Subject: [PATCH 027/163] Update to 41.alpha --- ...e-Hide-only-Web-and-Console-applicat.patch | 29 -------- ...t-gs_plugin_add_search_what_provides.patch | 72 ------------------- gnome-software.spec | 24 +++---- sources | 2 +- 4 files changed, 10 insertions(+), 117 deletions(-) delete mode 100644 0002-Revert-rpm-ostree-Hide-only-Web-and-Console-applicat.patch delete mode 100644 0003-flatpak-Implement-gs_plugin_add_search_what_provides.patch diff --git a/0002-Revert-rpm-ostree-Hide-only-Web-and-Console-applicat.patch b/0002-Revert-rpm-ostree-Hide-only-Web-and-Console-applicat.patch deleted file mode 100644 index bcec2fd..0000000 --- a/0002-Revert-rpm-ostree-Hide-only-Web-and-Console-applicat.patch +++ /dev/null @@ -1,29 +0,0 @@ -From 7667bb916408b61c4630837d4483be266bf6a799 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Mon, 12 Jul 2021 14:54:26 +0200 -Subject: [PATCH 1/2] Revert "rpm-ostree: Hide only Web and Console - applications from the search" - -This reverts commit ef67695cb2e20f0cb1cfcd8965173226dd755b09. - -The correct fix for https://gitlab.gnome.org/GNOME/gnome-software/-/issues/613 -is https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1210 ---- - plugins/rpm-ostree/gs-plugin-rpm-ostree.c | 1 + - 1 file changed, 1 insertion(+) - -diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -index 6b1a1351..541b59f8 100644 ---- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -+++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -@@ -1598,6 +1598,7 @@ resolve_available_packages_app (GsPlugin *plugin, - /* set hide-from-search quirk for available apps we don't want to show */ - if (!gs_app_is_installed (app)) { - switch (gs_app_get_kind (app)) { -+ case AS_COMPONENT_KIND_DESKTOP_APP: - case AS_COMPONENT_KIND_WEB_APP: - case AS_COMPONENT_KIND_CONSOLE_APP: - gs_app_add_quirk (app, GS_APP_QUIRK_HIDE_FROM_SEARCH); --- -2.31.1 - diff --git a/0003-flatpak-Implement-gs_plugin_add_search_what_provides.patch b/0003-flatpak-Implement-gs_plugin_add_search_what_provides.patch deleted file mode 100644 index d0b0e8d..0000000 --- a/0003-flatpak-Implement-gs_plugin_add_search_what_provides.patch +++ /dev/null @@ -1,72 +0,0 @@ -From f148ef7e91716bf6cac069eb61f0ecb370507dc9 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Thu, 15 Apr 2021 18:49:08 +0200 -Subject: [PATCH 2/2] flatpak: Implement gs_plugin_add_search_what_provides() - -Let the Flatpak plugin search for "what provides" as well. It's the same -search, due to the appstream search terms, and it gets more results to -pick from. - -Related https://gitlab.gnome.org/GNOME/gnome-software/-/issues/613 -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1210 ---- - plugins/flatpak/gs-plugin-flatpak.c | 33 +++++++++++++++++++++++------ - 1 file changed, 27 insertions(+), 6 deletions(-) - -diff --git a/plugins/flatpak/gs-plugin-flatpak.c b/plugins/flatpak/gs-plugin-flatpak.c -index 364bc27d..808e1a56 100644 ---- a/plugins/flatpak/gs-plugin-flatpak.c -+++ b/plugins/flatpak/gs-plugin-flatpak.c -@@ -1444,12 +1444,12 @@ gs_plugin_file_to_app (GsPlugin *plugin, - return TRUE; - } - --gboolean --gs_plugin_add_search (GsPlugin *plugin, -- gchar **values, -- GsAppList *list, -- GCancellable *cancellable, -- GError **error) -+static gboolean -+gs_plugin_flatpak_do_search (GsPlugin *plugin, -+ gchar **values, -+ GsAppList *list, -+ GCancellable *cancellable, -+ GError **error) - { - GsPluginData *priv = gs_plugin_get_data (plugin); - for (guint i = 0; i < priv->flatpaks->len; i++) { -@@ -1459,9 +1459,30 @@ gs_plugin_add_search (GsPlugin *plugin, - return FALSE; - } - } -+ - return TRUE; - } - -+gboolean -+gs_plugin_add_search (GsPlugin *plugin, -+ gchar **values, -+ GsAppList *list, -+ GCancellable *cancellable, -+ GError **error) -+{ -+ return gs_plugin_flatpak_do_search (plugin, values, list, cancellable, error); -+} -+ -+gboolean -+gs_plugin_add_search_what_provides (GsPlugin *plugin, -+ gchar **search, -+ GsAppList *list, -+ GCancellable *cancellable, -+ GError **error) -+{ -+ return gs_plugin_flatpak_do_search (plugin, search, list, cancellable, error); -+} -+ - gboolean - gs_plugin_add_categories (GsPlugin *plugin, - GPtrArray *list, --- -2.31.1 - diff --git a/gnome-software.spec b/gnome-software.spec index 36737c2..1203aff 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,17 +11,15 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 40.3 -Release: 2%{?dist} +Version: 41~alpha +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software -Source0: https://download.gnome.org/sources/gnome-software/40/%{name}-%{tarball_version}.tar.xz +Source0: https://download.gnome.org/sources/gnome-software/41/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -Patch02: 0002-Revert-rpm-ostree-Hide-only-Web-and-Console-applicat.patch -Patch03: 0003-flatpak-Implement-gs_plugin_add_search_what_provides.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -147,15 +145,15 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_mandir}/man1/gnome-software.1.gz %{_datadir}/icons/hicolor/*/apps/org.gnome.Software.svg %{_datadir}/icons/hicolor/symbolic/apps/org.gnome.Software-symbolic.svg +%{_datadir}/icons/hicolor/scalable/actions/app-remove-symbolic.svg %{_datadir}/icons/hicolor/scalable/actions/carousel-arrow-next-symbolic.svg %{_datadir}/icons/hicolor/scalable/actions/carousel-arrow-previous-symbolic.svg %{_datadir}/icons/hicolor/scalable/status/software-installed-symbolic.svg %{_datadir}/metainfo/org.gnome.Software.appdata.xml %{_datadir}/metainfo/org.gnome.Software.Plugin.Flatpak.metainfo.xml %{_datadir}/metainfo/org.gnome.Software.Plugin.Fwupd.metainfo.xml -%{_datadir}/metainfo/org.gnome.Software.Plugin.Odrs.metainfo.xml %dir %{_libdir}/gnome-software/plugins-%{gs_plugin_version} -%{_libdir}/gnome-software/libgnomesoftware.so +%{_libdir}/gnome-software/libgnomesoftware.so.%{gs_plugin_version} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_appstream.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dummy.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so @@ -167,17 +165,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-popular.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_icons.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_modalias.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_odrs.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_os-release.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-history.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-local.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-offline.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-proxy.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refine-repos.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refine.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refresh.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-upgrade.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-url-to-app.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance-license.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance.so @@ -201,9 +191,13 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/pkgconfig/gnome-software.pc %dir %{_includedir}/gnome-software %{_includedir}/gnome-software/*.h +%{_libdir}/gnome-software/libgnomesoftware.so %{_datadir}/gtk-doc/html/gnome-software %changelog +* Wed Jul 21 2021 Milan Crha - 41~alpha-1 +- Update to 41.alpha + * Mon Jul 12 2021 Milan Crha - 40.3-2 - Add rpm-ostree patch to hide packages from the search results - Add patch to implement what-provides search in the Flatpak plugin diff --git a/sources b/sources index 028dcb3..57f1785 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-40.3.tar.xz) = 6070f8f59fa9872282a081b6ba4f740616a799cffae43a8a541ebf4e0d7b189710dbdce679b1e5136a3fff5f8da29ec8e1ed9df7289c0a6ed697eb0ad693271f +SHA512 (gnome-software-41.alpha.tar.xz) = 2919e4d33c9a750ddbfb18834e1199a3162c9a8d0f0ddcb2bd95dfcdbe44712438c23c2648386a4f639c576589073184a1848a2155b4f31fc36616577d828a64 From 2d741fb23bedd9288e670fe7b6a9722ac8f9a120 Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Thu, 22 Jul 2021 02:22:23 +0000 Subject: [PATCH 028/163] - Rebuilt for https://fedoraproject.org/wiki/Fedora_35_Mass_Rebuild Signed-off-by: Fedora Release Engineering --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 1203aff..f179695 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 41~alpha -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -195,6 +195,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Thu Jul 22 2021 Fedora Release Engineering - 41~alpha-2 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_35_Mass_Rebuild + * Wed Jul 21 2021 Milan Crha - 41~alpha-1 - Update to 41.alpha From 6818c689ad62b605f445280baface87c448537fb Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 13 Aug 2021 18:20:57 +0200 Subject: [PATCH 029/163] Update to 41.beta --- gnome-software.spec | 7 +++++-- sources | 2 +- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index f179695..53c1719 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,8 +11,8 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 41~alpha -Release: 2%{?dist} +Version: 41~beta +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -195,6 +195,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri Aug 13 2021 Milan Crha - 41~beta-1 +- Update to 41.beta + * Thu Jul 22 2021 Fedora Release Engineering - 41~alpha-2 - Rebuilt for https://fedoraproject.org/wiki/Fedora_35_Mass_Rebuild diff --git a/sources b/sources index 57f1785..242d155 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-41.alpha.tar.xz) = 2919e4d33c9a750ddbfb18834e1199a3162c9a8d0f0ddcb2bd95dfcdbe44712438c23c2648386a4f639c576589073184a1848a2155b4f31fc36616577d828a64 +SHA512 (gnome-software-41.beta.tar.xz) = 8d552f508a74c19ed11ae465b901e8b9bda479bff8b9f582b65bbacdba6d91468e4a9676a85f54104d16ba061f0e5daff7a0000aec439e6c4ff2b22cc3a8ecd1 From 94b79ff8862694fe12bfcfe7f707169eb4105ec2 Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Tue, 24 Aug 2021 19:18:00 +0200 Subject: [PATCH 030/163] Enable parental controls support https://pagure.io/fedora-workstation/issue/186 --- gnome-software.spec | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 53c1719..64181c8 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 41~beta -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -39,6 +39,8 @@ BuildRequires: libdnf-devel BuildRequires: libhandy1-devel BuildRequires: libsoup-devel BuildRequires: libxmlb-devel >= %{libxmlb_version} +BuildRequires: malcontent-devel +BuildRequires: malcontent-ui-devel BuildRequires: meson BuildRequires: PackageKit-glib-devel >= %{packagekit_version} BuildRequires: polkit-devel @@ -105,7 +107,7 @@ This package includes the rpm-ostree backend. %build %meson \ -Dsnap=false \ - -Dmalcontent=false \ + -Dmalcontent=true \ -Dgudev=true \ -Dpackagekit=true \ -Dexternal_appstream=false \ @@ -164,6 +166,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-blocklist.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-popular.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_icons.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_malcontent.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_modalias.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_os-release.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refine-repos.so @@ -195,6 +198,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Tue Aug 24 2021 Kalev Lember - 41~beta-2 +- Enable parental controls support + * Fri Aug 13 2021 Milan Crha - 41~beta-1 - Update to 41.beta From 4ba65e69d0b643c1984d1ad0405f8adfb9b38d68 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Wed, 1 Sep 2021 21:10:08 +0200 Subject: [PATCH 031/163] Resolves: #1995817 (gs-updates-section: Check also dependencies' download size) --- gnome-software.spec | 6 +++++- rhbug1995817-fix-updates-page-button.patch | 14 ++++++++++++++ 2 files changed, 19 insertions(+), 1 deletion(-) create mode 100644 rhbug1995817-fix-updates-page-button.patch diff --git a/gnome-software.spec b/gnome-software.spec index 64181c8..58b6ccf 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 41~beta -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -20,6 +20,7 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/41/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +Patch02: rhbug1995817-fix-updates-page-button.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -198,6 +199,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Wed Sep 01 2021 Milan Crha - 41~beta-3 +- Resolves: #1995817 (gs-updates-section: Check also dependencies' download size) + * Tue Aug 24 2021 Kalev Lember - 41~beta-2 - Enable parental controls support diff --git a/rhbug1995817-fix-updates-page-button.patch b/rhbug1995817-fix-updates-page-button.patch new file mode 100644 index 0000000..b89b549 --- /dev/null +++ b/rhbug1995817-fix-updates-page-button.patch @@ -0,0 +1,14 @@ +diff --git a/src/gs-updates-section.c b/src/gs-updates-section.c +index 0f41ba66..fa050513 100644 +--- a/src/gs-updates-section.c ++++ b/src/gs-updates-section.c +@@ -293,6 +293,9 @@ _all_offline_updates_downloaded (GsUpdatesSection *self) + guint64 size = gs_app_get_size_download (app); + if (size != 0) + return FALSE; ++ size = gs_app_get_size_download_dependencies (app); ++ if (size != 0) ++ return FALSE; + } + + return TRUE; From 4f4ac53d683ca82be006f1bfc0c6117cd3040c96 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Wed, 8 Sep 2021 09:10:47 +0200 Subject: [PATCH 032/163] Update to 41.rc --- gnome-software.spec | 8 +++++--- rhbug1995817-fix-updates-page-button.patch | 14 -------------- sources | 2 +- 3 files changed, 6 insertions(+), 18 deletions(-) delete mode 100644 rhbug1995817-fix-updates-page-button.patch diff --git a/gnome-software.spec b/gnome-software.spec index 58b6ccf..f705316 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,8 +11,8 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 41~beta -Release: 3%{?dist} +Version: 41~rc +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -20,7 +20,6 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/41/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -Patch02: rhbug1995817-fix-updates-page-button.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -199,6 +198,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Wed Sep 08 2021 Milan Crha - 41~rc-1 +- Update to 41.rc + * Wed Sep 01 2021 Milan Crha - 41~beta-3 - Resolves: #1995817 (gs-updates-section: Check also dependencies' download size) diff --git a/rhbug1995817-fix-updates-page-button.patch b/rhbug1995817-fix-updates-page-button.patch deleted file mode 100644 index b89b549..0000000 --- a/rhbug1995817-fix-updates-page-button.patch +++ /dev/null @@ -1,14 +0,0 @@ -diff --git a/src/gs-updates-section.c b/src/gs-updates-section.c -index 0f41ba66..fa050513 100644 ---- a/src/gs-updates-section.c -+++ b/src/gs-updates-section.c -@@ -293,6 +293,9 @@ _all_offline_updates_downloaded (GsUpdatesSection *self) - guint64 size = gs_app_get_size_download (app); - if (size != 0) - return FALSE; -+ size = gs_app_get_size_download_dependencies (app); -+ if (size != 0) -+ return FALSE; - } - - return TRUE; diff --git a/sources b/sources index 242d155..6ff6324 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-41.beta.tar.xz) = 8d552f508a74c19ed11ae465b901e8b9bda479bff8b9f582b65bbacdba6d91468e4a9676a85f54104d16ba061f0e5daff7a0000aec439e6c4ff2b22cc3a8ecd1 +SHA512 (gnome-software-41.rc.tar.xz) = 6aec9a0ffc4957a62f8a25a4ba50b8f7539a701af8813f37310e6372c16b7c9c43ba5d97df05f202339eded5eb45c53bb9480727cfb3053d86ed16e20827cd23 From 95dd5f06f66e80223432fcc9e0c7363ac27e05d2 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 13 Sep 2021 15:13:00 +0200 Subject: [PATCH 033/163] Resolves: #2003365 (packagekit: Ensure PkClient::interactive flag being set) --- ...e-PkClient-interactive-flag-being-se.patch | 116 ++++++++++++++++++ gnome-software.spec | 6 +- 2 files changed, 121 insertions(+), 1 deletion(-) create mode 100644 0002-packagekit-Ensure-PkClient-interactive-flag-being-se.patch diff --git a/0002-packagekit-Ensure-PkClient-interactive-flag-being-se.patch b/0002-packagekit-Ensure-PkClient-interactive-flag-being-se.patch new file mode 100644 index 0000000..67e1d8e --- /dev/null +++ b/0002-packagekit-Ensure-PkClient-interactive-flag-being-se.patch @@ -0,0 +1,116 @@ +From 50ea9e8e6c4c3c23607b1ea9cc56e5e1b15c9e42 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Mon, 13 Sep 2021 15:02:37 +0200 +Subject: [PATCH] packagekit: Ensure PkClient::interactive flag being set + +That's required to properly ask or not ask for the root credentials on operations, +which require higher privileges. It's important to set the flag always before the call +to the PkTask/PkClient API, because other thread could change the value while +the corresponding lock was released by the execution thread. + +Downstream bug report: +https://bugzilla.redhat.com/show_bug.cgi?id=2003365 +--- + plugins/packagekit/gs-plugin-packagekit-refresh.c | 1 + + plugins/packagekit/gs-plugin-packagekit.c | 10 ++++++++++ + 2 files changed, 11 insertions(+) + +diff --git a/plugins/packagekit/gs-plugin-packagekit-refresh.c b/plugins/packagekit/gs-plugin-packagekit-refresh.c +index 338cc387..ef06bcd2 100644 +--- a/plugins/packagekit/gs-plugin-packagekit-refresh.c ++++ b/plugins/packagekit/gs-plugin-packagekit-refresh.c +@@ -94,6 +94,7 @@ _download_only (GsPlugin *plugin, GsAppList *list, + * we end up downloading a different set of packages than what was + * shown to the user */ + pk_client_set_cache_age (PK_CLIENT (priv->task), G_MAXUINT); ++ pk_client_set_interactive (PK_CLIENT (priv->task), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); + results2 = pk_task_update_packages_sync (priv->task, + package_ids, + cancellable, +diff --git a/plugins/packagekit/gs-plugin-packagekit.c b/plugins/packagekit/gs-plugin-packagekit.c +index da083019..c9e4e49f 100644 +--- a/plugins/packagekit/gs-plugin-packagekit.c ++++ b/plugins/packagekit/gs-plugin-packagekit.c +@@ -424,6 +424,7 @@ gs_plugin_app_install (GsPlugin *plugin, + /* actually install the package */ + gs_packagekit_helper_add_app (helper, app); + g_mutex_lock (&priv->task_mutex); ++ pk_client_set_interactive (PK_CLIENT (priv->task), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); + results = pk_task_install_packages_sync (priv->task, + package_ids, + cancellable, +@@ -501,6 +502,7 @@ gs_plugin_app_install (GsPlugin *plugin, + } + gs_packagekit_helper_add_app (helper, app); + g_mutex_lock (&priv->task_mutex); ++ pk_client_set_interactive (PK_CLIENT (priv->task), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); + results = pk_task_install_packages_sync (priv->task, + (gchar **) array_package_ids->pdata, + cancellable, +@@ -542,6 +544,7 @@ gs_plugin_app_install (GsPlugin *plugin, + gs_app_set_state (app, GS_APP_STATE_INSTALLING); + gs_packagekit_helper_add_app (helper, app); + g_mutex_lock (&priv->task_mutex); ++ pk_client_set_interactive (PK_CLIENT (priv->task), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); + results = pk_task_install_files_sync (priv->task, + package_ids, + cancellable, +@@ -627,6 +630,7 @@ gs_plugin_app_remove (GsPlugin *plugin, + gs_app_set_state (app, GS_APP_STATE_REMOVING); + gs_packagekit_helper_add_app (helper, app); + g_mutex_lock (&priv->task_mutex); ++ pk_client_set_interactive (PK_CLIENT (priv->task), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); + results = pk_task_remove_packages_sync (priv->task, + package_ids, + TRUE, GS_PACKAGEKIT_AUTOREMOVE, +@@ -862,6 +866,7 @@ gs_plugin_packagekit_resolve_packages_with_filter (GsPlugin *plugin, + + /* resolve them all at once */ + g_mutex_lock (&priv->client_mutex_refine); ++ pk_client_set_interactive (priv->client_refine, gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); + results = pk_client_resolve (priv->client_refine, + filter, + (gchar **) package_ids->pdata, +@@ -953,6 +958,7 @@ gs_plugin_packagekit_refine_from_desktop (GsPlugin *plugin, + to_array[0] = filename; + gs_packagekit_helper_add_app (helper, app); + g_mutex_lock (&priv->client_mutex_refine); ++ pk_client_set_interactive (priv->client_refine, gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); + results = pk_client_search_files (priv->client_refine, + pk_bitfield_from_enums (PK_FILTER_ENUM_INSTALLED, -1), + (gchar **) to_array, +@@ -1036,6 +1042,7 @@ gs_plugin_packagekit_refine_updatedetails (GsPlugin *plugin, + + /* get any update details */ + g_mutex_lock (&priv->client_mutex_refine); ++ pk_client_set_interactive (priv->client_refine, gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); + results = pk_client_get_update_detail (priv->client_refine, + (gchar **) package_ids, + cancellable, +@@ -1102,6 +1109,7 @@ gs_plugin_packagekit_refine_details2 (GsPlugin *plugin, + + /* get any details */ + g_mutex_lock (&priv->client_mutex_refine); ++ pk_client_set_interactive (priv->client_refine, gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); + results = pk_client_get_details (priv->client_refine, + (gchar **) package_ids->pdata, + cancellable, +@@ -1154,6 +1162,7 @@ gs_plugin_packagekit_refine_update_urgency (GsPlugin *plugin, + /* get the list of updates */ + filter = pk_bitfield_value (PK_FILTER_ENUM_NONE); + g_mutex_lock (&priv->client_mutex_refine); ++ pk_client_set_interactive (priv->client_refine, gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); + results = pk_client_get_updates (priv->client_refine, + filter, + cancellable, +@@ -1812,6 +1821,7 @@ gs_plugin_packagekit_refresh_guess_app_id (GsPlugin *plugin, + files = g_strsplit (filename, "\t", -1); + gs_packagekit_helper_add_app (helper, app); + g_mutex_lock (&priv->task_mutex_local); ++ pk_client_set_interactive (PK_CLIENT (priv->task_local), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); + results = pk_client_get_files_local (PK_CLIENT (priv->task_local), + files, + cancellable, +-- +2.31.1 + diff --git a/gnome-software.spec b/gnome-software.spec index f705316..1e6ff21 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 41~rc -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -20,6 +20,7 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/41/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +Patch02: 0002-packagekit-Ensure-PkClient-interactive-flag-being-se.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -198,6 +199,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Sep 13 2021 Milan Crha - 41~rc-2 +- Resolves: #2003365 (packagekit: Ensure PkClient::interactive flag being set) + * Wed Sep 08 2021 Milan Crha - 41~rc-1 - Update to 41.rc From 0537bfe484decc0254d74ea8b46b11a5c1c9f30d Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 20 Sep 2021 09:51:11 +0200 Subject: [PATCH 034/163] Update to 41.0 --- ...e-PkClient-interactive-flag-being-se.patch | 116 ------------------ gnome-software.spec | 14 ++- sources | 2 +- 3 files changed, 11 insertions(+), 121 deletions(-) delete mode 100644 0002-packagekit-Ensure-PkClient-interactive-flag-being-se.patch diff --git a/0002-packagekit-Ensure-PkClient-interactive-flag-being-se.patch b/0002-packagekit-Ensure-PkClient-interactive-flag-being-se.patch deleted file mode 100644 index 67e1d8e..0000000 --- a/0002-packagekit-Ensure-PkClient-interactive-flag-being-se.patch +++ /dev/null @@ -1,116 +0,0 @@ -From 50ea9e8e6c4c3c23607b1ea9cc56e5e1b15c9e42 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Mon, 13 Sep 2021 15:02:37 +0200 -Subject: [PATCH] packagekit: Ensure PkClient::interactive flag being set - -That's required to properly ask or not ask for the root credentials on operations, -which require higher privileges. It's important to set the flag always before the call -to the PkTask/PkClient API, because other thread could change the value while -the corresponding lock was released by the execution thread. - -Downstream bug report: -https://bugzilla.redhat.com/show_bug.cgi?id=2003365 ---- - plugins/packagekit/gs-plugin-packagekit-refresh.c | 1 + - plugins/packagekit/gs-plugin-packagekit.c | 10 ++++++++++ - 2 files changed, 11 insertions(+) - -diff --git a/plugins/packagekit/gs-plugin-packagekit-refresh.c b/plugins/packagekit/gs-plugin-packagekit-refresh.c -index 338cc387..ef06bcd2 100644 ---- a/plugins/packagekit/gs-plugin-packagekit-refresh.c -+++ b/plugins/packagekit/gs-plugin-packagekit-refresh.c -@@ -94,6 +94,7 @@ _download_only (GsPlugin *plugin, GsAppList *list, - * we end up downloading a different set of packages than what was - * shown to the user */ - pk_client_set_cache_age (PK_CLIENT (priv->task), G_MAXUINT); -+ pk_client_set_interactive (PK_CLIENT (priv->task), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); - results2 = pk_task_update_packages_sync (priv->task, - package_ids, - cancellable, -diff --git a/plugins/packagekit/gs-plugin-packagekit.c b/plugins/packagekit/gs-plugin-packagekit.c -index da083019..c9e4e49f 100644 ---- a/plugins/packagekit/gs-plugin-packagekit.c -+++ b/plugins/packagekit/gs-plugin-packagekit.c -@@ -424,6 +424,7 @@ gs_plugin_app_install (GsPlugin *plugin, - /* actually install the package */ - gs_packagekit_helper_add_app (helper, app); - g_mutex_lock (&priv->task_mutex); -+ pk_client_set_interactive (PK_CLIENT (priv->task), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); - results = pk_task_install_packages_sync (priv->task, - package_ids, - cancellable, -@@ -501,6 +502,7 @@ gs_plugin_app_install (GsPlugin *plugin, - } - gs_packagekit_helper_add_app (helper, app); - g_mutex_lock (&priv->task_mutex); -+ pk_client_set_interactive (PK_CLIENT (priv->task), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); - results = pk_task_install_packages_sync (priv->task, - (gchar **) array_package_ids->pdata, - cancellable, -@@ -542,6 +544,7 @@ gs_plugin_app_install (GsPlugin *plugin, - gs_app_set_state (app, GS_APP_STATE_INSTALLING); - gs_packagekit_helper_add_app (helper, app); - g_mutex_lock (&priv->task_mutex); -+ pk_client_set_interactive (PK_CLIENT (priv->task), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); - results = pk_task_install_files_sync (priv->task, - package_ids, - cancellable, -@@ -627,6 +630,7 @@ gs_plugin_app_remove (GsPlugin *plugin, - gs_app_set_state (app, GS_APP_STATE_REMOVING); - gs_packagekit_helper_add_app (helper, app); - g_mutex_lock (&priv->task_mutex); -+ pk_client_set_interactive (PK_CLIENT (priv->task), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); - results = pk_task_remove_packages_sync (priv->task, - package_ids, - TRUE, GS_PACKAGEKIT_AUTOREMOVE, -@@ -862,6 +866,7 @@ gs_plugin_packagekit_resolve_packages_with_filter (GsPlugin *plugin, - - /* resolve them all at once */ - g_mutex_lock (&priv->client_mutex_refine); -+ pk_client_set_interactive (priv->client_refine, gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); - results = pk_client_resolve (priv->client_refine, - filter, - (gchar **) package_ids->pdata, -@@ -953,6 +958,7 @@ gs_plugin_packagekit_refine_from_desktop (GsPlugin *plugin, - to_array[0] = filename; - gs_packagekit_helper_add_app (helper, app); - g_mutex_lock (&priv->client_mutex_refine); -+ pk_client_set_interactive (priv->client_refine, gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); - results = pk_client_search_files (priv->client_refine, - pk_bitfield_from_enums (PK_FILTER_ENUM_INSTALLED, -1), - (gchar **) to_array, -@@ -1036,6 +1042,7 @@ gs_plugin_packagekit_refine_updatedetails (GsPlugin *plugin, - - /* get any update details */ - g_mutex_lock (&priv->client_mutex_refine); -+ pk_client_set_interactive (priv->client_refine, gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); - results = pk_client_get_update_detail (priv->client_refine, - (gchar **) package_ids, - cancellable, -@@ -1102,6 +1109,7 @@ gs_plugin_packagekit_refine_details2 (GsPlugin *plugin, - - /* get any details */ - g_mutex_lock (&priv->client_mutex_refine); -+ pk_client_set_interactive (priv->client_refine, gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); - results = pk_client_get_details (priv->client_refine, - (gchar **) package_ids->pdata, - cancellable, -@@ -1154,6 +1162,7 @@ gs_plugin_packagekit_refine_update_urgency (GsPlugin *plugin, - /* get the list of updates */ - filter = pk_bitfield_value (PK_FILTER_ENUM_NONE); - g_mutex_lock (&priv->client_mutex_refine); -+ pk_client_set_interactive (priv->client_refine, gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); - results = pk_client_get_updates (priv->client_refine, - filter, - cancellable, -@@ -1812,6 +1821,7 @@ gs_plugin_packagekit_refresh_guess_app_id (GsPlugin *plugin, - files = g_strsplit (filename, "\t", -1); - gs_packagekit_helper_add_app (helper, app); - g_mutex_lock (&priv->task_mutex_local); -+ pk_client_set_interactive (PK_CLIENT (priv->task_local), gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE)); - results = pk_client_get_files_local (PK_CLIENT (priv->task_local), - files, - cancellable, --- -2.31.1 - diff --git a/gnome-software.spec b/gnome-software.spec index 1e6ff21..8c2a938 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,8 +11,8 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 41~rc -Release: 2%{?dist} +Version: 41.0 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -20,7 +20,6 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/41/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -Patch02: 0002-packagekit-Ensure-PkClient-interactive-flag-being-se.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -129,7 +128,11 @@ desktop-file-edit %{buildroot}%{_datadir}/applications/org.gnome.Software.deskto # set up for Fedora cat >> %{buildroot}%{_datadir}/glib-2.0/schemas/org.gnome.software-fedora.gschema.override << FOE [org.gnome.software] -official-repos = [ 'anaconda', 'fedora', 'fedora-debuginfo', 'fedora-source', 'koji-override-0', 'koji-override-1', 'rawhide', 'rawhide-debuginfo', 'rawhide-source', 'updates', 'updates-debuginfo', 'updates-source', 'updates-testing', 'updates-testing-debuginfo', 'updates-testing-source', 'fedora-modular', 'fedora-modular-debuginfo', 'fedora-modular-source', 'rawhide-modular', 'rawhide-modular-debuginfo', 'rawhide-modular-source' ] +%if 0%{?rhel} +official-repos = [ 'rhel-%{?rhel}' ] +%else +official-repos = [ 'anaconda', 'fedora', 'fedora-debuginfo', 'fedora-source', 'koji-override-0', 'koji-override-1', 'rawhide', 'rawhide-debuginfo', 'rawhide-source', 'updates', 'updates-debuginfo', 'updates-source', 'updates-testing', 'updates-testing-debuginfo', 'updates-testing-source', 'fedora-modular', 'fedora-modular-debuginfo', 'fedora-modular-source', 'rawhide-modular', 'rawhide-modular-debuginfo', 'rawhide-modular-source', 'fedora-cisco-openh264', 'fedora-cisco-openh264-debuginfo' ] +%endif FOE %find_lang %name --with-gnome @@ -199,6 +202,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Sep 20 2021 Milan Crha - 41.0-1 +- Update to 41.0 + * Mon Sep 13 2021 Milan Crha - 41~rc-2 - Resolves: #2003365 (packagekit: Ensure PkClient::interactive flag being set) diff --git a/sources b/sources index 6ff6324..4578578 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-41.rc.tar.xz) = 6aec9a0ffc4957a62f8a25a4ba50b8f7539a701af8813f37310e6372c16b7c9c43ba5d97df05f202339eded5eb45c53bb9480727cfb3053d86ed16e20827cd23 +SHA512 (gnome-software-41.0.tar.xz) = 6cc090f835e77d64abb0080d3b72494019d6f69c2144abea4dabdc4f52dc570a372159eb1e0b0d98ae33b31c134cc17673fe3fa243eed762eec55620ab146b26 From a63a7bde164181cf2604642c74e0594409f931de Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 4 Oct 2021 17:43:44 +0200 Subject: [PATCH 035/163] Resolves: #2009063 (Correct update notifications) --- 0002-correct-update-notifications.patch | 116 ++++++++++++++++++++++++ gnome-software.spec | 6 +- 2 files changed, 121 insertions(+), 1 deletion(-) create mode 100644 0002-correct-update-notifications.patch diff --git a/0002-correct-update-notifications.patch b/0002-correct-update-notifications.patch new file mode 100644 index 0000000..a8c8f08 --- /dev/null +++ b/0002-correct-update-notifications.patch @@ -0,0 +1,116 @@ +From 1b0c476d66f89332187da2894b06ec2d4b83fa2a Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Thu, 30 Sep 2021 16:28:11 +0200 +Subject: [PATCH 1/2] gs-update-monitor: Use wall-clock time for + one-notification-per-day check + +Instead of using the g_timeout_add_seconds(), which uses a monotonic time, +which may or may not increase when the machine is suspended, rather use +the wall-clock time, to avoid issues with machine suspend where the monotonic +time does not increase. +--- + src/gs-update-monitor.c | 31 +++++++++++++------------------ + 1 file changed, 13 insertions(+), 18 deletions(-) + +diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c +index bde39fbbb..787c605a1 100644 +--- a/src/gs-update-monitor.c ++++ b/src/gs-update-monitor.c +@@ -44,7 +44,8 @@ struct _GsUpdateMonitor { + guint check_startup_id; /* 60s after startup */ + guint check_hourly_id; /* and then every hour */ + guint check_daily_id; /* every 3rd day */ +- guint notification_blocked_id; /* rate limit notifications */ ++ ++ gint64 last_notification_time_usec; /* to notify once per day only */ + }; + + G_DEFINE_TYPE (GsUpdateMonitor, gs_update_monitor, G_TYPE_OBJECT) +@@ -88,14 +89,6 @@ with_app_data_free (WithAppData *data) + + G_DEFINE_AUTOPTR_CLEANUP_FUNC(WithAppData, with_app_data_free); + +-static gboolean +-reenable_offline_update_notification (gpointer data) +-{ +- GsUpdateMonitor *monitor = data; +- monitor->notification_blocked_id = 0; +- return G_SOURCE_REMOVE; +-} +- + static void + check_updates_kind (GsAppList *apps, + gboolean *out_has_important, +@@ -265,16 +258,22 @@ notify_about_pending_updates (GsUpdateMonitor *monitor, + GsAppList *apps) + { + const gchar *title = NULL, *body = NULL; ++ gint64 time_diff_sec; + g_autoptr(GNotification) nn = NULL; + +- if (monitor->notification_blocked_id > 0) ++ time_diff_sec = (g_get_real_time () - monitor->last_notification_time_usec) / G_USEC_PER_SEC; ++ if (time_diff_sec < SECONDS_IN_A_DAY) { ++ g_debug ("Skipping update notification daily check, because made one only %" G_GINT64_FORMAT "s ago", ++ time_diff_sec); + return; ++ } + +- /* rate limit update notifications to once per day */ +- monitor->notification_blocked_id = g_timeout_add_seconds (24 * SECONDS_IN_AN_HOUR, reenable_offline_update_notification, monitor); +- +- if (!should_notify_about_pending_updates (monitor, apps, &title, &body)) ++ if (!should_notify_about_pending_updates (monitor, apps, &title, &body)) { ++ g_debug ("No update notification needed"); + return; ++ } ++ ++ monitor->last_notification_time_usec = g_get_real_time (); + + g_debug ("Notify about update: '%s'", title); + +@@ -1394,10 +1393,6 @@ gs_update_monitor_dispose (GObject *object) + g_source_remove (monitor->check_startup_id); + monitor->check_startup_id = 0; + } +- if (monitor->notification_blocked_id != 0) { +- g_source_remove (monitor->notification_blocked_id); +- monitor->notification_blocked_id = 0; +- } + if (monitor->cleanup_notifications_id != 0) { + g_source_remove (monitor->cleanup_notifications_id); + monitor->cleanup_notifications_id = 0; +-- +GitLab + + +From 2ff332826f841c4ea1d9458df81648868745ea41 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Thu, 30 Sep 2021 16:47:40 +0200 +Subject: [PATCH 2/2] gs-update-monitor: Correct last notification timestamp + reset + +Do not reset the notification timestamp after the list of updates +is received, that should be done when the notification had been shown. + +Reported downstream at: +https://bugzilla.redhat.com/show_bug.cgi?id=2009063 +--- + src/gs-update-monitor.c | 1 - + 1 file changed, 1 deletion(-) + +diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c +index 787c605a1..a8421fcc4 100644 +--- a/src/gs-update-monitor.c ++++ b/src/gs-update-monitor.c +@@ -613,7 +613,6 @@ get_updates_finished_cb (GObject *object, GAsyncResult *res, gpointer data) + notify_list = apps; + + notify_about_pending_updates (monitor, notify_list); +- reset_update_notification_timestamp (monitor); + } + } + +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index 8c2a938..cbc22a8 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 41.0 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -20,6 +20,7 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/41/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +Patch02: 0002-correct-update-notifications.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -202,6 +203,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Oct 04 2021 Milan Crha - 41.0-2 +- Resolves: #2009063 (Correct update notifications) + * Mon Sep 20 2021 Milan Crha - 41.0-1 - Update to 41.0 From f47313a4ef978dde6fd7d1760c9baeaaca73f76a Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Thu, 7 Oct 2021 09:41:10 +0200 Subject: [PATCH 036/163] Resolves: #2010740 (Refresh on repository setup change) --- 0003-refresh-on-repository-change.patch | 233 ++++++++++++++++++++++++ gnome-software.spec | 6 +- 2 files changed, 238 insertions(+), 1 deletion(-) create mode 100644 0003-refresh-on-repository-change.patch diff --git a/0003-refresh-on-repository-change.patch b/0003-refresh-on-repository-change.patch new file mode 100644 index 0000000..3af8ef8 --- /dev/null +++ b/0003-refresh-on-repository-change.patch @@ -0,0 +1,233 @@ +From 5c203ae1b07e2c31ca39c3d6a793534d45c49125 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 5 Oct 2021 19:42:37 +0200 +Subject: [PATCH 1/5] gs-shell: Remove left-over function prototype declaration + +The function body does not exist. +--- + src/gs-shell.h | 2 -- + 1 file changed, 2 deletions(-) + +diff --git a/src/gs-shell.h b/src/gs-shell.h +index bb39fc928..46661db16 100644 +--- a/src/gs-shell.h ++++ b/src/gs-shell.h +@@ -43,8 +43,6 @@ typedef enum { + + GsShell *gs_shell_new (void); + void gs_shell_activate (GsShell *shell); +-void gs_shell_refresh (GsShell *shell, +- GCancellable *cancellable); + void gs_shell_change_mode (GsShell *shell, + GsShellMode mode, + gpointer data, +-- +GitLab + + +From ca49eb3974e220ff17262c6189e3cdf0a92746fe Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 5 Oct 2021 19:45:10 +0200 +Subject: [PATCH 2/5] gs-application: Introduce gs_application_refresh() + +It can be used to call a non-interactive refresh call for the plugins. +--- + src/gs-application.c | 28 ++++++++++++++++++++++++++++ + src/gs-application.h | 3 ++- + 2 files changed, 30 insertions(+), 1 deletion(-) + +diff --git a/src/gs-application.c b/src/gs-application.c +index 90487df62..df982df19 100644 +--- a/src/gs-application.c ++++ b/src/gs-application.c +@@ -1371,3 +1371,31 @@ gs_application_emit_install_resources_done (GsApplication *application, + { + g_signal_emit (application, signals[INSTALL_RESOURCES_DONE], 0, ident, op_error, NULL); + } ++ ++static void ++gs_application_refresh_cb (GsPluginLoader *plugin_loader, ++ GAsyncResult *result, ++ GsApplication *self) ++{ ++ gboolean success; ++ g_autoptr(GError) error = NULL; ++ ++ success = gs_plugin_loader_job_action_finish (plugin_loader, result, &error); ++ if (!success && ++ !g_error_matches (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_CANCELLED)) ++ g_warning ("failed to refresh: %s", error->message); ++} ++ ++void ++gs_application_refresh (GsApplication *self) ++{ ++ g_autoptr(GsPluginJob) plugin_job = NULL; ++ plugin_job = gs_plugin_job_newv (GS_PLUGIN_ACTION_REFRESH, ++ "interactive", FALSE, ++ "age", (guint64) 1, ++ NULL); ++ gs_plugin_loader_job_process_async (self->plugin_loader, plugin_job, ++ self->cancellable, ++ (GAsyncReadyCallback) gs_application_refresh_cb, ++ self); ++} +diff --git a/src/gs-application.h b/src/gs-application.h +index 40bad4d4c..92978e1f5 100644 +--- a/src/gs-application.h ++++ b/src/gs-application.h +@@ -23,4 +23,5 @@ gboolean gs_application_has_active_window (GsApplication *application); + void gs_application_emit_install_resources_done + (GsApplication *application, + const gchar *ident, +- const GError *op_error); +\ No newline at end of file ++ const GError *op_error); ++void gs_application_refresh (GsApplication *self); +-- +GitLab + + +From 2781d350a9a9ee1fd2078928f4e0933a34e05b9f Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 5 Oct 2021 19:46:17 +0200 +Subject: [PATCH 3/5] gs-repos-dialog: Call refresh on repository setup change + +When a repository is enabled/disabled/removed, call also the refresh +on the plugins, thus the data from those repos are available for the user. + +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1486 +--- + src/gs-repos-dialog.c | 16 ++++++++++++++++ + 1 file changed, 16 insertions(+) + +diff --git a/src/gs-repos-dialog.c b/src/gs-repos-dialog.c +index 1d6a82f48..c986ad724 100644 +--- a/src/gs-repos-dialog.c ++++ b/src/gs-repos-dialog.c +@@ -13,6 +13,7 @@ + #include "gs-repos-dialog.h" + + #include "gnome-software-private.h" ++#include "gs-application.h" + #include "gs-common.h" + #include "gs-os-release.h" + #include "gs-repo-row.h" +@@ -35,6 +36,8 @@ struct _GsReposDialog + GtkWidget *content_page; + GtkWidget *spinner; + GtkWidget *stack; ++ ++ gboolean changed; + }; + + G_DEFINE_TYPE (GsReposDialog, gs_repos_dialog, HDY_TYPE_WINDOW) +@@ -115,6 +118,8 @@ repo_enabled_cb (GObject *source, + } + + g_debug ("finished %s repo %s", action_str, gs_app_get_id (install_remove_data->repo)); ++ ++ install_remove_data->dialog->changed = TRUE; + } + + static void +@@ -710,6 +715,17 @@ gs_repos_dialog_dispose (GObject *object) + g_clear_object (&dialog->cancellable); + g_clear_object (&dialog->settings); + ++ if (dialog->changed) { ++ GApplication *app; ++ ++ dialog->changed = FALSE; ++ g_debug ("Repository setup changed, calling refresh..."); ++ ++ app = g_application_get_default (); ++ if (app) ++ gs_application_refresh (GS_APPLICATION (app)); ++ } ++ + G_OBJECT_CLASS (gs_repos_dialog_parent_class)->dispose (object); + } + +-- +GitLab + + +From 4c6f4f20c904600a3c5d8ea446ed3c3b0ef0808d Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 6 Oct 2021 14:41:55 +0200 +Subject: [PATCH 4/5] gs-application: Invoke page reload after the refresh is + finished + +The refresh can cause new applications or alternative sources being +found in the newly enabled repositories, thus reload the pages, to +reflect the current state. +--- + src/gs-application.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/src/gs-application.c b/src/gs-application.c +index df982df19..6ecc093f1 100644 +--- a/src/gs-application.c ++++ b/src/gs-application.c +@@ -1384,6 +1384,9 @@ gs_application_refresh_cb (GsPluginLoader *plugin_loader, + if (!success && + !g_error_matches (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_CANCELLED)) + g_warning ("failed to refresh: %s", error->message); ++ ++ if (success) ++ g_signal_emit_by_name (self->plugin_loader, "reload", 0, NULL); + } + + void +-- +GitLab + + +From b1277d97ba4495de434eb3be4ea1f17b80ac1ef8 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 6 Oct 2021 14:44:09 +0200 +Subject: [PATCH 5/5] gs-overview-page: Refresh the application after + third-party repositories enable/disable + +The enable/disable can cause other applications being found, thus call +the refresh, to update the repositories information. +--- + src/gs-overview-page.c | 7 +++++++ + 1 file changed, 7 insertions(+) + +diff --git a/src/gs-overview-page.c b/src/gs-overview-page.c +index 9ba33fb2b..bcf02243d 100644 +--- a/src/gs-overview-page.c ++++ b/src/gs-overview-page.c +@@ -13,6 +13,7 @@ + #include + #include + ++#include "gs-application.h" + #include "gs-shell.h" + #include "gs-overview-page.h" + #include "gs-app-list-private.h" +@@ -568,6 +569,8 @@ third_party_response_cb (GtkInfoBar *info_bar, + gint response_id, + GsOverviewPage *self) + { ++ GApplication *application; ++ + if (response_id == GTK_RESPONSE_YES) + fedora_third_party_enable (self); + else +@@ -575,6 +578,10 @@ third_party_response_cb (GtkInfoBar *info_bar, + + self->third_party_needs_question = FALSE; + refresh_third_party_repo (self); ++ ++ application = g_application_get_default (); ++ if (application) ++ gs_application_refresh (GS_APPLICATION (application)); + } + + static gboolean +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index cbc22a8..3d5d2f8 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 41.0 -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -21,6 +21,7 @@ Source0: https://download.gnome.org/sources/gnome-software/41/%{name}-%{tarbal Patch01: 0001-crash-with-broken-theme.patch Patch02: 0002-correct-update-notifications.patch +Patch03: 0003-refresh-on-repository-change.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -203,6 +204,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Thu Oct 07 2021 Milan Crha - 41.0-3 +- Resolves: #2010740 (Refresh on repository setup change) + * Mon Oct 04 2021 Milan Crha - 41.0-2 - Resolves: #2009063 (Correct update notifications) From 53b2166dfb243b9b5649972921de0d81ce06d639 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 8 Oct 2021 07:37:33 +0200 Subject: [PATCH 037/163] Resolves: #2011176, #2010660, #2010353 --- 0004-filtered-system-flathub.patch | 331 +++++++++ 0005-repos-dialog-can-show-apps.patch | 163 +++++ 0006-optional-repos-cannot-be-disabled.patch | 665 +++++++++++++++++++ gnome-software.spec | 11 +- 4 files changed, 1169 insertions(+), 1 deletion(-) create mode 100644 0004-filtered-system-flathub.patch create mode 100644 0005-repos-dialog-can-show-apps.patch create mode 100644 0006-optional-repos-cannot-be-disabled.patch diff --git a/0004-filtered-system-flathub.patch b/0004-filtered-system-flathub.patch new file mode 100644 index 0000000..93cd865 --- /dev/null +++ b/0004-filtered-system-flathub.patch @@ -0,0 +1,331 @@ +From 03ea59cc8db6bec34d56205d62ec495315e9ea96 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 21 Sep 2021 13:55:57 +0200 +Subject: [PATCH 1/5] gs-page: Use correct action when install/remove repo app + +Since the split of the install/remove action for apps and repos +the GsPage should use correct action too. This can happen for example +when installing a .flatpakrepo file. +--- + src/gs-page.c | 10 ++++++++-- + 1 file changed, 8 insertions(+), 2 deletions(-) + +diff --git a/src/gs-page.c b/src/gs-page.c +index ca1fbfc70..dfaadbc39 100644 +--- a/src/gs-page.c ++++ b/src/gs-page.c +@@ -280,7 +280,10 @@ gs_page_install_app (GsPage *page, + } + + helper = g_slice_new0 (GsPageHelper); +- helper->action = GS_PLUGIN_ACTION_INSTALL; ++ if (gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY) ++ helper->action = GS_PLUGIN_ACTION_INSTALL_REPO; ++ else ++ helper->action = GS_PLUGIN_ACTION_INSTALL; + helper->app = g_object_ref (app); + helper->page = g_object_ref (page); + helper->cancellable = g_object_ref (cancellable); +@@ -466,7 +469,10 @@ gs_page_remove_app (GsPage *page, GsApp *app, GCancellable *cancellable) + + /* pending install */ + helper = g_slice_new0 (GsPageHelper); +- helper->action = GS_PLUGIN_ACTION_REMOVE; ++ if (gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY) ++ helper->action = GS_PLUGIN_ACTION_REMOVE_REPO; ++ else ++ helper->action = GS_PLUGIN_ACTION_REMOVE; + helper->app = g_object_ref (app); + helper->page = g_object_ref (page); + helper->cancellable = cancellable != NULL ? g_object_ref (cancellable) : NULL; +-- +GitLab + + +From 576f9e6d25fcd3edd7fdf769e342a382af1307e3 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 21 Sep 2021 13:58:03 +0200 +Subject: [PATCH 2/5] flatpak: Save also remote's filter on the flatpak-app + +This can be used when updating existing remote, to reflect the new +filter. It can be also used to verify the installed and existing +remotes match with its filter. +--- + plugins/flatpak/gs-flatpak-app.c | 12 ++++++++++++ + plugins/flatpak/gs-flatpak-app.h | 3 +++ + 2 files changed, 15 insertions(+) + +diff --git a/plugins/flatpak/gs-flatpak-app.c b/plugins/flatpak/gs-flatpak-app.c +index cf98248a8..b59515b2f 100644 +--- a/plugins/flatpak/gs-flatpak-app.c ++++ b/plugins/flatpak/gs-flatpak-app.c +@@ -176,3 +176,15 @@ gs_flatpak_app_get_main_app_ref_name (GsApp *app) + { + return gs_app_get_metadata_item (app, "flatpak::mainApp"); + } ++ ++void ++gs_flatpak_app_set_repo_filter (GsApp *app, const gchar *filter) ++{ ++ gs_app_set_metadata (app, "flatpak::RepoFilter", filter); ++} ++ ++const gchar * ++gs_flatpak_app_get_repo_filter (GsApp *app) ++{ ++ return gs_app_get_metadata_item (app, "flatpak::RepoFilter"); ++} +diff --git a/plugins/flatpak/gs-flatpak-app.h b/plugins/flatpak/gs-flatpak-app.h +index ab6c10af4..610c8a8f3 100644 +--- a/plugins/flatpak/gs-flatpak-app.h ++++ b/plugins/flatpak/gs-flatpak-app.h +@@ -58,5 +58,8 @@ void gs_flatpak_app_set_runtime_url (GsApp *app, + void gs_flatpak_app_set_main_app_ref_name (GsApp *app, + const gchar *main_app_ref); + const gchar *gs_flatpak_app_get_main_app_ref_name (GsApp *app); ++void gs_flatpak_app_set_repo_filter (GsApp *app, ++ const gchar *filter); ++const gchar *gs_flatpak_app_get_repo_filter (GsApp *app); + + G_END_DECLS +-- +GitLab + + +From cb809158e81157b53245e4c290ada418d5bcd03d Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 21 Sep 2021 14:02:47 +0200 +Subject: [PATCH 3/5] flatpak: Store filter and description on a remote app + +Store the description also on an installed remote, not only on the file +remote. Similarly store also the filters for the remotes. +--- + plugins/flatpak/gs-flatpak-utils.c | 14 ++++++++++++++ + 1 file changed, 14 insertions(+) + +diff --git a/plugins/flatpak/gs-flatpak-utils.c b/plugins/flatpak/gs-flatpak-utils.c +index 8b107b37c..7aa735b0b 100644 +--- a/plugins/flatpak/gs-flatpak-utils.c ++++ b/plugins/flatpak/gs-flatpak-utils.c +@@ -72,6 +72,8 @@ gs_flatpak_app_new_from_remote (GsPlugin *plugin, + { + g_autofree gchar *title = NULL; + g_autofree gchar *url = NULL; ++ g_autofree gchar *filter = NULL; ++ g_autofree gchar *description = NULL; + g_autoptr(GsApp) app = NULL; + + app = gs_flatpak_app_new (flatpak_remote_get_name (xremote)); +@@ -101,11 +103,19 @@ gs_flatpak_app_new_from_remote (GsPlugin *plugin, + * not the remote title */ + gs_app_set_origin_ui (app, _("Applications")); + ++ description = flatpak_remote_get_description (xremote); ++ if (description != NULL) ++ gs_app_set_description (app, GS_APP_QUALITY_NORMAL, description); ++ + /* url */ + url = flatpak_remote_get_url (xremote); + if (url != NULL) + gs_app_set_url (app, AS_URL_KIND_HOMEPAGE, url); + ++ filter = flatpak_remote_get_filter (xremote); ++ if (filter != NULL) ++ gs_flatpak_app_set_repo_filter (app, filter); ++ + /* success */ + return g_steal_pointer (&app); + } +@@ -127,6 +137,7 @@ gs_flatpak_app_new_from_repo_file (GFile *file, + g_autofree gchar *repo_id = NULL; + g_autofree gchar *repo_title = NULL; + g_autofree gchar *repo_url = NULL; ++ g_autofree gchar *repo_filter = NULL; + g_autoptr(GError) error_local = NULL; + g_autoptr(GKeyFile) kf = NULL; + g_autoptr(GsApp) app = NULL; +@@ -229,6 +240,9 @@ gs_flatpak_app_new_from_repo_file (GFile *file, + g_autoptr(GIcon) icon = gs_remote_icon_new (repo_icon); + gs_app_add_icon (app, icon); + } ++ repo_filter = g_key_file_get_string (kf, "Flatpak Repo", "Filter", NULL); ++ if (repo_filter != NULL && *repo_filter != '\0') ++ gs_flatpak_app_set_repo_filter (app, repo_filter); + + /* success */ + return g_steal_pointer (&app); +-- +GitLab + + +From a4f8501e3e54b702b5ff2af4bb9aaf6f8d6c324c Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 21 Sep 2021 14:05:03 +0200 +Subject: [PATCH 4/5] flatpak: Match existing and file remote only if it + matches also the filter + +The filter can change the content, thus match two remotes only if also +the filter matches. +--- + plugins/flatpak/gs-plugin-flatpak.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/plugins/flatpak/gs-plugin-flatpak.c b/plugins/flatpak/gs-plugin-flatpak.c +index 9bdfa80bf..29ba29700 100644 +--- a/plugins/flatpak/gs-plugin-flatpak.c ++++ b/plugins/flatpak/gs-plugin-flatpak.c +@@ -1287,6 +1287,8 @@ gs_plugin_flatpak_file_to_app_repo (GsPlugin *plugin, + g_debug ("%s", error_local->message); + continue; + } ++ if (g_strcmp0 (gs_flatpak_app_get_repo_filter (app), gs_flatpak_app_get_repo_filter (app_tmp)) != 0) ++ continue; + return g_steal_pointer (&app_tmp); + } + +-- +GitLab + + +From 2a94efbda64d94ba6ac27cfd08190b62f52df000 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 21 Sep 2021 14:06:35 +0200 +Subject: [PATCH 5/5] flatpak: Update existing remote from a .flatpakref file + +Update existing remote's title, description and filter when installing +a .flatpakref file, to match what had been installed, with new-enough +flatpak library. + +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1453 +--- + plugins/flatpak/gs-flatpak-utils.c | 6 ++++++ + plugins/flatpak/gs-flatpak.c | 11 +++++++++-- + 2 files changed, 15 insertions(+), 2 deletions(-) + +diff --git a/plugins/flatpak/gs-flatpak-utils.c b/plugins/flatpak/gs-flatpak-utils.c +index 7aa735b0b..ec0b397e3 100644 +--- a/plugins/flatpak/gs-flatpak-utils.c ++++ b/plugins/flatpak/gs-flatpak-utils.c +@@ -72,8 +72,10 @@ gs_flatpak_app_new_from_remote (GsPlugin *plugin, + { + g_autofree gchar *title = NULL; + g_autofree gchar *url = NULL; ++ #if FLATPAK_CHECK_VERSION(1, 4, 0) + g_autofree gchar *filter = NULL; + g_autofree gchar *description = NULL; ++ #endif + g_autoptr(GsApp) app = NULL; + + app = gs_flatpak_app_new (flatpak_remote_get_name (xremote)); +@@ -103,18 +105,22 @@ gs_flatpak_app_new_from_remote (GsPlugin *plugin, + * not the remote title */ + gs_app_set_origin_ui (app, _("Applications")); + ++ #if FLATPAK_CHECK_VERSION(1, 4, 0) + description = flatpak_remote_get_description (xremote); + if (description != NULL) + gs_app_set_description (app, GS_APP_QUALITY_NORMAL, description); ++ #endif + + /* url */ + url = flatpak_remote_get_url (xremote); + if (url != NULL) + gs_app_set_url (app, AS_URL_KIND_HOMEPAGE, url); + ++ #if FLATPAK_CHECK_VERSION(1, 4, 0) + filter = flatpak_remote_get_filter (xremote); + if (filter != NULL) + gs_flatpak_app_set_repo_filter (app, filter); ++ #endif + + /* success */ + return g_steal_pointer (&app); +diff --git a/plugins/flatpak/gs-flatpak.c b/plugins/flatpak/gs-flatpak.c +index 55a91af2a..fa7df00c9 100644 +--- a/plugins/flatpak/gs-flatpak.c ++++ b/plugins/flatpak/gs-flatpak.c +@@ -1608,9 +1608,16 @@ gs_flatpak_app_install_source (GsFlatpak *self, + gs_app_get_id (app), + cancellable, NULL); + if (xremote != NULL) { +- /* if the remote already exists, just enable it */ +- g_debug ("enabling existing remote %s", flatpak_remote_get_name (xremote)); ++ /* if the remote already exists, just enable it and update it */ ++ g_debug ("modifying existing remote %s", flatpak_remote_get_name (xremote)); + flatpak_remote_set_disabled (xremote, FALSE); ++ if (gs_flatpak_app_get_file_kind (app) == GS_FLATPAK_APP_FILE_KIND_REPO) { ++ flatpak_remote_set_title (xremote, gs_app_get_origin_ui (app)); ++ #if FLATPAK_CHECK_VERSION(1, 4, 0) ++ flatpak_remote_set_filter (xremote, gs_flatpak_app_get_repo_filter (app)); ++ flatpak_remote_set_description (xremote, gs_app_get_description (app)); ++ #endif ++ } + } else if (!is_install) { + g_set_error (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_FAILED, "Cannot enable flatpak remote '%s', remote not found", gs_app_get_id (app)); + } else { +-- +GitLab + +From 1a32bd3eaaf7ec0322c46599e3b949080a410806 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Thu, 7 Oct 2021 19:28:38 +0200 +Subject: [PATCH] flatpak: Update remote appstream data when its filter changed + +When overwriting existing remote, make sure the appstream data is updated +as well when the filter changed, to have shown relevant applications. + +Related to https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1453 +--- + plugins/flatpak/gs-flatpak.c | 18 +++++++++++++++++- + 1 file changed, 17 insertions(+), 1 deletion(-) + +diff --git a/plugins/flatpak/gs-flatpak.c b/plugins/flatpak/gs-flatpak.c +index bd87d57ed..88bb69a72 100644 +--- a/plugins/flatpak/gs-flatpak.c ++++ b/plugins/flatpak/gs-flatpak.c +@@ -1623,6 +1623,9 @@ gs_flatpak_app_install_source (GsFlatpak *self, + GError **error) + { + g_autoptr(FlatpakRemote) xremote = NULL; ++ #if FLATPAK_CHECK_VERSION(1, 4, 0) ++ gboolean filter_changed = FALSE; ++ #endif + + xremote = flatpak_installation_get_remote_by_name (self->installation, + gs_app_get_id (app), +@@ -1632,11 +1635,13 @@ gs_flatpak_app_install_source (GsFlatpak *self, + g_debug ("modifying existing remote %s", flatpak_remote_get_name (xremote)); + flatpak_remote_set_disabled (xremote, FALSE); + if (gs_flatpak_app_get_file_kind (app) == GS_FLATPAK_APP_FILE_KIND_REPO) { +- flatpak_remote_set_title (xremote, gs_app_get_origin_ui (app)); + #if FLATPAK_CHECK_VERSION(1, 4, 0) ++ g_autofree gchar *current_filter = flatpak_remote_get_filter (xremote); ++ filter_changed = g_strcmp0 (current_filter, gs_flatpak_app_get_repo_filter (app)) != 0; + flatpak_remote_set_filter (xremote, gs_flatpak_app_get_repo_filter (app)); + flatpak_remote_set_description (xremote, gs_app_get_description (app)); + #endif ++ flatpak_remote_set_title (xremote, gs_app_get_origin_ui (app)); + } + } else if (!is_install) { + g_set_error (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_FAILED, "Cannot enable flatpak remote '%s', remote not found", gs_app_get_id (app)); +@@ -1666,6 +1671,17 @@ gs_flatpak_app_install_source (GsFlatpak *self, + /* success */ + gs_app_set_state (app, GS_APP_STATE_INSTALLED); + ++ #if FLATPAK_CHECK_VERSION(1, 4, 0) ++ if (filter_changed) { ++ g_autoptr(GError) local_error = NULL; ++ const gchar *remote_name = flatpak_remote_get_name (xremote); ++ if (!flatpak_installation_update_appstream_sync (self->installation, remote_name, NULL, NULL, cancellable, &local_error) && ++ !g_error_matches (local_error, G_IO_ERROR, G_IO_ERROR_CANCELLED)) { ++ g_warning ("Failed to update appstream data for flatpak remote '%s': %s", ++ remote_name, local_error->message); ++ } ++ } ++ #endif + gs_plugin_repository_changed (self->plugin, app); + + return TRUE; +-- +GitLab + diff --git a/0005-repos-dialog-can-show-apps.patch b/0005-repos-dialog-can-show-apps.patch new file mode 100644 index 0000000..eb985f3 --- /dev/null +++ b/0005-repos-dialog-can-show-apps.patch @@ -0,0 +1,163 @@ +From 1338c8f47b7ebd0e3bd360499c7ab42a0da885e8 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 5 Oct 2021 16:12:33 +0200 +Subject: [PATCH 1/2] packagekit: Update GsApp state and kind only when created + the app instance + +The gs_plugin_packagekit_add_results() can reuse GsApp instances from +the plugin cache, which can already have set property state and kind, +but this was not checked for, which could cause runtime warnings about +invalid state or kind change. + +A reproducer is to open Repositories dialog, which lists available repositories +and the applications being installed in each of them (added as 'related'). +These installed applications can have set state 'updatable' or have refined +their 'kind' already. +--- + plugins/packagekit/packagekit-common.c | 15 +++++++++------ + 1 file changed, 9 insertions(+), 6 deletions(-) + +diff --git a/plugins/packagekit/packagekit-common.c b/plugins/packagekit/packagekit-common.c +index 16b53727a..dc79c2f62 100644 +--- a/plugins/packagekit/packagekit-common.c ++++ b/plugins/packagekit/packagekit-common.c +@@ -241,12 +241,14 @@ gs_plugin_packagekit_add_results (GsPlugin *plugin, + /* process packages */ + for (i = 0; i < array_filtered->len; i++) { + g_autoptr(GsApp) app = NULL; ++ GsAppState state = GS_APP_STATE_UNKNOWN; + package = g_ptr_array_index (array_filtered, i); + + app = gs_plugin_cache_lookup (plugin, pk_package_get_id (package)); + if (app == NULL) { + app = gs_app_new (NULL); + gs_plugin_packagekit_set_packaging_format (plugin, app); ++ gs_app_set_management_plugin (app, "packagekit"); + gs_app_add_source (app, pk_package_get_name (package)); + gs_app_add_source_id (app, pk_package_get_id (package)); + gs_plugin_cache_add (plugin, pk_package_get_id (package), app); +@@ -259,14 +261,13 @@ gs_plugin_packagekit_add_results (GsPlugin *plugin, + pk_package_get_summary (package)); + gs_app_set_metadata (app, "GnomeSoftware::Creator", + gs_plugin_get_name (plugin)); +- gs_app_set_management_plugin (app, "packagekit"); + gs_app_set_version (app, pk_package_get_version (package)); + switch (pk_package_get_info (package)) { + case PK_INFO_ENUM_INSTALLED: +- gs_app_set_state (app, GS_APP_STATE_INSTALLED); ++ state = GS_APP_STATE_INSTALLED; + break; + case PK_INFO_ENUM_AVAILABLE: +- gs_app_set_state (app, GS_APP_STATE_AVAILABLE); ++ state = GS_APP_STATE_AVAILABLE; + break; + case PK_INFO_ENUM_INSTALLING: + case PK_INFO_ENUM_UPDATING: +@@ -276,14 +277,16 @@ gs_plugin_packagekit_add_results (GsPlugin *plugin, + break; + case PK_INFO_ENUM_UNAVAILABLE: + case PK_INFO_ENUM_REMOVING: +- gs_app_set_state (app, GS_APP_STATE_UNAVAILABLE); ++ state = GS_APP_STATE_UNAVAILABLE; + break; + default: +- gs_app_set_state (app, GS_APP_STATE_UNKNOWN); + g_warning ("unknown info state of %s", + pk_info_enum_to_string (pk_package_get_info (package))); + } +- gs_app_set_kind (app, AS_COMPONENT_KIND_GENERIC); ++ if (state != GS_APP_STATE_UNKNOWN && gs_app_get_state (app) == GS_APP_STATE_UNKNOWN) ++ gs_app_set_state (app, state); ++ if (gs_app_get_kind (app) == AS_COMPONENT_KIND_UNKNOWN) ++ gs_app_set_kind (app, AS_COMPONENT_KIND_GENERIC); + gs_app_set_bundle_kind (app, AS_BUNDLE_KIND_PACKAGE); + gs_app_list_add (list, app); + } +-- +GitLab + + +From 18a893fa83ebd10cea75831e9d9a7398a60c14ce Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 5 Oct 2021 16:18:22 +0200 +Subject: [PATCH 2/2] gs-plugin-loader: Ensure correct list is used on the job + when refining wildcards + +The plugin job is reused when refining the apps, including the wildcards, +but the gs_plugin_loader_run_refine_internal() can be called multiple times, +with different lists. Adding refined wildcards to the original list causes +invalid data being provided to the called. + +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1485 +--- + lib/gs-plugin-loader.c | 21 ++++++++++++++++++++- + 1 file changed, 20 insertions(+), 1 deletion(-) + +diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c +index 4d5240c32..7f5859a05 100644 +--- a/lib/gs-plugin-loader.c ++++ b/lib/gs-plugin-loader.c +@@ -937,14 +937,24 @@ gs_plugin_loader_run_refine_internal (GsPluginLoaderHelper *helper, + GCancellable *cancellable, + GError **error) + { ++ g_autoptr(GsAppList) previous_list = NULL; ++ ++ if (list != gs_plugin_job_get_list (helper->plugin_job)) { ++ previous_list = g_object_ref (gs_plugin_job_get_list (helper->plugin_job)); ++ gs_plugin_job_set_list (helper->plugin_job, list); ++ } ++ + /* try to adopt each application with a plugin */ + gs_plugin_loader_run_adopt (helper->plugin_loader, list); + + /* run each plugin */ + if (!gs_plugin_loader_run_refine_filter (helper, list, + GS_PLUGIN_REFINE_FLAGS_DEFAULT, +- cancellable, error)) ++ cancellable, error)) { ++ if (previous_list != NULL) ++ gs_plugin_job_set_list (helper->plugin_job, previous_list); + return FALSE; ++ } + + /* ensure these are sorted by score */ + if (gs_plugin_job_has_refine_flags (helper->plugin_job, +@@ -983,6 +993,8 @@ gs_plugin_loader_run_refine_internal (GsPluginLoaderHelper *helper, + addons_list, + cancellable, + error)) { ++ if (previous_list != NULL) ++ gs_plugin_job_set_list (helper->plugin_job, previous_list); + return FALSE; + } + } +@@ -1004,6 +1016,8 @@ gs_plugin_loader_run_refine_internal (GsPluginLoaderHelper *helper, + list2, + cancellable, + error)) { ++ if (previous_list != NULL) ++ gs_plugin_job_set_list (helper->plugin_job, previous_list); + return FALSE; + } + } +@@ -1032,11 +1046,16 @@ gs_plugin_loader_run_refine_internal (GsPluginLoaderHelper *helper, + related_list, + cancellable, + error)) { ++ if (previous_list != NULL) ++ gs_plugin_job_set_list (helper->plugin_job, previous_list); + return FALSE; + } + } + } + ++ if (previous_list != NULL) ++ gs_plugin_job_set_list (helper->plugin_job, previous_list); ++ + /* success */ + return TRUE; + } +-- +GitLab + diff --git a/0006-optional-repos-cannot-be-disabled.patch b/0006-optional-repos-cannot-be-disabled.patch new file mode 100644 index 0000000..20777b4 --- /dev/null +++ b/0006-optional-repos-cannot-be-disabled.patch @@ -0,0 +1,665 @@ +From 429ec744e6cdf2155772d7db463ca193231facdc Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 21 Sep 2021 14:53:27 +0200 +Subject: gs-repos-dialog: Cannot disable all 3rd-party repositories + +All the 3rd-party repositories should be disable-able, thus the 3rd-party +section should not use the heuristics to disallow disable of some of them. +This could be seen on a 'flathub' Flatpak repository installed for +the system, which is not allowed to be disabled in the Flatpak section. + +diff --git a/src/gs-repo-row.c b/src/gs-repo-row.c +index 57493c2c..7df24e0e 100644 +--- a/src/gs-repo-row.c ++++ b/src/gs-repo-row.c +@@ -27,6 +27,7 @@ typedef struct + guint busy_counter; + gboolean supports_remove; + gboolean supports_enable_disable; ++ gboolean always_allow_enable_disable; + } GsRepoRowPrivate; + + G_DEFINE_TYPE_WITH_PRIVATE (GsRepoRow, gs_repo_row, GTK_TYPE_LIST_BOX_ROW) +@@ -86,7 +87,7 @@ refresh_ui (GsRepoRow *row) + is_system_repo = gs_app_has_quirk (priv->repo, GS_APP_QUIRK_PROVENANCE); + + /* Disable for the system repos, if installed */ +- gtk_widget_set_sensitive (priv->disable_switch, priv->supports_enable_disable && (state_sensitive || !is_system_repo)); ++ gtk_widget_set_sensitive (priv->disable_switch, priv->supports_enable_disable && (state_sensitive || !is_system_repo || priv->always_allow_enable_disable)); + gtk_widget_set_visible (priv->remove_button, priv->supports_remove && !is_system_repo); + + /* Set only the 'state' to visually indicate the state is not saved yet */ +@@ -337,13 +338,30 @@ gs_repo_row_class_init (GsRepoRowClass *klass) + gtk_widget_class_bind_template_child_private (widget_class, GsRepoRow, disable_switch); + } + ++/* ++ * gs_repo_row_new: ++ * @plugin_loader: a #GsPluginLoader ++ * @repo: a #GsApp to represent the repo in the new row ++ * @always_allow_enable_disable: always allow enabled/disable of the @repo ++ * ++ * The @plugin_loader is used to check which operations the associated plugin ++ * for the @repo can do and which not, to show only relevant buttons on the row. ++ * ++ * The @always_allow_enable_disable, when %TRUE, means that the @repo in this row ++ * can be always enabled/disabled by the user, if supported by the related plugin, ++ * regardless of the other heuristics, which can avoid the repo enable/disable. ++ * ++ * Returns: (transfer full): a newly created #GsRepoRow ++ */ + GtkWidget * + gs_repo_row_new (GsPluginLoader *plugin_loader, +- GsApp *repo) ++ GsApp *repo, ++ gboolean always_allow_enable_disable) + { + GsRepoRow *row = g_object_new (GS_TYPE_REPO_ROW, NULL); + GsRepoRowPrivate *priv = gs_repo_row_get_instance_private (row); + priv->plugin_loader = g_object_ref (plugin_loader); ++ priv->always_allow_enable_disable = always_allow_enable_disable; + gs_repo_row_set_repo (row, repo); + return GTK_WIDGET (row); + } +diff --git a/src/gs-repo-row.h b/src/gs-repo-row.h +index e6f24bc8..83c8cdf4 100644 +--- a/src/gs-repo-row.h ++++ b/src/gs-repo-row.h +@@ -25,7 +25,8 @@ struct _GsRepoRowClass + }; + + GtkWidget *gs_repo_row_new (GsPluginLoader *plugin_loader, +- GsApp *repo); ++ GsApp *repo, ++ gboolean always_allow_enable_disable); + GsApp *gs_repo_row_get_repo (GsRepoRow *row); + void gs_repo_row_mark_busy (GsRepoRow *row); + void gs_repo_row_unmark_busy (GsRepoRow *row); +diff --git a/src/gs-repos-dialog.c b/src/gs-repos-dialog.c +index 98aa0f20..0f24149c 100644 +--- a/src/gs-repos-dialog.c ++++ b/src/gs-repos-dialog.c +@@ -484,7 +484,7 @@ add_repo (GsReposDialog *dialog, + origin_ui = g_strdup (gs_app_get_management_plugin (repo)); + section = g_hash_table_lookup (dialog->sections, origin_ui); + if (section == NULL) { +- section = gs_repos_section_new (dialog->plugin_loader); ++ section = gs_repos_section_new (dialog->plugin_loader, FALSE); + hdy_preferences_group_set_title (HDY_PREFERENCES_GROUP (section), + origin_ui); + g_signal_connect_object (section, "remove-clicked", +@@ -627,7 +627,7 @@ get_sources_cb (GsPluginLoader *plugin_loader, + gtk_container_add (GTK_CONTAINER (widget), row); + gtk_container_add (GTK_CONTAINER (dialog->content_page), widget); + +- section = GS_REPOS_SECTION (gs_repos_section_new (dialog->plugin_loader)); ++ section = GS_REPOS_SECTION (gs_repos_section_new (dialog->plugin_loader, TRUE)); + gs_repos_section_set_sort_key (section, "900"); + g_signal_connect_object (section, "switch-clicked", + G_CALLBACK (repo_section_switch_clicked_cb), dialog, 0); +diff --git a/src/gs-repos-section.c b/src/gs-repos-section.c +index 3bf59ad7..a9b08200 100644 +--- a/src/gs-repos-section.c ++++ b/src/gs-repos-section.c +@@ -20,6 +20,7 @@ struct _GsReposSection + GtkListBox *list; + GsPluginLoader *plugin_loader; + gchar *sort_key; ++ gboolean always_allow_enable_disable; + }; + + G_DEFINE_TYPE (GsReposSection, gs_repos_section, HDY_TYPE_PREFERENCES_GROUP) +@@ -130,8 +131,23 @@ gs_repos_section_init (GsReposSection *self) + G_CALLBACK (gs_repos_section_row_activated_cb), self); + } + ++/* ++ * gs_repos_section_new: ++ * @plugin_loader: a #GsPluginLoader ++ * @always_allow_enable_disable: always allow enable/disable of the repos in this section ++ * ++ * Creates a new #GsReposSection. The %plugin_loader is passed ++ * to each #GsRepoRow, the same as the @always_allow_enable_disable. ++ * ++ * The @always_allow_enable_disable, when %TRUE, means that every repo in this section ++ * can be enabled/disabled by the user, if supported by the related plugin, regardless ++ * of the other heuristics, which can avoid the repo enable/disable. ++ * ++ * Returns: (transfer full): a newly created #GsReposSection ++ */ + GtkWidget * +-gs_repos_section_new (GsPluginLoader *plugin_loader) ++gs_repos_section_new (GsPluginLoader *plugin_loader, ++ gboolean always_allow_enable_disable) + { + GsReposSection *self; + +@@ -140,6 +156,7 @@ gs_repos_section_new (GsPluginLoader *plugin_loader) + self = g_object_new (GS_TYPE_REPOS_SECTION, NULL); + + self->plugin_loader = g_object_ref (plugin_loader); ++ self->always_allow_enable_disable = always_allow_enable_disable; + + return GTK_WIDGET (self); + } +@@ -159,7 +176,7 @@ gs_repos_section_add_repo (GsReposSection *self, + if (!self->sort_key) + self->sort_key = g_strdup (gs_app_get_metadata_item (repo, "GnomeSoftware::SortKey")); + +- row = gs_repo_row_new (self->plugin_loader, repo); ++ row = gs_repo_row_new (self->plugin_loader, repo, self->always_allow_enable_disable); + + g_signal_connect (row, "remove-clicked", + G_CALLBACK (repo_remove_clicked_cb), self); +diff --git a/src/gs-repos-section.h b/src/gs-repos-section.h +index 6e29769c..9a58a3e1 100644 +--- a/src/gs-repos-section.h ++++ b/src/gs-repos-section.h +@@ -20,7 +20,8 @@ G_BEGIN_DECLS + + G_DECLARE_FINAL_TYPE (GsReposSection, gs_repos_section, GS, REPOS_SECTION, HdyPreferencesGroup) + +-GtkWidget *gs_repos_section_new (GsPluginLoader *plugin_loader); ++GtkWidget *gs_repos_section_new (GsPluginLoader *plugin_loader, ++ gboolean always_allow_enable_disable); + void gs_repos_section_add_repo (GsReposSection *self, + GsApp *repo); + const gchar *gs_repos_section_get_title (GsReposSection *self); +From dca731ff0daf904911dd6815fb9a1b181329c887 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 5 Oct 2021 11:00:20 +0200 +Subject: [PATCH 1/4] gs-repo-row: Use GS_APP_QUIRK_COMPULSORY to recognize + required repositories + +The GS_APP_QUIRK_PROVENANCE quirk does not mean it's also required repository, +thus use the GS_APP_QUIRK_COMPULSORY for repos, which cannot be disabled. +The GS_APP_QUIRK_PROVENANCE is used only for repositories, which cannot be removed. +--- + src/gs-repo-row.c | 10 ++++++---- + 1 file changed, 6 insertions(+), 4 deletions(-) + +diff --git a/src/gs-repo-row.c b/src/gs-repo-row.c +index 87926092f..bbf67c194 100644 +--- a/src/gs-repo-row.c ++++ b/src/gs-repo-row.c +@@ -48,7 +48,8 @@ refresh_ui (GsRepoRow *row) + gboolean active = FALSE; + gboolean state_sensitive = FALSE; + gboolean busy = priv->busy_counter> 0; +- gboolean is_system_repo; ++ gboolean is_provenance; ++ gboolean is_compulsory; + + if (priv->repo == NULL) { + gtk_widget_set_sensitive (priv->disable_switch, FALSE); +@@ -87,11 +88,12 @@ refresh_ui (GsRepoRow *row) + break; + } + +- is_system_repo = gs_app_has_quirk (priv->repo, GS_APP_QUIRK_PROVENANCE); ++ is_provenance = gs_app_has_quirk (priv->repo, GS_APP_QUIRK_PROVENANCE); ++ is_compulsory = gs_app_has_quirk (priv->repo, GS_APP_QUIRK_COMPULSORY); + + /* Disable for the system repos, if installed */ +- gtk_widget_set_sensitive (priv->disable_switch, priv->supports_enable_disable && (state_sensitive || !is_system_repo || priv->always_allow_enable_disable)); +- gtk_widget_set_visible (priv->remove_button, priv->supports_remove && !is_system_repo); ++ gtk_widget_set_sensitive (priv->disable_switch, priv->supports_enable_disable && (state_sensitive || !is_compulsory || priv->always_allow_enable_disable)); ++ gtk_widget_set_visible (priv->remove_button, priv->supports_remove && !is_provenance && !is_compulsory); + + /* Set only the 'state' to visually indicate the state is not saved yet */ + if (busy) +-- +GitLab + + +From 026218b9d3211de243dfc49eca8b8d46633882b0 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 5 Oct 2021 11:03:31 +0200 +Subject: [PATCH 2/4] gs-plugin-provenance: Improve search speed in list of + repositories + +Use a GHashTable for bare repository names and a GPtrArray for those +with wildcards. This helps with speed, due to not traversing all +the repository names with the fnmatch() call. +--- + plugins/core/gs-plugin-provenance.c | 55 ++++++++++++++++++++--------- + 1 file changed, 38 insertions(+), 17 deletions(-) + +diff --git a/plugins/core/gs-plugin-provenance.c b/plugins/core/gs-plugin-provenance.c +index 97ff76798..a72c25a27 100644 +--- a/plugins/core/gs-plugin-provenance.c ++++ b/plugins/core/gs-plugin-provenance.c +@@ -19,7 +19,8 @@ + + struct GsPluginData { + GSettings *settings; +- gchar **sources; ++ GHashTable *repos; /* gchar *name ~> NULL */ ++ GPtrArray *wildcards; /* non-NULL, when have names with wildcards */ + }; + + static gchar ** +@@ -42,8 +43,24 @@ gs_plugin_provenance_settings_changed_cb (GSettings *settings, + { + GsPluginData *priv = gs_plugin_get_data (plugin); + if (g_strcmp0 (key, "official-repos") == 0) { +- g_strfreev (priv->sources); +- priv->sources = gs_plugin_provenance_get_sources (plugin); ++ /* The keys are stolen by the hash table, thus free only the array */ ++ g_autofree gchar **repos = NULL; ++ g_hash_table_remove_all (priv->repos); ++ g_clear_pointer (&priv->wildcards, g_ptr_array_unref); ++ repos = gs_plugin_provenance_get_sources (plugin); ++ for (guint ii = 0; repos && repos[ii]; ii++) { ++ if (strchr (repos[ii], '*') || ++ strchr (repos[ii], '?') || ++ strchr (repos[ii], '[')) { ++ if (priv->wildcards == NULL) ++ priv->wildcards = g_ptr_array_new_with_free_func (g_free); ++ g_ptr_array_add (priv->wildcards, g_steal_pointer (&(repos[ii]))); ++ } else { ++ g_hash_table_insert (priv->repos, g_steal_pointer (&(repos[ii])), NULL); ++ } ++ } ++ if (priv->wildcards != NULL) ++ g_ptr_array_add (priv->wildcards, NULL); + } + } + +@@ -52,9 +69,10 @@ gs_plugin_initialize (GsPlugin *plugin) + { + GsPluginData *priv = gs_plugin_alloc_data (plugin, sizeof(GsPluginData)); + priv->settings = g_settings_new ("org.gnome.software"); ++ priv->repos = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); + g_signal_connect (priv->settings, "changed", + G_CALLBACK (gs_plugin_provenance_settings_changed_cb), plugin); +- priv->sources = gs_plugin_provenance_get_sources (plugin); ++ gs_plugin_provenance_settings_changed_cb (priv->settings, "official-repos", plugin); + + /* after the package source is set */ + gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_RUN_AFTER, "dummy"); +@@ -66,7 +84,8 @@ void + gs_plugin_destroy (GsPlugin *plugin) + { + GsPluginData *priv = gs_plugin_get_data (plugin); +- g_strfreev (priv->sources); ++ g_hash_table_unref (priv->repos); ++ g_clear_pointer (&priv->wildcards, g_ptr_array_unref); + g_object_unref (priv->settings); + } + +@@ -74,12 +93,12 @@ static gboolean + refine_app (GsPlugin *plugin, + GsApp *app, + GsPluginRefineFlags flags, ++ GHashTable *repos, ++ GPtrArray *wildcards, + GCancellable *cancellable, + GError **error) + { +- GsPluginData *priv = gs_plugin_get_data (plugin); + const gchar *origin; +- gchar **sources; + + /* not required */ + if ((flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_PROVENANCE) == 0) +@@ -87,14 +106,10 @@ refine_app (GsPlugin *plugin, + if (gs_app_has_quirk (app, GS_APP_QUIRK_PROVENANCE)) + return TRUE; + +- /* nothing to search */ +- sources = priv->sources; +- if (sources == NULL || sources[0] == NULL) +- return TRUE; +- + /* simple case */ + origin = gs_app_get_origin (app); +- if (origin != NULL && gs_utils_strv_fnmatch (sources, origin)) { ++ if (origin != NULL && (g_hash_table_contains (repos, origin) || ++ (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, origin)))) { + gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); + return TRUE; + } +@@ -103,7 +118,8 @@ refine_app (GsPlugin *plugin, + * provenance quirk to the system-configured repositories (but not + * user-configured ones). */ + if (gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY && +- gs_utils_strv_fnmatch (sources, gs_app_get_id (app))) { ++ (g_hash_table_contains (repos, gs_app_get_id (app)) || ++ (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, gs_app_get_id (app))))) { + if (gs_app_get_scope (app) != AS_COMPONENT_SCOPE_USER) + gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); + return TRUE; +@@ -118,7 +134,8 @@ refine_app (GsPlugin *plugin, + return TRUE; + if (g_str_has_prefix (origin + 1, "installed:")) + origin += 10; +- if (gs_utils_strv_fnmatch (sources, origin + 1)) { ++ if (g_hash_table_contains (repos, origin + 1) || ++ (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, origin + 1))) { + gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); + return TRUE; + } +@@ -133,17 +150,21 @@ gs_plugin_refine (GsPlugin *plugin, + GError **error) + { + GsPluginData *priv = gs_plugin_get_data (plugin); ++ g_autoptr(GHashTable) repos = NULL; ++ g_autoptr(GPtrArray) wildcards = NULL; + + /* nothing to do here */ + if ((flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_PROVENANCE) == 0) + return TRUE; ++ repos = g_hash_table_ref (priv->repos); ++ wildcards = priv->wildcards != NULL ? g_ptr_array_ref (priv->wildcards) : NULL; + /* nothing to search */ +- if (priv->sources == NULL || priv->sources[0] == NULL) ++ if (g_hash_table_size (repos) == 0) + return TRUE; + + for (guint i = 0; i < gs_app_list_length (list); i++) { + GsApp *app = gs_app_list_index (list, i); +- if (!refine_app (plugin, app, flags, cancellable, error)) ++ if (!refine_app (plugin, app, flags, repos, wildcards, cancellable, error)) + return FALSE; + } + +-- +GitLab + + +From b5e3356aff5fcd257248f9bb697e272c879249ae Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 5 Oct 2021 13:03:44 +0200 +Subject: [PATCH 3/4] settings: Add 'required-repos' key + +To be used to list repositories, which cannot be removed or disabled. +It's a complementary option for the 'official-repos' key. +--- + data/org.gnome.software.gschema.xml | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/data/org.gnome.software.gschema.xml b/data/org.gnome.software.gschema.xml +index db1c27ce4..0e5706b7c 100644 +--- a/data/org.gnome.software.gschema.xml ++++ b/data/org.gnome.software.gschema.xml +@@ -94,6 +94,10 @@ + [] + A list of official repositories that should not be considered 3rd party + ++ ++ [] ++ A list of required repositories that cannot be disabled or removed ++ + + [] + A list of official repositories that should be considered free software +-- +GitLab + + +From d6b8b206a596bb520a0b77066898b44a5ef18920 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Tue, 5 Oct 2021 14:16:56 +0200 +Subject: [PATCH 4/4] gs-plugin-provenance: Handle also 'required-repos' key + +Let it handle also 'required-repos' settings key, beside the 'official-repos' +key, which are close enough to share the same code and memory. With this +done the repositories can be marked as compulsory, independently from the official +repositories. + +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1479 +--- + plugins/core/gs-plugin-provenance.c | 142 +++++++++++++++++++++------- + 1 file changed, 108 insertions(+), 34 deletions(-) + +diff --git a/plugins/core/gs-plugin-provenance.c b/plugins/core/gs-plugin-provenance.c +index a72c25a27..22f3c98e1 100644 +--- a/plugins/core/gs-plugin-provenance.c ++++ b/plugins/core/gs-plugin-provenance.c +@@ -14,26 +14,61 @@ + /* + * SECTION: + * Sets the package provenance to TRUE if installed by an official +- * software source. ++ * software source. Also sets compulsory quirk when a required repository. + */ + + struct GsPluginData { + GSettings *settings; +- GHashTable *repos; /* gchar *name ~> NULL */ +- GPtrArray *wildcards; /* non-NULL, when have names with wildcards */ ++ GHashTable *repos; /* gchar *name ~> guint flags */ ++ GPtrArray *provenance_wildcards; /* non-NULL, when have names with wildcards */ ++ GPtrArray *compulsory_wildcards; /* non-NULL, when have names with wildcards */ + }; + ++static GHashTable * ++gs_plugin_provenance_remove_by_flag (GHashTable *old_repos, ++ GsAppQuirk quirk) ++{ ++ GHashTable *new_repos = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); ++ GHashTableIter iter; ++ gpointer key, value; ++ g_hash_table_iter_init (&iter, old_repos); ++ while (g_hash_table_iter_next (&iter, &key, &value)) { ++ guint flags = GPOINTER_TO_UINT (value); ++ flags = flags & (~quirk); ++ if (flags != 0) ++ g_hash_table_insert (new_repos, g_strdup (key), GUINT_TO_POINTER (flags)); ++ } ++ return new_repos; ++} ++ ++static void ++gs_plugin_provenance_add_quirks (GsApp *app, ++ guint quirks) ++{ ++ GsAppQuirk array[] = { ++ GS_APP_QUIRK_PROVENANCE, ++ GS_APP_QUIRK_COMPULSORY ++ }; ++ for (guint ii = 0; ii < G_N_ELEMENTS (array); ii++) { ++ if ((quirks & array[ii]) != 0) ++ gs_app_add_quirk (app, array[ii]); ++ } ++} ++ + static gchar ** +-gs_plugin_provenance_get_sources (GsPlugin *plugin) ++gs_plugin_provenance_get_sources (GsPlugin *plugin, ++ const gchar *key) + { + GsPluginData *priv = gs_plugin_get_data (plugin); + const gchar *tmp; + tmp = g_getenv ("GS_SELF_TEST_PROVENANCE_SOURCES"); + if (tmp != NULL) { ++ if (g_strcmp0 (key, "required-repos") == 0) ++ return NULL; + g_debug ("using custom provenance sources of %s", tmp); + return g_strsplit (tmp, ",", -1); + } +- return g_settings_get_strv (priv->settings, "official-repos"); ++ return g_settings_get_strv (priv->settings, key); + } + + static void +@@ -42,25 +77,43 @@ gs_plugin_provenance_settings_changed_cb (GSettings *settings, + GsPlugin *plugin) + { + GsPluginData *priv = gs_plugin_get_data (plugin); ++ GsAppQuirk quirk = GS_APP_QUIRK_NONE; ++ GPtrArray **pwildcards = NULL; ++ + if (g_strcmp0 (key, "official-repos") == 0) { ++ quirk = GS_APP_QUIRK_PROVENANCE; ++ pwildcards = &priv->provenance_wildcards; ++ } else if (g_strcmp0 (key, "required-repos") == 0) { ++ quirk = GS_APP_QUIRK_COMPULSORY; ++ pwildcards = &priv->compulsory_wildcards; ++ } ++ ++ if (quirk != GS_APP_QUIRK_NONE) { + /* The keys are stolen by the hash table, thus free only the array */ + g_autofree gchar **repos = NULL; +- g_hash_table_remove_all (priv->repos); +- g_clear_pointer (&priv->wildcards, g_ptr_array_unref); +- repos = gs_plugin_provenance_get_sources (plugin); ++ g_autoptr(GHashTable) old_repos = priv->repos; ++ g_autoptr(GPtrArray) old_wildcards = *pwildcards; ++ GHashTable *new_repos = gs_plugin_provenance_remove_by_flag (old_repos, quirk); ++ GPtrArray *new_wildcards = NULL; ++ repos = gs_plugin_provenance_get_sources (plugin, key); + for (guint ii = 0; repos && repos[ii]; ii++) { +- if (strchr (repos[ii], '*') || +- strchr (repos[ii], '?') || +- strchr (repos[ii], '[')) { +- if (priv->wildcards == NULL) +- priv->wildcards = g_ptr_array_new_with_free_func (g_free); +- g_ptr_array_add (priv->wildcards, g_steal_pointer (&(repos[ii]))); ++ gchar *repo = g_steal_pointer (&(repos[ii])); ++ if (strchr (repo, '*') || ++ strchr (repo, '?') || ++ strchr (repo, '[')) { ++ if (new_wildcards == NULL) ++ new_wildcards = g_ptr_array_new_with_free_func (g_free); ++ g_ptr_array_add (new_wildcards, repo); + } else { +- g_hash_table_insert (priv->repos, g_steal_pointer (&(repos[ii])), NULL); ++ g_hash_table_insert (new_repos, repo, ++ GUINT_TO_POINTER (quirk | ++ GPOINTER_TO_UINT (g_hash_table_lookup (new_repos, repo)))); + } + } +- if (priv->wildcards != NULL) +- g_ptr_array_add (priv->wildcards, NULL); ++ if (new_wildcards != NULL) ++ g_ptr_array_add (new_wildcards, NULL); ++ priv->repos = new_repos; ++ *pwildcards = new_wildcards; + } + } + +@@ -73,6 +126,7 @@ gs_plugin_initialize (GsPlugin *plugin) + g_signal_connect (priv->settings, "changed", + G_CALLBACK (gs_plugin_provenance_settings_changed_cb), plugin); + gs_plugin_provenance_settings_changed_cb (priv->settings, "official-repos", plugin); ++ gs_plugin_provenance_settings_changed_cb (priv->settings, "required-repos", plugin); + + /* after the package source is set */ + gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_RUN_AFTER, "dummy"); +@@ -85,20 +139,42 @@ gs_plugin_destroy (GsPlugin *plugin) + { + GsPluginData *priv = gs_plugin_get_data (plugin); + g_hash_table_unref (priv->repos); +- g_clear_pointer (&priv->wildcards, g_ptr_array_unref); ++ g_clear_pointer (&priv->provenance_wildcards, g_ptr_array_unref); ++ g_clear_pointer (&priv->compulsory_wildcards, g_ptr_array_unref); + g_object_unref (priv->settings); + } + ++static gboolean ++gs_plugin_provenance_find_repo_flags (GHashTable *repos, ++ GPtrArray *provenance_wildcards, ++ GPtrArray *compulsory_wildcards, ++ const gchar *repo, ++ guint *out_flags) ++{ ++ if (repo == NULL || *repo == '\0') ++ return FALSE; ++ *out_flags = GPOINTER_TO_UINT (g_hash_table_lookup (repos, repo)); ++ if (provenance_wildcards != NULL && ++ gs_utils_strv_fnmatch ((gchar **) provenance_wildcards->pdata, repo)) ++ *out_flags |= GS_APP_QUIRK_PROVENANCE; ++ if (compulsory_wildcards != NULL && ++ gs_utils_strv_fnmatch ((gchar **) compulsory_wildcards->pdata, repo)) ++ *out_flags |= GS_APP_QUIRK_COMPULSORY; ++ return *out_flags != 0; ++} ++ + static gboolean + refine_app (GsPlugin *plugin, + GsApp *app, + GsPluginRefineFlags flags, + GHashTable *repos, +- GPtrArray *wildcards, ++ GPtrArray *provenance_wildcards, ++ GPtrArray *compulsory_wildcards, + GCancellable *cancellable, + GError **error) + { + const gchar *origin; ++ guint quirks; + + /* not required */ + if ((flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_PROVENANCE) == 0) +@@ -108,9 +184,8 @@ refine_app (GsPlugin *plugin, + + /* simple case */ + origin = gs_app_get_origin (app); +- if (origin != NULL && (g_hash_table_contains (repos, origin) || +- (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, origin)))) { +- gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); ++ if (gs_plugin_provenance_find_repo_flags (repos, provenance_wildcards, compulsory_wildcards, origin, &quirks)) { ++ gs_plugin_provenance_add_quirks (app, quirks); + return TRUE; + } + +@@ -118,10 +193,9 @@ refine_app (GsPlugin *plugin, + * provenance quirk to the system-configured repositories (but not + * user-configured ones). */ + if (gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY && +- (g_hash_table_contains (repos, gs_app_get_id (app)) || +- (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, gs_app_get_id (app))))) { ++ gs_plugin_provenance_find_repo_flags (repos, provenance_wildcards, compulsory_wildcards, gs_app_get_id (app), &quirks)) { + if (gs_app_get_scope (app) != AS_COMPONENT_SCOPE_USER) +- gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); ++ gs_plugin_provenance_add_quirks (app, quirks); + return TRUE; + } + +@@ -134,11 +208,9 @@ refine_app (GsPlugin *plugin, + return TRUE; + if (g_str_has_prefix (origin + 1, "installed:")) + origin += 10; +- if (g_hash_table_contains (repos, origin + 1) || +- (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, origin + 1))) { +- gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); +- return TRUE; +- } ++ if (gs_plugin_provenance_find_repo_flags (repos, provenance_wildcards, compulsory_wildcards, origin + 1, &quirks)) ++ gs_plugin_provenance_add_quirks (app, quirks); ++ + return TRUE; + } + +@@ -151,20 +223,22 @@ gs_plugin_refine (GsPlugin *plugin, + { + GsPluginData *priv = gs_plugin_get_data (plugin); + g_autoptr(GHashTable) repos = NULL; +- g_autoptr(GPtrArray) wildcards = NULL; ++ g_autoptr(GPtrArray) provenance_wildcards = NULL; ++ g_autoptr(GPtrArray) compulsory_wildcards = NULL; + + /* nothing to do here */ + if ((flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_PROVENANCE) == 0) + return TRUE; + repos = g_hash_table_ref (priv->repos); +- wildcards = priv->wildcards != NULL ? g_ptr_array_ref (priv->wildcards) : NULL; ++ provenance_wildcards = priv->provenance_wildcards != NULL ? g_ptr_array_ref (priv->provenance_wildcards) : NULL; ++ compulsory_wildcards = priv->compulsory_wildcards != NULL ? g_ptr_array_ref (priv->compulsory_wildcards) : NULL; + /* nothing to search */ +- if (g_hash_table_size (repos) == 0) ++ if (g_hash_table_size (repos) == 0 && provenance_wildcards == NULL && compulsory_wildcards == NULL) + return TRUE; + + for (guint i = 0; i < gs_app_list_length (list); i++) { + GsApp *app = gs_app_list_index (list, i); +- if (!refine_app (plugin, app, flags, repos, wildcards, cancellable, error)) ++ if (!refine_app (plugin, app, flags, repos, provenance_wildcards, compulsory_wildcards, cancellable, error)) + return FALSE; + } + +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index 3d5d2f8..d40099d 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 41.0 -Release: 3%{?dist} +Release: 4%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -22,6 +22,9 @@ Source0: https://download.gnome.org/sources/gnome-software/41/%{name}-%{tarbal Patch01: 0001-crash-with-broken-theme.patch Patch02: 0002-correct-update-notifications.patch Patch03: 0003-refresh-on-repository-change.patch +Patch04: 0004-filtered-system-flathub.patch +Patch05: 0005-repos-dialog-can-show-apps.patch +Patch06: 0006-optional-repos-cannot-be-disabled.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -134,6 +137,7 @@ cat >> %{buildroot}%{_datadir}/glib-2.0/schemas/org.gnome.software-fedora.gschem official-repos = [ 'rhel-%{?rhel}' ] %else official-repos = [ 'anaconda', 'fedora', 'fedora-debuginfo', 'fedora-source', 'koji-override-0', 'koji-override-1', 'rawhide', 'rawhide-debuginfo', 'rawhide-source', 'updates', 'updates-debuginfo', 'updates-source', 'updates-testing', 'updates-testing-debuginfo', 'updates-testing-source', 'fedora-modular', 'fedora-modular-debuginfo', 'fedora-modular-source', 'rawhide-modular', 'rawhide-modular-debuginfo', 'rawhide-modular-source', 'fedora-cisco-openh264', 'fedora-cisco-openh264-debuginfo' ] +required-repos = [ 'fedora', 'updates' ] %endif FOE @@ -204,6 +208,11 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri Oct 08 2021 Milan Crha - 41.0-4 +- Resolves: #2011176 (flathub repo can't be added through gnome-software) +- Resolves: #2010660 (gs-repos-dialog: Can show also desktop applications) +- Resolves: #2010353 (Optional repos cannot be disabled) + * Thu Oct 07 2021 Milan Crha - 41.0-3 - Resolves: #2010740 (Refresh on repository setup change) From 5b411a73e700c6611ed3bdf584588460b51386b0 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 11 Oct 2021 09:19:59 +0200 Subject: [PATCH 038/163] Add patch to mark compulsory only repos, not apps from it --- 0007-compulsory-only-for-repos.patch | 42 ++++++++++++++++++++++++++++ gnome-software.spec | 6 +++- 2 files changed, 47 insertions(+), 1 deletion(-) create mode 100644 0007-compulsory-only-for-repos.patch diff --git a/0007-compulsory-only-for-repos.patch b/0007-compulsory-only-for-repos.patch new file mode 100644 index 0000000..fb266df --- /dev/null +++ b/0007-compulsory-only-for-repos.patch @@ -0,0 +1,42 @@ +From 895d1ca748f4f33a852853f5f07903fb549fb66f Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Mon, 11 Oct 2021 09:13:59 +0200 +Subject: [PATCH] gs-plugin-provenance: Set COMPULSORY quirk only on REPOSITORY + apps + +The compulsory quirk related to repositories, which cannot be removed, +not to the applications provided by those repositories, thus set that +quirk only on repositories, not on the apps from it. + +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1488 +--- + plugins/core/gs-plugin-provenance.c | 13 +++++-------- + 1 file changed, 5 insertions(+), 8 deletions(-) + +diff --git a/plugins/core/gs-plugin-provenance.c b/plugins/core/gs-plugin-provenance.c +index 22f3c98e..e44a55f0 100644 +--- a/plugins/core/gs-plugin-provenance.c ++++ b/plugins/core/gs-plugin-provenance.c +@@ -45,14 +45,11 @@ static void + gs_plugin_provenance_add_quirks (GsApp *app, + guint quirks) + { +- GsAppQuirk array[] = { +- GS_APP_QUIRK_PROVENANCE, +- GS_APP_QUIRK_COMPULSORY +- }; +- for (guint ii = 0; ii < G_N_ELEMENTS (array); ii++) { +- if ((quirks & array[ii]) != 0) +- gs_app_add_quirk (app, array[ii]); +- } ++ if ((quirks & GS_APP_QUIRK_PROVENANCE) != 0) ++ gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); ++ if ((quirks & GS_APP_QUIRK_COMPULSORY) != 0 && ++ gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY) ++ gs_app_add_quirk (app, GS_APP_QUIRK_COMPULSORY); + } + + static gchar ** +-- +2.31.1 + diff --git a/gnome-software.spec b/gnome-software.spec index d40099d..3993d43 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 41.0 -Release: 4%{?dist} +Release: 5%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -25,6 +25,7 @@ Patch03: 0003-refresh-on-repository-change.patch Patch04: 0004-filtered-system-flathub.patch Patch05: 0005-repos-dialog-can-show-apps.patch Patch06: 0006-optional-repos-cannot-be-disabled.patch +Patch07: 0007-compulsory-only-for-repos.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -208,6 +209,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Oct 11 2021 Milan Crha - 41.0-5 +- Add patch to mark compulsory only repos, not apps from it + * Fri Oct 08 2021 Milan Crha - 41.0-4 - Resolves: #2011176 (flathub repo can't be added through gnome-software) - Resolves: #2010660 (gs-repos-dialog: Can show also desktop applications) From 77240ed208913c9a4d53cd8c121916d9955aba9e Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Tue, 19 Oct 2021 07:57:57 +0200 Subject: [PATCH 039/163] Resolves: #2012863 (gs-installed-page: Change section on application state change) --- 0008-installed-page-section-change.patch | 264 +++++++++++++++++++++++ gnome-software.spec | 6 +- 2 files changed, 269 insertions(+), 1 deletion(-) create mode 100644 0008-installed-page-section-change.patch diff --git a/0008-installed-page-section-change.patch b/0008-installed-page-section-change.patch new file mode 100644 index 0000000..fd91a2b --- /dev/null +++ b/0008-installed-page-section-change.patch @@ -0,0 +1,264 @@ +From 65551cf41c8d6b3dcf0cf9b2ee2d46201b4e0ea4 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Thu, 14 Oct 2021 15:17:52 +0200 +Subject: [PATCH] gs-installed-page: Change section on application state change + +When an application is being installed, it's shown in the "In Progress" +section, but when the installation is finished it had been left in +that section, even it belongs to a different section. + +Similarly with the uninstall, the application was sorted to the top +of the section, but it might be better to be added to the "In Progress" +section. + +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1492 +--- + src/gs-installed-page.c | 168 +++++++++++++++++++++++++++++++++------- + 1 file changed, 141 insertions(+), 27 deletions(-) + +diff --git a/src/gs-installed-page.c b/src/gs-installed-page.c +index 67a4b7a51..56bf19df7 100644 +--- a/src/gs-installed-page.c ++++ b/src/gs-installed-page.c +@@ -59,6 +59,9 @@ static GParamSpec *obj_props[PROP_IS_NARROW + 1] = { NULL, }; + + static void gs_installed_page_pending_apps_changed_cb (GsPluginLoader *plugin_loader, + GsInstalledPage *self); ++static void gs_installed_page_notify_state_changed_cb (GsApp *app, ++ GParamSpec *pspec, ++ GsInstalledPage *self); + + typedef enum { + GS_UPDATE_LIST_SECTION_INSTALLING_AND_REMOVING, +@@ -91,6 +94,30 @@ gs_installed_page_get_app_section (GsApp *app) + return GS_UPDATE_LIST_SECTION_ADDONS; + } + ++static GsInstalledPageSection ++gs_installed_page_get_row_section (GsInstalledPage *self, ++ GsAppRow *app_row) ++{ ++ GtkWidget *parent; ++ ++ g_return_val_if_fail (GS_IS_INSTALLED_PAGE (self), GS_UPDATE_LIST_SECTION_LAST); ++ g_return_val_if_fail (GS_IS_APP_ROW (app_row), GS_UPDATE_LIST_SECTION_LAST); ++ ++ parent = gtk_widget_get_parent (GTK_WIDGET (app_row)); ++ if (parent == self->list_box_install_in_progress) ++ return GS_UPDATE_LIST_SECTION_INSTALLING_AND_REMOVING; ++ if (parent == self->list_box_install_apps) ++ return GS_UPDATE_LIST_SECTION_REMOVABLE_APPS; ++ if (parent == self->list_box_install_system_apps) ++ return GS_UPDATE_LIST_SECTION_SYSTEM_APPS; ++ if (parent == self->list_box_install_addons) ++ return GS_UPDATE_LIST_SECTION_ADDONS; ++ ++ g_warn_if_reached (); ++ ++ return GS_UPDATE_LIST_SECTION_LAST; ++} ++ + static void + gs_installed_page_invalidate (GsInstalledPage *self) + { +@@ -121,15 +148,29 @@ row_unrevealed (GObject *row, GParamSpec *pspec, gpointer data) + static void + gs_installed_page_unreveal_row (GsAppRow *app_row) + { +- g_signal_connect (app_row, "unrevealed", +- G_CALLBACK (row_unrevealed), NULL); +- gs_app_row_unreveal (app_row); ++ GsApp *app = gs_app_row_get_app (app_row); ++ if (app != NULL) { ++ g_signal_handlers_disconnect_matched (app, G_SIGNAL_MATCH_FUNC, 0, 0, NULL, ++ G_CALLBACK (gs_installed_page_notify_state_changed_cb), NULL); ++ } ++ ++ /* This check is required, because GsAppRow does not emit ++ * the signal when the row is not realized. This can happen ++ * when installing/uninstalling an app without visiting ++ * the Installed page. */ ++ if (!gtk_widget_get_mapped (GTK_WIDGET (app_row))) { ++ row_unrevealed (G_OBJECT (app_row), NULL, NULL); ++ } else { ++ g_signal_connect (app_row, "unrevealed", ++ G_CALLBACK (row_unrevealed), NULL); ++ gs_app_row_unreveal (app_row); ++ } + } + +-static void +-gs_installed_page_app_removed (GsPage *page, GsApp *app) ++static GsAppRow * /* (transfer none) */ ++gs_installed_page_find_app_row (GsInstalledPage *self, ++ GsApp *app) + { +- GsInstalledPage *self = GS_INSTALLED_PAGE (page); + GtkWidget *lists[] = { + self->list_box_install_in_progress, + self->list_box_install_apps, +@@ -145,10 +186,22 @@ gs_installed_page_app_removed (GsPage *page, GsApp *app) + for (GList *l = children; l; l = l->next) { + GsAppRow *app_row = GS_APP_ROW (l->data); + if (gs_app_row_get_app (app_row) == app) { +- gs_installed_page_unreveal_row (app_row); ++ return app_row; + } + } + } ++ ++ return NULL; ++} ++ ++ ++static void ++gs_installed_page_app_removed (GsPage *page, GsApp *app) ++{ ++ GsInstalledPage *self = GS_INSTALLED_PAGE (page); ++ GsAppRow *app_row = gs_installed_page_find_app_row (self, app); ++ if (app_row != NULL) ++ gs_installed_page_unreveal_row (app_row); + } + + static void +@@ -161,12 +214,56 @@ gs_installed_page_app_remove_cb (GsAppRow *app_row, + gs_page_remove_app (GS_PAGE (self), app, self->cancellable); + } + +-static gboolean +-gs_installed_page_invalidate_sort_idle (gpointer user_data) ++static void ++gs_installed_page_maybe_move_app_row (GsInstalledPage *self, ++ GsAppRow *app_row) ++{ ++ GsInstalledPageSection current_section, expected_section; ++ ++ current_section = gs_installed_page_get_row_section (self, app_row); ++ g_return_if_fail (current_section != GS_UPDATE_LIST_SECTION_LAST); ++ ++ expected_section = gs_installed_page_get_app_section (gs_app_row_get_app (app_row)); ++ if (expected_section != current_section) { ++ GtkWidget *widget = GTK_WIDGET (app_row); ++ ++ g_object_ref (app_row); ++ gtk_container_remove (GTK_CONTAINER (gtk_widget_get_parent (widget)), widget); ++ switch (expected_section) { ++ case GS_UPDATE_LIST_SECTION_INSTALLING_AND_REMOVING: ++ widget = self->list_box_install_in_progress; ++ break; ++ case GS_UPDATE_LIST_SECTION_REMOVABLE_APPS: ++ widget = self->list_box_install_apps; ++ break; ++ case GS_UPDATE_LIST_SECTION_SYSTEM_APPS: ++ widget = self->list_box_install_system_apps; ++ break; ++ case GS_UPDATE_LIST_SECTION_ADDONS: ++ widget = self->list_box_install_addons; ++ break; ++ default: ++ g_warn_if_reached (); ++ widget = NULL; ++ break; ++ } ++ ++ if (widget != NULL) ++ gtk_container_add (GTK_CONTAINER (widget), GTK_WIDGET (app_row)); ++ ++ g_object_unref (app_row); ++ } ++} ++ ++static void ++gs_installed_page_notify_state_changed_cb (GsApp *app, ++ GParamSpec *pspec, ++ GsInstalledPage *self) + { +- GsAppRow *app_row = user_data; +- GsApp *app = gs_app_row_get_app (app_row); + GsAppState state = gs_app_get_state (app); ++ GsAppRow *app_row = gs_installed_page_find_app_row (self, app); ++ ++ g_assert (app_row != NULL); + + gtk_list_box_row_changed (GTK_LIST_BOX_ROW (app_row)); + +@@ -177,17 +274,8 @@ gs_installed_page_invalidate_sort_idle (gpointer user_data) + state != GS_APP_STATE_UPDATABLE && + state != GS_APP_STATE_UPDATABLE_LIVE) + gs_installed_page_unreveal_row (app_row); +- +- g_object_unref (app_row); +- return G_SOURCE_REMOVE; +-} +- +-static void +-gs_installed_page_notify_state_changed_cb (GsApp *app, +- GParamSpec *pspec, +- GsAppRow *app_row) +-{ +- g_idle_add (gs_installed_page_invalidate_sort_idle, g_object_ref (app_row)); ++ else ++ gs_installed_page_maybe_move_app_row (self, app_row); + } + + static gboolean +@@ -229,7 +317,7 @@ gs_installed_page_add_app (GsInstalledPage *self, GsAppList *list, GsApp *app) + G_CALLBACK (gs_installed_page_app_remove_cb), self); + g_signal_connect_object (app, "notify::state", + G_CALLBACK (gs_installed_page_notify_state_changed_cb), +- app_row, 0); ++ self, 0); + + switch (gs_installed_page_get_app_section (app)) { + case GS_UPDATE_LIST_SECTION_INSTALLING_AND_REMOVING: +@@ -294,6 +382,32 @@ out: + gs_installed_page_pending_apps_changed_cb (plugin_loader, self); + } + ++static void ++gs_installed_page_remove_all_cb (GtkWidget *child, ++ gpointer user_data) ++{ ++ GtkContainer *container = user_data; ++ ++ if (GS_IS_APP_ROW (child)) { ++ GsApp *app = gs_app_row_get_app (GS_APP_ROW (child)); ++ if (app != NULL) { ++ g_signal_handlers_disconnect_matched (app, G_SIGNAL_MATCH_FUNC, 0, 0, NULL, ++ G_CALLBACK (gs_installed_page_notify_state_changed_cb), NULL); ++ } ++ } else { ++ g_warn_if_reached (); ++ } ++ ++ gtk_container_remove (container, child); ++} ++ ++static void ++gs_container_remove_all_with_cb (GtkContainer *container, ++ GtkCallback callback) ++{ ++ gtk_container_foreach (container, callback, container); ++} ++ + static void + gs_installed_page_load (GsInstalledPage *self) + { +@@ -305,10 +419,10 @@ gs_installed_page_load (GsInstalledPage *self) + self->waiting = TRUE; + + /* remove old entries */ +- gs_container_remove_all (GTK_CONTAINER (self->list_box_install_in_progress)); +- gs_container_remove_all (GTK_CONTAINER (self->list_box_install_apps)); +- gs_container_remove_all (GTK_CONTAINER (self->list_box_install_system_apps)); +- gs_container_remove_all (GTK_CONTAINER (self->list_box_install_addons)); ++ gs_container_remove_all_with_cb (GTK_CONTAINER (self->list_box_install_in_progress), gs_installed_page_remove_all_cb); ++ gs_container_remove_all_with_cb (GTK_CONTAINER (self->list_box_install_apps), gs_installed_page_remove_all_cb); ++ gs_container_remove_all_with_cb (GTK_CONTAINER (self->list_box_install_system_apps), gs_installed_page_remove_all_cb); ++ gs_container_remove_all_with_cb (GTK_CONTAINER (self->list_box_install_addons), gs_installed_page_remove_all_cb); + + flags = GS_PLUGIN_REFINE_FLAGS_REQUIRE_ICON | + GS_PLUGIN_REFINE_FLAGS_REQUIRE_HISTORY | +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index 3993d43..5c9d9fc 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 41.0 -Release: 5%{?dist} +Release: 6%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -26,6 +26,7 @@ Patch04: 0004-filtered-system-flathub.patch Patch05: 0005-repos-dialog-can-show-apps.patch Patch06: 0006-optional-repos-cannot-be-disabled.patch Patch07: 0007-compulsory-only-for-repos.patch +Patch08: 0008-installed-page-section-change.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -209,6 +210,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Tue Oct 19 2021 Milan Crha - 41.0-6 +- Resolves: #2012863 (gs-installed-page: Change section on application state change) + * Mon Oct 11 2021 Milan Crha - 41.0-5 - Add patch to mark compulsory only repos, not apps from it From 856444f98aa4286c5520714658e54e317cec090b Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 29 Oct 2021 10:09:12 +0200 Subject: [PATCH 040/163] Update to 41.1 --- 0002-correct-update-notifications.patch | 116 ---- 0003-refresh-on-repository-change.patch | 233 ------- 0004-filtered-system-flathub.patch | 331 --------- 0005-repos-dialog-can-show-apps.patch | 163 ----- 0006-optional-repos-cannot-be-disabled.patch | 665 ------------------- 0007-compulsory-only-for-repos.patch | 42 -- 0008-installed-page-section-change.patch | 264 -------- gnome-software.spec | 14 +- sources | 2 +- 9 files changed, 6 insertions(+), 1824 deletions(-) delete mode 100644 0002-correct-update-notifications.patch delete mode 100644 0003-refresh-on-repository-change.patch delete mode 100644 0004-filtered-system-flathub.patch delete mode 100644 0005-repos-dialog-can-show-apps.patch delete mode 100644 0006-optional-repos-cannot-be-disabled.patch delete mode 100644 0007-compulsory-only-for-repos.patch delete mode 100644 0008-installed-page-section-change.patch diff --git a/0002-correct-update-notifications.patch b/0002-correct-update-notifications.patch deleted file mode 100644 index a8c8f08..0000000 --- a/0002-correct-update-notifications.patch +++ /dev/null @@ -1,116 +0,0 @@ -From 1b0c476d66f89332187da2894b06ec2d4b83fa2a Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Thu, 30 Sep 2021 16:28:11 +0200 -Subject: [PATCH 1/2] gs-update-monitor: Use wall-clock time for - one-notification-per-day check - -Instead of using the g_timeout_add_seconds(), which uses a monotonic time, -which may or may not increase when the machine is suspended, rather use -the wall-clock time, to avoid issues with machine suspend where the monotonic -time does not increase. ---- - src/gs-update-monitor.c | 31 +++++++++++++------------------ - 1 file changed, 13 insertions(+), 18 deletions(-) - -diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c -index bde39fbbb..787c605a1 100644 ---- a/src/gs-update-monitor.c -+++ b/src/gs-update-monitor.c -@@ -44,7 +44,8 @@ struct _GsUpdateMonitor { - guint check_startup_id; /* 60s after startup */ - guint check_hourly_id; /* and then every hour */ - guint check_daily_id; /* every 3rd day */ -- guint notification_blocked_id; /* rate limit notifications */ -+ -+ gint64 last_notification_time_usec; /* to notify once per day only */ - }; - - G_DEFINE_TYPE (GsUpdateMonitor, gs_update_monitor, G_TYPE_OBJECT) -@@ -88,14 +89,6 @@ with_app_data_free (WithAppData *data) - - G_DEFINE_AUTOPTR_CLEANUP_FUNC(WithAppData, with_app_data_free); - --static gboolean --reenable_offline_update_notification (gpointer data) --{ -- GsUpdateMonitor *monitor = data; -- monitor->notification_blocked_id = 0; -- return G_SOURCE_REMOVE; --} -- - static void - check_updates_kind (GsAppList *apps, - gboolean *out_has_important, -@@ -265,16 +258,22 @@ notify_about_pending_updates (GsUpdateMonitor *monitor, - GsAppList *apps) - { - const gchar *title = NULL, *body = NULL; -+ gint64 time_diff_sec; - g_autoptr(GNotification) nn = NULL; - -- if (monitor->notification_blocked_id > 0) -+ time_diff_sec = (g_get_real_time () - monitor->last_notification_time_usec) / G_USEC_PER_SEC; -+ if (time_diff_sec < SECONDS_IN_A_DAY) { -+ g_debug ("Skipping update notification daily check, because made one only %" G_GINT64_FORMAT "s ago", -+ time_diff_sec); - return; -+ } - -- /* rate limit update notifications to once per day */ -- monitor->notification_blocked_id = g_timeout_add_seconds (24 * SECONDS_IN_AN_HOUR, reenable_offline_update_notification, monitor); -- -- if (!should_notify_about_pending_updates (monitor, apps, &title, &body)) -+ if (!should_notify_about_pending_updates (monitor, apps, &title, &body)) { -+ g_debug ("No update notification needed"); - return; -+ } -+ -+ monitor->last_notification_time_usec = g_get_real_time (); - - g_debug ("Notify about update: '%s'", title); - -@@ -1394,10 +1393,6 @@ gs_update_monitor_dispose (GObject *object) - g_source_remove (monitor->check_startup_id); - monitor->check_startup_id = 0; - } -- if (monitor->notification_blocked_id != 0) { -- g_source_remove (monitor->notification_blocked_id); -- monitor->notification_blocked_id = 0; -- } - if (monitor->cleanup_notifications_id != 0) { - g_source_remove (monitor->cleanup_notifications_id); - monitor->cleanup_notifications_id = 0; --- -GitLab - - -From 2ff332826f841c4ea1d9458df81648868745ea41 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Thu, 30 Sep 2021 16:47:40 +0200 -Subject: [PATCH 2/2] gs-update-monitor: Correct last notification timestamp - reset - -Do not reset the notification timestamp after the list of updates -is received, that should be done when the notification had been shown. - -Reported downstream at: -https://bugzilla.redhat.com/show_bug.cgi?id=2009063 ---- - src/gs-update-monitor.c | 1 - - 1 file changed, 1 deletion(-) - -diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c -index 787c605a1..a8421fcc4 100644 ---- a/src/gs-update-monitor.c -+++ b/src/gs-update-monitor.c -@@ -613,7 +613,6 @@ get_updates_finished_cb (GObject *object, GAsyncResult *res, gpointer data) - notify_list = apps; - - notify_about_pending_updates (monitor, notify_list); -- reset_update_notification_timestamp (monitor); - } - } - --- -GitLab - diff --git a/0003-refresh-on-repository-change.patch b/0003-refresh-on-repository-change.patch deleted file mode 100644 index 3af8ef8..0000000 --- a/0003-refresh-on-repository-change.patch +++ /dev/null @@ -1,233 +0,0 @@ -From 5c203ae1b07e2c31ca39c3d6a793534d45c49125 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 5 Oct 2021 19:42:37 +0200 -Subject: [PATCH 1/5] gs-shell: Remove left-over function prototype declaration - -The function body does not exist. ---- - src/gs-shell.h | 2 -- - 1 file changed, 2 deletions(-) - -diff --git a/src/gs-shell.h b/src/gs-shell.h -index bb39fc928..46661db16 100644 ---- a/src/gs-shell.h -+++ b/src/gs-shell.h -@@ -43,8 +43,6 @@ typedef enum { - - GsShell *gs_shell_new (void); - void gs_shell_activate (GsShell *shell); --void gs_shell_refresh (GsShell *shell, -- GCancellable *cancellable); - void gs_shell_change_mode (GsShell *shell, - GsShellMode mode, - gpointer data, --- -GitLab - - -From ca49eb3974e220ff17262c6189e3cdf0a92746fe Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 5 Oct 2021 19:45:10 +0200 -Subject: [PATCH 2/5] gs-application: Introduce gs_application_refresh() - -It can be used to call a non-interactive refresh call for the plugins. ---- - src/gs-application.c | 28 ++++++++++++++++++++++++++++ - src/gs-application.h | 3 ++- - 2 files changed, 30 insertions(+), 1 deletion(-) - -diff --git a/src/gs-application.c b/src/gs-application.c -index 90487df62..df982df19 100644 ---- a/src/gs-application.c -+++ b/src/gs-application.c -@@ -1371,3 +1371,31 @@ gs_application_emit_install_resources_done (GsApplication *application, - { - g_signal_emit (application, signals[INSTALL_RESOURCES_DONE], 0, ident, op_error, NULL); - } -+ -+static void -+gs_application_refresh_cb (GsPluginLoader *plugin_loader, -+ GAsyncResult *result, -+ GsApplication *self) -+{ -+ gboolean success; -+ g_autoptr(GError) error = NULL; -+ -+ success = gs_plugin_loader_job_action_finish (plugin_loader, result, &error); -+ if (!success && -+ !g_error_matches (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_CANCELLED)) -+ g_warning ("failed to refresh: %s", error->message); -+} -+ -+void -+gs_application_refresh (GsApplication *self) -+{ -+ g_autoptr(GsPluginJob) plugin_job = NULL; -+ plugin_job = gs_plugin_job_newv (GS_PLUGIN_ACTION_REFRESH, -+ "interactive", FALSE, -+ "age", (guint64) 1, -+ NULL); -+ gs_plugin_loader_job_process_async (self->plugin_loader, plugin_job, -+ self->cancellable, -+ (GAsyncReadyCallback) gs_application_refresh_cb, -+ self); -+} -diff --git a/src/gs-application.h b/src/gs-application.h -index 40bad4d4c..92978e1f5 100644 ---- a/src/gs-application.h -+++ b/src/gs-application.h -@@ -23,4 +23,5 @@ gboolean gs_application_has_active_window (GsApplication *application); - void gs_application_emit_install_resources_done - (GsApplication *application, - const gchar *ident, -- const GError *op_error); -\ No newline at end of file -+ const GError *op_error); -+void gs_application_refresh (GsApplication *self); --- -GitLab - - -From 2781d350a9a9ee1fd2078928f4e0933a34e05b9f Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 5 Oct 2021 19:46:17 +0200 -Subject: [PATCH 3/5] gs-repos-dialog: Call refresh on repository setup change - -When a repository is enabled/disabled/removed, call also the refresh -on the plugins, thus the data from those repos are available for the user. - -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1486 ---- - src/gs-repos-dialog.c | 16 ++++++++++++++++ - 1 file changed, 16 insertions(+) - -diff --git a/src/gs-repos-dialog.c b/src/gs-repos-dialog.c -index 1d6a82f48..c986ad724 100644 ---- a/src/gs-repos-dialog.c -+++ b/src/gs-repos-dialog.c -@@ -13,6 +13,7 @@ - #include "gs-repos-dialog.h" - - #include "gnome-software-private.h" -+#include "gs-application.h" - #include "gs-common.h" - #include "gs-os-release.h" - #include "gs-repo-row.h" -@@ -35,6 +36,8 @@ struct _GsReposDialog - GtkWidget *content_page; - GtkWidget *spinner; - GtkWidget *stack; -+ -+ gboolean changed; - }; - - G_DEFINE_TYPE (GsReposDialog, gs_repos_dialog, HDY_TYPE_WINDOW) -@@ -115,6 +118,8 @@ repo_enabled_cb (GObject *source, - } - - g_debug ("finished %s repo %s", action_str, gs_app_get_id (install_remove_data->repo)); -+ -+ install_remove_data->dialog->changed = TRUE; - } - - static void -@@ -710,6 +715,17 @@ gs_repos_dialog_dispose (GObject *object) - g_clear_object (&dialog->cancellable); - g_clear_object (&dialog->settings); - -+ if (dialog->changed) { -+ GApplication *app; -+ -+ dialog->changed = FALSE; -+ g_debug ("Repository setup changed, calling refresh..."); -+ -+ app = g_application_get_default (); -+ if (app) -+ gs_application_refresh (GS_APPLICATION (app)); -+ } -+ - G_OBJECT_CLASS (gs_repos_dialog_parent_class)->dispose (object); - } - --- -GitLab - - -From 4c6f4f20c904600a3c5d8ea446ed3c3b0ef0808d Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 6 Oct 2021 14:41:55 +0200 -Subject: [PATCH 4/5] gs-application: Invoke page reload after the refresh is - finished - -The refresh can cause new applications or alternative sources being -found in the newly enabled repositories, thus reload the pages, to -reflect the current state. ---- - src/gs-application.c | 3 +++ - 1 file changed, 3 insertions(+) - -diff --git a/src/gs-application.c b/src/gs-application.c -index df982df19..6ecc093f1 100644 ---- a/src/gs-application.c -+++ b/src/gs-application.c -@@ -1384,6 +1384,9 @@ gs_application_refresh_cb (GsPluginLoader *plugin_loader, - if (!success && - !g_error_matches (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_CANCELLED)) - g_warning ("failed to refresh: %s", error->message); -+ -+ if (success) -+ g_signal_emit_by_name (self->plugin_loader, "reload", 0, NULL); - } - - void --- -GitLab - - -From b1277d97ba4495de434eb3be4ea1f17b80ac1ef8 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 6 Oct 2021 14:44:09 +0200 -Subject: [PATCH 5/5] gs-overview-page: Refresh the application after - third-party repositories enable/disable - -The enable/disable can cause other applications being found, thus call -the refresh, to update the repositories information. ---- - src/gs-overview-page.c | 7 +++++++ - 1 file changed, 7 insertions(+) - -diff --git a/src/gs-overview-page.c b/src/gs-overview-page.c -index 9ba33fb2b..bcf02243d 100644 ---- a/src/gs-overview-page.c -+++ b/src/gs-overview-page.c -@@ -13,6 +13,7 @@ - #include - #include - -+#include "gs-application.h" - #include "gs-shell.h" - #include "gs-overview-page.h" - #include "gs-app-list-private.h" -@@ -568,6 +569,8 @@ third_party_response_cb (GtkInfoBar *info_bar, - gint response_id, - GsOverviewPage *self) - { -+ GApplication *application; -+ - if (response_id == GTK_RESPONSE_YES) - fedora_third_party_enable (self); - else -@@ -575,6 +578,10 @@ third_party_response_cb (GtkInfoBar *info_bar, - - self->third_party_needs_question = FALSE; - refresh_third_party_repo (self); -+ -+ application = g_application_get_default (); -+ if (application) -+ gs_application_refresh (GS_APPLICATION (application)); - } - - static gboolean --- -GitLab - diff --git a/0004-filtered-system-flathub.patch b/0004-filtered-system-flathub.patch deleted file mode 100644 index 93cd865..0000000 --- a/0004-filtered-system-flathub.patch +++ /dev/null @@ -1,331 +0,0 @@ -From 03ea59cc8db6bec34d56205d62ec495315e9ea96 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 21 Sep 2021 13:55:57 +0200 -Subject: [PATCH 1/5] gs-page: Use correct action when install/remove repo app - -Since the split of the install/remove action for apps and repos -the GsPage should use correct action too. This can happen for example -when installing a .flatpakrepo file. ---- - src/gs-page.c | 10 ++++++++-- - 1 file changed, 8 insertions(+), 2 deletions(-) - -diff --git a/src/gs-page.c b/src/gs-page.c -index ca1fbfc70..dfaadbc39 100644 ---- a/src/gs-page.c -+++ b/src/gs-page.c -@@ -280,7 +280,10 @@ gs_page_install_app (GsPage *page, - } - - helper = g_slice_new0 (GsPageHelper); -- helper->action = GS_PLUGIN_ACTION_INSTALL; -+ if (gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY) -+ helper->action = GS_PLUGIN_ACTION_INSTALL_REPO; -+ else -+ helper->action = GS_PLUGIN_ACTION_INSTALL; - helper->app = g_object_ref (app); - helper->page = g_object_ref (page); - helper->cancellable = g_object_ref (cancellable); -@@ -466,7 +469,10 @@ gs_page_remove_app (GsPage *page, GsApp *app, GCancellable *cancellable) - - /* pending install */ - helper = g_slice_new0 (GsPageHelper); -- helper->action = GS_PLUGIN_ACTION_REMOVE; -+ if (gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY) -+ helper->action = GS_PLUGIN_ACTION_REMOVE_REPO; -+ else -+ helper->action = GS_PLUGIN_ACTION_REMOVE; - helper->app = g_object_ref (app); - helper->page = g_object_ref (page); - helper->cancellable = cancellable != NULL ? g_object_ref (cancellable) : NULL; --- -GitLab - - -From 576f9e6d25fcd3edd7fdf769e342a382af1307e3 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 21 Sep 2021 13:58:03 +0200 -Subject: [PATCH 2/5] flatpak: Save also remote's filter on the flatpak-app - -This can be used when updating existing remote, to reflect the new -filter. It can be also used to verify the installed and existing -remotes match with its filter. ---- - plugins/flatpak/gs-flatpak-app.c | 12 ++++++++++++ - plugins/flatpak/gs-flatpak-app.h | 3 +++ - 2 files changed, 15 insertions(+) - -diff --git a/plugins/flatpak/gs-flatpak-app.c b/plugins/flatpak/gs-flatpak-app.c -index cf98248a8..b59515b2f 100644 ---- a/plugins/flatpak/gs-flatpak-app.c -+++ b/plugins/flatpak/gs-flatpak-app.c -@@ -176,3 +176,15 @@ gs_flatpak_app_get_main_app_ref_name (GsApp *app) - { - return gs_app_get_metadata_item (app, "flatpak::mainApp"); - } -+ -+void -+gs_flatpak_app_set_repo_filter (GsApp *app, const gchar *filter) -+{ -+ gs_app_set_metadata (app, "flatpak::RepoFilter", filter); -+} -+ -+const gchar * -+gs_flatpak_app_get_repo_filter (GsApp *app) -+{ -+ return gs_app_get_metadata_item (app, "flatpak::RepoFilter"); -+} -diff --git a/plugins/flatpak/gs-flatpak-app.h b/plugins/flatpak/gs-flatpak-app.h -index ab6c10af4..610c8a8f3 100644 ---- a/plugins/flatpak/gs-flatpak-app.h -+++ b/plugins/flatpak/gs-flatpak-app.h -@@ -58,5 +58,8 @@ void gs_flatpak_app_set_runtime_url (GsApp *app, - void gs_flatpak_app_set_main_app_ref_name (GsApp *app, - const gchar *main_app_ref); - const gchar *gs_flatpak_app_get_main_app_ref_name (GsApp *app); -+void gs_flatpak_app_set_repo_filter (GsApp *app, -+ const gchar *filter); -+const gchar *gs_flatpak_app_get_repo_filter (GsApp *app); - - G_END_DECLS --- -GitLab - - -From cb809158e81157b53245e4c290ada418d5bcd03d Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 21 Sep 2021 14:02:47 +0200 -Subject: [PATCH 3/5] flatpak: Store filter and description on a remote app - -Store the description also on an installed remote, not only on the file -remote. Similarly store also the filters for the remotes. ---- - plugins/flatpak/gs-flatpak-utils.c | 14 ++++++++++++++ - 1 file changed, 14 insertions(+) - -diff --git a/plugins/flatpak/gs-flatpak-utils.c b/plugins/flatpak/gs-flatpak-utils.c -index 8b107b37c..7aa735b0b 100644 ---- a/plugins/flatpak/gs-flatpak-utils.c -+++ b/plugins/flatpak/gs-flatpak-utils.c -@@ -72,6 +72,8 @@ gs_flatpak_app_new_from_remote (GsPlugin *plugin, - { - g_autofree gchar *title = NULL; - g_autofree gchar *url = NULL; -+ g_autofree gchar *filter = NULL; -+ g_autofree gchar *description = NULL; - g_autoptr(GsApp) app = NULL; - - app = gs_flatpak_app_new (flatpak_remote_get_name (xremote)); -@@ -101,11 +103,19 @@ gs_flatpak_app_new_from_remote (GsPlugin *plugin, - * not the remote title */ - gs_app_set_origin_ui (app, _("Applications")); - -+ description = flatpak_remote_get_description (xremote); -+ if (description != NULL) -+ gs_app_set_description (app, GS_APP_QUALITY_NORMAL, description); -+ - /* url */ - url = flatpak_remote_get_url (xremote); - if (url != NULL) - gs_app_set_url (app, AS_URL_KIND_HOMEPAGE, url); - -+ filter = flatpak_remote_get_filter (xremote); -+ if (filter != NULL) -+ gs_flatpak_app_set_repo_filter (app, filter); -+ - /* success */ - return g_steal_pointer (&app); - } -@@ -127,6 +137,7 @@ gs_flatpak_app_new_from_repo_file (GFile *file, - g_autofree gchar *repo_id = NULL; - g_autofree gchar *repo_title = NULL; - g_autofree gchar *repo_url = NULL; -+ g_autofree gchar *repo_filter = NULL; - g_autoptr(GError) error_local = NULL; - g_autoptr(GKeyFile) kf = NULL; - g_autoptr(GsApp) app = NULL; -@@ -229,6 +240,9 @@ gs_flatpak_app_new_from_repo_file (GFile *file, - g_autoptr(GIcon) icon = gs_remote_icon_new (repo_icon); - gs_app_add_icon (app, icon); - } -+ repo_filter = g_key_file_get_string (kf, "Flatpak Repo", "Filter", NULL); -+ if (repo_filter != NULL && *repo_filter != '\0') -+ gs_flatpak_app_set_repo_filter (app, repo_filter); - - /* success */ - return g_steal_pointer (&app); --- -GitLab - - -From a4f8501e3e54b702b5ff2af4bb9aaf6f8d6c324c Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 21 Sep 2021 14:05:03 +0200 -Subject: [PATCH 4/5] flatpak: Match existing and file remote only if it - matches also the filter - -The filter can change the content, thus match two remotes only if also -the filter matches. ---- - plugins/flatpak/gs-plugin-flatpak.c | 2 ++ - 1 file changed, 2 insertions(+) - -diff --git a/plugins/flatpak/gs-plugin-flatpak.c b/plugins/flatpak/gs-plugin-flatpak.c -index 9bdfa80bf..29ba29700 100644 ---- a/plugins/flatpak/gs-plugin-flatpak.c -+++ b/plugins/flatpak/gs-plugin-flatpak.c -@@ -1287,6 +1287,8 @@ gs_plugin_flatpak_file_to_app_repo (GsPlugin *plugin, - g_debug ("%s", error_local->message); - continue; - } -+ if (g_strcmp0 (gs_flatpak_app_get_repo_filter (app), gs_flatpak_app_get_repo_filter (app_tmp)) != 0) -+ continue; - return g_steal_pointer (&app_tmp); - } - --- -GitLab - - -From 2a94efbda64d94ba6ac27cfd08190b62f52df000 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 21 Sep 2021 14:06:35 +0200 -Subject: [PATCH 5/5] flatpak: Update existing remote from a .flatpakref file - -Update existing remote's title, description and filter when installing -a .flatpakref file, to match what had been installed, with new-enough -flatpak library. - -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1453 ---- - plugins/flatpak/gs-flatpak-utils.c | 6 ++++++ - plugins/flatpak/gs-flatpak.c | 11 +++++++++-- - 2 files changed, 15 insertions(+), 2 deletions(-) - -diff --git a/plugins/flatpak/gs-flatpak-utils.c b/plugins/flatpak/gs-flatpak-utils.c -index 7aa735b0b..ec0b397e3 100644 ---- a/plugins/flatpak/gs-flatpak-utils.c -+++ b/plugins/flatpak/gs-flatpak-utils.c -@@ -72,8 +72,10 @@ gs_flatpak_app_new_from_remote (GsPlugin *plugin, - { - g_autofree gchar *title = NULL; - g_autofree gchar *url = NULL; -+ #if FLATPAK_CHECK_VERSION(1, 4, 0) - g_autofree gchar *filter = NULL; - g_autofree gchar *description = NULL; -+ #endif - g_autoptr(GsApp) app = NULL; - - app = gs_flatpak_app_new (flatpak_remote_get_name (xremote)); -@@ -103,18 +105,22 @@ gs_flatpak_app_new_from_remote (GsPlugin *plugin, - * not the remote title */ - gs_app_set_origin_ui (app, _("Applications")); - -+ #if FLATPAK_CHECK_VERSION(1, 4, 0) - description = flatpak_remote_get_description (xremote); - if (description != NULL) - gs_app_set_description (app, GS_APP_QUALITY_NORMAL, description); -+ #endif - - /* url */ - url = flatpak_remote_get_url (xremote); - if (url != NULL) - gs_app_set_url (app, AS_URL_KIND_HOMEPAGE, url); - -+ #if FLATPAK_CHECK_VERSION(1, 4, 0) - filter = flatpak_remote_get_filter (xremote); - if (filter != NULL) - gs_flatpak_app_set_repo_filter (app, filter); -+ #endif - - /* success */ - return g_steal_pointer (&app); -diff --git a/plugins/flatpak/gs-flatpak.c b/plugins/flatpak/gs-flatpak.c -index 55a91af2a..fa7df00c9 100644 ---- a/plugins/flatpak/gs-flatpak.c -+++ b/plugins/flatpak/gs-flatpak.c -@@ -1608,9 +1608,16 @@ gs_flatpak_app_install_source (GsFlatpak *self, - gs_app_get_id (app), - cancellable, NULL); - if (xremote != NULL) { -- /* if the remote already exists, just enable it */ -- g_debug ("enabling existing remote %s", flatpak_remote_get_name (xremote)); -+ /* if the remote already exists, just enable it and update it */ -+ g_debug ("modifying existing remote %s", flatpak_remote_get_name (xremote)); - flatpak_remote_set_disabled (xremote, FALSE); -+ if (gs_flatpak_app_get_file_kind (app) == GS_FLATPAK_APP_FILE_KIND_REPO) { -+ flatpak_remote_set_title (xremote, gs_app_get_origin_ui (app)); -+ #if FLATPAK_CHECK_VERSION(1, 4, 0) -+ flatpak_remote_set_filter (xremote, gs_flatpak_app_get_repo_filter (app)); -+ flatpak_remote_set_description (xremote, gs_app_get_description (app)); -+ #endif -+ } - } else if (!is_install) { - g_set_error (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_FAILED, "Cannot enable flatpak remote '%s', remote not found", gs_app_get_id (app)); - } else { --- -GitLab - -From 1a32bd3eaaf7ec0322c46599e3b949080a410806 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Thu, 7 Oct 2021 19:28:38 +0200 -Subject: [PATCH] flatpak: Update remote appstream data when its filter changed - -When overwriting existing remote, make sure the appstream data is updated -as well when the filter changed, to have shown relevant applications. - -Related to https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1453 ---- - plugins/flatpak/gs-flatpak.c | 18 +++++++++++++++++- - 1 file changed, 17 insertions(+), 1 deletion(-) - -diff --git a/plugins/flatpak/gs-flatpak.c b/plugins/flatpak/gs-flatpak.c -index bd87d57ed..88bb69a72 100644 ---- a/plugins/flatpak/gs-flatpak.c -+++ b/plugins/flatpak/gs-flatpak.c -@@ -1623,6 +1623,9 @@ gs_flatpak_app_install_source (GsFlatpak *self, - GError **error) - { - g_autoptr(FlatpakRemote) xremote = NULL; -+ #if FLATPAK_CHECK_VERSION(1, 4, 0) -+ gboolean filter_changed = FALSE; -+ #endif - - xremote = flatpak_installation_get_remote_by_name (self->installation, - gs_app_get_id (app), -@@ -1632,11 +1635,13 @@ gs_flatpak_app_install_source (GsFlatpak *self, - g_debug ("modifying existing remote %s", flatpak_remote_get_name (xremote)); - flatpak_remote_set_disabled (xremote, FALSE); - if (gs_flatpak_app_get_file_kind (app) == GS_FLATPAK_APP_FILE_KIND_REPO) { -- flatpak_remote_set_title (xremote, gs_app_get_origin_ui (app)); - #if FLATPAK_CHECK_VERSION(1, 4, 0) -+ g_autofree gchar *current_filter = flatpak_remote_get_filter (xremote); -+ filter_changed = g_strcmp0 (current_filter, gs_flatpak_app_get_repo_filter (app)) != 0; - flatpak_remote_set_filter (xremote, gs_flatpak_app_get_repo_filter (app)); - flatpak_remote_set_description (xremote, gs_app_get_description (app)); - #endif -+ flatpak_remote_set_title (xremote, gs_app_get_origin_ui (app)); - } - } else if (!is_install) { - g_set_error (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_FAILED, "Cannot enable flatpak remote '%s', remote not found", gs_app_get_id (app)); -@@ -1666,6 +1671,17 @@ gs_flatpak_app_install_source (GsFlatpak *self, - /* success */ - gs_app_set_state (app, GS_APP_STATE_INSTALLED); - -+ #if FLATPAK_CHECK_VERSION(1, 4, 0) -+ if (filter_changed) { -+ g_autoptr(GError) local_error = NULL; -+ const gchar *remote_name = flatpak_remote_get_name (xremote); -+ if (!flatpak_installation_update_appstream_sync (self->installation, remote_name, NULL, NULL, cancellable, &local_error) && -+ !g_error_matches (local_error, G_IO_ERROR, G_IO_ERROR_CANCELLED)) { -+ g_warning ("Failed to update appstream data for flatpak remote '%s': %s", -+ remote_name, local_error->message); -+ } -+ } -+ #endif - gs_plugin_repository_changed (self->plugin, app); - - return TRUE; --- -GitLab - diff --git a/0005-repos-dialog-can-show-apps.patch b/0005-repos-dialog-can-show-apps.patch deleted file mode 100644 index eb985f3..0000000 --- a/0005-repos-dialog-can-show-apps.patch +++ /dev/null @@ -1,163 +0,0 @@ -From 1338c8f47b7ebd0e3bd360499c7ab42a0da885e8 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 5 Oct 2021 16:12:33 +0200 -Subject: [PATCH 1/2] packagekit: Update GsApp state and kind only when created - the app instance - -The gs_plugin_packagekit_add_results() can reuse GsApp instances from -the plugin cache, which can already have set property state and kind, -but this was not checked for, which could cause runtime warnings about -invalid state or kind change. - -A reproducer is to open Repositories dialog, which lists available repositories -and the applications being installed in each of them (added as 'related'). -These installed applications can have set state 'updatable' or have refined -their 'kind' already. ---- - plugins/packagekit/packagekit-common.c | 15 +++++++++------ - 1 file changed, 9 insertions(+), 6 deletions(-) - -diff --git a/plugins/packagekit/packagekit-common.c b/plugins/packagekit/packagekit-common.c -index 16b53727a..dc79c2f62 100644 ---- a/plugins/packagekit/packagekit-common.c -+++ b/plugins/packagekit/packagekit-common.c -@@ -241,12 +241,14 @@ gs_plugin_packagekit_add_results (GsPlugin *plugin, - /* process packages */ - for (i = 0; i < array_filtered->len; i++) { - g_autoptr(GsApp) app = NULL; -+ GsAppState state = GS_APP_STATE_UNKNOWN; - package = g_ptr_array_index (array_filtered, i); - - app = gs_plugin_cache_lookup (plugin, pk_package_get_id (package)); - if (app == NULL) { - app = gs_app_new (NULL); - gs_plugin_packagekit_set_packaging_format (plugin, app); -+ gs_app_set_management_plugin (app, "packagekit"); - gs_app_add_source (app, pk_package_get_name (package)); - gs_app_add_source_id (app, pk_package_get_id (package)); - gs_plugin_cache_add (plugin, pk_package_get_id (package), app); -@@ -259,14 +261,13 @@ gs_plugin_packagekit_add_results (GsPlugin *plugin, - pk_package_get_summary (package)); - gs_app_set_metadata (app, "GnomeSoftware::Creator", - gs_plugin_get_name (plugin)); -- gs_app_set_management_plugin (app, "packagekit"); - gs_app_set_version (app, pk_package_get_version (package)); - switch (pk_package_get_info (package)) { - case PK_INFO_ENUM_INSTALLED: -- gs_app_set_state (app, GS_APP_STATE_INSTALLED); -+ state = GS_APP_STATE_INSTALLED; - break; - case PK_INFO_ENUM_AVAILABLE: -- gs_app_set_state (app, GS_APP_STATE_AVAILABLE); -+ state = GS_APP_STATE_AVAILABLE; - break; - case PK_INFO_ENUM_INSTALLING: - case PK_INFO_ENUM_UPDATING: -@@ -276,14 +277,16 @@ gs_plugin_packagekit_add_results (GsPlugin *plugin, - break; - case PK_INFO_ENUM_UNAVAILABLE: - case PK_INFO_ENUM_REMOVING: -- gs_app_set_state (app, GS_APP_STATE_UNAVAILABLE); -+ state = GS_APP_STATE_UNAVAILABLE; - break; - default: -- gs_app_set_state (app, GS_APP_STATE_UNKNOWN); - g_warning ("unknown info state of %s", - pk_info_enum_to_string (pk_package_get_info (package))); - } -- gs_app_set_kind (app, AS_COMPONENT_KIND_GENERIC); -+ if (state != GS_APP_STATE_UNKNOWN && gs_app_get_state (app) == GS_APP_STATE_UNKNOWN) -+ gs_app_set_state (app, state); -+ if (gs_app_get_kind (app) == AS_COMPONENT_KIND_UNKNOWN) -+ gs_app_set_kind (app, AS_COMPONENT_KIND_GENERIC); - gs_app_set_bundle_kind (app, AS_BUNDLE_KIND_PACKAGE); - gs_app_list_add (list, app); - } --- -GitLab - - -From 18a893fa83ebd10cea75831e9d9a7398a60c14ce Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 5 Oct 2021 16:18:22 +0200 -Subject: [PATCH 2/2] gs-plugin-loader: Ensure correct list is used on the job - when refining wildcards - -The plugin job is reused when refining the apps, including the wildcards, -but the gs_plugin_loader_run_refine_internal() can be called multiple times, -with different lists. Adding refined wildcards to the original list causes -invalid data being provided to the called. - -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1485 ---- - lib/gs-plugin-loader.c | 21 ++++++++++++++++++++- - 1 file changed, 20 insertions(+), 1 deletion(-) - -diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c -index 4d5240c32..7f5859a05 100644 ---- a/lib/gs-plugin-loader.c -+++ b/lib/gs-plugin-loader.c -@@ -937,14 +937,24 @@ gs_plugin_loader_run_refine_internal (GsPluginLoaderHelper *helper, - GCancellable *cancellable, - GError **error) - { -+ g_autoptr(GsAppList) previous_list = NULL; -+ -+ if (list != gs_plugin_job_get_list (helper->plugin_job)) { -+ previous_list = g_object_ref (gs_plugin_job_get_list (helper->plugin_job)); -+ gs_plugin_job_set_list (helper->plugin_job, list); -+ } -+ - /* try to adopt each application with a plugin */ - gs_plugin_loader_run_adopt (helper->plugin_loader, list); - - /* run each plugin */ - if (!gs_plugin_loader_run_refine_filter (helper, list, - GS_PLUGIN_REFINE_FLAGS_DEFAULT, -- cancellable, error)) -+ cancellable, error)) { -+ if (previous_list != NULL) -+ gs_plugin_job_set_list (helper->plugin_job, previous_list); - return FALSE; -+ } - - /* ensure these are sorted by score */ - if (gs_plugin_job_has_refine_flags (helper->plugin_job, -@@ -983,6 +993,8 @@ gs_plugin_loader_run_refine_internal (GsPluginLoaderHelper *helper, - addons_list, - cancellable, - error)) { -+ if (previous_list != NULL) -+ gs_plugin_job_set_list (helper->plugin_job, previous_list); - return FALSE; - } - } -@@ -1004,6 +1016,8 @@ gs_plugin_loader_run_refine_internal (GsPluginLoaderHelper *helper, - list2, - cancellable, - error)) { -+ if (previous_list != NULL) -+ gs_plugin_job_set_list (helper->plugin_job, previous_list); - return FALSE; - } - } -@@ -1032,11 +1046,16 @@ gs_plugin_loader_run_refine_internal (GsPluginLoaderHelper *helper, - related_list, - cancellable, - error)) { -+ if (previous_list != NULL) -+ gs_plugin_job_set_list (helper->plugin_job, previous_list); - return FALSE; - } - } - } - -+ if (previous_list != NULL) -+ gs_plugin_job_set_list (helper->plugin_job, previous_list); -+ - /* success */ - return TRUE; - } --- -GitLab - diff --git a/0006-optional-repos-cannot-be-disabled.patch b/0006-optional-repos-cannot-be-disabled.patch deleted file mode 100644 index 20777b4..0000000 --- a/0006-optional-repos-cannot-be-disabled.patch +++ /dev/null @@ -1,665 +0,0 @@ -From 429ec744e6cdf2155772d7db463ca193231facdc Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 21 Sep 2021 14:53:27 +0200 -Subject: gs-repos-dialog: Cannot disable all 3rd-party repositories - -All the 3rd-party repositories should be disable-able, thus the 3rd-party -section should not use the heuristics to disallow disable of some of them. -This could be seen on a 'flathub' Flatpak repository installed for -the system, which is not allowed to be disabled in the Flatpak section. - -diff --git a/src/gs-repo-row.c b/src/gs-repo-row.c -index 57493c2c..7df24e0e 100644 ---- a/src/gs-repo-row.c -+++ b/src/gs-repo-row.c -@@ -27,6 +27,7 @@ typedef struct - guint busy_counter; - gboolean supports_remove; - gboolean supports_enable_disable; -+ gboolean always_allow_enable_disable; - } GsRepoRowPrivate; - - G_DEFINE_TYPE_WITH_PRIVATE (GsRepoRow, gs_repo_row, GTK_TYPE_LIST_BOX_ROW) -@@ -86,7 +87,7 @@ refresh_ui (GsRepoRow *row) - is_system_repo = gs_app_has_quirk (priv->repo, GS_APP_QUIRK_PROVENANCE); - - /* Disable for the system repos, if installed */ -- gtk_widget_set_sensitive (priv->disable_switch, priv->supports_enable_disable && (state_sensitive || !is_system_repo)); -+ gtk_widget_set_sensitive (priv->disable_switch, priv->supports_enable_disable && (state_sensitive || !is_system_repo || priv->always_allow_enable_disable)); - gtk_widget_set_visible (priv->remove_button, priv->supports_remove && !is_system_repo); - - /* Set only the 'state' to visually indicate the state is not saved yet */ -@@ -337,13 +338,30 @@ gs_repo_row_class_init (GsRepoRowClass *klass) - gtk_widget_class_bind_template_child_private (widget_class, GsRepoRow, disable_switch); - } - -+/* -+ * gs_repo_row_new: -+ * @plugin_loader: a #GsPluginLoader -+ * @repo: a #GsApp to represent the repo in the new row -+ * @always_allow_enable_disable: always allow enabled/disable of the @repo -+ * -+ * The @plugin_loader is used to check which operations the associated plugin -+ * for the @repo can do and which not, to show only relevant buttons on the row. -+ * -+ * The @always_allow_enable_disable, when %TRUE, means that the @repo in this row -+ * can be always enabled/disabled by the user, if supported by the related plugin, -+ * regardless of the other heuristics, which can avoid the repo enable/disable. -+ * -+ * Returns: (transfer full): a newly created #GsRepoRow -+ */ - GtkWidget * - gs_repo_row_new (GsPluginLoader *plugin_loader, -- GsApp *repo) -+ GsApp *repo, -+ gboolean always_allow_enable_disable) - { - GsRepoRow *row = g_object_new (GS_TYPE_REPO_ROW, NULL); - GsRepoRowPrivate *priv = gs_repo_row_get_instance_private (row); - priv->plugin_loader = g_object_ref (plugin_loader); -+ priv->always_allow_enable_disable = always_allow_enable_disable; - gs_repo_row_set_repo (row, repo); - return GTK_WIDGET (row); - } -diff --git a/src/gs-repo-row.h b/src/gs-repo-row.h -index e6f24bc8..83c8cdf4 100644 ---- a/src/gs-repo-row.h -+++ b/src/gs-repo-row.h -@@ -25,7 +25,8 @@ struct _GsRepoRowClass - }; - - GtkWidget *gs_repo_row_new (GsPluginLoader *plugin_loader, -- GsApp *repo); -+ GsApp *repo, -+ gboolean always_allow_enable_disable); - GsApp *gs_repo_row_get_repo (GsRepoRow *row); - void gs_repo_row_mark_busy (GsRepoRow *row); - void gs_repo_row_unmark_busy (GsRepoRow *row); -diff --git a/src/gs-repos-dialog.c b/src/gs-repos-dialog.c -index 98aa0f20..0f24149c 100644 ---- a/src/gs-repos-dialog.c -+++ b/src/gs-repos-dialog.c -@@ -484,7 +484,7 @@ add_repo (GsReposDialog *dialog, - origin_ui = g_strdup (gs_app_get_management_plugin (repo)); - section = g_hash_table_lookup (dialog->sections, origin_ui); - if (section == NULL) { -- section = gs_repos_section_new (dialog->plugin_loader); -+ section = gs_repos_section_new (dialog->plugin_loader, FALSE); - hdy_preferences_group_set_title (HDY_PREFERENCES_GROUP (section), - origin_ui); - g_signal_connect_object (section, "remove-clicked", -@@ -627,7 +627,7 @@ get_sources_cb (GsPluginLoader *plugin_loader, - gtk_container_add (GTK_CONTAINER (widget), row); - gtk_container_add (GTK_CONTAINER (dialog->content_page), widget); - -- section = GS_REPOS_SECTION (gs_repos_section_new (dialog->plugin_loader)); -+ section = GS_REPOS_SECTION (gs_repos_section_new (dialog->plugin_loader, TRUE)); - gs_repos_section_set_sort_key (section, "900"); - g_signal_connect_object (section, "switch-clicked", - G_CALLBACK (repo_section_switch_clicked_cb), dialog, 0); -diff --git a/src/gs-repos-section.c b/src/gs-repos-section.c -index 3bf59ad7..a9b08200 100644 ---- a/src/gs-repos-section.c -+++ b/src/gs-repos-section.c -@@ -20,6 +20,7 @@ struct _GsReposSection - GtkListBox *list; - GsPluginLoader *plugin_loader; - gchar *sort_key; -+ gboolean always_allow_enable_disable; - }; - - G_DEFINE_TYPE (GsReposSection, gs_repos_section, HDY_TYPE_PREFERENCES_GROUP) -@@ -130,8 +131,23 @@ gs_repos_section_init (GsReposSection *self) - G_CALLBACK (gs_repos_section_row_activated_cb), self); - } - -+/* -+ * gs_repos_section_new: -+ * @plugin_loader: a #GsPluginLoader -+ * @always_allow_enable_disable: always allow enable/disable of the repos in this section -+ * -+ * Creates a new #GsReposSection. The %plugin_loader is passed -+ * to each #GsRepoRow, the same as the @always_allow_enable_disable. -+ * -+ * The @always_allow_enable_disable, when %TRUE, means that every repo in this section -+ * can be enabled/disabled by the user, if supported by the related plugin, regardless -+ * of the other heuristics, which can avoid the repo enable/disable. -+ * -+ * Returns: (transfer full): a newly created #GsReposSection -+ */ - GtkWidget * --gs_repos_section_new (GsPluginLoader *plugin_loader) -+gs_repos_section_new (GsPluginLoader *plugin_loader, -+ gboolean always_allow_enable_disable) - { - GsReposSection *self; - -@@ -140,6 +156,7 @@ gs_repos_section_new (GsPluginLoader *plugin_loader) - self = g_object_new (GS_TYPE_REPOS_SECTION, NULL); - - self->plugin_loader = g_object_ref (plugin_loader); -+ self->always_allow_enable_disable = always_allow_enable_disable; - - return GTK_WIDGET (self); - } -@@ -159,7 +176,7 @@ gs_repos_section_add_repo (GsReposSection *self, - if (!self->sort_key) - self->sort_key = g_strdup (gs_app_get_metadata_item (repo, "GnomeSoftware::SortKey")); - -- row = gs_repo_row_new (self->plugin_loader, repo); -+ row = gs_repo_row_new (self->plugin_loader, repo, self->always_allow_enable_disable); - - g_signal_connect (row, "remove-clicked", - G_CALLBACK (repo_remove_clicked_cb), self); -diff --git a/src/gs-repos-section.h b/src/gs-repos-section.h -index 6e29769c..9a58a3e1 100644 ---- a/src/gs-repos-section.h -+++ b/src/gs-repos-section.h -@@ -20,7 +20,8 @@ G_BEGIN_DECLS - - G_DECLARE_FINAL_TYPE (GsReposSection, gs_repos_section, GS, REPOS_SECTION, HdyPreferencesGroup) - --GtkWidget *gs_repos_section_new (GsPluginLoader *plugin_loader); -+GtkWidget *gs_repos_section_new (GsPluginLoader *plugin_loader, -+ gboolean always_allow_enable_disable); - void gs_repos_section_add_repo (GsReposSection *self, - GsApp *repo); - const gchar *gs_repos_section_get_title (GsReposSection *self); -From dca731ff0daf904911dd6815fb9a1b181329c887 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 5 Oct 2021 11:00:20 +0200 -Subject: [PATCH 1/4] gs-repo-row: Use GS_APP_QUIRK_COMPULSORY to recognize - required repositories - -The GS_APP_QUIRK_PROVENANCE quirk does not mean it's also required repository, -thus use the GS_APP_QUIRK_COMPULSORY for repos, which cannot be disabled. -The GS_APP_QUIRK_PROVENANCE is used only for repositories, which cannot be removed. ---- - src/gs-repo-row.c | 10 ++++++---- - 1 file changed, 6 insertions(+), 4 deletions(-) - -diff --git a/src/gs-repo-row.c b/src/gs-repo-row.c -index 87926092f..bbf67c194 100644 ---- a/src/gs-repo-row.c -+++ b/src/gs-repo-row.c -@@ -48,7 +48,8 @@ refresh_ui (GsRepoRow *row) - gboolean active = FALSE; - gboolean state_sensitive = FALSE; - gboolean busy = priv->busy_counter> 0; -- gboolean is_system_repo; -+ gboolean is_provenance; -+ gboolean is_compulsory; - - if (priv->repo == NULL) { - gtk_widget_set_sensitive (priv->disable_switch, FALSE); -@@ -87,11 +88,12 @@ refresh_ui (GsRepoRow *row) - break; - } - -- is_system_repo = gs_app_has_quirk (priv->repo, GS_APP_QUIRK_PROVENANCE); -+ is_provenance = gs_app_has_quirk (priv->repo, GS_APP_QUIRK_PROVENANCE); -+ is_compulsory = gs_app_has_quirk (priv->repo, GS_APP_QUIRK_COMPULSORY); - - /* Disable for the system repos, if installed */ -- gtk_widget_set_sensitive (priv->disable_switch, priv->supports_enable_disable && (state_sensitive || !is_system_repo || priv->always_allow_enable_disable)); -- gtk_widget_set_visible (priv->remove_button, priv->supports_remove && !is_system_repo); -+ gtk_widget_set_sensitive (priv->disable_switch, priv->supports_enable_disable && (state_sensitive || !is_compulsory || priv->always_allow_enable_disable)); -+ gtk_widget_set_visible (priv->remove_button, priv->supports_remove && !is_provenance && !is_compulsory); - - /* Set only the 'state' to visually indicate the state is not saved yet */ - if (busy) --- -GitLab - - -From 026218b9d3211de243dfc49eca8b8d46633882b0 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 5 Oct 2021 11:03:31 +0200 -Subject: [PATCH 2/4] gs-plugin-provenance: Improve search speed in list of - repositories - -Use a GHashTable for bare repository names and a GPtrArray for those -with wildcards. This helps with speed, due to not traversing all -the repository names with the fnmatch() call. ---- - plugins/core/gs-plugin-provenance.c | 55 ++++++++++++++++++++--------- - 1 file changed, 38 insertions(+), 17 deletions(-) - -diff --git a/plugins/core/gs-plugin-provenance.c b/plugins/core/gs-plugin-provenance.c -index 97ff76798..a72c25a27 100644 ---- a/plugins/core/gs-plugin-provenance.c -+++ b/plugins/core/gs-plugin-provenance.c -@@ -19,7 +19,8 @@ - - struct GsPluginData { - GSettings *settings; -- gchar **sources; -+ GHashTable *repos; /* gchar *name ~> NULL */ -+ GPtrArray *wildcards; /* non-NULL, when have names with wildcards */ - }; - - static gchar ** -@@ -42,8 +43,24 @@ gs_plugin_provenance_settings_changed_cb (GSettings *settings, - { - GsPluginData *priv = gs_plugin_get_data (plugin); - if (g_strcmp0 (key, "official-repos") == 0) { -- g_strfreev (priv->sources); -- priv->sources = gs_plugin_provenance_get_sources (plugin); -+ /* The keys are stolen by the hash table, thus free only the array */ -+ g_autofree gchar **repos = NULL; -+ g_hash_table_remove_all (priv->repos); -+ g_clear_pointer (&priv->wildcards, g_ptr_array_unref); -+ repos = gs_plugin_provenance_get_sources (plugin); -+ for (guint ii = 0; repos && repos[ii]; ii++) { -+ if (strchr (repos[ii], '*') || -+ strchr (repos[ii], '?') || -+ strchr (repos[ii], '[')) { -+ if (priv->wildcards == NULL) -+ priv->wildcards = g_ptr_array_new_with_free_func (g_free); -+ g_ptr_array_add (priv->wildcards, g_steal_pointer (&(repos[ii]))); -+ } else { -+ g_hash_table_insert (priv->repos, g_steal_pointer (&(repos[ii])), NULL); -+ } -+ } -+ if (priv->wildcards != NULL) -+ g_ptr_array_add (priv->wildcards, NULL); - } - } - -@@ -52,9 +69,10 @@ gs_plugin_initialize (GsPlugin *plugin) - { - GsPluginData *priv = gs_plugin_alloc_data (plugin, sizeof(GsPluginData)); - priv->settings = g_settings_new ("org.gnome.software"); -+ priv->repos = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); - g_signal_connect (priv->settings, "changed", - G_CALLBACK (gs_plugin_provenance_settings_changed_cb), plugin); -- priv->sources = gs_plugin_provenance_get_sources (plugin); -+ gs_plugin_provenance_settings_changed_cb (priv->settings, "official-repos", plugin); - - /* after the package source is set */ - gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_RUN_AFTER, "dummy"); -@@ -66,7 +84,8 @@ void - gs_plugin_destroy (GsPlugin *plugin) - { - GsPluginData *priv = gs_plugin_get_data (plugin); -- g_strfreev (priv->sources); -+ g_hash_table_unref (priv->repos); -+ g_clear_pointer (&priv->wildcards, g_ptr_array_unref); - g_object_unref (priv->settings); - } - -@@ -74,12 +93,12 @@ static gboolean - refine_app (GsPlugin *plugin, - GsApp *app, - GsPluginRefineFlags flags, -+ GHashTable *repos, -+ GPtrArray *wildcards, - GCancellable *cancellable, - GError **error) - { -- GsPluginData *priv = gs_plugin_get_data (plugin); - const gchar *origin; -- gchar **sources; - - /* not required */ - if ((flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_PROVENANCE) == 0) -@@ -87,14 +106,10 @@ refine_app (GsPlugin *plugin, - if (gs_app_has_quirk (app, GS_APP_QUIRK_PROVENANCE)) - return TRUE; - -- /* nothing to search */ -- sources = priv->sources; -- if (sources == NULL || sources[0] == NULL) -- return TRUE; -- - /* simple case */ - origin = gs_app_get_origin (app); -- if (origin != NULL && gs_utils_strv_fnmatch (sources, origin)) { -+ if (origin != NULL && (g_hash_table_contains (repos, origin) || -+ (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, origin)))) { - gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); - return TRUE; - } -@@ -103,7 +118,8 @@ refine_app (GsPlugin *plugin, - * provenance quirk to the system-configured repositories (but not - * user-configured ones). */ - if (gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY && -- gs_utils_strv_fnmatch (sources, gs_app_get_id (app))) { -+ (g_hash_table_contains (repos, gs_app_get_id (app)) || -+ (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, gs_app_get_id (app))))) { - if (gs_app_get_scope (app) != AS_COMPONENT_SCOPE_USER) - gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); - return TRUE; -@@ -118,7 +134,8 @@ refine_app (GsPlugin *plugin, - return TRUE; - if (g_str_has_prefix (origin + 1, "installed:")) - origin += 10; -- if (gs_utils_strv_fnmatch (sources, origin + 1)) { -+ if (g_hash_table_contains (repos, origin + 1) || -+ (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, origin + 1))) { - gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); - return TRUE; - } -@@ -133,17 +150,21 @@ gs_plugin_refine (GsPlugin *plugin, - GError **error) - { - GsPluginData *priv = gs_plugin_get_data (plugin); -+ g_autoptr(GHashTable) repos = NULL; -+ g_autoptr(GPtrArray) wildcards = NULL; - - /* nothing to do here */ - if ((flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_PROVENANCE) == 0) - return TRUE; -+ repos = g_hash_table_ref (priv->repos); -+ wildcards = priv->wildcards != NULL ? g_ptr_array_ref (priv->wildcards) : NULL; - /* nothing to search */ -- if (priv->sources == NULL || priv->sources[0] == NULL) -+ if (g_hash_table_size (repos) == 0) - return TRUE; - - for (guint i = 0; i < gs_app_list_length (list); i++) { - GsApp *app = gs_app_list_index (list, i); -- if (!refine_app (plugin, app, flags, cancellable, error)) -+ if (!refine_app (plugin, app, flags, repos, wildcards, cancellable, error)) - return FALSE; - } - --- -GitLab - - -From b5e3356aff5fcd257248f9bb697e272c879249ae Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 5 Oct 2021 13:03:44 +0200 -Subject: [PATCH 3/4] settings: Add 'required-repos' key - -To be used to list repositories, which cannot be removed or disabled. -It's a complementary option for the 'official-repos' key. ---- - data/org.gnome.software.gschema.xml | 4 ++++ - 1 file changed, 4 insertions(+) - -diff --git a/data/org.gnome.software.gschema.xml b/data/org.gnome.software.gschema.xml -index db1c27ce4..0e5706b7c 100644 ---- a/data/org.gnome.software.gschema.xml -+++ b/data/org.gnome.software.gschema.xml -@@ -94,6 +94,10 @@ - [] - A list of official repositories that should not be considered 3rd party - -+ -+ [] -+ A list of required repositories that cannot be disabled or removed -+ - - [] - A list of official repositories that should be considered free software --- -GitLab - - -From d6b8b206a596bb520a0b77066898b44a5ef18920 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Tue, 5 Oct 2021 14:16:56 +0200 -Subject: [PATCH 4/4] gs-plugin-provenance: Handle also 'required-repos' key - -Let it handle also 'required-repos' settings key, beside the 'official-repos' -key, which are close enough to share the same code and memory. With this -done the repositories can be marked as compulsory, independently from the official -repositories. - -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1479 ---- - plugins/core/gs-plugin-provenance.c | 142 +++++++++++++++++++++------- - 1 file changed, 108 insertions(+), 34 deletions(-) - -diff --git a/plugins/core/gs-plugin-provenance.c b/plugins/core/gs-plugin-provenance.c -index a72c25a27..22f3c98e1 100644 ---- a/plugins/core/gs-plugin-provenance.c -+++ b/plugins/core/gs-plugin-provenance.c -@@ -14,26 +14,61 @@ - /* - * SECTION: - * Sets the package provenance to TRUE if installed by an official -- * software source. -+ * software source. Also sets compulsory quirk when a required repository. - */ - - struct GsPluginData { - GSettings *settings; -- GHashTable *repos; /* gchar *name ~> NULL */ -- GPtrArray *wildcards; /* non-NULL, when have names with wildcards */ -+ GHashTable *repos; /* gchar *name ~> guint flags */ -+ GPtrArray *provenance_wildcards; /* non-NULL, when have names with wildcards */ -+ GPtrArray *compulsory_wildcards; /* non-NULL, when have names with wildcards */ - }; - -+static GHashTable * -+gs_plugin_provenance_remove_by_flag (GHashTable *old_repos, -+ GsAppQuirk quirk) -+{ -+ GHashTable *new_repos = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL); -+ GHashTableIter iter; -+ gpointer key, value; -+ g_hash_table_iter_init (&iter, old_repos); -+ while (g_hash_table_iter_next (&iter, &key, &value)) { -+ guint flags = GPOINTER_TO_UINT (value); -+ flags = flags & (~quirk); -+ if (flags != 0) -+ g_hash_table_insert (new_repos, g_strdup (key), GUINT_TO_POINTER (flags)); -+ } -+ return new_repos; -+} -+ -+static void -+gs_plugin_provenance_add_quirks (GsApp *app, -+ guint quirks) -+{ -+ GsAppQuirk array[] = { -+ GS_APP_QUIRK_PROVENANCE, -+ GS_APP_QUIRK_COMPULSORY -+ }; -+ for (guint ii = 0; ii < G_N_ELEMENTS (array); ii++) { -+ if ((quirks & array[ii]) != 0) -+ gs_app_add_quirk (app, array[ii]); -+ } -+} -+ - static gchar ** --gs_plugin_provenance_get_sources (GsPlugin *plugin) -+gs_plugin_provenance_get_sources (GsPlugin *plugin, -+ const gchar *key) - { - GsPluginData *priv = gs_plugin_get_data (plugin); - const gchar *tmp; - tmp = g_getenv ("GS_SELF_TEST_PROVENANCE_SOURCES"); - if (tmp != NULL) { -+ if (g_strcmp0 (key, "required-repos") == 0) -+ return NULL; - g_debug ("using custom provenance sources of %s", tmp); - return g_strsplit (tmp, ",", -1); - } -- return g_settings_get_strv (priv->settings, "official-repos"); -+ return g_settings_get_strv (priv->settings, key); - } - - static void -@@ -42,25 +77,43 @@ gs_plugin_provenance_settings_changed_cb (GSettings *settings, - GsPlugin *plugin) - { - GsPluginData *priv = gs_plugin_get_data (plugin); -+ GsAppQuirk quirk = GS_APP_QUIRK_NONE; -+ GPtrArray **pwildcards = NULL; -+ - if (g_strcmp0 (key, "official-repos") == 0) { -+ quirk = GS_APP_QUIRK_PROVENANCE; -+ pwildcards = &priv->provenance_wildcards; -+ } else if (g_strcmp0 (key, "required-repos") == 0) { -+ quirk = GS_APP_QUIRK_COMPULSORY; -+ pwildcards = &priv->compulsory_wildcards; -+ } -+ -+ if (quirk != GS_APP_QUIRK_NONE) { - /* The keys are stolen by the hash table, thus free only the array */ - g_autofree gchar **repos = NULL; -- g_hash_table_remove_all (priv->repos); -- g_clear_pointer (&priv->wildcards, g_ptr_array_unref); -- repos = gs_plugin_provenance_get_sources (plugin); -+ g_autoptr(GHashTable) old_repos = priv->repos; -+ g_autoptr(GPtrArray) old_wildcards = *pwildcards; -+ GHashTable *new_repos = gs_plugin_provenance_remove_by_flag (old_repos, quirk); -+ GPtrArray *new_wildcards = NULL; -+ repos = gs_plugin_provenance_get_sources (plugin, key); - for (guint ii = 0; repos && repos[ii]; ii++) { -- if (strchr (repos[ii], '*') || -- strchr (repos[ii], '?') || -- strchr (repos[ii], '[')) { -- if (priv->wildcards == NULL) -- priv->wildcards = g_ptr_array_new_with_free_func (g_free); -- g_ptr_array_add (priv->wildcards, g_steal_pointer (&(repos[ii]))); -+ gchar *repo = g_steal_pointer (&(repos[ii])); -+ if (strchr (repo, '*') || -+ strchr (repo, '?') || -+ strchr (repo, '[')) { -+ if (new_wildcards == NULL) -+ new_wildcards = g_ptr_array_new_with_free_func (g_free); -+ g_ptr_array_add (new_wildcards, repo); - } else { -- g_hash_table_insert (priv->repos, g_steal_pointer (&(repos[ii])), NULL); -+ g_hash_table_insert (new_repos, repo, -+ GUINT_TO_POINTER (quirk | -+ GPOINTER_TO_UINT (g_hash_table_lookup (new_repos, repo)))); - } - } -- if (priv->wildcards != NULL) -- g_ptr_array_add (priv->wildcards, NULL); -+ if (new_wildcards != NULL) -+ g_ptr_array_add (new_wildcards, NULL); -+ priv->repos = new_repos; -+ *pwildcards = new_wildcards; - } - } - -@@ -73,6 +126,7 @@ gs_plugin_initialize (GsPlugin *plugin) - g_signal_connect (priv->settings, "changed", - G_CALLBACK (gs_plugin_provenance_settings_changed_cb), plugin); - gs_plugin_provenance_settings_changed_cb (priv->settings, "official-repos", plugin); -+ gs_plugin_provenance_settings_changed_cb (priv->settings, "required-repos", plugin); - - /* after the package source is set */ - gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_RUN_AFTER, "dummy"); -@@ -85,20 +139,42 @@ gs_plugin_destroy (GsPlugin *plugin) - { - GsPluginData *priv = gs_plugin_get_data (plugin); - g_hash_table_unref (priv->repos); -- g_clear_pointer (&priv->wildcards, g_ptr_array_unref); -+ g_clear_pointer (&priv->provenance_wildcards, g_ptr_array_unref); -+ g_clear_pointer (&priv->compulsory_wildcards, g_ptr_array_unref); - g_object_unref (priv->settings); - } - -+static gboolean -+gs_plugin_provenance_find_repo_flags (GHashTable *repos, -+ GPtrArray *provenance_wildcards, -+ GPtrArray *compulsory_wildcards, -+ const gchar *repo, -+ guint *out_flags) -+{ -+ if (repo == NULL || *repo == '\0') -+ return FALSE; -+ *out_flags = GPOINTER_TO_UINT (g_hash_table_lookup (repos, repo)); -+ if (provenance_wildcards != NULL && -+ gs_utils_strv_fnmatch ((gchar **) provenance_wildcards->pdata, repo)) -+ *out_flags |= GS_APP_QUIRK_PROVENANCE; -+ if (compulsory_wildcards != NULL && -+ gs_utils_strv_fnmatch ((gchar **) compulsory_wildcards->pdata, repo)) -+ *out_flags |= GS_APP_QUIRK_COMPULSORY; -+ return *out_flags != 0; -+} -+ - static gboolean - refine_app (GsPlugin *plugin, - GsApp *app, - GsPluginRefineFlags flags, - GHashTable *repos, -- GPtrArray *wildcards, -+ GPtrArray *provenance_wildcards, -+ GPtrArray *compulsory_wildcards, - GCancellable *cancellable, - GError **error) - { - const gchar *origin; -+ guint quirks; - - /* not required */ - if ((flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_PROVENANCE) == 0) -@@ -108,9 +184,8 @@ refine_app (GsPlugin *plugin, - - /* simple case */ - origin = gs_app_get_origin (app); -- if (origin != NULL && (g_hash_table_contains (repos, origin) || -- (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, origin)))) { -- gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); -+ if (gs_plugin_provenance_find_repo_flags (repos, provenance_wildcards, compulsory_wildcards, origin, &quirks)) { -+ gs_plugin_provenance_add_quirks (app, quirks); - return TRUE; - } - -@@ -118,10 +193,9 @@ refine_app (GsPlugin *plugin, - * provenance quirk to the system-configured repositories (but not - * user-configured ones). */ - if (gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY && -- (g_hash_table_contains (repos, gs_app_get_id (app)) || -- (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, gs_app_get_id (app))))) { -+ gs_plugin_provenance_find_repo_flags (repos, provenance_wildcards, compulsory_wildcards, gs_app_get_id (app), &quirks)) { - if (gs_app_get_scope (app) != AS_COMPONENT_SCOPE_USER) -- gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); -+ gs_plugin_provenance_add_quirks (app, quirks); - return TRUE; - } - -@@ -134,11 +208,9 @@ refine_app (GsPlugin *plugin, - return TRUE; - if (g_str_has_prefix (origin + 1, "installed:")) - origin += 10; -- if (g_hash_table_contains (repos, origin + 1) || -- (wildcards != NULL && gs_utils_strv_fnmatch ((gchar **) wildcards->pdata, origin + 1))) { -- gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); -- return TRUE; -- } -+ if (gs_plugin_provenance_find_repo_flags (repos, provenance_wildcards, compulsory_wildcards, origin + 1, &quirks)) -+ gs_plugin_provenance_add_quirks (app, quirks); -+ - return TRUE; - } - -@@ -151,20 +223,22 @@ gs_plugin_refine (GsPlugin *plugin, - { - GsPluginData *priv = gs_plugin_get_data (plugin); - g_autoptr(GHashTable) repos = NULL; -- g_autoptr(GPtrArray) wildcards = NULL; -+ g_autoptr(GPtrArray) provenance_wildcards = NULL; -+ g_autoptr(GPtrArray) compulsory_wildcards = NULL; - - /* nothing to do here */ - if ((flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_PROVENANCE) == 0) - return TRUE; - repos = g_hash_table_ref (priv->repos); -- wildcards = priv->wildcards != NULL ? g_ptr_array_ref (priv->wildcards) : NULL; -+ provenance_wildcards = priv->provenance_wildcards != NULL ? g_ptr_array_ref (priv->provenance_wildcards) : NULL; -+ compulsory_wildcards = priv->compulsory_wildcards != NULL ? g_ptr_array_ref (priv->compulsory_wildcards) : NULL; - /* nothing to search */ -- if (g_hash_table_size (repos) == 0) -+ if (g_hash_table_size (repos) == 0 && provenance_wildcards == NULL && compulsory_wildcards == NULL) - return TRUE; - - for (guint i = 0; i < gs_app_list_length (list); i++) { - GsApp *app = gs_app_list_index (list, i); -- if (!refine_app (plugin, app, flags, repos, wildcards, cancellable, error)) -+ if (!refine_app (plugin, app, flags, repos, provenance_wildcards, compulsory_wildcards, cancellable, error)) - return FALSE; - } - --- -GitLab - diff --git a/0007-compulsory-only-for-repos.patch b/0007-compulsory-only-for-repos.patch deleted file mode 100644 index fb266df..0000000 --- a/0007-compulsory-only-for-repos.patch +++ /dev/null @@ -1,42 +0,0 @@ -From 895d1ca748f4f33a852853f5f07903fb549fb66f Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Mon, 11 Oct 2021 09:13:59 +0200 -Subject: [PATCH] gs-plugin-provenance: Set COMPULSORY quirk only on REPOSITORY - apps - -The compulsory quirk related to repositories, which cannot be removed, -not to the applications provided by those repositories, thus set that -quirk only on repositories, not on the apps from it. - -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1488 ---- - plugins/core/gs-plugin-provenance.c | 13 +++++-------- - 1 file changed, 5 insertions(+), 8 deletions(-) - -diff --git a/plugins/core/gs-plugin-provenance.c b/plugins/core/gs-plugin-provenance.c -index 22f3c98e..e44a55f0 100644 ---- a/plugins/core/gs-plugin-provenance.c -+++ b/plugins/core/gs-plugin-provenance.c -@@ -45,14 +45,11 @@ static void - gs_plugin_provenance_add_quirks (GsApp *app, - guint quirks) - { -- GsAppQuirk array[] = { -- GS_APP_QUIRK_PROVENANCE, -- GS_APP_QUIRK_COMPULSORY -- }; -- for (guint ii = 0; ii < G_N_ELEMENTS (array); ii++) { -- if ((quirks & array[ii]) != 0) -- gs_app_add_quirk (app, array[ii]); -- } -+ if ((quirks & GS_APP_QUIRK_PROVENANCE) != 0) -+ gs_app_add_quirk (app, GS_APP_QUIRK_PROVENANCE); -+ if ((quirks & GS_APP_QUIRK_COMPULSORY) != 0 && -+ gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY) -+ gs_app_add_quirk (app, GS_APP_QUIRK_COMPULSORY); - } - - static gchar ** --- -2.31.1 - diff --git a/0008-installed-page-section-change.patch b/0008-installed-page-section-change.patch deleted file mode 100644 index fd91a2b..0000000 --- a/0008-installed-page-section-change.patch +++ /dev/null @@ -1,264 +0,0 @@ -From 65551cf41c8d6b3dcf0cf9b2ee2d46201b4e0ea4 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Thu, 14 Oct 2021 15:17:52 +0200 -Subject: [PATCH] gs-installed-page: Change section on application state change - -When an application is being installed, it's shown in the "In Progress" -section, but when the installation is finished it had been left in -that section, even it belongs to a different section. - -Similarly with the uninstall, the application was sorted to the top -of the section, but it might be better to be added to the "In Progress" -section. - -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1492 ---- - src/gs-installed-page.c | 168 +++++++++++++++++++++++++++++++++------- - 1 file changed, 141 insertions(+), 27 deletions(-) - -diff --git a/src/gs-installed-page.c b/src/gs-installed-page.c -index 67a4b7a51..56bf19df7 100644 ---- a/src/gs-installed-page.c -+++ b/src/gs-installed-page.c -@@ -59,6 +59,9 @@ static GParamSpec *obj_props[PROP_IS_NARROW + 1] = { NULL, }; - - static void gs_installed_page_pending_apps_changed_cb (GsPluginLoader *plugin_loader, - GsInstalledPage *self); -+static void gs_installed_page_notify_state_changed_cb (GsApp *app, -+ GParamSpec *pspec, -+ GsInstalledPage *self); - - typedef enum { - GS_UPDATE_LIST_SECTION_INSTALLING_AND_REMOVING, -@@ -91,6 +94,30 @@ gs_installed_page_get_app_section (GsApp *app) - return GS_UPDATE_LIST_SECTION_ADDONS; - } - -+static GsInstalledPageSection -+gs_installed_page_get_row_section (GsInstalledPage *self, -+ GsAppRow *app_row) -+{ -+ GtkWidget *parent; -+ -+ g_return_val_if_fail (GS_IS_INSTALLED_PAGE (self), GS_UPDATE_LIST_SECTION_LAST); -+ g_return_val_if_fail (GS_IS_APP_ROW (app_row), GS_UPDATE_LIST_SECTION_LAST); -+ -+ parent = gtk_widget_get_parent (GTK_WIDGET (app_row)); -+ if (parent == self->list_box_install_in_progress) -+ return GS_UPDATE_LIST_SECTION_INSTALLING_AND_REMOVING; -+ if (parent == self->list_box_install_apps) -+ return GS_UPDATE_LIST_SECTION_REMOVABLE_APPS; -+ if (parent == self->list_box_install_system_apps) -+ return GS_UPDATE_LIST_SECTION_SYSTEM_APPS; -+ if (parent == self->list_box_install_addons) -+ return GS_UPDATE_LIST_SECTION_ADDONS; -+ -+ g_warn_if_reached (); -+ -+ return GS_UPDATE_LIST_SECTION_LAST; -+} -+ - static void - gs_installed_page_invalidate (GsInstalledPage *self) - { -@@ -121,15 +148,29 @@ row_unrevealed (GObject *row, GParamSpec *pspec, gpointer data) - static void - gs_installed_page_unreveal_row (GsAppRow *app_row) - { -- g_signal_connect (app_row, "unrevealed", -- G_CALLBACK (row_unrevealed), NULL); -- gs_app_row_unreveal (app_row); -+ GsApp *app = gs_app_row_get_app (app_row); -+ if (app != NULL) { -+ g_signal_handlers_disconnect_matched (app, G_SIGNAL_MATCH_FUNC, 0, 0, NULL, -+ G_CALLBACK (gs_installed_page_notify_state_changed_cb), NULL); -+ } -+ -+ /* This check is required, because GsAppRow does not emit -+ * the signal when the row is not realized. This can happen -+ * when installing/uninstalling an app without visiting -+ * the Installed page. */ -+ if (!gtk_widget_get_mapped (GTK_WIDGET (app_row))) { -+ row_unrevealed (G_OBJECT (app_row), NULL, NULL); -+ } else { -+ g_signal_connect (app_row, "unrevealed", -+ G_CALLBACK (row_unrevealed), NULL); -+ gs_app_row_unreveal (app_row); -+ } - } - --static void --gs_installed_page_app_removed (GsPage *page, GsApp *app) -+static GsAppRow * /* (transfer none) */ -+gs_installed_page_find_app_row (GsInstalledPage *self, -+ GsApp *app) - { -- GsInstalledPage *self = GS_INSTALLED_PAGE (page); - GtkWidget *lists[] = { - self->list_box_install_in_progress, - self->list_box_install_apps, -@@ -145,10 +186,22 @@ gs_installed_page_app_removed (GsPage *page, GsApp *app) - for (GList *l = children; l; l = l->next) { - GsAppRow *app_row = GS_APP_ROW (l->data); - if (gs_app_row_get_app (app_row) == app) { -- gs_installed_page_unreveal_row (app_row); -+ return app_row; - } - } - } -+ -+ return NULL; -+} -+ -+ -+static void -+gs_installed_page_app_removed (GsPage *page, GsApp *app) -+{ -+ GsInstalledPage *self = GS_INSTALLED_PAGE (page); -+ GsAppRow *app_row = gs_installed_page_find_app_row (self, app); -+ if (app_row != NULL) -+ gs_installed_page_unreveal_row (app_row); - } - - static void -@@ -161,12 +214,56 @@ gs_installed_page_app_remove_cb (GsAppRow *app_row, - gs_page_remove_app (GS_PAGE (self), app, self->cancellable); - } - --static gboolean --gs_installed_page_invalidate_sort_idle (gpointer user_data) -+static void -+gs_installed_page_maybe_move_app_row (GsInstalledPage *self, -+ GsAppRow *app_row) -+{ -+ GsInstalledPageSection current_section, expected_section; -+ -+ current_section = gs_installed_page_get_row_section (self, app_row); -+ g_return_if_fail (current_section != GS_UPDATE_LIST_SECTION_LAST); -+ -+ expected_section = gs_installed_page_get_app_section (gs_app_row_get_app (app_row)); -+ if (expected_section != current_section) { -+ GtkWidget *widget = GTK_WIDGET (app_row); -+ -+ g_object_ref (app_row); -+ gtk_container_remove (GTK_CONTAINER (gtk_widget_get_parent (widget)), widget); -+ switch (expected_section) { -+ case GS_UPDATE_LIST_SECTION_INSTALLING_AND_REMOVING: -+ widget = self->list_box_install_in_progress; -+ break; -+ case GS_UPDATE_LIST_SECTION_REMOVABLE_APPS: -+ widget = self->list_box_install_apps; -+ break; -+ case GS_UPDATE_LIST_SECTION_SYSTEM_APPS: -+ widget = self->list_box_install_system_apps; -+ break; -+ case GS_UPDATE_LIST_SECTION_ADDONS: -+ widget = self->list_box_install_addons; -+ break; -+ default: -+ g_warn_if_reached (); -+ widget = NULL; -+ break; -+ } -+ -+ if (widget != NULL) -+ gtk_container_add (GTK_CONTAINER (widget), GTK_WIDGET (app_row)); -+ -+ g_object_unref (app_row); -+ } -+} -+ -+static void -+gs_installed_page_notify_state_changed_cb (GsApp *app, -+ GParamSpec *pspec, -+ GsInstalledPage *self) - { -- GsAppRow *app_row = user_data; -- GsApp *app = gs_app_row_get_app (app_row); - GsAppState state = gs_app_get_state (app); -+ GsAppRow *app_row = gs_installed_page_find_app_row (self, app); -+ -+ g_assert (app_row != NULL); - - gtk_list_box_row_changed (GTK_LIST_BOX_ROW (app_row)); - -@@ -177,17 +274,8 @@ gs_installed_page_invalidate_sort_idle (gpointer user_data) - state != GS_APP_STATE_UPDATABLE && - state != GS_APP_STATE_UPDATABLE_LIVE) - gs_installed_page_unreveal_row (app_row); -- -- g_object_unref (app_row); -- return G_SOURCE_REMOVE; --} -- --static void --gs_installed_page_notify_state_changed_cb (GsApp *app, -- GParamSpec *pspec, -- GsAppRow *app_row) --{ -- g_idle_add (gs_installed_page_invalidate_sort_idle, g_object_ref (app_row)); -+ else -+ gs_installed_page_maybe_move_app_row (self, app_row); - } - - static gboolean -@@ -229,7 +317,7 @@ gs_installed_page_add_app (GsInstalledPage *self, GsAppList *list, GsApp *app) - G_CALLBACK (gs_installed_page_app_remove_cb), self); - g_signal_connect_object (app, "notify::state", - G_CALLBACK (gs_installed_page_notify_state_changed_cb), -- app_row, 0); -+ self, 0); - - switch (gs_installed_page_get_app_section (app)) { - case GS_UPDATE_LIST_SECTION_INSTALLING_AND_REMOVING: -@@ -294,6 +382,32 @@ out: - gs_installed_page_pending_apps_changed_cb (plugin_loader, self); - } - -+static void -+gs_installed_page_remove_all_cb (GtkWidget *child, -+ gpointer user_data) -+{ -+ GtkContainer *container = user_data; -+ -+ if (GS_IS_APP_ROW (child)) { -+ GsApp *app = gs_app_row_get_app (GS_APP_ROW (child)); -+ if (app != NULL) { -+ g_signal_handlers_disconnect_matched (app, G_SIGNAL_MATCH_FUNC, 0, 0, NULL, -+ G_CALLBACK (gs_installed_page_notify_state_changed_cb), NULL); -+ } -+ } else { -+ g_warn_if_reached (); -+ } -+ -+ gtk_container_remove (container, child); -+} -+ -+static void -+gs_container_remove_all_with_cb (GtkContainer *container, -+ GtkCallback callback) -+{ -+ gtk_container_foreach (container, callback, container); -+} -+ - static void - gs_installed_page_load (GsInstalledPage *self) - { -@@ -305,10 +419,10 @@ gs_installed_page_load (GsInstalledPage *self) - self->waiting = TRUE; - - /* remove old entries */ -- gs_container_remove_all (GTK_CONTAINER (self->list_box_install_in_progress)); -- gs_container_remove_all (GTK_CONTAINER (self->list_box_install_apps)); -- gs_container_remove_all (GTK_CONTAINER (self->list_box_install_system_apps)); -- gs_container_remove_all (GTK_CONTAINER (self->list_box_install_addons)); -+ gs_container_remove_all_with_cb (GTK_CONTAINER (self->list_box_install_in_progress), gs_installed_page_remove_all_cb); -+ gs_container_remove_all_with_cb (GTK_CONTAINER (self->list_box_install_apps), gs_installed_page_remove_all_cb); -+ gs_container_remove_all_with_cb (GTK_CONTAINER (self->list_box_install_system_apps), gs_installed_page_remove_all_cb); -+ gs_container_remove_all_with_cb (GTK_CONTAINER (self->list_box_install_addons), gs_installed_page_remove_all_cb); - - flags = GS_PLUGIN_REFINE_FLAGS_REQUIRE_ICON | - GS_PLUGIN_REFINE_FLAGS_REQUIRE_HISTORY | --- -GitLab - diff --git a/gnome-software.spec b/gnome-software.spec index 5c9d9fc..7222117 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,8 +11,8 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 41.0 -Release: 6%{?dist} +Version: 41.1 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -20,13 +20,6 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/41/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -Patch02: 0002-correct-update-notifications.patch -Patch03: 0003-refresh-on-repository-change.patch -Patch04: 0004-filtered-system-flathub.patch -Patch05: 0005-repos-dialog-can-show-apps.patch -Patch06: 0006-optional-repos-cannot-be-disabled.patch -Patch07: 0007-compulsory-only-for-repos.patch -Patch08: 0008-installed-page-section-change.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -210,6 +203,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri Oct 29 2021 Milan Crha - 41.1-1 +- Update to 41.1 + * Tue Oct 19 2021 Milan Crha - 41.0-6 - Resolves: #2012863 (gs-installed-page: Change section on application state change) diff --git a/sources b/sources index 4578578..9e33e1e 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-41.0.tar.xz) = 6cc090f835e77d64abb0080d3b72494019d6f69c2144abea4dabdc4f52dc570a372159eb1e0b0d98ae33b31c134cc17673fe3fa243eed762eec55620ab146b26 +SHA512 (gnome-software-41.1.tar.xz) = e5586d901f9b178961a9030cafbc1ec346d3a52e91af11234d28eaeb7d95e12083d8a9e7e90fb7c64e720b7394e83733fcbb6912ca1ef0bcd2c431acad25fe3c From 398071803670444cf1289d525fb94e6a9b499d5a Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 3 Dec 2021 09:30:50 +0100 Subject: [PATCH 041/163] Update to 41.2 --- gnome-software.spec | 5 ++++- sources | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 7222117..d8a8ee1 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -11,7 +11,7 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 41.1 +Version: 41.2 Release: 1%{?dist} Summary: A software center for GNOME @@ -203,6 +203,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri Dec 03 2021 Milan Crha - 41.2-1 +- Update to 41.2 + * Fri Oct 29 2021 Milan Crha - 41.1-1 - Update to 41.1 diff --git a/sources b/sources index 9e33e1e..f57b0c8 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-41.1.tar.xz) = e5586d901f9b178961a9030cafbc1ec346d3a52e91af11234d28eaeb7d95e12083d8a9e7e90fb7c64e720b7394e83733fcbb6912ca1ef0bcd2c431acad25fe3c +SHA512 (gnome-software-41.2.tar.xz) = 0c7662940c0fcd3267ad08e2d16f753eb5933c28311166a718cbedb06ab932a5bfe961848e13f265474f33ee5421d99a5638976edeb49a801fad41b4bb8ce90b From 81a6f050fb44907df5fe4504dc5768816e1dc37a Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 7 Jan 2022 11:06:27 +0100 Subject: [PATCH 042/163] Update to 42.alpha --- gnome-software.spec | 22 ++++++++++------------ sources | 2 +- 2 files changed, 11 insertions(+), 13 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index d8a8ee1..e8a559b 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -1,7 +1,7 @@ %global appstream_version 0.14.0 %global libxmlb_version 0.1.7 %global glib2_version 2.61.1 -%global gtk3_version 3.22.4 +%global gtk4_version 4.4.0 %global json_glib_version 1.2.0 %global libsoup_version 2.52.0 %global packagekit_version 1.1.1 @@ -11,13 +11,13 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 41.2 +Version: 42~alpha Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software -Source0: https://download.gnome.org/sources/gnome-software/41/%{name}-%{tarball_version}.tar.xz +Source0: https://download.gnome.org/sources/gnome-software/42/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch @@ -32,11 +32,11 @@ BuildRequires: glib2-devel >= %{glib2_version} BuildRequires: gnome-online-accounts-devel BuildRequires: gsettings-desktop-schemas-devel BuildRequires: gspell-devel -BuildRequires: gtk3-devel >= %{gtk3_version} +BuildRequires: pkgconfig(gtk4) >= %{gtk4_version} BuildRequires: gtk-doc BuildRequires: json-glib-devel >= %{json_glib_version} BuildRequires: libdnf-devel -BuildRequires: libhandy1-devel +BuildRequires: pkgconfig(libadwaita-1) BuildRequires: libsoup-devel BuildRequires: libxmlb-devel >= %{libxmlb_version} BuildRequires: malcontent-devel @@ -61,7 +61,6 @@ Requires: glib2%{?_isa} >= %{glib2_version} # gnome-menus is needed for app folder .directory entries Requires: gnome-menus%{?_isa} Requires: gsettings-desktop-schemas%{?_isa} -Requires: gtk3%{?_isa} >= %{gtk3_version} Requires: json-glib%{?_isa} >= %{json_glib_version} Requires: iso-codes # librsvg2 is needed for gdk-pixbuf svg loader @@ -75,7 +74,7 @@ Obsoletes: gnome-software-snap < 3.33.1 Obsoletes: gnome-software-editor < 3.35.1 # this is not a library version -%define gs_plugin_version 16 +%define gs_plugin_version 17 %description gnome-software is an application that makes it easy to add, remove @@ -106,6 +105,7 @@ This package includes the rpm-ostree backend. %build %meson \ + -Dsoup2=true \ -Dsnap=false \ -Dmalcontent=true \ -Dgudev=true \ @@ -153,8 +153,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/icons/hicolor/*/apps/org.gnome.Software.svg %{_datadir}/icons/hicolor/symbolic/apps/org.gnome.Software-symbolic.svg %{_datadir}/icons/hicolor/scalable/actions/app-remove-symbolic.svg -%{_datadir}/icons/hicolor/scalable/actions/carousel-arrow-next-symbolic.svg -%{_datadir}/icons/hicolor/scalable/actions/carousel-arrow-previous-symbolic.svg %{_datadir}/icons/hicolor/scalable/status/software-installed-symbolic.svg %{_datadir}/metainfo/org.gnome.Software.appdata.xml %{_datadir}/metainfo/org.gnome.Software.Plugin.Flatpak.metainfo.xml @@ -174,14 +172,11 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_malcontent.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_modalias.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_os-release.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refine-repos.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit-refresh.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance-license.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_repos.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rewrite-resource.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_systemd-updates.so %{_sysconfdir}/xdg/autostart/gnome-software-service.desktop %{_datadir}/app-info/xmls/org.gnome.Software.Featured.xml %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service @@ -203,6 +198,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri Jan 07 2022 Milan Crha - 42.alpha-1 +- Update to 42.alpha + * Fri Dec 03 2021 Milan Crha - 41.2-1 - Update to 41.2 diff --git a/sources b/sources index f57b0c8..3210d9f 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-41.2.tar.xz) = 0c7662940c0fcd3267ad08e2d16f753eb5933c28311166a718cbedb06ab932a5bfe961848e13f265474f33ee5421d99a5638976edeb49a801fad41b4bb8ce90b +SHA512 (gnome-software-42.alpha.tar.xz) = fa63ab4cffe72f9f8b348cd7e021da515963258271310d3933d985f00190c3ffe0f1d664d65ec5ff577d153c6de5d11eef9b1e6d9aa1e171d27f0f1b570dbdeb From 9365ecb05c965a42863c674691ca733ea28e936c Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Thu, 20 Jan 2022 06:45:38 +0000 Subject: [PATCH 043/163] - Rebuilt for https://fedoraproject.org/wiki/Fedora_36_Mass_Rebuild Signed-off-by: Fedora Release Engineering --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index e8a559b..221afbc 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,7 +12,7 @@ Name: gnome-software Version: 42~alpha -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -198,6 +198,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Thu Jan 20 2022 Fedora Release Engineering - 42~alpha-2 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_36_Mass_Rebuild + * Fri Jan 07 2022 Milan Crha - 42.alpha-1 - Update to 42.alpha From 142b342f076d0d237abb8feacb0c46ffbe7f0c0f Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 11 Feb 2022 11:39:45 +0100 Subject: [PATCH 044/163] Update to 42.beta --- gnome-software.spec | 12 +++++++----- sources | 2 +- 2 files changed, 8 insertions(+), 6 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 221afbc..7929076 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -1,4 +1,5 @@ %global appstream_version 0.14.0 +%global libadwaita_version 1.0.1 %global libxmlb_version 0.1.7 %global glib2_version 2.61.1 %global gtk4_version 4.4.0 @@ -11,8 +12,8 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 42~alpha -Release: 2%{?dist} +Version: 42~beta +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -36,7 +37,7 @@ BuildRequires: pkgconfig(gtk4) >= %{gtk4_version} BuildRequires: gtk-doc BuildRequires: json-glib-devel >= %{json_glib_version} BuildRequires: libdnf-devel -BuildRequires: pkgconfig(libadwaita-1) +BuildRequires: pkgconfig(libadwaita-1) >= %{libadwaita_version} BuildRequires: libsoup-devel BuildRequires: libxmlb-devel >= %{libxmlb_version} BuildRequires: malcontent-devel @@ -147,8 +148,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_bindir}/gnome-software %{_datadir}/applications/gnome-software-local-file.desktop %{_datadir}/applications/org.gnome.Software.desktop -%dir %{_datadir}/gnome-software -%{_datadir}/gnome-software/*.png %{_mandir}/man1/gnome-software.1.gz %{_datadir}/icons/hicolor/*/apps/org.gnome.Software.svg %{_datadir}/icons/hicolor/symbolic/apps/org.gnome.Software-symbolic.svg @@ -198,6 +197,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri Feb 11 2022 Milan Crha - 42.beta-1 +- Update to 42.beta + * Thu Jan 20 2022 Fedora Release Engineering - 42~alpha-2 - Rebuilt for https://fedoraproject.org/wiki/Fedora_36_Mass_Rebuild diff --git a/sources b/sources index 3210d9f..2f9377d 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-42.alpha.tar.xz) = fa63ab4cffe72f9f8b348cd7e021da515963258271310d3933d985f00190c3ffe0f1d664d65ec5ff577d153c6de5d11eef9b1e6d9aa1e171d27f0f1b570dbdeb +SHA512 (gnome-software-42.beta.tar.xz) = 3ae22c9a37a134a6340191aabc7b02f6b53322820853aacd36e6d43893d7118d177defff44de93b627e488411798570b9c82c99b354966a899563e27d8c32a6a From f6af9a7826fd165c5f82401798d9769940d92b56 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 11 Feb 2022 12:28:17 +0100 Subject: [PATCH 045/163] Correct files list for popular plugin removal --- gnome-software.spec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 7929076..d77af53 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -166,7 +166,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fwupd.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_generic-updates.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-blocklist.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-popular.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_icons.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_malcontent.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_modalias.so @@ -178,6 +177,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rewrite-resource.so %{_sysconfdir}/xdg/autostart/gnome-software-service.desktop %{_datadir}/app-info/xmls/org.gnome.Software.Featured.xml +%{_datadir}/app-info/xmls/org.gnome.Software.Popular.xml %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service %{_datadir}/dbus-1/services/org.gnome.Software.service %{_datadir}/gnome-shell/search-providers/org.gnome.Software-search-provider.ini From 1fac831a3136d218196aece5b6da4200f953641b Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Wed, 16 Feb 2022 17:41:29 +0100 Subject: [PATCH 046/163] Resolves: #2054939 (Crash on a PackageKit app install) --- 0002-packagekit-crash-on-app-install.patch | 28 ++++++++++++++++++++++ gnome-software.spec | 6 ++++- 2 files changed, 33 insertions(+), 1 deletion(-) create mode 100644 0002-packagekit-crash-on-app-install.patch diff --git a/0002-packagekit-crash-on-app-install.patch b/0002-packagekit-crash-on-app-install.patch new file mode 100644 index 0000000..04e85b3 --- /dev/null +++ b/0002-packagekit-crash-on-app-install.patch @@ -0,0 +1,28 @@ +From 73d1c9fd58d2fdf2c2d84e70cce678390679baa9 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 16 Feb 2022 15:01:46 +0100 +Subject: [PATCH] PackageKit: Fix a crash on app install + +The array should be NULL-terminated, thus add the NULL at the end. + +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1648 +--- + plugins/packagekit/gs-plugin-packagekit.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/plugins/packagekit/gs-plugin-packagekit.c b/plugins/packagekit/gs-plugin-packagekit.c +index 1ad913af5..56ddb1ccc 100644 +--- a/plugins/packagekit/gs-plugin-packagekit.c ++++ b/plugins/packagekit/gs-plugin-packagekit.c +@@ -612,6 +612,8 @@ gs_plugin_app_install (GsPlugin *plugin, + return FALSE; + } + ++ g_ptr_array_add (array_package_ids, NULL); ++ + gs_app_set_state (app, GS_APP_STATE_INSTALLING); + + for (i = 0; i < gs_app_list_length (addons); i++) { +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index d77af53..b30cd16 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -13,7 +13,7 @@ Name: gnome-software Version: 42~beta -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -21,6 +21,7 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/42/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +Patch02: 0002-packagekit-crash-on-app-install.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -197,6 +198,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Wed Feb 16 2022 Milan Crha - 42.beta-2 +- Resolves: #2054939 (Crash on a PackageKit app install) + * Fri Feb 11 2022 Milan Crha - 42.beta-1 - Update to 42.beta From 422e17de7730df6eb6696ce702c7733faaaf591c Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Wed, 16 Feb 2022 17:49:57 +0100 Subject: [PATCH 047/163] Add a temporary workaround for gtk_widget_measure error flood on GsAppRow --- ...pprow-gtk_widget_measure-error-flood.patch | 39 +++++++++++++++++++ gnome-software.spec | 4 +- 2 files changed, 42 insertions(+), 1 deletion(-) create mode 100644 0003-workaround-gsapprow-gtk_widget_measure-error-flood.patch diff --git a/0003-workaround-gsapprow-gtk_widget_measure-error-flood.patch b/0003-workaround-gsapprow-gtk_widget_measure-error-flood.patch new file mode 100644 index 0000000..0a24881 --- /dev/null +++ b/0003-workaround-gsapprow-gtk_widget_measure-error-flood.patch @@ -0,0 +1,39 @@ +diff -up gnome-software-42.beta/src/gs-app-row.ui.3 gnome-software-42.beta/src/gs-app-row.ui +--- gnome-software-42.beta/src/gs-app-row.ui.3 2022-02-10 20:53:14.109477000 +0100 ++++ gnome-software-42.beta/src/gs-app-row.ui 2022-02-16 17:49:02.583817963 +0100 +@@ -26,7 +26,7 @@ + center + + +- True ++ False + 0.0 + 0.5 + end +@@ -80,7 +80,7 @@ + False + 0.0 + 0.5 +- True ++ False + word-char + end + 2 +@@ -119,7 +119,7 @@ + True + 24 + 24 +- True ++ False + word-char + end + 2 +@@ -187,7 +187,7 @@ + False + warning-text + start +- True ++ False + 0 + + diff --git a/gnome-software.spec b/gnome-software.spec index b30cd16..280f9df 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -22,6 +22,7 @@ Source0: https://download.gnome.org/sources/gnome-software/42/%{name}-%{tarbal Patch01: 0001-crash-with-broken-theme.patch Patch02: 0002-packagekit-crash-on-app-install.patch +Patch03: 0003-workaround-gsapprow-gtk_widget_measure-error-flood.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -103,7 +104,7 @@ and update software in the GNOME desktop. This package includes the rpm-ostree backend. %prep -%autosetup -p1 -n %{name}-%{tarball_version} +%autosetup -p1 -S gendiff -n %{name}-%{tarball_version} %build %meson \ @@ -200,6 +201,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %changelog * Wed Feb 16 2022 Milan Crha - 42.beta-2 - Resolves: #2054939 (Crash on a PackageKit app install) +- Add a temporary workaround for gtk_widget_measure error flood on GsAppRow * Fri Feb 11 2022 Milan Crha - 42.beta-1 - Update to 42.beta From 913366d7d63e62d9fbd302a9c820237b69ad3df2 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 21 Feb 2022 10:30:51 +0100 Subject: [PATCH 048/163] Resolves: #2056082 (Enable PackageKit autoremove option) --- gnome-software.spec | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 280f9df..eb8cb8b 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -13,7 +13,7 @@ Name: gnome-software Version: 42~beta -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -113,6 +113,7 @@ This package includes the rpm-ostree backend. -Dmalcontent=true \ -Dgudev=true \ -Dpackagekit=true \ + -Dpackagekit_autoremove=true \ -Dexternal_appstream=false \ -Drpm_ostree=true \ -Dtests=false @@ -199,6 +200,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Feb 21 2022 Milan Crha - 42.beta-3 +- Resolves: #2056082 (Enable PackageKit autoremove option) + * Wed Feb 16 2022 Milan Crha - 42.beta-2 - Resolves: #2054939 (Crash on a PackageKit app install) - Add a temporary workaround for gtk_widget_measure error flood on GsAppRow From f3f073c56f8e1a73d147ef540210328338cd92d5 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 7 Mar 2022 08:15:08 +0100 Subject: [PATCH 049/163] Update to 42.rc --- 0001-crash-with-broken-theme.patch | 24 ++++-------- 0002-packagekit-crash-on-app-install.patch | 28 ------------- ...pprow-gtk_widget_measure-error-flood.patch | 39 ------------------- gnome-software.spec | 11 +++--- sources | 2 +- 5 files changed, 14 insertions(+), 90 deletions(-) delete mode 100644 0002-packagekit-crash-on-app-install.patch delete mode 100644 0003-workaround-gsapprow-gtk_widget_measure-error-flood.patch diff --git a/0001-crash-with-broken-theme.patch b/0001-crash-with-broken-theme.patch index fd37e80..ddbef4a 100644 --- a/0001-crash-with-broken-theme.patch +++ b/0001-crash-with-broken-theme.patch @@ -1,29 +1,22 @@ -From 3a644c151f27f439c36170f0958fd21cf1cc54d0 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Thu, 3 Jun 2021 08:33:53 +0200 Subject: [PATCH] gs-feature-tile: Do not abort when the theme is broken Just print a warning when the theme doesn't provide 'theme_fg_color' and fallback to black color. Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1228 ---- - src/gs-feature-tile.c | 14 +++++++++++--- - 1 file changed, 11 insertions(+), 3 deletions(-) -diff --git a/src/gs-feature-tile.c b/src/gs-feature-tile.c -index 1c85083eb..158af1e56 100644 ---- a/src/gs-feature-tile.c -+++ b/src/gs-feature-tile.c -@@ -268,7 +268,6 @@ gs_feature_tile_refresh (GsAppTile *self) +diff -up gnome-software-42.rc/src/gs-feature-tile.c.1 gnome-software-42.rc/src/gs-feature-tile.c +--- gnome-software-42.rc/src/gs-feature-tile.c.1 2022-03-04 16:23:58.566735700 +0100 ++++ gnome-software-42.rc/src/gs-feature-tile.c 2022-03-07 08:06:29.046595524 +0100 +@@ -411,7 +411,6 @@ gs_feature_tile_refresh (GsAppTile *self if (key_colors != tile->key_colors_cache) { g_autoptr(GArray) colors = NULL; GdkRGBA fg_rgba; - gboolean fg_rgba_valid; GsHSBC fg_hsbc; - - /* Look up the foreground colour for the feature tile, -@@ -283,8 +282,17 @@ gs_feature_tile_refresh (GsAppTile *self) + const GsHSBC *chosen_hsbc; + GsHSBC chosen_hsbc_modified; +@@ -429,8 +428,17 @@ gs_feature_tile_refresh (GsAppTile *self * @min_abs_contrast contrast with the foreground, so * that the text is legible. */ @@ -43,6 +36,3 @@ index 1c85083eb..158af1e56 100644 gtk_rgb_to_hsv (fg_rgba.red, fg_rgba.green, fg_rgba.blue, &fg_hsbc.hue, &fg_hsbc.saturation, &fg_hsbc.brightness); --- -GitLab - diff --git a/0002-packagekit-crash-on-app-install.patch b/0002-packagekit-crash-on-app-install.patch deleted file mode 100644 index 04e85b3..0000000 --- a/0002-packagekit-crash-on-app-install.patch +++ /dev/null @@ -1,28 +0,0 @@ -From 73d1c9fd58d2fdf2c2d84e70cce678390679baa9 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 16 Feb 2022 15:01:46 +0100 -Subject: [PATCH] PackageKit: Fix a crash on app install - -The array should be NULL-terminated, thus add the NULL at the end. - -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1648 ---- - plugins/packagekit/gs-plugin-packagekit.c | 2 ++ - 1 file changed, 2 insertions(+) - -diff --git a/plugins/packagekit/gs-plugin-packagekit.c b/plugins/packagekit/gs-plugin-packagekit.c -index 1ad913af5..56ddb1ccc 100644 ---- a/plugins/packagekit/gs-plugin-packagekit.c -+++ b/plugins/packagekit/gs-plugin-packagekit.c -@@ -612,6 +612,8 @@ gs_plugin_app_install (GsPlugin *plugin, - return FALSE; - } - -+ g_ptr_array_add (array_package_ids, NULL); -+ - gs_app_set_state (app, GS_APP_STATE_INSTALLING); - - for (i = 0; i < gs_app_list_length (addons); i++) { --- -GitLab - diff --git a/0003-workaround-gsapprow-gtk_widget_measure-error-flood.patch b/0003-workaround-gsapprow-gtk_widget_measure-error-flood.patch deleted file mode 100644 index 0a24881..0000000 --- a/0003-workaround-gsapprow-gtk_widget_measure-error-flood.patch +++ /dev/null @@ -1,39 +0,0 @@ -diff -up gnome-software-42.beta/src/gs-app-row.ui.3 gnome-software-42.beta/src/gs-app-row.ui ---- gnome-software-42.beta/src/gs-app-row.ui.3 2022-02-10 20:53:14.109477000 +0100 -+++ gnome-software-42.beta/src/gs-app-row.ui 2022-02-16 17:49:02.583817963 +0100 -@@ -26,7 +26,7 @@ - center - - -- True -+ False - 0.0 - 0.5 - end -@@ -80,7 +80,7 @@ - False - 0.0 - 0.5 -- True -+ False - word-char - end - 2 -@@ -119,7 +119,7 @@ - True - 24 - 24 -- True -+ False - word-char - end - 2 -@@ -187,7 +187,7 @@ - False - warning-text - start -- True -+ False - 0 - - diff --git a/gnome-software.spec b/gnome-software.spec index eb8cb8b..913fede 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,8 +12,8 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 42~beta -Release: 3%{?dist} +Version: 42~rc +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -21,8 +21,6 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/42/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -Patch02: 0002-packagekit-crash-on-app-install.patch -Patch03: 0003-workaround-gsapprow-gtk_widget_measure-error-flood.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -178,7 +176,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_repos.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rewrite-resource.so -%{_sysconfdir}/xdg/autostart/gnome-software-service.desktop +%{_sysconfdir}/xdg/autostart/org.gnome.Software.desktop %{_datadir}/app-info/xmls/org.gnome.Software.Featured.xml %{_datadir}/app-info/xmls/org.gnome.Software.Popular.xml %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service @@ -200,6 +198,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Mar 07 2022 Milan Crha - 42.rc-1 +- Update to 42.rc + * Mon Feb 21 2022 Milan Crha - 42.beta-3 - Resolves: #2056082 (Enable PackageKit autoremove option) diff --git a/sources b/sources index 2f9377d..6afee80 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-42.beta.tar.xz) = 3ae22c9a37a134a6340191aabc7b02f6b53322820853aacd36e6d43893d7118d177defff44de93b627e488411798570b9c82c99b354966a899563e27d8c32a6a +SHA512 (gnome-software-42.rc.tar.xz) = cd9c465d73b8998c0ebc49d5e40fec22522e0f125cbce5ff59a7a13d779a3793ac57dfb606d9b918e0c198b6b6cd62657483dc8e83a77ed84966c5f44980f38b From 154dca4c08a12081aa5dd30c7955e2adaf1dae18 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Thu, 10 Mar 2022 17:34:44 +0100 Subject: [PATCH 050/163] Add upstream patches for gs-download-utils (i#1677 and i#1679) --- 1282.patch | 182 ++++++++++++++++++++++++++++++++++++++++++++ 1285.patch | 45 +++++++++++ gnome-software.spec | 7 +- 3 files changed, 233 insertions(+), 1 deletion(-) create mode 100644 1282.patch create mode 100644 1285.patch diff --git a/1282.patch b/1282.patch new file mode 100644 index 0000000..f6cc6fd --- /dev/null +++ b/1282.patch @@ -0,0 +1,182 @@ +From edbeab87ce5aa48bd9fe49dd22acfcce2b8b0fc0 Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Thu, 10 Mar 2022 13:20:58 +0000 +Subject: [PATCH 1/3] =?UTF-8?q?gs-download-utils:=20Don=E2=80=99t=20use=20?= + =?UTF-8?q?ETag=20when=20writing=20local=20file?= +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +The ETag we care about for the download is the ETag returned by the +server, not the ETag of the local file. Passing the server’s ETag to the +local file operations may result in the local file not being written to, +with a “The file was externally modified” error. + +Signed-off-by: Philip Withnall + +Fixes: #1677 +--- + lib/gs-download-utils.c | 20 +++++++++++++++++--- + 1 file changed, 17 insertions(+), 3 deletions(-) + +diff --git a/lib/gs-download-utils.c b/lib/gs-download-utils.c +index f3a64479b..a6d930587 100644 +--- a/lib/gs-download-utils.c ++++ b/lib/gs-download-utils.c +@@ -134,6 +134,9 @@ static void download_progress (GTask *task); + * existing content of the output stream (if it’s a file, for example) will not + * be overwritten. + * ++ * Note that @last_etag must be the ETag value returned by the server last time ++ * the file was downloaded, not the local file ETag generated by GLib. ++ * + * If specified, @progress_callback will be called zero or more times until + * @callback is called, providing progress updates on the download. + * +@@ -644,9 +647,20 @@ gs_download_file_async (SoupSession *soup_session, + /* Query the old ETag if the file already exists. */ + data->last_etag = gs_utils_get_file_etag (output_file, cancellable); + +- /* Create the output file. */ ++ /* Create the output file. ++ * ++ * Note that `data->last_etag` is *not* passed in here, as the ETag from ++ * the server and the file modification ETag that GLib uses are ++ * different things. For g_file_replace_async(), GLib always uses an ++ * ETag it generates internally based on the file mtime (see ++ * _g_local_file_info_create_etag()), which will never match what the ++ * server returns in its ETag header. ++ * ++ * This is fine, as we are using the ETag to avoid an unnecessary HTTP ++ * download if possible. We don’t care about tracking changes to the ++ * file on disk. */ + g_file_replace_async (output_file, +- data->last_etag, ++ NULL, /* ETag */ + FALSE, /* make_backup */ + G_FILE_CREATE_PRIVATE | G_FILE_CREATE_REPLACE_DESTINATION, + io_priority, +@@ -699,7 +713,7 @@ download_file_cb (GObject *source_object, + return; + } + +- /* Update the ETag. */ ++ /* Update the stored HTTP ETag. */ + gs_utils_set_file_etag (data->output_file, new_etag, cancellable); + + g_task_return_boolean (task, TRUE); +-- +GitLab + + +From 040e2dca3904d965450158dcdaeedfca12965682 Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Thu, 10 Mar 2022 13:27:21 +0000 +Subject: [PATCH 2/3] gs-utils: Add some debug messages for getting/setting + ETags + +Signed-off-by: Philip Withnall + +Helps: #1677 +--- + lib/gs-utils.c | 28 +++++++++++++++++++++++----- + 1 file changed, 23 insertions(+), 5 deletions(-) + +diff --git a/lib/gs-utils.c b/lib/gs-utils.c +index 89349b1fe..6dc4d28a0 100644 +--- a/lib/gs-utils.c ++++ b/lib/gs-utils.c +@@ -1509,14 +1509,18 @@ gs_utils_get_file_etag (GFile *file, + GCancellable *cancellable) + { + g_autoptr(GFileInfo) info = NULL; ++ g_autoptr(GError) local_error = NULL; + + g_return_val_if_fail (G_IS_FILE (file), NULL); + g_return_val_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable), NULL); + +- info = g_file_query_info (file, METADATA_ETAG_ATTRIBUTE, G_FILE_QUERY_INFO_NONE, cancellable, NULL); ++ info = g_file_query_info (file, METADATA_ETAG_ATTRIBUTE, G_FILE_QUERY_INFO_NONE, cancellable, &local_error); + +- if (info == NULL) ++ if (info == NULL) { ++ g_debug ("Error getting attribute ‘%s’ for file ‘%s’: %s", ++ METADATA_ETAG_ATTRIBUTE, g_file_peek_path (file), local_error->message); + return NULL; ++ } + + return g_strdup (g_file_info_get_attribute_string (info, METADATA_ETAG_ATTRIBUTE)); + } +@@ -1542,15 +1546,29 @@ gs_utils_set_file_etag (GFile *file, + const gchar *etag, + GCancellable *cancellable) + { ++ g_autoptr(GError) local_error = NULL; ++ + g_return_val_if_fail (G_IS_FILE (file), FALSE); + g_return_val_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable), FALSE); + + if (etag == NULL || *etag == '\0') { +- return g_file_set_attribute (file, METADATA_ETAG_ATTRIBUTE, G_FILE_ATTRIBUTE_TYPE_INVALID, +- NULL, G_FILE_QUERY_INFO_NONE, cancellable, NULL); ++ if (!g_file_set_attribute (file, METADATA_ETAG_ATTRIBUTE, G_FILE_ATTRIBUTE_TYPE_INVALID, ++ NULL, G_FILE_QUERY_INFO_NONE, cancellable, &local_error)) { ++ g_debug ("Error clearing attribute ‘%s’ on file ‘%s’: %s", ++ METADATA_ETAG_ATTRIBUTE, g_file_peek_path (file), local_error->message); ++ return FALSE; ++ } ++ ++ return TRUE; ++ } ++ ++ if (!g_file_set_attribute_string (file, METADATA_ETAG_ATTRIBUTE, etag, G_FILE_QUERY_INFO_NONE, cancellable, &local_error)) { ++ g_debug ("Error setting attribute ‘%s’ to ‘%s’ on file ‘%s’: %s", ++ METADATA_ETAG_ATTRIBUTE, etag, g_file_peek_path (file), local_error->message); ++ return FALSE; + } + +- return g_file_set_attribute_string (file, METADATA_ETAG_ATTRIBUTE, etag, G_FILE_QUERY_INFO_NONE, cancellable, NULL); ++ return TRUE; + } + + /** +-- +GitLab + + +From c46d656c51938adb994b4597c766259bf1813fe5 Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Thu, 10 Mar 2022 13:27:50 +0000 +Subject: [PATCH 3/3] gs-utils: Change ETag attribute namespace from metadata + to xattr +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +The xattr namespace is likely to be supported on all modern Linux +distributions for local files, and doesn’t require IPC with +`gvfsd-metadata`. + +Signed-off-by: Philip Withnall + +Helps: #1677 +--- + lib/gs-utils.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/lib/gs-utils.c b/lib/gs-utils.c +index 6dc4d28a0..b8eefe36e 100644 +--- a/lib/gs-utils.c ++++ b/lib/gs-utils.c +@@ -1488,7 +1488,7 @@ gs_utils_get_file_size (const gchar *filename, + return size; + } + +-#define METADATA_ETAG_ATTRIBUTE "metadata::etag" ++#define METADATA_ETAG_ATTRIBUTE "xattr::gnome-software::etag" + + /** + * gs_utils_get_file_etag: +-- +GitLab + diff --git a/1285.patch b/1285.patch new file mode 100644 index 0000000..1caae0c --- /dev/null +++ b/1285.patch @@ -0,0 +1,45 @@ +From 92da7c98217856785dfea518890fa25acd3a055e Mon Sep 17 00:00:00 2001 +From: Philip Withnall +Date: Thu, 10 Mar 2022 14:25:05 +0000 +Subject: [PATCH] =?UTF-8?q?gs-download-utils:=20Ignore=20cancellation=20er?= + =?UTF-8?q?rors=20when=20there=E2=80=99s=20a=20cache=20hit?= +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +In order to avoid overwriting an existing cache file when the server has +said it’s up to date, we cancel closing the output stream. + +Avoid propagating that cancellation error up to the caller; to them, the +operation should seem like a success rather than returning +`G_IO_ERROR_CANCELLED`. + +Signed-off-by: Philip Withnall + +Fixes: #1679 +--- + lib/gs-download-utils.c | 8 +++++++- + 1 file changed, 7 insertions(+), 1 deletion(-) + +diff --git a/lib/gs-download-utils.c b/lib/gs-download-utils.c +index f3a64479b..4ab15c098 100644 +--- a/lib/gs-download-utils.c ++++ b/lib/gs-download-utils.c +@@ -467,7 +467,13 @@ close_stream_cb (GObject *source_object, + * overwrite errors set earlier in the operation. */ + if (!g_output_stream_close_finish (G_OUTPUT_STREAM (source_object), + result, &local_error)) { +- if (data->error == NULL) ++ /* If we are aborting writing the output stream (perhaps ++ * because of a cache hit), don’t report the error at ++ * all. */ ++ if (data->discard_output_stream && ++ g_error_matches (local_error, G_IO_ERROR, G_IO_ERROR_CANCELLED)) ++ g_clear_error (&local_error); ++ else if (data->error == NULL) + data->error = g_steal_pointer (&local_error); + else if (!g_error_matches (local_error, G_IO_ERROR, G_IO_ERROR_CANCELLED)) + g_debug ("Error closing output stream: %s", local_error->message); +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index 913fede..41d6c9d 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -13,7 +13,7 @@ Name: gnome-software Version: 42~rc -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -21,6 +21,8 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/42/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +Patch02: 1282.patch +Patch03: 1285.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -198,6 +200,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Thu Mar 10 2022 Milan Crha - 42.rc-2 +- Add upstream patches for gs-download-utils (i#1677 and i#1679) + * Mon Mar 07 2022 Milan Crha - 42.rc-1 - Update to 42.rc From 0db1b574e2399a7f816e40c1a7d4de06d56e1613 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 18 Mar 2022 10:13:22 +0100 Subject: [PATCH 051/163] Update to 42.0 --- 1282.patch | 182 -------------------------------------------- 1285.patch | 45 ----------- gnome-software.spec | 9 ++- sources | 2 +- 4 files changed, 6 insertions(+), 232 deletions(-) delete mode 100644 1282.patch delete mode 100644 1285.patch diff --git a/1282.patch b/1282.patch deleted file mode 100644 index f6cc6fd..0000000 --- a/1282.patch +++ /dev/null @@ -1,182 +0,0 @@ -From edbeab87ce5aa48bd9fe49dd22acfcce2b8b0fc0 Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Thu, 10 Mar 2022 13:20:58 +0000 -Subject: [PATCH 1/3] =?UTF-8?q?gs-download-utils:=20Don=E2=80=99t=20use=20?= - =?UTF-8?q?ETag=20when=20writing=20local=20file?= -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -The ETag we care about for the download is the ETag returned by the -server, not the ETag of the local file. Passing the server’s ETag to the -local file operations may result in the local file not being written to, -with a “The file was externally modified” error. - -Signed-off-by: Philip Withnall - -Fixes: #1677 ---- - lib/gs-download-utils.c | 20 +++++++++++++++++--- - 1 file changed, 17 insertions(+), 3 deletions(-) - -diff --git a/lib/gs-download-utils.c b/lib/gs-download-utils.c -index f3a64479b..a6d930587 100644 ---- a/lib/gs-download-utils.c -+++ b/lib/gs-download-utils.c -@@ -134,6 +134,9 @@ static void download_progress (GTask *task); - * existing content of the output stream (if it’s a file, for example) will not - * be overwritten. - * -+ * Note that @last_etag must be the ETag value returned by the server last time -+ * the file was downloaded, not the local file ETag generated by GLib. -+ * - * If specified, @progress_callback will be called zero or more times until - * @callback is called, providing progress updates on the download. - * -@@ -644,9 +647,20 @@ gs_download_file_async (SoupSession *soup_session, - /* Query the old ETag if the file already exists. */ - data->last_etag = gs_utils_get_file_etag (output_file, cancellable); - -- /* Create the output file. */ -+ /* Create the output file. -+ * -+ * Note that `data->last_etag` is *not* passed in here, as the ETag from -+ * the server and the file modification ETag that GLib uses are -+ * different things. For g_file_replace_async(), GLib always uses an -+ * ETag it generates internally based on the file mtime (see -+ * _g_local_file_info_create_etag()), which will never match what the -+ * server returns in its ETag header. -+ * -+ * This is fine, as we are using the ETag to avoid an unnecessary HTTP -+ * download if possible. We don’t care about tracking changes to the -+ * file on disk. */ - g_file_replace_async (output_file, -- data->last_etag, -+ NULL, /* ETag */ - FALSE, /* make_backup */ - G_FILE_CREATE_PRIVATE | G_FILE_CREATE_REPLACE_DESTINATION, - io_priority, -@@ -699,7 +713,7 @@ download_file_cb (GObject *source_object, - return; - } - -- /* Update the ETag. */ -+ /* Update the stored HTTP ETag. */ - gs_utils_set_file_etag (data->output_file, new_etag, cancellable); - - g_task_return_boolean (task, TRUE); --- -GitLab - - -From 040e2dca3904d965450158dcdaeedfca12965682 Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Thu, 10 Mar 2022 13:27:21 +0000 -Subject: [PATCH 2/3] gs-utils: Add some debug messages for getting/setting - ETags - -Signed-off-by: Philip Withnall - -Helps: #1677 ---- - lib/gs-utils.c | 28 +++++++++++++++++++++++----- - 1 file changed, 23 insertions(+), 5 deletions(-) - -diff --git a/lib/gs-utils.c b/lib/gs-utils.c -index 89349b1fe..6dc4d28a0 100644 ---- a/lib/gs-utils.c -+++ b/lib/gs-utils.c -@@ -1509,14 +1509,18 @@ gs_utils_get_file_etag (GFile *file, - GCancellable *cancellable) - { - g_autoptr(GFileInfo) info = NULL; -+ g_autoptr(GError) local_error = NULL; - - g_return_val_if_fail (G_IS_FILE (file), NULL); - g_return_val_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable), NULL); - -- info = g_file_query_info (file, METADATA_ETAG_ATTRIBUTE, G_FILE_QUERY_INFO_NONE, cancellable, NULL); -+ info = g_file_query_info (file, METADATA_ETAG_ATTRIBUTE, G_FILE_QUERY_INFO_NONE, cancellable, &local_error); - -- if (info == NULL) -+ if (info == NULL) { -+ g_debug ("Error getting attribute ‘%s’ for file ‘%s’: %s", -+ METADATA_ETAG_ATTRIBUTE, g_file_peek_path (file), local_error->message); - return NULL; -+ } - - return g_strdup (g_file_info_get_attribute_string (info, METADATA_ETAG_ATTRIBUTE)); - } -@@ -1542,15 +1546,29 @@ gs_utils_set_file_etag (GFile *file, - const gchar *etag, - GCancellable *cancellable) - { -+ g_autoptr(GError) local_error = NULL; -+ - g_return_val_if_fail (G_IS_FILE (file), FALSE); - g_return_val_if_fail (cancellable == NULL || G_IS_CANCELLABLE (cancellable), FALSE); - - if (etag == NULL || *etag == '\0') { -- return g_file_set_attribute (file, METADATA_ETAG_ATTRIBUTE, G_FILE_ATTRIBUTE_TYPE_INVALID, -- NULL, G_FILE_QUERY_INFO_NONE, cancellable, NULL); -+ if (!g_file_set_attribute (file, METADATA_ETAG_ATTRIBUTE, G_FILE_ATTRIBUTE_TYPE_INVALID, -+ NULL, G_FILE_QUERY_INFO_NONE, cancellable, &local_error)) { -+ g_debug ("Error clearing attribute ‘%s’ on file ‘%s’: %s", -+ METADATA_ETAG_ATTRIBUTE, g_file_peek_path (file), local_error->message); -+ return FALSE; -+ } -+ -+ return TRUE; -+ } -+ -+ if (!g_file_set_attribute_string (file, METADATA_ETAG_ATTRIBUTE, etag, G_FILE_QUERY_INFO_NONE, cancellable, &local_error)) { -+ g_debug ("Error setting attribute ‘%s’ to ‘%s’ on file ‘%s’: %s", -+ METADATA_ETAG_ATTRIBUTE, etag, g_file_peek_path (file), local_error->message); -+ return FALSE; - } - -- return g_file_set_attribute_string (file, METADATA_ETAG_ATTRIBUTE, etag, G_FILE_QUERY_INFO_NONE, cancellable, NULL); -+ return TRUE; - } - - /** --- -GitLab - - -From c46d656c51938adb994b4597c766259bf1813fe5 Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Thu, 10 Mar 2022 13:27:50 +0000 -Subject: [PATCH 3/3] gs-utils: Change ETag attribute namespace from metadata - to xattr -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -The xattr namespace is likely to be supported on all modern Linux -distributions for local files, and doesn’t require IPC with -`gvfsd-metadata`. - -Signed-off-by: Philip Withnall - -Helps: #1677 ---- - lib/gs-utils.c | 2 +- - 1 file changed, 1 insertion(+), 1 deletion(-) - -diff --git a/lib/gs-utils.c b/lib/gs-utils.c -index 6dc4d28a0..b8eefe36e 100644 ---- a/lib/gs-utils.c -+++ b/lib/gs-utils.c -@@ -1488,7 +1488,7 @@ gs_utils_get_file_size (const gchar *filename, - return size; - } - --#define METADATA_ETAG_ATTRIBUTE "metadata::etag" -+#define METADATA_ETAG_ATTRIBUTE "xattr::gnome-software::etag" - - /** - * gs_utils_get_file_etag: --- -GitLab - diff --git a/1285.patch b/1285.patch deleted file mode 100644 index 1caae0c..0000000 --- a/1285.patch +++ /dev/null @@ -1,45 +0,0 @@ -From 92da7c98217856785dfea518890fa25acd3a055e Mon Sep 17 00:00:00 2001 -From: Philip Withnall -Date: Thu, 10 Mar 2022 14:25:05 +0000 -Subject: [PATCH] =?UTF-8?q?gs-download-utils:=20Ignore=20cancellation=20er?= - =?UTF-8?q?rors=20when=20there=E2=80=99s=20a=20cache=20hit?= -MIME-Version: 1.0 -Content-Type: text/plain; charset=UTF-8 -Content-Transfer-Encoding: 8bit - -In order to avoid overwriting an existing cache file when the server has -said it’s up to date, we cancel closing the output stream. - -Avoid propagating that cancellation error up to the caller; to them, the -operation should seem like a success rather than returning -`G_IO_ERROR_CANCELLED`. - -Signed-off-by: Philip Withnall - -Fixes: #1679 ---- - lib/gs-download-utils.c | 8 +++++++- - 1 file changed, 7 insertions(+), 1 deletion(-) - -diff --git a/lib/gs-download-utils.c b/lib/gs-download-utils.c -index f3a64479b..4ab15c098 100644 ---- a/lib/gs-download-utils.c -+++ b/lib/gs-download-utils.c -@@ -467,7 +467,13 @@ close_stream_cb (GObject *source_object, - * overwrite errors set earlier in the operation. */ - if (!g_output_stream_close_finish (G_OUTPUT_STREAM (source_object), - result, &local_error)) { -- if (data->error == NULL) -+ /* If we are aborting writing the output stream (perhaps -+ * because of a cache hit), don’t report the error at -+ * all. */ -+ if (data->discard_output_stream && -+ g_error_matches (local_error, G_IO_ERROR, G_IO_ERROR_CANCELLED)) -+ g_clear_error (&local_error); -+ else if (data->error == NULL) - data->error = g_steal_pointer (&local_error); - else if (!g_error_matches (local_error, G_IO_ERROR, G_IO_ERROR_CANCELLED)) - g_debug ("Error closing output stream: %s", local_error->message); --- -GitLab - diff --git a/gnome-software.spec b/gnome-software.spec index 41d6c9d..bc27980 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -12,8 +12,8 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 42~rc -Release: 2%{?dist} +Version: 42.0 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -21,8 +21,6 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/42/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -Patch02: 1282.patch -Patch03: 1285.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -200,6 +198,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Fri Mar 18 2022 Milan Crha - 42.0-1 +- Update to 42.0 + * Thu Mar 10 2022 Milan Crha - 42.rc-2 - Add upstream patches for gs-download-utils (i#1677 and i#1679) diff --git a/sources b/sources index 6afee80..2a6fbea 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-42.rc.tar.xz) = cd9c465d73b8998c0ebc49d5e40fec22522e0f125cbce5ff59a7a13d779a3793ac57dfb606d9b918e0c198b6b6cd62657483dc8e83a77ed84966c5f44980f38b +SHA512 (gnome-software-42.0.tar.xz) = f630232d164d1a7adcf9a91133769c6fe4ce62cdaeccd49b991330682eeccfddc8f83c7326802aaabdb4fc537243c0fd19741c702f4d23d75ebd71e9abb3da92 From 82d21baa53b72f37b9370b734b414157750bceab Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Wed, 27 Apr 2022 09:09:39 +0200 Subject: [PATCH 052/163] Update to 42.1 --- gnome-software.spec | 15 +++++++++------ sources | 2 +- 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index bc27980..ee7eb05 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -9,10 +9,13 @@ %global fwupd_version 1.3.3 %global flatpak_version 1.5.1 +# this is not a library version +%define gs_plugin_version 18 + %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 42.0 +Version: 42.1 Release: 1%{?dist} Summary: A software center for GNOME @@ -74,9 +77,6 @@ Recommends: PackageKit%{?_isa} >= %{packagekit_version} Obsoletes: gnome-software-snap < 3.33.1 Obsoletes: gnome-software-editor < 3.35.1 -# this is not a library version -%define gs_plugin_version 17 - %description gnome-software is an application that makes it easy to add, remove and update software in the GNOME desktop. @@ -177,8 +177,8 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_repos.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rewrite-resource.so %{_sysconfdir}/xdg/autostart/org.gnome.Software.desktop -%{_datadir}/app-info/xmls/org.gnome.Software.Featured.xml -%{_datadir}/app-info/xmls/org.gnome.Software.Popular.xml +%{_datadir}/swcatalog/xml/org.gnome.Software.Featured.xml +%{_datadir}/swcatalog/xml/org.gnome.Software.Popular.xml %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service %{_datadir}/dbus-1/services/org.gnome.Software.service %{_datadir}/gnome-shell/search-providers/org.gnome.Software-search-provider.ini @@ -198,6 +198,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Wed Apr 27 2022 Milan Crha - 42.1-1 +- Update to 42.1 + * Fri Mar 18 2022 Milan Crha - 42.0-1 - Update to 42.0 diff --git a/sources b/sources index 2a6fbea..326494a 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-42.0.tar.xz) = f630232d164d1a7adcf9a91133769c6fe4ce62cdaeccd49b991330682eeccfddc8f83c7326802aaabdb4fc537243c0fd19741c702f4d23d75ebd71e9abb3da92 +SHA512 (gnome-software-42.1.tar.xz) = 292a17e94c7409198fdff4250a88cb240a126c3d77a9cfee1ea8608fdc482d75af6f8fc91c5c6c068b474edea6dcb197f88ec09081a8b270d5f3eda67db755ad From b0b459586b215a14dac347bd45e930e9a15eb07a Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 30 May 2022 17:51:05 +0200 Subject: [PATCH 053/163] Update to 42.2; Add patch to correct order of the setup of the GsShell --- 0002-shell-setup-order.patch | 134 +++++++++++++++++++++++++++++++++++ gnome-software.spec | 7 +- sources | 2 +- 3 files changed, 141 insertions(+), 2 deletions(-) create mode 100644 0002-shell-setup-order.patch diff --git a/0002-shell-setup-order.patch b/0002-shell-setup-order.patch new file mode 100644 index 0000000..c0ba76b --- /dev/null +++ b/0002-shell-setup-order.patch @@ -0,0 +1,134 @@ +diff --git a/lib/gs-appstream.c b/lib/gs-appstream.c +index 38cc31bb5..c73adce6d 100644 +--- a/lib/gs-appstream.c ++++ b/lib/gs-appstream.c +@@ -1626,12 +1626,12 @@ gs_appstream_add_categories (XbSilo *silo, + for (guint k = 0; k < groups->len; k++) { + const gchar *group = g_ptr_array_index (groups, k); + guint cnt = gs_appstream_count_component_for_groups (silo, group); +- for (guint l = 0; l < cnt; l++) { +- gs_category_increment_size (parent); ++ if (cnt > 0) { ++ gs_category_increment_size (parent, cnt); + if (children->len > 1) { + /* Parent category has multiple groups, so increment + * each group's size too */ +- gs_category_increment_size (cat); ++ gs_category_increment_size (cat, cnt); + } + } + } +diff --git a/lib/gs-category.c b/lib/gs-category.c +index b311c4941..4baede3bc 100644 +--- a/lib/gs-category.c ++++ b/lib/gs-category.c +@@ -147,17 +147,19 @@ gs_category_set_size (GsCategory *category, guint size) + /** + * gs_category_increment_size: + * @category: a #GsCategory ++ * @value: how many to add + * +- * Adds one to the size count if an application is available ++ * Adds @value to the size count. + * + * Since: 3.22 + **/ + void +-gs_category_increment_size (GsCategory *category) ++gs_category_increment_size (GsCategory *category, ++ guint value) + { + g_return_if_fail (GS_IS_CATEGORY (category)); + +- category->size++; ++ category->size += value; + g_object_notify_by_pspec (G_OBJECT (category), obj_props[PROP_SIZE]); + } + +diff --git a/lib/gs-category.h b/lib/gs-category.h +index ecd2e1e23..1e82591aa 100644 +--- a/lib/gs-category.h ++++ b/lib/gs-category.h +@@ -39,6 +39,7 @@ GsCategory *gs_category_find_child (GsCategory *category, + GPtrArray *gs_category_get_children (GsCategory *category); + + guint gs_category_get_size (GsCategory *category); +-void gs_category_increment_size (GsCategory *category); ++void gs_category_increment_size (GsCategory *category, ++ guint value); + + G_END_DECLS +diff --git a/src/gs-shell.c b/src/gs-shell.c +index db449a9b0..796d7b05a 100644 +--- a/src/gs-shell.c ++++ b/src/gs-shell.c +@@ -107,6 +107,7 @@ struct _GsShell + GtkWidget *primary_menu; + GtkWidget *sub_page_header_title; + ++ gboolean active_after_setup; + gboolean is_narrow; + guint allocation_changed_cb_id; + +@@ -165,6 +166,12 @@ gs_shell_modal_dialog_present (GsShell *shell, GtkWindow *window) + void + gs_shell_activate (GsShell *shell) + { ++ /* Waiting for plugin loader to setup first */ ++ if (shell->plugin_loader == NULL) { ++ shell->active_after_setup = TRUE; ++ return; ++ } ++ + gtk_widget_show (GTK_WIDGET (shell)); + gtk_window_present (GTK_WINDOW (shell)); + } +@@ -2237,6 +2244,11 @@ gs_shell_setup (GsShell *shell, GsPluginLoader *plugin_loader, GCancellable *can + if (g_settings_get_boolean (shell->settings, "first-run")) + g_settings_set_boolean (shell->settings, "first-run", FALSE); + } ++ ++ if (shell->active_after_setup) { ++ shell->active_after_setup = FALSE; ++ gs_shell_activate (shell); ++ } + } + + void +diff --git a/src/gs-application.c b/src/gs-application.c +index e3f5f55c7..bdadd5c34 100644 +--- a/src/gs-application.c ++++ b/src/gs-application.c +@@ -968,12 +968,9 @@ gs_application_startup (GApplication *application) + G_CALLBACK (gs_application_shell_loaded_cb), + app); + +- gs_shell_setup (app->shell, app->plugin_loader, app->cancellable); + app->main_window = GTK_WINDOW (app->shell); + gtk_application_add_window (GTK_APPLICATION (app), app->main_window); + +- app->update_monitor = gs_update_monitor_new (app, app->plugin_loader); +- + gs_application_update_software_sources_presence (application); + + /* Set up the plugins. */ +@@ -990,6 +987,7 @@ startup_cb (GObject *source_object, + GAsyncResult *result, + gpointer user_data) + { ++ GsApplication *app = GS_APPLICATION (user_data); + GsPluginLoader *plugin_loader = GS_PLUGIN_LOADER (source_object); + g_autoptr(GError) local_error = NULL; + +@@ -1002,6 +1000,11 @@ startup_cb (GObject *source_object, + + /* show the priority of each plugin */ + gs_plugin_loader_dump_state (plugin_loader); ++ ++ /* Setup the shell only after the plugin loader finished its setup, ++ thus all plugins are loaded and ready for the jobs. */ ++ gs_shell_setup (app->shell, app->plugin_loader, app->cancellable); ++ app->update_monitor = gs_update_monitor_new (app, app->plugin_loader); + } + + static void diff --git a/gnome-software.spec b/gnome-software.spec index ee7eb05..61f0509 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -15,7 +15,7 @@ %global tarball_version %%(echo %{version} | tr '~' '.') Name: gnome-software -Version: 42.1 +Version: 42.2 Release: 1%{?dist} Summary: A software center for GNOME @@ -24,6 +24,7 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/42/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +Patch02: 0002-shell-setup-order.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -198,6 +199,10 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon May 30 2022 Milan Crha - 42.2-1 +- Update to 42.2 +- Add patch to correct order of the setup of the GsShell + * Wed Apr 27 2022 Milan Crha - 42.1-1 - Update to 42.1 diff --git a/sources b/sources index 326494a..fc682d9 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-42.1.tar.xz) = 292a17e94c7409198fdff4250a88cb240a126c3d77a9cfee1ea8608fdc482d75af6f8fc91c5c6c068b474edea6dcb197f88ec09081a8b270d5f3eda67db755ad +SHA512 (gnome-software-42.2.tar.xz) = 2b231afbedb241b8957fa902c37cd85734cdb8b2071cd32ac75ae2e9e064483fe1e9e8d49f2e6df478fdd01e9c6225a85887ba2af1792a9150b89cea75ef8bb4 From 5575960754e99686dc508bdf62786708af80cbe6 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 13 Jun 2022 14:43:28 +0200 Subject: [PATCH 054/163] Add patch for crash under gs_flatpak_refine_app_unlocked() --- ...under-gs-flatpak-refine-app-unlocked.patch | 386 ++++++++++++++++++ gnome-software.spec | 6 +- 2 files changed, 391 insertions(+), 1 deletion(-) create mode 100644 0003-crash-under-gs-flatpak-refine-app-unlocked.patch diff --git a/0003-crash-under-gs-flatpak-refine-app-unlocked.patch b/0003-crash-under-gs-flatpak-refine-app-unlocked.patch new file mode 100644 index 0000000..701e7ef --- /dev/null +++ b/0003-crash-under-gs-flatpak-refine-app-unlocked.patch @@ -0,0 +1,386 @@ +diff -up gnome-software-42.2/lib/gs-appstream.c.3 gnome-software-42.2/lib/gs-appstream.c +--- gnome-software-42.2/lib/gs-appstream.c.3 2022-06-13 14:34:05.477145977 +0200 ++++ gnome-software-42.2/lib/gs-appstream.c 2022-06-13 14:36:26.640218337 +0200 +@@ -20,7 +20,13 @@ GsApp * + gs_appstream_create_app (GsPlugin *plugin, XbSilo *silo, XbNode *component, GError **error) + { + GsApp *app; +- g_autoptr(GsApp) app_new = gs_app_new (NULL); ++ g_autoptr(GsApp) app_new = NULL; ++ ++ g_return_val_if_fail (GS_IS_PLUGIN (plugin), NULL); ++ g_return_val_if_fail (XB_IS_SILO (silo), NULL); ++ g_return_val_if_fail (XB_IS_NODE (component), NULL); ++ ++ app_new = gs_app_new (NULL); + + /* refine enough to get the unique ID */ + if (!gs_appstream_refine_app (plugin, app_new, silo, component, +@@ -967,6 +973,11 @@ gs_appstream_refine_app (GsPlugin *plugi + g_autoptr(GPtrArray) launchables = NULL; + g_autoptr(XbNode) req = NULL; + ++ g_return_val_if_fail (GS_IS_PLUGIN (plugin), FALSE); ++ g_return_val_if_fail (GS_IS_APP (app), FALSE); ++ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); ++ g_return_val_if_fail (XB_IS_NODE (component), FALSE); ++ + /* is compatible */ + req = xb_node_query_first (component, + "requires/id[@type='id']" +@@ -1411,6 +1422,11 @@ gs_appstream_search (GsPlugin *plugin, + { AS_SEARCH_TOKEN_MATCH_NONE, NULL } + }; + ++ g_return_val_if_fail (GS_IS_PLUGIN (plugin), FALSE); ++ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); ++ g_return_val_if_fail (values != NULL, FALSE); ++ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); ++ + /* add some weighted queries */ + for (guint i = 0; queries[i].xpath != NULL; i++) { + g_autoptr(GError) error_query = NULL; +@@ -1487,6 +1503,11 @@ gs_appstream_add_category_apps (GsPlugin + { + GPtrArray *desktop_groups; + ++ g_return_val_if_fail (GS_IS_PLUGIN (plugin), FALSE); ++ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); ++ g_return_val_if_fail (GS_IS_CATEGORY (category), FALSE); ++ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); ++ + desktop_groups = gs_category_get_desktop_groups (category); + if (desktop_groups->len == 0) { + g_warning ("no desktop_groups for %s", gs_category_get_id (category)); +@@ -1577,6 +1598,9 @@ gs_appstream_add_categories (XbSilo *sil + GCancellable *cancellable, + GError **error) + { ++ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); ++ g_return_val_if_fail (list != NULL, FALSE); ++ + for (guint j = 0; j < list->len; j++) { + GsCategory *parent = GS_CATEGORY (g_ptr_array_index (list, j)); + GPtrArray *children = gs_category_get_children (parent); +@@ -1611,6 +1635,9 @@ gs_appstream_add_popular (XbSilo *silo, + g_autoptr(GError) error_local = NULL; + g_autoptr(GPtrArray) array = NULL; + ++ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); ++ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); ++ + /* find out how many packages are in each category */ + array = xb_silo_query (silo, + "components/component/kudos/" +@@ -1648,6 +1675,10 @@ gs_appstream_add_recent (GsPlugin *plugi + g_autoptr(GError) error_local = NULL; + g_autoptr(GPtrArray) array = NULL; + ++ g_return_val_if_fail (GS_IS_PLUGIN (plugin), FALSE); ++ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); ++ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); ++ + /* use predicate conditions to the max */ + xpath = g_strdup_printf ("components/component/releases/" + "release[@timestamp>%" G_GUINT64_FORMAT "]/../..", +@@ -1686,6 +1717,10 @@ gs_appstream_add_alternates (XbSilo *sil + g_autoptr(GPtrArray) ids = NULL; + g_autoptr(GString) xpath = g_string_new (NULL); + ++ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); ++ g_return_val_if_fail (GS_IS_APP (app), FALSE); ++ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); ++ + /* probably a package we know nothing about */ + if (gs_app_get_id (app) == NULL) + return TRUE; +@@ -1743,6 +1778,9 @@ gs_appstream_add_featured (XbSilo *silo, + g_autoptr(GError) error_local = NULL; + g_autoptr(GPtrArray) array = NULL; + ++ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); ++ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); ++ + /* find out how many packages are in each category */ + array = xb_silo_query (silo, + "components/component/custom/value[@key='GnomeSoftware::FeatureTile']/../..|" +@@ -1782,6 +1820,11 @@ gs_appstream_url_to_app (GsPlugin *plugi + g_autofree gchar *xpath = NULL; + g_autoptr(GPtrArray) components = NULL; + ++ g_return_val_if_fail (GS_IS_PLUGIN (plugin), FALSE); ++ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); ++ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); ++ g_return_val_if_fail (url != NULL, FALSE); ++ + /* not us */ + scheme = gs_utils_get_url_scheme (url); + if (g_strcmp0 (scheme, "appstream") != 0) +@@ -1812,6 +1855,9 @@ gs_appstream_component_add_keyword (XbBu + g_autoptr(XbBuilderNode) keyword = NULL; + g_autoptr(XbBuilderNode) keywords = NULL; + ++ g_return_if_fail (XB_IS_BUILDER_NODE (component)); ++ g_return_if_fail (str != NULL); ++ + /* create if it does not already exist */ + keywords = xb_builder_node_get_child (component, "keywords", NULL); + if (keywords == NULL) +@@ -1831,6 +1877,9 @@ gs_appstream_component_add_provide (XbBu + g_autoptr(XbBuilderNode) provide = NULL; + g_autoptr(XbBuilderNode) provides = NULL; + ++ g_return_if_fail (XB_IS_BUILDER_NODE (component)); ++ g_return_if_fail (str != NULL); ++ + /* create if it does not already exist */ + provides = xb_builder_node_get_child (component, "provides", NULL); + if (provides == NULL) +@@ -1850,6 +1899,9 @@ gs_appstream_component_add_category (XbB + g_autoptr(XbBuilderNode) category = NULL; + g_autoptr(XbBuilderNode) categories = NULL; + ++ g_return_if_fail (XB_IS_BUILDER_NODE (component)); ++ g_return_if_fail (str != NULL); ++ + /* create if it does not already exist */ + categories = xb_builder_node_get_child (component, "categories", NULL); + if (categories == NULL) +@@ -1868,6 +1920,9 @@ gs_appstream_component_add_icon (XbBuild + { + g_autoptr(XbBuilderNode) icon = NULL; + ++ g_return_if_fail (XB_IS_BUILDER_NODE (component)); ++ g_return_if_fail (str != NULL); ++ + /* create str if it does not already exist */ + icon = xb_builder_node_get_child (component, "icon", NULL); + if (icon == NULL) { +@@ -1881,7 +1936,11 @@ gs_appstream_component_add_icon (XbBuild + void + gs_appstream_component_add_extra_info (XbBuilderNode *component) + { +- const gchar *kind = xb_builder_node_get_attr (component, "type"); ++ const gchar *kind; ++ ++ g_return_if_fail (XB_IS_BUILDER_NODE (component)); ++ ++ kind = xb_builder_node_get_attr (component, "type"); + + /* add the gnome-software-specific 'Addon' group and ensure they + * all have an icon set */ +@@ -1927,9 +1986,14 @@ gs_appstream_component_add_extra_info (X + void + gs_appstream_component_fix_url (XbBuilderNode *component, const gchar *baseurl) + { +- const gchar *text = xb_builder_node_get_text (component); ++ const gchar *text; + g_autofree gchar *url = NULL; + ++ g_return_if_fail (XB_IS_BUILDER_NODE (component)); ++ g_return_if_fail (baseurl != NULL); ++ ++ text = xb_builder_node_get_text (component); ++ + if (text == NULL) + return; + +diff -up gnome-software-42.2/plugins/flatpak/gs-flatpak.c.3 gnome-software-42.2/plugins/flatpak/gs-flatpak.c +--- gnome-software-42.2/plugins/flatpak/gs-flatpak.c.3 2022-05-30 13:43:00.000000000 +0200 ++++ gnome-software-42.2/plugins/flatpak/gs-flatpak.c 2022-06-13 14:34:05.480145978 +0200 +@@ -467,10 +467,18 @@ gs_flatpak_create_source (GsFlatpak *sel + } + + static void ++gs_flatpak_invalidate_silo (GsFlatpak *self) ++{ ++ g_rw_lock_writer_lock (&self->silo_lock); ++ if (self->silo != NULL) ++ xb_silo_invalidate (self->silo); ++ g_rw_lock_writer_unlock (&self->silo_lock); ++} ++ ++static void + gs_flatpak_internal_data_changed (GsFlatpak *self) + { + g_autoptr(GMutexLocker) locker = NULL; +- g_autoptr(GRWLockWriterLocker) writer_locker = NULL; + + /* drop the installed refs cache */ + locker = g_mutex_locker_new (&self->installed_refs_mutex); +@@ -487,10 +495,7 @@ gs_flatpak_internal_data_changed (GsFlat + g_hash_table_remove_all (self->broken_remotes); + g_clear_pointer (&locker, g_mutex_locker_free); + +- writer_locker = g_rw_lock_writer_locker_new (&self->silo_lock); +- if (self->silo) +- xb_silo_invalidate (self->silo); +- g_clear_pointer (&writer_locker, g_rw_lock_writer_locker_free); ++ gs_flatpak_invalidate_silo (self); + + self->requires_full_rescan = TRUE; + } +@@ -2009,10 +2014,7 @@ gs_flatpak_refresh (GsFlatpak *self, + g_mutex_unlock (&self->installed_refs_mutex); + + /* manually do this in case we created the first appstream file */ +- g_rw_lock_reader_lock (&self->silo_lock); +- if (self->silo != NULL) +- xb_silo_invalidate (self->silo); +- g_rw_lock_reader_unlock (&self->silo_lock); ++ gs_flatpak_invalidate_silo (self); + + /* update AppStream metadata */ + if (!gs_flatpak_refresh_appstream (self, cache_age_secs, interactive, cancellable, error)) +@@ -3197,6 +3199,20 @@ gs_flatpak_refine_app_unlocked (GsFlatpa + + locker = g_rw_lock_reader_locker_new (&self->silo_lock); + ++ if (self->silo == NULL) { ++ g_clear_pointer (&locker, g_rw_lock_reader_locker_free); ++ if (!gs_flatpak_rescan_appstream_store (self, interactive, cancellable, error)) ++ return FALSE; ++ ++ locker = g_rw_lock_reader_locker_new (&self->silo_lock); ++ if (self->silo == NULL) { ++ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, ++ "failed to setup XbSilo for '%s'", ++ gs_flatpak_get_id (self)); ++ return FALSE; ++ } ++ } ++ + /* always do AppStream properties */ + if (!gs_flatpak_refine_appstream (self, app, self->silo, flags, interactive, cancellable, error)) + return FALSE; +@@ -3394,6 +3410,13 @@ gs_flatpak_refine_wildcard (GsFlatpak *s + + locker = g_rw_lock_reader_locker_new (&self->silo_lock); + ++ if (self->silo == NULL) { ++ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, ++ "failed to setup XbSilo for '%s'", ++ gs_flatpak_get_id (self)); ++ return FALSE; ++ } ++ + /* find all apps when matching any prefixes */ + xpath = g_strdup_printf ("components/component/id[text()='%s']/..", id); + components = xb_silo_query (self->silo, xpath, 0, &error_local); +@@ -3487,10 +3510,7 @@ gs_flatpak_app_remove_source (GsFlatpak + } + + /* invalidate cache */ +- g_rw_lock_reader_lock (&self->silo_lock); +- if (self->silo != NULL) +- xb_silo_invalidate (self->silo); +- g_rw_lock_reader_unlock (&self->silo_lock); ++ gs_flatpak_invalidate_silo (self); + + gs_app_set_state (app, is_remove ? GS_APP_STATE_UNAVAILABLE : GS_APP_STATE_AVAILABLE); + +@@ -3953,6 +3973,13 @@ gs_flatpak_search (GsFlatpak *self, + return FALSE; + + locker = g_rw_lock_reader_locker_new (&self->silo_lock); ++ if (self->silo == NULL) { ++ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, ++ "failed to setup XbSilo for '%s'", ++ gs_flatpak_get_id (self)); ++ return FALSE; ++ } ++ + if (!gs_appstream_search (self->plugin, self->silo, values, list_tmp, + cancellable, error)) + return FALSE; +@@ -4022,6 +4049,12 @@ gs_flatpak_add_category_apps (GsFlatpak + return FALSE; + + locker = g_rw_lock_reader_locker_new (&self->silo_lock); ++ if (self->silo == NULL) { ++ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, ++ "failed to setup XbSilo for '%s'", ++ gs_flatpak_get_id (self)); ++ return FALSE; ++ } + return gs_appstream_add_category_apps (self->plugin, self->silo, + category, list, + cancellable, error); +@@ -4040,6 +4073,12 @@ gs_flatpak_add_categories (GsFlatpak *se + return FALSE; + + locker = g_rw_lock_reader_locker_new (&self->silo_lock); ++ if (self->silo == NULL) { ++ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, ++ "failed to setup XbSilo for '%s'", ++ gs_flatpak_get_id (self)); ++ return FALSE; ++ } + return gs_appstream_add_categories (self->silo, + list, cancellable, error); + } +@@ -4058,6 +4097,12 @@ gs_flatpak_add_popular (GsFlatpak *self, + return FALSE; + + locker = g_rw_lock_reader_locker_new (&self->silo_lock); ++ if (self->silo == NULL) { ++ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, ++ "failed to setup XbSilo for '%s'", ++ gs_flatpak_get_id (self)); ++ return FALSE; ++ } + if (!gs_appstream_add_popular (self->silo, list_tmp, + cancellable, error)) + return FALSE; +@@ -4081,6 +4126,12 @@ gs_flatpak_add_featured (GsFlatpak *self + return FALSE; + + locker = g_rw_lock_reader_locker_new (&self->silo_lock); ++ if (self->silo == NULL) { ++ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, ++ "failed to setup XbSilo for '%s'", ++ gs_flatpak_get_id (self)); ++ return FALSE; ++ } + if (!gs_appstream_add_featured (self->silo, list_tmp, + cancellable, error)) + return FALSE; +@@ -4105,6 +4156,12 @@ gs_flatpak_add_alternates (GsFlatpak *se + return FALSE; + + locker = g_rw_lock_reader_locker_new (&self->silo_lock); ++ if (self->silo == NULL) { ++ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, ++ "failed to setup XbSilo for '%s'", ++ gs_flatpak_get_id (self)); ++ return FALSE; ++ } + if (!gs_appstream_add_alternates (self->silo, app, list_tmp, + cancellable, error)) + return FALSE; +@@ -4129,6 +4186,12 @@ gs_flatpak_add_recent (GsFlatpak *self, + return FALSE; + + locker = g_rw_lock_reader_locker_new (&self->silo_lock); ++ if (self->silo == NULL) { ++ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, ++ "failed to setup XbSilo for '%s'", ++ gs_flatpak_get_id (self)); ++ return FALSE; ++ } + if (!gs_appstream_add_recent (self->plugin, self->silo, list_tmp, age, + cancellable, error)) + return FALSE; +@@ -4154,6 +4217,12 @@ gs_flatpak_url_to_app (GsFlatpak *self, + return FALSE; + + locker = g_rw_lock_reader_locker_new (&self->silo_lock); ++ if (self->silo == NULL) { ++ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, ++ "failed to setup XbSilo for '%s'", ++ gs_flatpak_get_id (self)); ++ return FALSE; ++ } + if (!gs_appstream_url_to_app (self->plugin, self->silo, list_tmp, url, cancellable, error)) + return FALSE; + diff --git a/gnome-software.spec b/gnome-software.spec index 61f0509..e2ed0ec 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -16,7 +16,7 @@ Name: gnome-software Version: 42.2 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -25,6 +25,7 @@ Source0: https://download.gnome.org/sources/gnome-software/42/%{name}-%{tarbal Patch01: 0001-crash-with-broken-theme.patch Patch02: 0002-shell-setup-order.patch +Patch03: 0003-crash-under-gs-flatpak-refine-app-unlocked.patch BuildRequires: appstream-devel >= %{appstream_version} BuildRequires: gcc @@ -199,6 +200,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Mon Jun 13 2022 Milan Crha - 42.2-2 +- Add patch for crash under gs_flatpak_refine_app_unlocked() + * Mon May 30 2022 Milan Crha - 42.2-1 - Update to 42.2 - Add patch to correct order of the setup of the GsShell From 1e2c0b7474885bf58b1e63ba6373ee9ad3f6e47f Mon Sep 17 00:00:00 2001 From: David King Date: Thu, 16 Jun 2022 11:18:32 +0100 Subject: [PATCH 055/163] Filter private libraries from Provides --- gnome-software.spec | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index e2ed0ec..102f7d1 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -14,9 +14,11 @@ %global tarball_version %%(echo %{version} | tr '~' '.') +%global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ + Name: gnome-software Version: 42.2 -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -200,6 +202,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software %changelog +* Thu Jun 16 2022 David King - 42.2-3 +- Filter private libraries from Provides + * Mon Jun 13 2022 Milan Crha - 42.2-2 - Add patch for crash under gs_flatpak_refine_app_unlocked() From d2c0a6431e436b98dc9bbad79e0487e6e34b4c62 Mon Sep 17 00:00:00 2001 From: David King Date: Thu, 16 Jun 2022 11:28:31 +0100 Subject: [PATCH 056/163] Use pkgconfig for BuildRequires https://fedoraproject.org/wiki/Packaging:PkgConfigBuildRequires --- gnome-software.spec | 61 +++++++++++++++++++++++---------------------- 1 file changed, 31 insertions(+), 30 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 102f7d1..45d45ed 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -1,13 +1,13 @@ %global appstream_version 0.14.0 -%global libadwaita_version 1.0.1 -%global libxmlb_version 0.1.7 +%global flatpak_version 1.5.1 +%global fwupd_version 1.3.3 %global glib2_version 2.61.1 %global gtk4_version 4.4.0 %global json_glib_version 1.2.0 +%global libadwaita_version 1.0.1 %global libsoup_version 2.52.0 +%global libxmlb_version 0.1.7 %global packagekit_version 1.1.1 -%global fwupd_version 1.3.3 -%global flatpak_version 1.5.1 # this is not a library version %define gs_plugin_version 18 @@ -29,36 +29,36 @@ Patch01: 0001-crash-with-broken-theme.patch Patch02: 0002-shell-setup-order.patch Patch03: 0003-crash-under-gs-flatpak-refine-app-unlocked.patch -BuildRequires: appstream-devel >= %{appstream_version} -BuildRequires: gcc -BuildRequires: gettext -BuildRequires: libxslt BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils -BuildRequires: fwupd-devel >= %{fwupd_version} -BuildRequires: glib2-devel >= %{glib2_version} -BuildRequires: gnome-online-accounts-devel -BuildRequires: gsettings-desktop-schemas-devel -BuildRequires: gspell-devel -BuildRequires: pkgconfig(gtk4) >= %{gtk4_version} +BuildRequires: gcc +BuildRequires: gettext BuildRequires: gtk-doc -BuildRequires: json-glib-devel >= %{json_glib_version} -BuildRequires: libdnf-devel -BuildRequires: pkgconfig(libadwaita-1) >= %{libadwaita_version} -BuildRequires: libsoup-devel -BuildRequires: libxmlb-devel >= %{libxmlb_version} -BuildRequires: malcontent-devel -BuildRequires: malcontent-ui-devel +BuildRequires: libxslt BuildRequires: meson -BuildRequires: PackageKit-glib-devel >= %{packagekit_version} -BuildRequires: polkit-devel -BuildRequires: flatpak-devel >= %{flatpak_version} -BuildRequires: ostree-devel -BuildRequires: rpm-devel -BuildRequires: rpm-ostree-devel -BuildRequires: libgudev1-devel -BuildRequires: sysprof-capture-devel -BuildRequires: valgrind-devel +BuildRequires: pkgconfig(appstream) >= %{appstream_version} +BuildRequires: pkgconfig(flatpak) >= %{flatpak_version} +BuildRequires: pkgconfig(fwupd) >= %{fwupd_version} +BuildRequires: pkgconfig(gdk-pixbuf-2.0) +BuildRequires: pkgconfig(gio-unix-2.0) >= %{glib2_version} +BuildRequires: pkgconfig(glib-2.0) >= %{glib2_version} +BuildRequires: pkgconfig(gmodule-2.0) >= %{glib2_version} +BuildRequires: pkgconfig(gsettings-desktop-schemas) +BuildRequires: pkgconfig(gtk4) >= %{gtk4_version} +BuildRequires: pkgconfig(gudev-1.0) +BuildRequires: pkgconfig(json-glib-1.0) >= %{json_glib_version} +BuildRequires: pkgconfig(libadwaita-1) >= %{libadwaita_version} +BuildRequires: pkgconfig(libdnf) +BuildRequires: pkgconfig(libsoup-2.4) +BuildRequires: pkgconfig(malcontent-0) +BuildRequires: pkgconfig(ostree-1) +BuildRequires: pkgconfig(packagekit-glib2) >= %{packagekit_version} +BuildRequires: pkgconfig(polkit-gobject-1) +BuildRequires: pkgconfig(rpm) +BuildRequires: pkgconfig(rpm-ostree-1) +BuildRequires: pkgconfig(sysprof-capture-4) +BuildRequires: pkgconfig(valgrind) +BuildRequires: pkgconfig(xmlb) >= %{libxmlb_version} Requires: appstream-data Requires: appstream%{?_isa} >= %{appstream_version} @@ -204,6 +204,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %changelog * Thu Jun 16 2022 David King - 42.2-3 - Filter private libraries from Provides +- Use pkgconfig for BuildRequires * Mon Jun 13 2022 Milan Crha - 42.2-2 - Add patch for crash under gs_flatpak_refine_app_unlocked() From 597c207c2d9b64f849c54605dd74e720ab277e50 Mon Sep 17 00:00:00 2001 From: David King Date: Thu, 16 Jun 2022 11:44:26 +0100 Subject: [PATCH 057/163] Improve directory ownership --- gnome-software.spec | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 45d45ed..ceee634 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -153,7 +153,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_bindir}/gnome-software %{_datadir}/applications/gnome-software-local-file.desktop %{_datadir}/applications/org.gnome.Software.desktop -%{_mandir}/man1/gnome-software.1.gz +%{_mandir}/man1/gnome-software.1* %{_datadir}/icons/hicolor/*/apps/org.gnome.Software.svg %{_datadir}/icons/hicolor/symbolic/apps/org.gnome.Software-symbolic.svg %{_datadir}/icons/hicolor/scalable/actions/app-remove-symbolic.svg @@ -181,6 +181,8 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_repos.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rewrite-resource.so %{_sysconfdir}/xdg/autostart/org.gnome.Software.desktop +%dir %{_datadir}/swcatalog +%dir %{_datadir}/swcatalog/xml %{_datadir}/swcatalog/xml/org.gnome.Software.Featured.xml %{_datadir}/swcatalog/xml/org.gnome.Software.Popular.xml %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service @@ -199,12 +201,15 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %dir %{_includedir}/gnome-software %{_includedir}/gnome-software/*.h %{_libdir}/gnome-software/libgnomesoftware.so -%{_datadir}/gtk-doc/html/gnome-software +%dir %{_datadir}/gtk-doc +%dir %{_datadir}/gtk-doc/html +%{_datadir}/gtk-doc/html/gnome-software/ %changelog * Thu Jun 16 2022 David King - 42.2-3 - Filter private libraries from Provides - Use pkgconfig for BuildRequires +- Improve directory onwership * Mon Jun 13 2022 Milan Crha - 42.2-2 - Add patch for crash under gs_flatpak_refine_app_unlocked() From 5d7e2fdfe9b89c9071c4c6603fb4bcb3b6ac2f3b Mon Sep 17 00:00:00 2001 From: Richard Hughes Date: Fri, 17 Jun 2022 13:08:37 +0100 Subject: [PATCH 058/163] Add patch to make fwupd user requests work --- 0018-fwupd-Fix-the-user-action-dialogs.patch | 46 ++++++++++++++++++++ gnome-software.spec | 6 ++- 2 files changed, 51 insertions(+), 1 deletion(-) create mode 100644 0018-fwupd-Fix-the-user-action-dialogs.patch diff --git a/0018-fwupd-Fix-the-user-action-dialogs.patch b/0018-fwupd-Fix-the-user-action-dialogs.patch new file mode 100644 index 0000000..e45e21e --- /dev/null +++ b/0018-fwupd-Fix-the-user-action-dialogs.patch @@ -0,0 +1,46 @@ +From 9aba963f2274e929658b632d6f6ce9c73ee83156 Mon Sep 17 00:00:00 2001 +From: Richard Hughes +Date: Tue, 14 Jun 2022 13:04:31 +0100 +Subject: [PATCH 18/18] fwupd: Fix the user action dialogs + +When gnome-software was ported from appstream-glib to libappstream we +missed that the locale arguments are now swapped -- i.e. the former +specified "locale, value" and the latter specified "value, locale". + +This fixes installing software on any devices that require some kind of +user-prompting to complete the update, e.g. buttons that need pressing +or cables that need replugging. +--- + plugins/fwupd/gs-fwupd-app.c | 2 +- + plugins/fwupd/gs-plugin-fwupd.c | 2 +- + 2 files changed, 2 insertions(+), 2 deletions(-) + +diff --git a/plugins/fwupd/gs-fwupd-app.c b/plugins/fwupd/gs-fwupd-app.c +index 03103a3e9..7fcbdadab 100644 +--- a/plugins/fwupd/gs-fwupd-app.c ++++ b/plugins/fwupd/gs-fwupd-app.c +@@ -283,7 +283,7 @@ gs_fwupd_app_set_from_release (GsApp *app, FwupdRelease *rel) + as_screenshot_set_kind (ss, AS_SCREENSHOT_KIND_DEFAULT); + as_screenshot_add_image (ss, im); + if (fwupd_release_get_detach_caption (rel) != NULL) +- as_screenshot_set_caption (ss, NULL, fwupd_release_get_detach_caption (rel)); ++ as_screenshot_set_caption (ss, fwupd_release_get_detach_caption (rel), NULL); + gs_app_set_action_screenshot (app, ss); + } + } +diff --git a/plugins/fwupd/gs-plugin-fwupd.c b/plugins/fwupd/gs-plugin-fwupd.c +index cac6a324a..3171eb96d 100644 +--- a/plugins/fwupd/gs-plugin-fwupd.c ++++ b/plugins/fwupd/gs-plugin-fwupd.c +@@ -945,7 +945,7 @@ gs_plugin_fwupd_install (GsPluginFwupd *self, + + /* caption is required */ + as_screenshot_set_kind (ss, AS_SCREENSHOT_KIND_DEFAULT); +- as_screenshot_set_caption (ss, NULL, fwupd_device_get_update_message (dev)); ++ as_screenshot_set_caption (ss, fwupd_device_get_update_message (dev), NULL); + gs_app_set_action_screenshot (app, ss); + + /* require the dialog */ +-- +2.36.1 + diff --git a/gnome-software.spec b/gnome-software.spec index ceee634..57180c7 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -18,7 +18,7 @@ Name: gnome-software Version: 42.2 -Release: 3%{?dist} +Release: 4%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -28,6 +28,7 @@ Source0: https://download.gnome.org/sources/gnome-software/42/%{name}-%{tarbal Patch01: 0001-crash-with-broken-theme.patch Patch02: 0002-shell-setup-order.patch Patch03: 0003-crash-under-gs-flatpak-refine-app-unlocked.patch +Patch04: 0018-fwupd-Fix-the-user-action-dialogs.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -206,6 +207,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Jun 17 2022 Richard Hughes - 42.2-4 +- Add patch to make fwupd user requests work + * Thu Jun 16 2022 David King - 42.2-3 - Filter private libraries from Provides - Use pkgconfig for BuildRequires From 4afe518accfd1faa928103929e6dfcfe39ff38c6 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 1 Jul 2022 12:41:08 +0200 Subject: [PATCH 059/163] Update to 43.alpha --- 0002-shell-setup-order.patch | 113 +++-- ...under-gs-flatpak-refine-app-unlocked.patch | 386 ------------------ 0018-fwupd-Fix-the-user-action-dialogs.patch | 46 --- gnome-software.spec | 24 +- sources | 2 +- 5 files changed, 71 insertions(+), 500 deletions(-) delete mode 100644 0003-crash-under-gs-flatpak-refine-app-unlocked.patch delete mode 100644 0018-fwupd-Fix-the-user-action-dialogs.patch diff --git a/0002-shell-setup-order.patch b/0002-shell-setup-order.patch index c0ba76b..37da5c0 100644 --- a/0002-shell-setup-order.patch +++ b/0002-shell-setup-order.patch @@ -1,8 +1,7 @@ -diff --git a/lib/gs-appstream.c b/lib/gs-appstream.c -index 38cc31bb5..c73adce6d 100644 ---- a/lib/gs-appstream.c -+++ b/lib/gs-appstream.c -@@ -1626,12 +1626,12 @@ gs_appstream_add_categories (XbSilo *silo, +diff -up gnome-software-43.alpha/lib/gs-appstream.c.2 gnome-software-43.alpha/lib/gs-appstream.c +--- gnome-software-43.alpha/lib/gs-appstream.c.2 2022-06-30 20:03:37.000000000 +0200 ++++ gnome-software-43.alpha/lib/gs-appstream.c 2022-07-01 12:01:07.781026426 +0200 +@@ -1648,12 +1648,12 @@ gs_appstream_add_categories (XbSilo *sil for (guint k = 0; k < groups->len; k++) { const gchar *group = g_ptr_array_index (groups, k); guint cnt = gs_appstream_count_component_for_groups (silo, group); @@ -18,11 +17,10 @@ index 38cc31bb5..c73adce6d 100644 } } } -diff --git a/lib/gs-category.c b/lib/gs-category.c -index b311c4941..4baede3bc 100644 ---- a/lib/gs-category.c -+++ b/lib/gs-category.c -@@ -147,17 +147,19 @@ gs_category_set_size (GsCategory *category, guint size) +diff -up gnome-software-43.alpha/lib/gs-category.c.2 gnome-software-43.alpha/lib/gs-category.c +--- gnome-software-43.alpha/lib/gs-category.c.2 2022-06-30 20:03:37.000000000 +0200 ++++ gnome-software-43.alpha/lib/gs-category.c 2022-07-01 12:01:07.781026426 +0200 +@@ -147,17 +147,19 @@ gs_category_set_size (GsCategory *catego /** * gs_category_increment_size: * @category: a #GsCategory @@ -45,11 +43,10 @@ index b311c4941..4baede3bc 100644 g_object_notify_by_pspec (G_OBJECT (category), obj_props[PROP_SIZE]); } -diff --git a/lib/gs-category.h b/lib/gs-category.h -index ecd2e1e23..1e82591aa 100644 ---- a/lib/gs-category.h -+++ b/lib/gs-category.h -@@ -39,6 +39,7 @@ GsCategory *gs_category_find_child (GsCategory *category, +diff -up gnome-software-43.alpha/lib/gs-category.h.2 gnome-software-43.alpha/lib/gs-category.h +--- gnome-software-43.alpha/lib/gs-category.h.2 2022-06-30 20:03:37.000000000 +0200 ++++ gnome-software-43.alpha/lib/gs-category.h 2022-07-01 12:01:07.781026426 +0200 +@@ -39,6 +39,7 @@ GsCategory *gs_category_find_child (GsC GPtrArray *gs_category_get_children (GsCategory *category); guint gs_category_get_size (GsCategory *category); @@ -58,11 +55,46 @@ index ecd2e1e23..1e82591aa 100644 + guint value); G_END_DECLS -diff --git a/src/gs-shell.c b/src/gs-shell.c -index db449a9b0..796d7b05a 100644 ---- a/src/gs-shell.c -+++ b/src/gs-shell.c -@@ -107,6 +107,7 @@ struct _GsShell +diff -up gnome-software-43.alpha/src/gs-application.c.2 gnome-software-43.alpha/src/gs-application.c +--- gnome-software-43.alpha/src/gs-application.c.2 2022-06-30 20:03:37.000000000 +0200 ++++ gnome-software-43.alpha/src/gs-application.c 2022-07-01 12:02:05.799267693 +0200 +@@ -1036,12 +1036,9 @@ gs_application_startup (GApplication *ap + G_CALLBACK (gs_application_shell_loaded_cb), + app); + +- gs_shell_setup (app->shell, app->plugin_loader, app->cancellable); + app->main_window = GTK_WINDOW (app->shell); + gtk_application_add_window (GTK_APPLICATION (app), app->main_window); + +- app->update_monitor = gs_update_monitor_new (app, app->plugin_loader); +- + gs_application_update_software_sources_presence (application); + + /* Remove possibly obsolete notifications */ +@@ -1067,6 +1064,7 @@ startup_cb (GObject *source_object, + GAsyncResult *result, + gpointer user_data) + { ++ GsApplication *app = GS_APPLICATION (user_data); + GsPluginLoader *plugin_loader = GS_PLUGIN_LOADER (source_object); + g_autoptr(GError) local_error = NULL; + +@@ -1079,6 +1077,11 @@ startup_cb (GObject *source_object, + + /* show the priority of each plugin */ + gs_plugin_loader_dump_state (plugin_loader); ++ ++ /* Setup the shell only after the plugin loader finished its setup, ++ thus all plugins are loaded and ready for the jobs. */ ++ gs_shell_setup (app->shell, app->plugin_loader, app->cancellable); ++ app->update_monitor = gs_update_monitor_new (app, app->plugin_loader); + } + + static void +diff -up gnome-software-43.alpha/src/gs-shell.c.2 gnome-software-43.alpha/src/gs-shell.c +--- gnome-software-43.alpha/src/gs-shell.c.2 2022-06-30 20:03:37.000000000 +0200 ++++ gnome-software-43.alpha/src/gs-shell.c 2022-07-01 12:01:07.782026430 +0200 +@@ -109,6 +109,7 @@ struct _GsShell GtkWidget *primary_menu; GtkWidget *sub_page_header_title; @@ -70,7 +102,7 @@ index db449a9b0..796d7b05a 100644 gboolean is_narrow; guint allocation_changed_cb_id; -@@ -165,6 +166,12 @@ gs_shell_modal_dialog_present (GsShell *shell, GtkWindow *window) +@@ -167,6 +168,12 @@ gs_shell_modal_dialog_present (GsShell * void gs_shell_activate (GsShell *shell) { @@ -83,7 +115,7 @@ index db449a9b0..796d7b05a 100644 gtk_widget_show (GTK_WIDGET (shell)); gtk_window_present (GTK_WINDOW (shell)); } -@@ -2237,6 +2244,11 @@ gs_shell_setup (GsShell *shell, GsPluginLoader *plugin_loader, GCancellable *can +@@ -2265,6 +2272,11 @@ gs_shell_setup (GsShell *shell, GsPlugin if (g_settings_get_boolean (shell->settings, "first-run")) g_settings_set_boolean (shell->settings, "first-run", FALSE); } @@ -95,40 +127,3 @@ index db449a9b0..796d7b05a 100644 } void -diff --git a/src/gs-application.c b/src/gs-application.c -index e3f5f55c7..bdadd5c34 100644 ---- a/src/gs-application.c -+++ b/src/gs-application.c -@@ -968,12 +968,9 @@ gs_application_startup (GApplication *application) - G_CALLBACK (gs_application_shell_loaded_cb), - app); - -- gs_shell_setup (app->shell, app->plugin_loader, app->cancellable); - app->main_window = GTK_WINDOW (app->shell); - gtk_application_add_window (GTK_APPLICATION (app), app->main_window); - -- app->update_monitor = gs_update_monitor_new (app, app->plugin_loader); -- - gs_application_update_software_sources_presence (application); - - /* Set up the plugins. */ -@@ -990,6 +987,7 @@ startup_cb (GObject *source_object, - GAsyncResult *result, - gpointer user_data) - { -+ GsApplication *app = GS_APPLICATION (user_data); - GsPluginLoader *plugin_loader = GS_PLUGIN_LOADER (source_object); - g_autoptr(GError) local_error = NULL; - -@@ -1002,6 +1000,11 @@ startup_cb (GObject *source_object, - - /* show the priority of each plugin */ - gs_plugin_loader_dump_state (plugin_loader); -+ -+ /* Setup the shell only after the plugin loader finished its setup, -+ thus all plugins are loaded and ready for the jobs. */ -+ gs_shell_setup (app->shell, app->plugin_loader, app->cancellable); -+ app->update_monitor = gs_update_monitor_new (app, app->plugin_loader); - } - - static void diff --git a/0003-crash-under-gs-flatpak-refine-app-unlocked.patch b/0003-crash-under-gs-flatpak-refine-app-unlocked.patch deleted file mode 100644 index 701e7ef..0000000 --- a/0003-crash-under-gs-flatpak-refine-app-unlocked.patch +++ /dev/null @@ -1,386 +0,0 @@ -diff -up gnome-software-42.2/lib/gs-appstream.c.3 gnome-software-42.2/lib/gs-appstream.c ---- gnome-software-42.2/lib/gs-appstream.c.3 2022-06-13 14:34:05.477145977 +0200 -+++ gnome-software-42.2/lib/gs-appstream.c 2022-06-13 14:36:26.640218337 +0200 -@@ -20,7 +20,13 @@ GsApp * - gs_appstream_create_app (GsPlugin *plugin, XbSilo *silo, XbNode *component, GError **error) - { - GsApp *app; -- g_autoptr(GsApp) app_new = gs_app_new (NULL); -+ g_autoptr(GsApp) app_new = NULL; -+ -+ g_return_val_if_fail (GS_IS_PLUGIN (plugin), NULL); -+ g_return_val_if_fail (XB_IS_SILO (silo), NULL); -+ g_return_val_if_fail (XB_IS_NODE (component), NULL); -+ -+ app_new = gs_app_new (NULL); - - /* refine enough to get the unique ID */ - if (!gs_appstream_refine_app (plugin, app_new, silo, component, -@@ -967,6 +973,11 @@ gs_appstream_refine_app (GsPlugin *plugi - g_autoptr(GPtrArray) launchables = NULL; - g_autoptr(XbNode) req = NULL; - -+ g_return_val_if_fail (GS_IS_PLUGIN (plugin), FALSE); -+ g_return_val_if_fail (GS_IS_APP (app), FALSE); -+ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); -+ g_return_val_if_fail (XB_IS_NODE (component), FALSE); -+ - /* is compatible */ - req = xb_node_query_first (component, - "requires/id[@type='id']" -@@ -1411,6 +1422,11 @@ gs_appstream_search (GsPlugin *plugin, - { AS_SEARCH_TOKEN_MATCH_NONE, NULL } - }; - -+ g_return_val_if_fail (GS_IS_PLUGIN (plugin), FALSE); -+ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); -+ g_return_val_if_fail (values != NULL, FALSE); -+ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); -+ - /* add some weighted queries */ - for (guint i = 0; queries[i].xpath != NULL; i++) { - g_autoptr(GError) error_query = NULL; -@@ -1487,6 +1503,11 @@ gs_appstream_add_category_apps (GsPlugin - { - GPtrArray *desktop_groups; - -+ g_return_val_if_fail (GS_IS_PLUGIN (plugin), FALSE); -+ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); -+ g_return_val_if_fail (GS_IS_CATEGORY (category), FALSE); -+ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); -+ - desktop_groups = gs_category_get_desktop_groups (category); - if (desktop_groups->len == 0) { - g_warning ("no desktop_groups for %s", gs_category_get_id (category)); -@@ -1577,6 +1598,9 @@ gs_appstream_add_categories (XbSilo *sil - GCancellable *cancellable, - GError **error) - { -+ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); -+ g_return_val_if_fail (list != NULL, FALSE); -+ - for (guint j = 0; j < list->len; j++) { - GsCategory *parent = GS_CATEGORY (g_ptr_array_index (list, j)); - GPtrArray *children = gs_category_get_children (parent); -@@ -1611,6 +1635,9 @@ gs_appstream_add_popular (XbSilo *silo, - g_autoptr(GError) error_local = NULL; - g_autoptr(GPtrArray) array = NULL; - -+ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); -+ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); -+ - /* find out how many packages are in each category */ - array = xb_silo_query (silo, - "components/component/kudos/" -@@ -1648,6 +1675,10 @@ gs_appstream_add_recent (GsPlugin *plugi - g_autoptr(GError) error_local = NULL; - g_autoptr(GPtrArray) array = NULL; - -+ g_return_val_if_fail (GS_IS_PLUGIN (plugin), FALSE); -+ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); -+ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); -+ - /* use predicate conditions to the max */ - xpath = g_strdup_printf ("components/component/releases/" - "release[@timestamp>%" G_GUINT64_FORMAT "]/../..", -@@ -1686,6 +1717,10 @@ gs_appstream_add_alternates (XbSilo *sil - g_autoptr(GPtrArray) ids = NULL; - g_autoptr(GString) xpath = g_string_new (NULL); - -+ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); -+ g_return_val_if_fail (GS_IS_APP (app), FALSE); -+ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); -+ - /* probably a package we know nothing about */ - if (gs_app_get_id (app) == NULL) - return TRUE; -@@ -1743,6 +1778,9 @@ gs_appstream_add_featured (XbSilo *silo, - g_autoptr(GError) error_local = NULL; - g_autoptr(GPtrArray) array = NULL; - -+ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); -+ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); -+ - /* find out how many packages are in each category */ - array = xb_silo_query (silo, - "components/component/custom/value[@key='GnomeSoftware::FeatureTile']/../..|" -@@ -1782,6 +1820,11 @@ gs_appstream_url_to_app (GsPlugin *plugi - g_autofree gchar *xpath = NULL; - g_autoptr(GPtrArray) components = NULL; - -+ g_return_val_if_fail (GS_IS_PLUGIN (plugin), FALSE); -+ g_return_val_if_fail (XB_IS_SILO (silo), FALSE); -+ g_return_val_if_fail (GS_IS_APP_LIST (list), FALSE); -+ g_return_val_if_fail (url != NULL, FALSE); -+ - /* not us */ - scheme = gs_utils_get_url_scheme (url); - if (g_strcmp0 (scheme, "appstream") != 0) -@@ -1812,6 +1855,9 @@ gs_appstream_component_add_keyword (XbBu - g_autoptr(XbBuilderNode) keyword = NULL; - g_autoptr(XbBuilderNode) keywords = NULL; - -+ g_return_if_fail (XB_IS_BUILDER_NODE (component)); -+ g_return_if_fail (str != NULL); -+ - /* create if it does not already exist */ - keywords = xb_builder_node_get_child (component, "keywords", NULL); - if (keywords == NULL) -@@ -1831,6 +1877,9 @@ gs_appstream_component_add_provide (XbBu - g_autoptr(XbBuilderNode) provide = NULL; - g_autoptr(XbBuilderNode) provides = NULL; - -+ g_return_if_fail (XB_IS_BUILDER_NODE (component)); -+ g_return_if_fail (str != NULL); -+ - /* create if it does not already exist */ - provides = xb_builder_node_get_child (component, "provides", NULL); - if (provides == NULL) -@@ -1850,6 +1899,9 @@ gs_appstream_component_add_category (XbB - g_autoptr(XbBuilderNode) category = NULL; - g_autoptr(XbBuilderNode) categories = NULL; - -+ g_return_if_fail (XB_IS_BUILDER_NODE (component)); -+ g_return_if_fail (str != NULL); -+ - /* create if it does not already exist */ - categories = xb_builder_node_get_child (component, "categories", NULL); - if (categories == NULL) -@@ -1868,6 +1920,9 @@ gs_appstream_component_add_icon (XbBuild - { - g_autoptr(XbBuilderNode) icon = NULL; - -+ g_return_if_fail (XB_IS_BUILDER_NODE (component)); -+ g_return_if_fail (str != NULL); -+ - /* create str if it does not already exist */ - icon = xb_builder_node_get_child (component, "icon", NULL); - if (icon == NULL) { -@@ -1881,7 +1936,11 @@ gs_appstream_component_add_icon (XbBuild - void - gs_appstream_component_add_extra_info (XbBuilderNode *component) - { -- const gchar *kind = xb_builder_node_get_attr (component, "type"); -+ const gchar *kind; -+ -+ g_return_if_fail (XB_IS_BUILDER_NODE (component)); -+ -+ kind = xb_builder_node_get_attr (component, "type"); - - /* add the gnome-software-specific 'Addon' group and ensure they - * all have an icon set */ -@@ -1927,9 +1986,14 @@ gs_appstream_component_add_extra_info (X - void - gs_appstream_component_fix_url (XbBuilderNode *component, const gchar *baseurl) - { -- const gchar *text = xb_builder_node_get_text (component); -+ const gchar *text; - g_autofree gchar *url = NULL; - -+ g_return_if_fail (XB_IS_BUILDER_NODE (component)); -+ g_return_if_fail (baseurl != NULL); -+ -+ text = xb_builder_node_get_text (component); -+ - if (text == NULL) - return; - -diff -up gnome-software-42.2/plugins/flatpak/gs-flatpak.c.3 gnome-software-42.2/plugins/flatpak/gs-flatpak.c ---- gnome-software-42.2/plugins/flatpak/gs-flatpak.c.3 2022-05-30 13:43:00.000000000 +0200 -+++ gnome-software-42.2/plugins/flatpak/gs-flatpak.c 2022-06-13 14:34:05.480145978 +0200 -@@ -467,10 +467,18 @@ gs_flatpak_create_source (GsFlatpak *sel - } - - static void -+gs_flatpak_invalidate_silo (GsFlatpak *self) -+{ -+ g_rw_lock_writer_lock (&self->silo_lock); -+ if (self->silo != NULL) -+ xb_silo_invalidate (self->silo); -+ g_rw_lock_writer_unlock (&self->silo_lock); -+} -+ -+static void - gs_flatpak_internal_data_changed (GsFlatpak *self) - { - g_autoptr(GMutexLocker) locker = NULL; -- g_autoptr(GRWLockWriterLocker) writer_locker = NULL; - - /* drop the installed refs cache */ - locker = g_mutex_locker_new (&self->installed_refs_mutex); -@@ -487,10 +495,7 @@ gs_flatpak_internal_data_changed (GsFlat - g_hash_table_remove_all (self->broken_remotes); - g_clear_pointer (&locker, g_mutex_locker_free); - -- writer_locker = g_rw_lock_writer_locker_new (&self->silo_lock); -- if (self->silo) -- xb_silo_invalidate (self->silo); -- g_clear_pointer (&writer_locker, g_rw_lock_writer_locker_free); -+ gs_flatpak_invalidate_silo (self); - - self->requires_full_rescan = TRUE; - } -@@ -2009,10 +2014,7 @@ gs_flatpak_refresh (GsFlatpak *self, - g_mutex_unlock (&self->installed_refs_mutex); - - /* manually do this in case we created the first appstream file */ -- g_rw_lock_reader_lock (&self->silo_lock); -- if (self->silo != NULL) -- xb_silo_invalidate (self->silo); -- g_rw_lock_reader_unlock (&self->silo_lock); -+ gs_flatpak_invalidate_silo (self); - - /* update AppStream metadata */ - if (!gs_flatpak_refresh_appstream (self, cache_age_secs, interactive, cancellable, error)) -@@ -3197,6 +3199,20 @@ gs_flatpak_refine_app_unlocked (GsFlatpa - - locker = g_rw_lock_reader_locker_new (&self->silo_lock); - -+ if (self->silo == NULL) { -+ g_clear_pointer (&locker, g_rw_lock_reader_locker_free); -+ if (!gs_flatpak_rescan_appstream_store (self, interactive, cancellable, error)) -+ return FALSE; -+ -+ locker = g_rw_lock_reader_locker_new (&self->silo_lock); -+ if (self->silo == NULL) { -+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, -+ "failed to setup XbSilo for '%s'", -+ gs_flatpak_get_id (self)); -+ return FALSE; -+ } -+ } -+ - /* always do AppStream properties */ - if (!gs_flatpak_refine_appstream (self, app, self->silo, flags, interactive, cancellable, error)) - return FALSE; -@@ -3394,6 +3410,13 @@ gs_flatpak_refine_wildcard (GsFlatpak *s - - locker = g_rw_lock_reader_locker_new (&self->silo_lock); - -+ if (self->silo == NULL) { -+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, -+ "failed to setup XbSilo for '%s'", -+ gs_flatpak_get_id (self)); -+ return FALSE; -+ } -+ - /* find all apps when matching any prefixes */ - xpath = g_strdup_printf ("components/component/id[text()='%s']/..", id); - components = xb_silo_query (self->silo, xpath, 0, &error_local); -@@ -3487,10 +3510,7 @@ gs_flatpak_app_remove_source (GsFlatpak - } - - /* invalidate cache */ -- g_rw_lock_reader_lock (&self->silo_lock); -- if (self->silo != NULL) -- xb_silo_invalidate (self->silo); -- g_rw_lock_reader_unlock (&self->silo_lock); -+ gs_flatpak_invalidate_silo (self); - - gs_app_set_state (app, is_remove ? GS_APP_STATE_UNAVAILABLE : GS_APP_STATE_AVAILABLE); - -@@ -3953,6 +3973,13 @@ gs_flatpak_search (GsFlatpak *self, - return FALSE; - - locker = g_rw_lock_reader_locker_new (&self->silo_lock); -+ if (self->silo == NULL) { -+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, -+ "failed to setup XbSilo for '%s'", -+ gs_flatpak_get_id (self)); -+ return FALSE; -+ } -+ - if (!gs_appstream_search (self->plugin, self->silo, values, list_tmp, - cancellable, error)) - return FALSE; -@@ -4022,6 +4049,12 @@ gs_flatpak_add_category_apps (GsFlatpak - return FALSE; - - locker = g_rw_lock_reader_locker_new (&self->silo_lock); -+ if (self->silo == NULL) { -+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, -+ "failed to setup XbSilo for '%s'", -+ gs_flatpak_get_id (self)); -+ return FALSE; -+ } - return gs_appstream_add_category_apps (self->plugin, self->silo, - category, list, - cancellable, error); -@@ -4040,6 +4073,12 @@ gs_flatpak_add_categories (GsFlatpak *se - return FALSE; - - locker = g_rw_lock_reader_locker_new (&self->silo_lock); -+ if (self->silo == NULL) { -+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, -+ "failed to setup XbSilo for '%s'", -+ gs_flatpak_get_id (self)); -+ return FALSE; -+ } - return gs_appstream_add_categories (self->silo, - list, cancellable, error); - } -@@ -4058,6 +4097,12 @@ gs_flatpak_add_popular (GsFlatpak *self, - return FALSE; - - locker = g_rw_lock_reader_locker_new (&self->silo_lock); -+ if (self->silo == NULL) { -+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, -+ "failed to setup XbSilo for '%s'", -+ gs_flatpak_get_id (self)); -+ return FALSE; -+ } - if (!gs_appstream_add_popular (self->silo, list_tmp, - cancellable, error)) - return FALSE; -@@ -4081,6 +4126,12 @@ gs_flatpak_add_featured (GsFlatpak *self - return FALSE; - - locker = g_rw_lock_reader_locker_new (&self->silo_lock); -+ if (self->silo == NULL) { -+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, -+ "failed to setup XbSilo for '%s'", -+ gs_flatpak_get_id (self)); -+ return FALSE; -+ } - if (!gs_appstream_add_featured (self->silo, list_tmp, - cancellable, error)) - return FALSE; -@@ -4105,6 +4156,12 @@ gs_flatpak_add_alternates (GsFlatpak *se - return FALSE; - - locker = g_rw_lock_reader_locker_new (&self->silo_lock); -+ if (self->silo == NULL) { -+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, -+ "failed to setup XbSilo for '%s'", -+ gs_flatpak_get_id (self)); -+ return FALSE; -+ } - if (!gs_appstream_add_alternates (self->silo, app, list_tmp, - cancellable, error)) - return FALSE; -@@ -4129,6 +4186,12 @@ gs_flatpak_add_recent (GsFlatpak *self, - return FALSE; - - locker = g_rw_lock_reader_locker_new (&self->silo_lock); -+ if (self->silo == NULL) { -+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, -+ "failed to setup XbSilo for '%s'", -+ gs_flatpak_get_id (self)); -+ return FALSE; -+ } - if (!gs_appstream_add_recent (self->plugin, self->silo, list_tmp, age, - cancellable, error)) - return FALSE; -@@ -4154,6 +4217,12 @@ gs_flatpak_url_to_app (GsFlatpak *self, - return FALSE; - - locker = g_rw_lock_reader_locker_new (&self->silo_lock); -+ if (self->silo == NULL) { -+ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, -+ "failed to setup XbSilo for '%s'", -+ gs_flatpak_get_id (self)); -+ return FALSE; -+ } - if (!gs_appstream_url_to_app (self->plugin, self->silo, list_tmp, url, cancellable, error)) - return FALSE; - diff --git a/0018-fwupd-Fix-the-user-action-dialogs.patch b/0018-fwupd-Fix-the-user-action-dialogs.patch deleted file mode 100644 index e45e21e..0000000 --- a/0018-fwupd-Fix-the-user-action-dialogs.patch +++ /dev/null @@ -1,46 +0,0 @@ -From 9aba963f2274e929658b632d6f6ce9c73ee83156 Mon Sep 17 00:00:00 2001 -From: Richard Hughes -Date: Tue, 14 Jun 2022 13:04:31 +0100 -Subject: [PATCH 18/18] fwupd: Fix the user action dialogs - -When gnome-software was ported from appstream-glib to libappstream we -missed that the locale arguments are now swapped -- i.e. the former -specified "locale, value" and the latter specified "value, locale". - -This fixes installing software on any devices that require some kind of -user-prompting to complete the update, e.g. buttons that need pressing -or cables that need replugging. ---- - plugins/fwupd/gs-fwupd-app.c | 2 +- - plugins/fwupd/gs-plugin-fwupd.c | 2 +- - 2 files changed, 2 insertions(+), 2 deletions(-) - -diff --git a/plugins/fwupd/gs-fwupd-app.c b/plugins/fwupd/gs-fwupd-app.c -index 03103a3e9..7fcbdadab 100644 ---- a/plugins/fwupd/gs-fwupd-app.c -+++ b/plugins/fwupd/gs-fwupd-app.c -@@ -283,7 +283,7 @@ gs_fwupd_app_set_from_release (GsApp *app, FwupdRelease *rel) - as_screenshot_set_kind (ss, AS_SCREENSHOT_KIND_DEFAULT); - as_screenshot_add_image (ss, im); - if (fwupd_release_get_detach_caption (rel) != NULL) -- as_screenshot_set_caption (ss, NULL, fwupd_release_get_detach_caption (rel)); -+ as_screenshot_set_caption (ss, fwupd_release_get_detach_caption (rel), NULL); - gs_app_set_action_screenshot (app, ss); - } - } -diff --git a/plugins/fwupd/gs-plugin-fwupd.c b/plugins/fwupd/gs-plugin-fwupd.c -index cac6a324a..3171eb96d 100644 ---- a/plugins/fwupd/gs-plugin-fwupd.c -+++ b/plugins/fwupd/gs-plugin-fwupd.c -@@ -945,7 +945,7 @@ gs_plugin_fwupd_install (GsPluginFwupd *self, - - /* caption is required */ - as_screenshot_set_kind (ss, AS_SCREENSHOT_KIND_DEFAULT); -- as_screenshot_set_caption (ss, NULL, fwupd_device_get_update_message (dev)); -+ as_screenshot_set_caption (ss, fwupd_device_get_update_message (dev), NULL); - gs_app_set_action_screenshot (app, ss); - - /* require the dialog */ --- -2.36.1 - diff --git a/gnome-software.spec b/gnome-software.spec index 57180c7..b1a88f5 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -10,25 +10,23 @@ %global packagekit_version 1.1.1 # this is not a library version -%define gs_plugin_version 18 +%define gs_plugin_version 19 %global tarball_version %%(echo %{version} | tr '~' '.') %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 42.2 -Release: 4%{?dist} +Version: 43.alpha +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ URL: https://wiki.gnome.org/Apps/Software -Source0: https://download.gnome.org/sources/gnome-software/42/%{name}-%{tarball_version}.tar.xz +Source0: https://download.gnome.org/sources/gnome-software/43/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch Patch02: 0002-shell-setup-order.patch -Patch03: 0003-crash-under-gs-flatpak-refine-app-unlocked.patch -Patch04: 0018-fwupd-Fix-the-user-action-dialogs.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -63,6 +61,7 @@ BuildRequires: pkgconfig(xmlb) >= %{libxmlb_version} Requires: appstream-data Requires: appstream%{?_isa} >= %{appstream_version} +Requires: epiphany-runtime%{?_isa} Requires: flatpak%{?_isa} >= %{flatpak_version} Requires: flatpak-libs%{?_isa} >= %{flatpak_version} Requires: fwupd%{?_isa} >= %{fwupd_version} @@ -119,6 +118,9 @@ This package includes the rpm-ostree backend. -Dpackagekit_autoremove=true \ -Dexternal_appstream=false \ -Drpm_ostree=true \ + -Dwebapps=true \ + -Dhardcoded_foss_webapps=true \ + -Dhardcoded_proprietary_webapps=false \ -Dtests=false %meson_build @@ -159,13 +161,15 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/icons/hicolor/symbolic/apps/org.gnome.Software-symbolic.svg %{_datadir}/icons/hicolor/scalable/actions/app-remove-symbolic.svg %{_datadir}/icons/hicolor/scalable/status/software-installed-symbolic.svg -%{_datadir}/metainfo/org.gnome.Software.appdata.xml +%{_datadir}/metainfo/org.gnome.Software.metainfo.xml +%{_datadir}/metainfo/org.gnome.Software.Plugin.Epiphany.metainfo.xml %{_datadir}/metainfo/org.gnome.Software.Plugin.Flatpak.metainfo.xml %{_datadir}/metainfo/org.gnome.Software.Plugin.Fwupd.metainfo.xml %dir %{_libdir}/gnome-software/plugins-%{gs_plugin_version} %{_libdir}/gnome-software/libgnomesoftware.so.%{gs_plugin_version} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_appstream.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dummy.so +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_epiphany.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-pkgdb-collections.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_flatpak.so @@ -184,8 +188,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_sysconfdir}/xdg/autostart/org.gnome.Software.desktop %dir %{_datadir}/swcatalog %dir %{_datadir}/swcatalog/xml +%{_datadir}/swcatalog/xml/gnome-pwa-list-foss.xml +%{_datadir}/swcatalog/xml/org.gnome.Software.Curated.xml %{_datadir}/swcatalog/xml/org.gnome.Software.Featured.xml -%{_datadir}/swcatalog/xml/org.gnome.Software.Popular.xml %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service %{_datadir}/dbus-1/services/org.gnome.Software.service %{_datadir}/gnome-shell/search-providers/org.gnome.Software-search-provider.ini @@ -207,6 +212,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Jul 01 2022 Milan Crha - 43.alpha-1 +- Update to 43.alpha + * Fri Jun 17 2022 Richard Hughes - 42.2-4 - Add patch to make fwupd user requests work diff --git a/sources b/sources index fc682d9..5bbe6b2 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-42.2.tar.xz) = 2b231afbedb241b8957fa902c37cd85734cdb8b2071cd32ac75ae2e9e064483fe1e9e8d49f2e6df478fdd01e9c6225a85887ba2af1792a9150b89cea75ef8bb4 +SHA512 (gnome-software-43.alpha.tar.xz) = 796b77e763f0ad0c8103b39563ce792b9354126762594addba38a993628f273938a27ed09b9d3c469fb9d11d7a86502960faf9c88914347ec5263e0f626dbb1e From 9786c4ea7ff32ab52f758959778d7a2f791242c0 Mon Sep 17 00:00:00 2001 From: Adam Williamson Date: Thu, 7 Jul 2022 09:39:41 -0700 Subject: [PATCH 060/163] Backport MR #1401 to fix issue #1816 and fedora-workstation #107 --- 1401.patch | 630 ++++++++++++++++++++++++++++++++++++++++++++ gnome-software.spec | 11 +- 2 files changed, 640 insertions(+), 1 deletion(-) create mode 100644 1401.patch diff --git a/1401.patch b/1401.patch new file mode 100644 index 0000000..dfe1925 --- /dev/null +++ b/1401.patch @@ -0,0 +1,630 @@ +From 892acd197630fb3f52ddfac5fc73196ba6759318 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 15 Jun 2022 17:47:11 +0200 +Subject: [PATCH 01/10] plugin-loader: Actively track count of running jobs + +This helps to avoid mistakes when hinting a job finished. +--- + lib/gs-plugin-loader.c | 18 ++++++++++++++++++ + 1 file changed, 18 insertions(+) + +diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c +index a7f86d5f2..e5c2a2c23 100644 +--- a/lib/gs-plugin-loader.c ++++ b/lib/gs-plugin-loader.c +@@ -56,6 +56,7 @@ struct _GsPluginLoader + GsAppList *pending_apps; /* (nullable) (owned) */ + + GThreadPool *queued_ops_pool; ++ gint active_jobs; + + GSettings *settings; + +@@ -3911,6 +3912,19 @@ cancellable_data_free (CancellableData *data) + + G_DEFINE_AUTOPTR_CLEANUP_FUNC (CancellableData, cancellable_data_free) + ++static void ++plugin_loader_task_freed_cb (gpointer user_data, ++ GObject *freed_object) ++{ ++ g_autoptr(GsPluginLoader) plugin_loader = user_data; ++ if (g_atomic_int_dec_and_test (&plugin_loader->active_jobs)) { ++ /* if the plugin used updates-changed during its job, actually schedule ++ * the signal emission now */ ++ if (plugin_loader->updates_changed_cnt > 0) ++ gs_plugin_loader_updates_changed (plugin_loader); ++ } ++} ++ + static gboolean job_process_setup_complete_cb (GCancellable *cancellable, + gpointer user_data); + static void job_process_cb (GTask *task); +@@ -3977,6 +3991,10 @@ gs_plugin_loader_job_process_async (GsPluginLoader *plugin_loader, + g_task_set_name (task, task_name); + g_task_set_task_data (task, g_object_ref (plugin_job), (GDestroyNotify) g_object_unref); + ++ g_atomic_int_inc (&plugin_loader->active_jobs); ++ g_object_weak_ref (G_OBJECT (task), ++ plugin_loader_task_freed_cb, g_object_ref (plugin_loader)); ++ + /* Wait until the plugin has finished setting up. + * + * Do this using a #GCancellable. While we’re not using the #GCancellable +-- +GitLab + + +From 89a3767bd0ad94d3f3d83f8c4ecbb2b79072f536 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 15 Jun 2022 17:51:13 +0200 +Subject: [PATCH 02/10] plugin-loader: Remove obsolete + gs_plugin_loader_hint_job_finished() + +The function is not needed, since the plugin loader tracks count +of active jobs automatically now. +--- + lib/gs-plugin-job-refresh-metadata.c | 5 ----- + lib/gs-plugin-loader.c | 28 ---------------------------- + lib/gs-plugin-loader.h | 2 -- + 3 files changed, 35 deletions(-) + +diff --git a/lib/gs-plugin-job-refresh-metadata.c b/lib/gs-plugin-job-refresh-metadata.c +index a57b194bc..8d0b95b5d 100644 +--- a/lib/gs-plugin-job-refresh-metadata.c ++++ b/lib/gs-plugin-job-refresh-metadata.c +@@ -387,7 +387,6 @@ finish_op (GTask *task, + GError *error) + { + GsPluginJobRefreshMetadata *self = g_task_get_source_object (task); +- GsPluginLoader *plugin_loader = g_task_get_task_data (task); + g_autoptr(GError) error_owned = g_steal_pointer (&error); + g_autofree gchar *job_debug = NULL; + +@@ -408,10 +407,6 @@ finish_op (GTask *task, + progress_cb (self); + g_source_destroy (self->progress_source); + +- /* If any plugin emitted updates-changed, actually schedule it to be +- * emitted now (even if the overall operation failed). */ +- gs_plugin_loader_hint_job_finished (plugin_loader); +- + /* Get the results of the parallel ops. */ + if (self->saved_error != NULL) { + g_task_return_error (task, g_steal_pointer (&self->saved_error)); +diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c +index e5c2a2c23..fc374256d 100644 +--- a/lib/gs-plugin-loader.c ++++ b/lib/gs-plugin-loader.c +@@ -3676,9 +3676,6 @@ gs_plugin_loader_process_thread_cb (GTask *task, + /* sort these again as the refine may have added useful metadata */ + gs_plugin_loader_job_sorted_truncation_again (helper->plugin_job, list); + +- /* Hint that the job has finished. */ +- gs_plugin_loader_hint_job_finished (plugin_loader); +- + #ifdef HAVE_SYSPROF + if (plugin_loader->sysprof_writer != NULL) { + g_autofree gchar *sysprof_name = g_strconcat ("process-thread:", gs_plugin_action_to_string (action), NULL); +@@ -3849,9 +3846,6 @@ run_job_cb (GObject *source_object, + } + #endif /* HAVE_SYSPROF */ + +- /* Hint that the job has finished. */ +- gs_plugin_loader_hint_job_finished (plugin_loader); +- + /* FIXME: This will eventually go away when + * gs_plugin_loader_job_process_finish() is removed. */ + job_class = GS_PLUGIN_JOB_GET_CLASS (plugin_job); +@@ -4459,25 +4453,3 @@ gs_plugin_loader_get_category_manager (GsPluginLoader *plugin_loader) + + return plugin_loader->category_manager; + } +- +-/** +- * gs_plugin_loader_hint_job_finished: +- * @plugin_loader: a #GsPluginLoader +- * +- * Hint to the @plugin_loader that the set of changes caused by the current +- * #GsPluginJob is likely to be finished. +- * +- * The @plugin_loader may emit queued-up signals as a result. +- * +- * Since: 42 +- */ +-void +-gs_plugin_loader_hint_job_finished (GsPluginLoader *plugin_loader) +-{ +- g_return_if_fail (GS_IS_PLUGIN_LOADER (plugin_loader)); +- +- /* if the plugin used updates-changed during its job, actually schedule +- * the signal emission now */ +- if (plugin_loader->updates_changed_cnt > 0) +- gs_plugin_loader_updates_changed (plugin_loader); +-} +diff --git a/lib/gs-plugin-loader.h b/lib/gs-plugin-loader.h +index 0d2035bfd..bb2c7d8e6 100644 +--- a/lib/gs-plugin-loader.h ++++ b/lib/gs-plugin-loader.h +@@ -126,6 +126,4 @@ gboolean gs_plugin_loader_app_is_compatible (GsPluginLoader *plugin_loader, + void gs_plugin_loader_run_adopt (GsPluginLoader *plugin_loader, + GsAppList *list); + +-void gs_plugin_loader_hint_job_finished (GsPluginLoader *plugin_loader); +- + G_END_DECLS +-- +GitLab + + +From 680726fa2fa5b7f39aa86da05f161604a132085f Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 15 Jun 2022 17:55:31 +0200 +Subject: [PATCH 03/10] plugin-loader: Schedule 'updates-changed' signal when + received with no job running + +This helps to avoid a race condition when a plugin calls +updates-changed at the end of the job, but the job is +finished before the callback gets called in the main thread. +--- + lib/gs-plugin-loader.c | 22 +++++++++++++++------- + 1 file changed, 15 insertions(+), 7 deletions(-) + +diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c +index fc374256d..d728bfc5c 100644 +--- a/lib/gs-plugin-loader.c ++++ b/lib/gs-plugin-loader.c +@@ -1774,12 +1774,6 @@ gs_plugin_loader_job_actions_changed_delay_cb (gpointer user_data) + return FALSE; + } + +-static void +-gs_plugin_loader_job_actions_changed_cb (GsPlugin *plugin, GsPluginLoader *plugin_loader) +-{ +- plugin_loader->updates_changed_cnt++; +-} +- + static void + gs_plugin_loader_updates_changed (GsPluginLoader *plugin_loader) + { +@@ -1791,6 +1785,20 @@ gs_plugin_loader_updates_changed (GsPluginLoader *plugin_loader) + g_object_ref (plugin_loader)); + } + ++static void ++gs_plugin_loader_job_updates_changed_cb (GsPlugin *plugin, ++ GsPluginLoader *plugin_loader) ++{ ++ plugin_loader->updates_changed_cnt++; ++ ++ /* Schedule emit of updates changed when no job is active. ++ This helps to avoid a race condition when a plugin calls ++ updates-changed at the end of the job, but the job is ++ finished before the callback gets called in the main thread. */ ++ if (!g_atomic_int_get (&plugin_loader->active_jobs)) ++ gs_plugin_loader_updates_changed (plugin_loader); ++} ++ + static gboolean + gs_plugin_loader_reload_delay_cb (gpointer user_data) + { +@@ -1849,7 +1857,7 @@ gs_plugin_loader_open_plugin (GsPluginLoader *plugin_loader, + return; + } + g_signal_connect (plugin, "updates-changed", +- G_CALLBACK (gs_plugin_loader_job_actions_changed_cb), ++ G_CALLBACK (gs_plugin_loader_job_updates_changed_cb), + plugin_loader); + g_signal_connect (plugin, "reload", + G_CALLBACK (gs_plugin_loader_reload_cb), +-- +GitLab + + +From 3c915f31197addf8becf9aa62a07dae35b440044 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 15 Jun 2022 17:58:32 +0200 +Subject: [PATCH 04/10] plugin-loader: Change how updates-checked is scheduled + for emission + +This way the GSource can be removed without leaking the plugin loader. +--- + lib/gs-plugin-loader.c | 11 ++++++----- + 1 file changed, 6 insertions(+), 5 deletions(-) + +diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c +index d728bfc5c..9f64a3559 100644 +--- a/lib/gs-plugin-loader.c ++++ b/lib/gs-plugin-loader.c +@@ -1760,7 +1760,7 @@ gs_plugin_loader_ask_untrusted_cb (GsPlugin *plugin, + } + + static gboolean +-gs_plugin_loader_job_actions_changed_delay_cb (gpointer user_data) ++gs_plugin_loader_job_updates_changed_delay_cb (gpointer user_data) + { + GsPluginLoader *plugin_loader = GS_PLUGIN_LOADER (user_data); + +@@ -1770,7 +1770,6 @@ gs_plugin_loader_job_actions_changed_delay_cb (gpointer user_data) + plugin_loader->updates_changed_id = 0; + plugin_loader->updates_changed_cnt = 0; + +- g_object_unref (plugin_loader); + return FALSE; + } + +@@ -1780,9 +1779,11 @@ gs_plugin_loader_updates_changed (GsPluginLoader *plugin_loader) + if (plugin_loader->updates_changed_id != 0) + return; + plugin_loader->updates_changed_id = +- g_timeout_add_seconds (GS_PLUGIN_LOADER_UPDATES_CHANGED_DELAY, +- gs_plugin_loader_job_actions_changed_delay_cb, +- g_object_ref (plugin_loader)); ++ g_timeout_add_seconds_full (G_PRIORITY_DEFAULT, ++ GS_PLUGIN_LOADER_UPDATES_CHANGED_DELAY, ++ gs_plugin_loader_job_updates_changed_delay_cb, ++ g_object_ref (plugin_loader), ++ g_object_unref); + } + + static void +-- +GitLab + + +From 2930c01ee97a10577fa2860bd8df1124cfb7128d Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 15 Jun 2022 18:02:11 +0200 +Subject: [PATCH 05/10] plugin-loader: Add + gs_plugin_loader_emit_updates_changed() + +It will help to avoid delays with the GUI after changes in the updates. +--- + lib/gs-plugin-loader.c | 23 +++++++++++++++++++++++ + lib/gs-plugin-loader.h | 1 + + 2 files changed, 24 insertions(+) + +diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c +index 9f64a3559..c0e711477 100644 +--- a/lib/gs-plugin-loader.c ++++ b/lib/gs-plugin-loader.c +@@ -4462,3 +4462,26 @@ gs_plugin_loader_get_category_manager (GsPluginLoader *plugin_loader) + + return plugin_loader->category_manager; + } ++ ++/** ++ * gs_plugin_loader_emit_updates_changed: ++ * @self: a #GsPluginLoader ++ * ++ * Emits the #GsPluginLoader:updates-changed signal in the nearest ++ * idle in the main thread. ++ * ++ * Since: 43 ++ **/ ++void ++gs_plugin_loader_emit_updates_changed (GsPluginLoader *self) ++{ ++ g_return_if_fail (GS_IS_PLUGIN_LOADER (self)); ++ ++ if (self->updates_changed_id != 0) ++ g_source_remove (self->updates_changed_id); ++ ++ self->updates_changed_id = ++ g_idle_add_full (G_PRIORITY_HIGH_IDLE, ++ gs_plugin_loader_job_updates_changed_delay_cb, ++ g_object_ref (self), g_object_unref); ++} +diff --git a/lib/gs-plugin-loader.h b/lib/gs-plugin-loader.h +index bb2c7d8e6..91c5f643c 100644 +--- a/lib/gs-plugin-loader.h ++++ b/lib/gs-plugin-loader.h +@@ -125,5 +125,6 @@ gboolean gs_plugin_loader_app_is_compatible (GsPluginLoader *plugin_loader, + + void gs_plugin_loader_run_adopt (GsPluginLoader *plugin_loader, + GsAppList *list); ++void gs_plugin_loader_emit_updates_changed (GsPluginLoader *self); + + G_END_DECLS +-- +GitLab + + +From edfbbfb0be112b76becc1f38c920cfd45a95885c Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 15 Jun 2022 18:05:38 +0200 +Subject: [PATCH 06/10] gs-app: Add gs_app_is_downloaded() + +This avoid code duplication on two places. It also makes sure the places +agree on the way the app is/is-not downloaded is determined. +--- + lib/gs-app.c | 32 ++++++++++++++++++++++++++++++++ + lib/gs-app.h | 1 + + 2 files changed, 33 insertions(+) + +diff --git a/lib/gs-app.c b/lib/gs-app.c +index 29898765b..d7f8be279 100644 +--- a/lib/gs-app.c ++++ b/lib/gs-app.c +@@ -6656,3 +6656,35 @@ gs_app_set_has_translations (GsApp *app, + priv->has_translations = has_translations; + gs_app_queue_notify (app, obj_props[PROP_HAS_TRANSLATIONS]); + } ++ ++/** ++ * gs_app_is_downloaded: ++ * @app: a #GsApp ++ * ++ * Returns whether the @app is downloaded for updates or not, ++ * considering also its dependencies. ++ * ++ * Returns: %TRUE, when the @app is downloaded, %FALSE otherwise ++ * ++ * Since: 43 ++ **/ ++gboolean ++gs_app_is_downloaded (GsApp *app) ++{ ++ GsSizeType size_type; ++ guint64 size_bytes = 0; ++ ++ g_return_val_if_fail (GS_IS_APP (app), FALSE); ++ ++ if (!gs_app_has_quirk (app, GS_APP_QUIRK_IS_PROXY)) { ++ size_type = gs_app_get_size_download (app, &size_bytes); ++ if (size_type != GS_SIZE_TYPE_VALID || size_bytes != 0) ++ return FALSE; ++ } ++ ++ size_type = gs_app_get_size_download_dependencies (app, &size_bytes); ++ if (size_type != GS_SIZE_TYPE_VALID || size_bytes != 0) ++ return FALSE; ++ ++ return TRUE; ++} +diff --git a/lib/gs-app.h b/lib/gs-app.h +index d78503c3e..a053299f2 100644 +--- a/lib/gs-app.h ++++ b/lib/gs-app.h +@@ -516,5 +516,6 @@ void gs_app_set_relations (GsApp *app, + gboolean gs_app_get_has_translations (GsApp *app); + void gs_app_set_has_translations (GsApp *app, + gboolean has_translations); ++gboolean gs_app_is_downloaded (GsApp *app); + + G_END_DECLS +-- +GitLab + + +From c6903fd6b74ddbde5db045ea67fc826824153210 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 15 Jun 2022 18:15:04 +0200 +Subject: [PATCH 07/10] updates-section: Use gs_app_is_downloaded() + +--- + src/gs-updates-section.c | 10 +--------- + 1 file changed, 1 insertion(+), 9 deletions(-) + +diff --git a/src/gs-updates-section.c b/src/gs-updates-section.c +index ca39e6fab..69e083984 100644 +--- a/src/gs-updates-section.c ++++ b/src/gs-updates-section.c +@@ -288,15 +288,7 @@ _all_offline_updates_downloaded (GsUpdatesSection *self) + /* use the download size to figure out what is downloaded and what not */ + for (guint i = 0; i < gs_app_list_length (self->list); i++) { + GsApp *app = gs_app_list_index (self->list, i); +- GsSizeType size_type; +- guint64 size_bytes; +- +- size_type = gs_app_get_size_download (app, &size_bytes); +- if (size_type != GS_SIZE_TYPE_VALID || size_bytes != 0) +- return FALSE; +- +- size_type = gs_app_get_size_download_dependencies (app, &size_bytes); +- if (size_type != GS_SIZE_TYPE_VALID || size_bytes != 0) ++ if (!gs_app_is_downloaded (app)) + return FALSE; + } + +-- +GitLab + + +From 972def24d2bc54b09fe57879efb4c30962858dc0 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 15 Jun 2022 18:15:25 +0200 +Subject: [PATCH 08/10] update-monitor: Use gs_app_is_downloaded() + +--- + src/gs-update-monitor.c | 10 +++------- + 1 file changed, 3 insertions(+), 7 deletions(-) + +diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c +index 324ff4d3e..a2dc9bb92 100644 +--- a/src/gs-update-monitor.c ++++ b/src/gs-update-monitor.c +@@ -125,22 +125,18 @@ check_updates_kind (GsAppList *apps, + + for (ii = 0; ii < len && (!has_important || all_downloaded || !any_downloaded); ii++) { + gboolean is_important; +- guint64 size_download_bytes; + + app = gs_app_list_index (apps, ii); + + is_important = gs_app_get_update_urgency (app) == AS_URGENCY_KIND_CRITICAL; + has_important = has_important || is_important; + +- /* took from gs-updates-section.c: _all_offline_updates_downloaded(); +- the app is considered downloaded, when its download size is 0 */ +- if (gs_app_get_size_download (app, &size_download_bytes) != GS_SIZE_TYPE_VALID || +- size_download_bytes != 0) { +- all_downloaded = FALSE; +- } else { ++ if (gs_app_is_downloaded (app)) { + any_downloaded = TRUE; + if (is_important) + any_important_downloaded = TRUE; ++ } else { ++ all_downloaded = FALSE; + } + } + +-- +GitLab + + +From 1aaa9617fc81651f17ed2f864bec35b958d67eed Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 15 Jun 2022 18:17:18 +0200 +Subject: [PATCH 09/10] update-monitor: Force reload of the Updates page before + showing notification + +Thus it reflects what the update-monitor notifies about. +--- + src/gs-update-monitor.c | 4 ++++ + 1 file changed, 4 insertions(+) + +diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c +index a2dc9bb92..01e5869eb 100644 +--- a/src/gs-update-monitor.c ++++ b/src/gs-update-monitor.c +@@ -288,6 +288,10 @@ notify_about_pending_updates (GsUpdateMonitor *monitor, + return; + } + ++ /* To force reload of the Updates page, thus it reflects what ++ the update-monitor notifies about */ ++ gs_plugin_loader_emit_updates_changed (monitor->plugin_loader); ++ + monitor->last_notification_time_usec = g_get_real_time (); + + g_debug ("Notify about update: '%s'", title); +-- +GitLab + + +From 64585205437371c459d5de792d50af95e23ba346 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 15 Jun 2022 18:19:36 +0200 +Subject: [PATCH 10/10] update-monitor: Change when notifications are shown + +This handles the fact that offline updates can be installed either +all in once or none of them, which is reflected in the notification. +--- + src/gs-update-monitor.c | 34 ++++++++++++++-------------------- + 1 file changed, 14 insertions(+), 20 deletions(-) + +diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c +index 01e5869eb..292d2bc4b 100644 +--- a/src/gs-update-monitor.c ++++ b/src/gs-update-monitor.c +@@ -109,17 +109,15 @@ G_DEFINE_AUTOPTR_CLEANUP_FUNC(WithAppData, with_app_data_free); + static void + check_updates_kind (GsAppList *apps, + gboolean *out_has_important, +- gboolean *out_any_important_downloaded, + gboolean *out_all_downloaded, + gboolean *out_any_downloaded) + { +- gboolean has_important, any_important_downloaded, all_downloaded, any_downloaded; ++ gboolean has_important, all_downloaded, any_downloaded; + guint ii, len; + GsApp *app; + + len = gs_app_list_length (apps); + has_important = FALSE; +- any_important_downloaded = FALSE; + all_downloaded = len > 0; + any_downloaded = FALSE; + +@@ -131,17 +129,13 @@ check_updates_kind (GsAppList *apps, + is_important = gs_app_get_update_urgency (app) == AS_URGENCY_KIND_CRITICAL; + has_important = has_important || is_important; + +- if (gs_app_is_downloaded (app)) { ++ if (gs_app_is_downloaded (app)) + any_downloaded = TRUE; +- if (is_important) +- any_important_downloaded = TRUE; +- } else { ++ else + all_downloaded = FALSE; +- } + } + + *out_has_important = has_important; +- *out_any_important_downloaded = any_important_downloaded; + *out_all_downloaded = all_downloaded; + *out_any_downloaded = any_downloaded; + } +@@ -193,14 +187,15 @@ should_download_updates (GsUpdateMonitor *monitor) + #endif + } + +-/* The days below are discussed at https://gitlab.gnome.org/GNOME/gnome-software/-/issues/947 */ ++/* The days below are discussed at https://gitlab.gnome.org/GNOME/gnome-software/-/issues/947 ++ and https://wiki.gnome.org/Design/Apps/Software/Updates#Tentative_Design */ + static gboolean + should_notify_about_pending_updates (GsUpdateMonitor *monitor, + GsAppList *apps, + const gchar **out_title, + const gchar **out_body) + { +- gboolean has_important = FALSE, any_important_downloaded = FALSE, all_downloaded = FALSE, any_downloaded = FALSE; ++ gboolean has_important = FALSE, all_downloaded = FALSE, any_downloaded = FALSE; + gboolean should_download, res = FALSE; + gint64 timestamp_days; + +@@ -210,7 +205,7 @@ should_notify_about_pending_updates (GsUpdateMonitor *monitor, + } + + should_download = should_download_updates (monitor); +- check_updates_kind (apps, &has_important, &any_important_downloaded, &all_downloaded, &any_downloaded); ++ check_updates_kind (apps, &has_important, &all_downloaded, &any_downloaded); + + if (!gs_app_list_length (apps)) { + /* Notify only when the download is disabled and it's the 4th day or it's more than 7 days */ +@@ -221,7 +216,7 @@ should_notify_about_pending_updates (GsUpdateMonitor *monitor, + } + } else if (has_important) { + if (timestamp_days >= 1) { +- if (any_important_downloaded) { ++ if (all_downloaded) { + *out_title = _("Critical Software Update Ready to Install"); + *out_body = _("An important software update is ready to be installed."); + res = TRUE; +@@ -231,24 +226,23 @@ should_notify_about_pending_updates (GsUpdateMonitor *monitor, + res = TRUE; + } + } +- /* When automatic updates are on and there are things ready to be installed, then rather claim +- * about things to be installed, than things to be downloaded. */ +- } else if (all_downloaded || (any_downloaded && should_download)) { ++ } else if (all_downloaded) { + if (timestamp_days >= 3) { + *out_title = _("Software Updates Ready to Install"); + *out_body = _("Software updates are waiting and ready to be installed."); + res = TRUE; + } +- /* To not hide downloaded updates for 14 days when new updates were discovered meanwhile */ +- } else if (timestamp_days >= (any_downloaded ? 3 : 14)) { ++ /* To not hide downloaded updates for 14 days when new updates were discovered meanwhile. ++ Never show "Available to Download" when it's supposed to download the updates. */ ++ } else if (!should_download && timestamp_days >= 14) { + *out_title = _("Software Updates Available to Download"); + *out_body = _("Please download waiting software updates."); + res = TRUE; + } + +- g_debug ("%s: last_test_days:%" G_GINT64_FORMAT " n-apps:%u should_download:%d has_important:%d any_important_downloaded:%d " ++ g_debug ("%s: last_test_days:%" G_GINT64_FORMAT " n-apps:%u should_download:%d has_important:%d " + "all_downloaded:%d any_downloaded:%d res:%d%s%s%s%s", G_STRFUNC, +- timestamp_days, gs_app_list_length (apps), should_download, has_important, any_important_downloaded, ++ timestamp_days, gs_app_list_length (apps), should_download, has_important, + all_downloaded, any_downloaded, res, + res ? " reason:" : "", + res ? *out_title : "", +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index b1a88f5..da7f757 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -18,7 +18,7 @@ Name: gnome-software Version: 43.alpha -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -27,6 +27,12 @@ Source0: https://download.gnome.org/sources/gnome-software/43/%{name}-%{tarbal Patch01: 0001-crash-with-broken-theme.patch Patch02: 0002-shell-setup-order.patch +# Fix bug that makes update impossible when "System Updates" present +# Fix issues with notifications and app not matching +# https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1816 +# https://pagure.io/fedora-workstation/issue/107 +# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/1401 +Patch03: 1401.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -212,6 +218,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Jul 07 2022 Adam Williamson - 43.alpha-2 +- Backport MR #1401 to fix issue #1816 and fedora-workstation #107 + * Fri Jul 01 2022 Milan Crha - 43.alpha-1 - Update to 43.alpha From 9ef98a7975c651ec6fc09f2bbc232caab39ccc79 Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Thu, 21 Jul 2022 07:03:42 +0000 Subject: [PATCH 061/163] Rebuilt for https://fedoraproject.org/wiki/Fedora_37_Mass_Rebuild Signed-off-by: Fedora Release Engineering --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index da7f757..4ba8c34 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -18,7 +18,7 @@ Name: gnome-software Version: 43.alpha -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -218,6 +218,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Jul 21 2022 Fedora Release Engineering - 43.alpha-3 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_37_Mass_Rebuild + * Thu Jul 07 2022 Adam Williamson - 43.alpha-2 - Backport MR #1401 to fix issue #1816 and fedora-workstation #107 From c73577f732c4268c0c8489045ed86c4661169ab6 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 5 Aug 2022 13:54:15 +0200 Subject: [PATCH 062/163] Update to 43.beta --- 0002-shell-setup-order.patch | 129 ------- 1401.patch | 630 ----------------------------------- gnome-software.spec | 19 +- sources | 2 +- 4 files changed, 9 insertions(+), 771 deletions(-) delete mode 100644 0002-shell-setup-order.patch delete mode 100644 1401.patch diff --git a/0002-shell-setup-order.patch b/0002-shell-setup-order.patch deleted file mode 100644 index 37da5c0..0000000 --- a/0002-shell-setup-order.patch +++ /dev/null @@ -1,129 +0,0 @@ -diff -up gnome-software-43.alpha/lib/gs-appstream.c.2 gnome-software-43.alpha/lib/gs-appstream.c ---- gnome-software-43.alpha/lib/gs-appstream.c.2 2022-06-30 20:03:37.000000000 +0200 -+++ gnome-software-43.alpha/lib/gs-appstream.c 2022-07-01 12:01:07.781026426 +0200 -@@ -1648,12 +1648,12 @@ gs_appstream_add_categories (XbSilo *sil - for (guint k = 0; k < groups->len; k++) { - const gchar *group = g_ptr_array_index (groups, k); - guint cnt = gs_appstream_count_component_for_groups (silo, group); -- for (guint l = 0; l < cnt; l++) { -- gs_category_increment_size (parent); -+ if (cnt > 0) { -+ gs_category_increment_size (parent, cnt); - if (children->len > 1) { - /* Parent category has multiple groups, so increment - * each group's size too */ -- gs_category_increment_size (cat); -+ gs_category_increment_size (cat, cnt); - } - } - } -diff -up gnome-software-43.alpha/lib/gs-category.c.2 gnome-software-43.alpha/lib/gs-category.c ---- gnome-software-43.alpha/lib/gs-category.c.2 2022-06-30 20:03:37.000000000 +0200 -+++ gnome-software-43.alpha/lib/gs-category.c 2022-07-01 12:01:07.781026426 +0200 -@@ -147,17 +147,19 @@ gs_category_set_size (GsCategory *catego - /** - * gs_category_increment_size: - * @category: a #GsCategory -+ * @value: how many to add - * -- * Adds one to the size count if an application is available -+ * Adds @value to the size count. - * - * Since: 3.22 - **/ - void --gs_category_increment_size (GsCategory *category) -+gs_category_increment_size (GsCategory *category, -+ guint value) - { - g_return_if_fail (GS_IS_CATEGORY (category)); - -- category->size++; -+ category->size += value; - g_object_notify_by_pspec (G_OBJECT (category), obj_props[PROP_SIZE]); - } - -diff -up gnome-software-43.alpha/lib/gs-category.h.2 gnome-software-43.alpha/lib/gs-category.h ---- gnome-software-43.alpha/lib/gs-category.h.2 2022-06-30 20:03:37.000000000 +0200 -+++ gnome-software-43.alpha/lib/gs-category.h 2022-07-01 12:01:07.781026426 +0200 -@@ -39,6 +39,7 @@ GsCategory *gs_category_find_child (GsC - GPtrArray *gs_category_get_children (GsCategory *category); - - guint gs_category_get_size (GsCategory *category); --void gs_category_increment_size (GsCategory *category); -+void gs_category_increment_size (GsCategory *category, -+ guint value); - - G_END_DECLS -diff -up gnome-software-43.alpha/src/gs-application.c.2 gnome-software-43.alpha/src/gs-application.c ---- gnome-software-43.alpha/src/gs-application.c.2 2022-06-30 20:03:37.000000000 +0200 -+++ gnome-software-43.alpha/src/gs-application.c 2022-07-01 12:02:05.799267693 +0200 -@@ -1036,12 +1036,9 @@ gs_application_startup (GApplication *ap - G_CALLBACK (gs_application_shell_loaded_cb), - app); - -- gs_shell_setup (app->shell, app->plugin_loader, app->cancellable); - app->main_window = GTK_WINDOW (app->shell); - gtk_application_add_window (GTK_APPLICATION (app), app->main_window); - -- app->update_monitor = gs_update_monitor_new (app, app->plugin_loader); -- - gs_application_update_software_sources_presence (application); - - /* Remove possibly obsolete notifications */ -@@ -1067,6 +1064,7 @@ startup_cb (GObject *source_object, - GAsyncResult *result, - gpointer user_data) - { -+ GsApplication *app = GS_APPLICATION (user_data); - GsPluginLoader *plugin_loader = GS_PLUGIN_LOADER (source_object); - g_autoptr(GError) local_error = NULL; - -@@ -1079,6 +1077,11 @@ startup_cb (GObject *source_object, - - /* show the priority of each plugin */ - gs_plugin_loader_dump_state (plugin_loader); -+ -+ /* Setup the shell only after the plugin loader finished its setup, -+ thus all plugins are loaded and ready for the jobs. */ -+ gs_shell_setup (app->shell, app->plugin_loader, app->cancellable); -+ app->update_monitor = gs_update_monitor_new (app, app->plugin_loader); - } - - static void -diff -up gnome-software-43.alpha/src/gs-shell.c.2 gnome-software-43.alpha/src/gs-shell.c ---- gnome-software-43.alpha/src/gs-shell.c.2 2022-06-30 20:03:37.000000000 +0200 -+++ gnome-software-43.alpha/src/gs-shell.c 2022-07-01 12:01:07.782026430 +0200 -@@ -109,6 +109,7 @@ struct _GsShell - GtkWidget *primary_menu; - GtkWidget *sub_page_header_title; - -+ gboolean active_after_setup; - gboolean is_narrow; - guint allocation_changed_cb_id; - -@@ -167,6 +168,12 @@ gs_shell_modal_dialog_present (GsShell * - void - gs_shell_activate (GsShell *shell) - { -+ /* Waiting for plugin loader to setup first */ -+ if (shell->plugin_loader == NULL) { -+ shell->active_after_setup = TRUE; -+ return; -+ } -+ - gtk_widget_show (GTK_WIDGET (shell)); - gtk_window_present (GTK_WINDOW (shell)); - } -@@ -2265,6 +2272,11 @@ gs_shell_setup (GsShell *shell, GsPlugin - if (g_settings_get_boolean (shell->settings, "first-run")) - g_settings_set_boolean (shell->settings, "first-run", FALSE); - } -+ -+ if (shell->active_after_setup) { -+ shell->active_after_setup = FALSE; -+ gs_shell_activate (shell); -+ } - } - - void diff --git a/1401.patch b/1401.patch deleted file mode 100644 index dfe1925..0000000 --- a/1401.patch +++ /dev/null @@ -1,630 +0,0 @@ -From 892acd197630fb3f52ddfac5fc73196ba6759318 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 15 Jun 2022 17:47:11 +0200 -Subject: [PATCH 01/10] plugin-loader: Actively track count of running jobs - -This helps to avoid mistakes when hinting a job finished. ---- - lib/gs-plugin-loader.c | 18 ++++++++++++++++++ - 1 file changed, 18 insertions(+) - -diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c -index a7f86d5f2..e5c2a2c23 100644 ---- a/lib/gs-plugin-loader.c -+++ b/lib/gs-plugin-loader.c -@@ -56,6 +56,7 @@ struct _GsPluginLoader - GsAppList *pending_apps; /* (nullable) (owned) */ - - GThreadPool *queued_ops_pool; -+ gint active_jobs; - - GSettings *settings; - -@@ -3911,6 +3912,19 @@ cancellable_data_free (CancellableData *data) - - G_DEFINE_AUTOPTR_CLEANUP_FUNC (CancellableData, cancellable_data_free) - -+static void -+plugin_loader_task_freed_cb (gpointer user_data, -+ GObject *freed_object) -+{ -+ g_autoptr(GsPluginLoader) plugin_loader = user_data; -+ if (g_atomic_int_dec_and_test (&plugin_loader->active_jobs)) { -+ /* if the plugin used updates-changed during its job, actually schedule -+ * the signal emission now */ -+ if (plugin_loader->updates_changed_cnt > 0) -+ gs_plugin_loader_updates_changed (plugin_loader); -+ } -+} -+ - static gboolean job_process_setup_complete_cb (GCancellable *cancellable, - gpointer user_data); - static void job_process_cb (GTask *task); -@@ -3977,6 +3991,10 @@ gs_plugin_loader_job_process_async (GsPluginLoader *plugin_loader, - g_task_set_name (task, task_name); - g_task_set_task_data (task, g_object_ref (plugin_job), (GDestroyNotify) g_object_unref); - -+ g_atomic_int_inc (&plugin_loader->active_jobs); -+ g_object_weak_ref (G_OBJECT (task), -+ plugin_loader_task_freed_cb, g_object_ref (plugin_loader)); -+ - /* Wait until the plugin has finished setting up. - * - * Do this using a #GCancellable. While we’re not using the #GCancellable --- -GitLab - - -From 89a3767bd0ad94d3f3d83f8c4ecbb2b79072f536 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 15 Jun 2022 17:51:13 +0200 -Subject: [PATCH 02/10] plugin-loader: Remove obsolete - gs_plugin_loader_hint_job_finished() - -The function is not needed, since the plugin loader tracks count -of active jobs automatically now. ---- - lib/gs-plugin-job-refresh-metadata.c | 5 ----- - lib/gs-plugin-loader.c | 28 ---------------------------- - lib/gs-plugin-loader.h | 2 -- - 3 files changed, 35 deletions(-) - -diff --git a/lib/gs-plugin-job-refresh-metadata.c b/lib/gs-plugin-job-refresh-metadata.c -index a57b194bc..8d0b95b5d 100644 ---- a/lib/gs-plugin-job-refresh-metadata.c -+++ b/lib/gs-plugin-job-refresh-metadata.c -@@ -387,7 +387,6 @@ finish_op (GTask *task, - GError *error) - { - GsPluginJobRefreshMetadata *self = g_task_get_source_object (task); -- GsPluginLoader *plugin_loader = g_task_get_task_data (task); - g_autoptr(GError) error_owned = g_steal_pointer (&error); - g_autofree gchar *job_debug = NULL; - -@@ -408,10 +407,6 @@ finish_op (GTask *task, - progress_cb (self); - g_source_destroy (self->progress_source); - -- /* If any plugin emitted updates-changed, actually schedule it to be -- * emitted now (even if the overall operation failed). */ -- gs_plugin_loader_hint_job_finished (plugin_loader); -- - /* Get the results of the parallel ops. */ - if (self->saved_error != NULL) { - g_task_return_error (task, g_steal_pointer (&self->saved_error)); -diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c -index e5c2a2c23..fc374256d 100644 ---- a/lib/gs-plugin-loader.c -+++ b/lib/gs-plugin-loader.c -@@ -3676,9 +3676,6 @@ gs_plugin_loader_process_thread_cb (GTask *task, - /* sort these again as the refine may have added useful metadata */ - gs_plugin_loader_job_sorted_truncation_again (helper->plugin_job, list); - -- /* Hint that the job has finished. */ -- gs_plugin_loader_hint_job_finished (plugin_loader); -- - #ifdef HAVE_SYSPROF - if (plugin_loader->sysprof_writer != NULL) { - g_autofree gchar *sysprof_name = g_strconcat ("process-thread:", gs_plugin_action_to_string (action), NULL); -@@ -3849,9 +3846,6 @@ run_job_cb (GObject *source_object, - } - #endif /* HAVE_SYSPROF */ - -- /* Hint that the job has finished. */ -- gs_plugin_loader_hint_job_finished (plugin_loader); -- - /* FIXME: This will eventually go away when - * gs_plugin_loader_job_process_finish() is removed. */ - job_class = GS_PLUGIN_JOB_GET_CLASS (plugin_job); -@@ -4459,25 +4453,3 @@ gs_plugin_loader_get_category_manager (GsPluginLoader *plugin_loader) - - return plugin_loader->category_manager; - } -- --/** -- * gs_plugin_loader_hint_job_finished: -- * @plugin_loader: a #GsPluginLoader -- * -- * Hint to the @plugin_loader that the set of changes caused by the current -- * #GsPluginJob is likely to be finished. -- * -- * The @plugin_loader may emit queued-up signals as a result. -- * -- * Since: 42 -- */ --void --gs_plugin_loader_hint_job_finished (GsPluginLoader *plugin_loader) --{ -- g_return_if_fail (GS_IS_PLUGIN_LOADER (plugin_loader)); -- -- /* if the plugin used updates-changed during its job, actually schedule -- * the signal emission now */ -- if (plugin_loader->updates_changed_cnt > 0) -- gs_plugin_loader_updates_changed (plugin_loader); --} -diff --git a/lib/gs-plugin-loader.h b/lib/gs-plugin-loader.h -index 0d2035bfd..bb2c7d8e6 100644 ---- a/lib/gs-plugin-loader.h -+++ b/lib/gs-plugin-loader.h -@@ -126,6 +126,4 @@ gboolean gs_plugin_loader_app_is_compatible (GsPluginLoader *plugin_loader, - void gs_plugin_loader_run_adopt (GsPluginLoader *plugin_loader, - GsAppList *list); - --void gs_plugin_loader_hint_job_finished (GsPluginLoader *plugin_loader); -- - G_END_DECLS --- -GitLab - - -From 680726fa2fa5b7f39aa86da05f161604a132085f Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 15 Jun 2022 17:55:31 +0200 -Subject: [PATCH 03/10] plugin-loader: Schedule 'updates-changed' signal when - received with no job running - -This helps to avoid a race condition when a plugin calls -updates-changed at the end of the job, but the job is -finished before the callback gets called in the main thread. ---- - lib/gs-plugin-loader.c | 22 +++++++++++++++------- - 1 file changed, 15 insertions(+), 7 deletions(-) - -diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c -index fc374256d..d728bfc5c 100644 ---- a/lib/gs-plugin-loader.c -+++ b/lib/gs-plugin-loader.c -@@ -1774,12 +1774,6 @@ gs_plugin_loader_job_actions_changed_delay_cb (gpointer user_data) - return FALSE; - } - --static void --gs_plugin_loader_job_actions_changed_cb (GsPlugin *plugin, GsPluginLoader *plugin_loader) --{ -- plugin_loader->updates_changed_cnt++; --} -- - static void - gs_plugin_loader_updates_changed (GsPluginLoader *plugin_loader) - { -@@ -1791,6 +1785,20 @@ gs_plugin_loader_updates_changed (GsPluginLoader *plugin_loader) - g_object_ref (plugin_loader)); - } - -+static void -+gs_plugin_loader_job_updates_changed_cb (GsPlugin *plugin, -+ GsPluginLoader *plugin_loader) -+{ -+ plugin_loader->updates_changed_cnt++; -+ -+ /* Schedule emit of updates changed when no job is active. -+ This helps to avoid a race condition when a plugin calls -+ updates-changed at the end of the job, but the job is -+ finished before the callback gets called in the main thread. */ -+ if (!g_atomic_int_get (&plugin_loader->active_jobs)) -+ gs_plugin_loader_updates_changed (plugin_loader); -+} -+ - static gboolean - gs_plugin_loader_reload_delay_cb (gpointer user_data) - { -@@ -1849,7 +1857,7 @@ gs_plugin_loader_open_plugin (GsPluginLoader *plugin_loader, - return; - } - g_signal_connect (plugin, "updates-changed", -- G_CALLBACK (gs_plugin_loader_job_actions_changed_cb), -+ G_CALLBACK (gs_plugin_loader_job_updates_changed_cb), - plugin_loader); - g_signal_connect (plugin, "reload", - G_CALLBACK (gs_plugin_loader_reload_cb), --- -GitLab - - -From 3c915f31197addf8becf9aa62a07dae35b440044 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 15 Jun 2022 17:58:32 +0200 -Subject: [PATCH 04/10] plugin-loader: Change how updates-checked is scheduled - for emission - -This way the GSource can be removed without leaking the plugin loader. ---- - lib/gs-plugin-loader.c | 11 ++++++----- - 1 file changed, 6 insertions(+), 5 deletions(-) - -diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c -index d728bfc5c..9f64a3559 100644 ---- a/lib/gs-plugin-loader.c -+++ b/lib/gs-plugin-loader.c -@@ -1760,7 +1760,7 @@ gs_plugin_loader_ask_untrusted_cb (GsPlugin *plugin, - } - - static gboolean --gs_plugin_loader_job_actions_changed_delay_cb (gpointer user_data) -+gs_plugin_loader_job_updates_changed_delay_cb (gpointer user_data) - { - GsPluginLoader *plugin_loader = GS_PLUGIN_LOADER (user_data); - -@@ -1770,7 +1770,6 @@ gs_plugin_loader_job_actions_changed_delay_cb (gpointer user_data) - plugin_loader->updates_changed_id = 0; - plugin_loader->updates_changed_cnt = 0; - -- g_object_unref (plugin_loader); - return FALSE; - } - -@@ -1780,9 +1779,11 @@ gs_plugin_loader_updates_changed (GsPluginLoader *plugin_loader) - if (plugin_loader->updates_changed_id != 0) - return; - plugin_loader->updates_changed_id = -- g_timeout_add_seconds (GS_PLUGIN_LOADER_UPDATES_CHANGED_DELAY, -- gs_plugin_loader_job_actions_changed_delay_cb, -- g_object_ref (plugin_loader)); -+ g_timeout_add_seconds_full (G_PRIORITY_DEFAULT, -+ GS_PLUGIN_LOADER_UPDATES_CHANGED_DELAY, -+ gs_plugin_loader_job_updates_changed_delay_cb, -+ g_object_ref (plugin_loader), -+ g_object_unref); - } - - static void --- -GitLab - - -From 2930c01ee97a10577fa2860bd8df1124cfb7128d Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 15 Jun 2022 18:02:11 +0200 -Subject: [PATCH 05/10] plugin-loader: Add - gs_plugin_loader_emit_updates_changed() - -It will help to avoid delays with the GUI after changes in the updates. ---- - lib/gs-plugin-loader.c | 23 +++++++++++++++++++++++ - lib/gs-plugin-loader.h | 1 + - 2 files changed, 24 insertions(+) - -diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c -index 9f64a3559..c0e711477 100644 ---- a/lib/gs-plugin-loader.c -+++ b/lib/gs-plugin-loader.c -@@ -4462,3 +4462,26 @@ gs_plugin_loader_get_category_manager (GsPluginLoader *plugin_loader) - - return plugin_loader->category_manager; - } -+ -+/** -+ * gs_plugin_loader_emit_updates_changed: -+ * @self: a #GsPluginLoader -+ * -+ * Emits the #GsPluginLoader:updates-changed signal in the nearest -+ * idle in the main thread. -+ * -+ * Since: 43 -+ **/ -+void -+gs_plugin_loader_emit_updates_changed (GsPluginLoader *self) -+{ -+ g_return_if_fail (GS_IS_PLUGIN_LOADER (self)); -+ -+ if (self->updates_changed_id != 0) -+ g_source_remove (self->updates_changed_id); -+ -+ self->updates_changed_id = -+ g_idle_add_full (G_PRIORITY_HIGH_IDLE, -+ gs_plugin_loader_job_updates_changed_delay_cb, -+ g_object_ref (self), g_object_unref); -+} -diff --git a/lib/gs-plugin-loader.h b/lib/gs-plugin-loader.h -index bb2c7d8e6..91c5f643c 100644 ---- a/lib/gs-plugin-loader.h -+++ b/lib/gs-plugin-loader.h -@@ -125,5 +125,6 @@ gboolean gs_plugin_loader_app_is_compatible (GsPluginLoader *plugin_loader, - - void gs_plugin_loader_run_adopt (GsPluginLoader *plugin_loader, - GsAppList *list); -+void gs_plugin_loader_emit_updates_changed (GsPluginLoader *self); - - G_END_DECLS --- -GitLab - - -From edfbbfb0be112b76becc1f38c920cfd45a95885c Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 15 Jun 2022 18:05:38 +0200 -Subject: [PATCH 06/10] gs-app: Add gs_app_is_downloaded() - -This avoid code duplication on two places. It also makes sure the places -agree on the way the app is/is-not downloaded is determined. ---- - lib/gs-app.c | 32 ++++++++++++++++++++++++++++++++ - lib/gs-app.h | 1 + - 2 files changed, 33 insertions(+) - -diff --git a/lib/gs-app.c b/lib/gs-app.c -index 29898765b..d7f8be279 100644 ---- a/lib/gs-app.c -+++ b/lib/gs-app.c -@@ -6656,3 +6656,35 @@ gs_app_set_has_translations (GsApp *app, - priv->has_translations = has_translations; - gs_app_queue_notify (app, obj_props[PROP_HAS_TRANSLATIONS]); - } -+ -+/** -+ * gs_app_is_downloaded: -+ * @app: a #GsApp -+ * -+ * Returns whether the @app is downloaded for updates or not, -+ * considering also its dependencies. -+ * -+ * Returns: %TRUE, when the @app is downloaded, %FALSE otherwise -+ * -+ * Since: 43 -+ **/ -+gboolean -+gs_app_is_downloaded (GsApp *app) -+{ -+ GsSizeType size_type; -+ guint64 size_bytes = 0; -+ -+ g_return_val_if_fail (GS_IS_APP (app), FALSE); -+ -+ if (!gs_app_has_quirk (app, GS_APP_QUIRK_IS_PROXY)) { -+ size_type = gs_app_get_size_download (app, &size_bytes); -+ if (size_type != GS_SIZE_TYPE_VALID || size_bytes != 0) -+ return FALSE; -+ } -+ -+ size_type = gs_app_get_size_download_dependencies (app, &size_bytes); -+ if (size_type != GS_SIZE_TYPE_VALID || size_bytes != 0) -+ return FALSE; -+ -+ return TRUE; -+} -diff --git a/lib/gs-app.h b/lib/gs-app.h -index d78503c3e..a053299f2 100644 ---- a/lib/gs-app.h -+++ b/lib/gs-app.h -@@ -516,5 +516,6 @@ void gs_app_set_relations (GsApp *app, - gboolean gs_app_get_has_translations (GsApp *app); - void gs_app_set_has_translations (GsApp *app, - gboolean has_translations); -+gboolean gs_app_is_downloaded (GsApp *app); - - G_END_DECLS --- -GitLab - - -From c6903fd6b74ddbde5db045ea67fc826824153210 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 15 Jun 2022 18:15:04 +0200 -Subject: [PATCH 07/10] updates-section: Use gs_app_is_downloaded() - ---- - src/gs-updates-section.c | 10 +--------- - 1 file changed, 1 insertion(+), 9 deletions(-) - -diff --git a/src/gs-updates-section.c b/src/gs-updates-section.c -index ca39e6fab..69e083984 100644 ---- a/src/gs-updates-section.c -+++ b/src/gs-updates-section.c -@@ -288,15 +288,7 @@ _all_offline_updates_downloaded (GsUpdatesSection *self) - /* use the download size to figure out what is downloaded and what not */ - for (guint i = 0; i < gs_app_list_length (self->list); i++) { - GsApp *app = gs_app_list_index (self->list, i); -- GsSizeType size_type; -- guint64 size_bytes; -- -- size_type = gs_app_get_size_download (app, &size_bytes); -- if (size_type != GS_SIZE_TYPE_VALID || size_bytes != 0) -- return FALSE; -- -- size_type = gs_app_get_size_download_dependencies (app, &size_bytes); -- if (size_type != GS_SIZE_TYPE_VALID || size_bytes != 0) -+ if (!gs_app_is_downloaded (app)) - return FALSE; - } - --- -GitLab - - -From 972def24d2bc54b09fe57879efb4c30962858dc0 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 15 Jun 2022 18:15:25 +0200 -Subject: [PATCH 08/10] update-monitor: Use gs_app_is_downloaded() - ---- - src/gs-update-monitor.c | 10 +++------- - 1 file changed, 3 insertions(+), 7 deletions(-) - -diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c -index 324ff4d3e..a2dc9bb92 100644 ---- a/src/gs-update-monitor.c -+++ b/src/gs-update-monitor.c -@@ -125,22 +125,18 @@ check_updates_kind (GsAppList *apps, - - for (ii = 0; ii < len && (!has_important || all_downloaded || !any_downloaded); ii++) { - gboolean is_important; -- guint64 size_download_bytes; - - app = gs_app_list_index (apps, ii); - - is_important = gs_app_get_update_urgency (app) == AS_URGENCY_KIND_CRITICAL; - has_important = has_important || is_important; - -- /* took from gs-updates-section.c: _all_offline_updates_downloaded(); -- the app is considered downloaded, when its download size is 0 */ -- if (gs_app_get_size_download (app, &size_download_bytes) != GS_SIZE_TYPE_VALID || -- size_download_bytes != 0) { -- all_downloaded = FALSE; -- } else { -+ if (gs_app_is_downloaded (app)) { - any_downloaded = TRUE; - if (is_important) - any_important_downloaded = TRUE; -+ } else { -+ all_downloaded = FALSE; - } - } - --- -GitLab - - -From 1aaa9617fc81651f17ed2f864bec35b958d67eed Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 15 Jun 2022 18:17:18 +0200 -Subject: [PATCH 09/10] update-monitor: Force reload of the Updates page before - showing notification - -Thus it reflects what the update-monitor notifies about. ---- - src/gs-update-monitor.c | 4 ++++ - 1 file changed, 4 insertions(+) - -diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c -index a2dc9bb92..01e5869eb 100644 ---- a/src/gs-update-monitor.c -+++ b/src/gs-update-monitor.c -@@ -288,6 +288,10 @@ notify_about_pending_updates (GsUpdateMonitor *monitor, - return; - } - -+ /* To force reload of the Updates page, thus it reflects what -+ the update-monitor notifies about */ -+ gs_plugin_loader_emit_updates_changed (monitor->plugin_loader); -+ - monitor->last_notification_time_usec = g_get_real_time (); - - g_debug ("Notify about update: '%s'", title); --- -GitLab - - -From 64585205437371c459d5de792d50af95e23ba346 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 15 Jun 2022 18:19:36 +0200 -Subject: [PATCH 10/10] update-monitor: Change when notifications are shown - -This handles the fact that offline updates can be installed either -all in once or none of them, which is reflected in the notification. ---- - src/gs-update-monitor.c | 34 ++++++++++++++-------------------- - 1 file changed, 14 insertions(+), 20 deletions(-) - -diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c -index 01e5869eb..292d2bc4b 100644 ---- a/src/gs-update-monitor.c -+++ b/src/gs-update-monitor.c -@@ -109,17 +109,15 @@ G_DEFINE_AUTOPTR_CLEANUP_FUNC(WithAppData, with_app_data_free); - static void - check_updates_kind (GsAppList *apps, - gboolean *out_has_important, -- gboolean *out_any_important_downloaded, - gboolean *out_all_downloaded, - gboolean *out_any_downloaded) - { -- gboolean has_important, any_important_downloaded, all_downloaded, any_downloaded; -+ gboolean has_important, all_downloaded, any_downloaded; - guint ii, len; - GsApp *app; - - len = gs_app_list_length (apps); - has_important = FALSE; -- any_important_downloaded = FALSE; - all_downloaded = len > 0; - any_downloaded = FALSE; - -@@ -131,17 +129,13 @@ check_updates_kind (GsAppList *apps, - is_important = gs_app_get_update_urgency (app) == AS_URGENCY_KIND_CRITICAL; - has_important = has_important || is_important; - -- if (gs_app_is_downloaded (app)) { -+ if (gs_app_is_downloaded (app)) - any_downloaded = TRUE; -- if (is_important) -- any_important_downloaded = TRUE; -- } else { -+ else - all_downloaded = FALSE; -- } - } - - *out_has_important = has_important; -- *out_any_important_downloaded = any_important_downloaded; - *out_all_downloaded = all_downloaded; - *out_any_downloaded = any_downloaded; - } -@@ -193,14 +187,15 @@ should_download_updates (GsUpdateMonitor *monitor) - #endif - } - --/* The days below are discussed at https://gitlab.gnome.org/GNOME/gnome-software/-/issues/947 */ -+/* The days below are discussed at https://gitlab.gnome.org/GNOME/gnome-software/-/issues/947 -+ and https://wiki.gnome.org/Design/Apps/Software/Updates#Tentative_Design */ - static gboolean - should_notify_about_pending_updates (GsUpdateMonitor *monitor, - GsAppList *apps, - const gchar **out_title, - const gchar **out_body) - { -- gboolean has_important = FALSE, any_important_downloaded = FALSE, all_downloaded = FALSE, any_downloaded = FALSE; -+ gboolean has_important = FALSE, all_downloaded = FALSE, any_downloaded = FALSE; - gboolean should_download, res = FALSE; - gint64 timestamp_days; - -@@ -210,7 +205,7 @@ should_notify_about_pending_updates (GsUpdateMonitor *monitor, - } - - should_download = should_download_updates (monitor); -- check_updates_kind (apps, &has_important, &any_important_downloaded, &all_downloaded, &any_downloaded); -+ check_updates_kind (apps, &has_important, &all_downloaded, &any_downloaded); - - if (!gs_app_list_length (apps)) { - /* Notify only when the download is disabled and it's the 4th day or it's more than 7 days */ -@@ -221,7 +216,7 @@ should_notify_about_pending_updates (GsUpdateMonitor *monitor, - } - } else if (has_important) { - if (timestamp_days >= 1) { -- if (any_important_downloaded) { -+ if (all_downloaded) { - *out_title = _("Critical Software Update Ready to Install"); - *out_body = _("An important software update is ready to be installed."); - res = TRUE; -@@ -231,24 +226,23 @@ should_notify_about_pending_updates (GsUpdateMonitor *monitor, - res = TRUE; - } - } -- /* When automatic updates are on and there are things ready to be installed, then rather claim -- * about things to be installed, than things to be downloaded. */ -- } else if (all_downloaded || (any_downloaded && should_download)) { -+ } else if (all_downloaded) { - if (timestamp_days >= 3) { - *out_title = _("Software Updates Ready to Install"); - *out_body = _("Software updates are waiting and ready to be installed."); - res = TRUE; - } -- /* To not hide downloaded updates for 14 days when new updates were discovered meanwhile */ -- } else if (timestamp_days >= (any_downloaded ? 3 : 14)) { -+ /* To not hide downloaded updates for 14 days when new updates were discovered meanwhile. -+ Never show "Available to Download" when it's supposed to download the updates. */ -+ } else if (!should_download && timestamp_days >= 14) { - *out_title = _("Software Updates Available to Download"); - *out_body = _("Please download waiting software updates."); - res = TRUE; - } - -- g_debug ("%s: last_test_days:%" G_GINT64_FORMAT " n-apps:%u should_download:%d has_important:%d any_important_downloaded:%d " -+ g_debug ("%s: last_test_days:%" G_GINT64_FORMAT " n-apps:%u should_download:%d has_important:%d " - "all_downloaded:%d any_downloaded:%d res:%d%s%s%s%s", G_STRFUNC, -- timestamp_days, gs_app_list_length (apps), should_download, has_important, any_important_downloaded, -+ timestamp_days, gs_app_list_length (apps), should_download, has_important, - all_downloaded, any_downloaded, res, - res ? " reason:" : "", - res ? *out_title : "", --- -GitLab - diff --git a/gnome-software.spec b/gnome-software.spec index 4ba8c34..59d9ebe 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -17,8 +17,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 43.alpha -Release: 3%{?dist} +Version: 43.beta +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -26,13 +26,6 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/43/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -Patch02: 0002-shell-setup-order.patch -# Fix bug that makes update impossible when "System Updates" present -# Fix issues with notifications and app not matching -# https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1816 -# https://pagure.io/fedora-workstation/issue/107 -# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/1401 -Patch03: 1401.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -136,6 +129,9 @@ This package includes the rpm-ostree backend. # remove unneeded dpkg plugin rm %{buildroot}%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dpkg.so +# not meant to be installed by the distros +rm %{buildroot}%{_datadir}/swcatalog/xml/org.gnome.Software.Curated.xml + # make the software center load faster desktop-file-edit %{buildroot}%{_datadir}/applications/org.gnome.Software.desktop \ --set-key=X-AppInstall-Package --set-value=%{name} @@ -166,7 +162,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/icons/hicolor/*/apps/org.gnome.Software.svg %{_datadir}/icons/hicolor/symbolic/apps/org.gnome.Software-symbolic.svg %{_datadir}/icons/hicolor/scalable/actions/app-remove-symbolic.svg -%{_datadir}/icons/hicolor/scalable/status/software-installed-symbolic.svg %{_datadir}/metainfo/org.gnome.Software.metainfo.xml %{_datadir}/metainfo/org.gnome.Software.Plugin.Epiphany.metainfo.xml %{_datadir}/metainfo/org.gnome.Software.Plugin.Flatpak.metainfo.xml @@ -195,7 +190,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %dir %{_datadir}/swcatalog %dir %{_datadir}/swcatalog/xml %{_datadir}/swcatalog/xml/gnome-pwa-list-foss.xml -%{_datadir}/swcatalog/xml/org.gnome.Software.Curated.xml %{_datadir}/swcatalog/xml/org.gnome.Software.Featured.xml %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service %{_datadir}/dbus-1/services/org.gnome.Software.service @@ -218,6 +212,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Aug 05 2022 Milan Crha - 43.beta-1 +- Update to 43.beta + * Thu Jul 21 2022 Fedora Release Engineering - 43.alpha-3 - Rebuilt for https://fedoraproject.org/wiki/Fedora_37_Mass_Rebuild diff --git a/sources b/sources index 5bbe6b2..27a6c41 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-43.alpha.tar.xz) = 796b77e763f0ad0c8103b39563ce792b9354126762594addba38a993628f273938a27ed09b9d3c469fb9d11d7a86502960faf9c88914347ec5263e0f626dbb1e +SHA512 (gnome-software-43.beta.tar.xz) = 9dd2d1f3bebf4715dfbe4db636ca068ac53ae4d463d20f02421eb2990edc75e3b29b78436b8539027056042b6dda2ff55e9d6add1c5c9f8693899ce7a80065de From a0175cb9f497b5145d5d0b95ebb9830f637358e1 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 15 Aug 2022 13:37:14 +0200 Subject: [PATCH 063/163] Add patch for install-queue (RH bug #2118265) --- 0002-install-queue.patch | 112 +++++++++++++++++++++++++++++++++++++++ gnome-software.spec | 6 ++- 2 files changed, 117 insertions(+), 1 deletion(-) create mode 100644 0002-install-queue.patch diff --git a/0002-install-queue.patch b/0002-install-queue.patch new file mode 100644 index 0000000..698d1d0 --- /dev/null +++ b/0002-install-queue.patch @@ -0,0 +1,112 @@ +From d9e28b8cb59c805f2df8954637f2056467ff1be3 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 10 Aug 2022 13:41:46 +0200 +Subject: [PATCH 1/2] packagekit: Allow install of apps in the "queued for + install" state + +Treat the "queued for install" state the same as if "available/updatable" +state is set. Without that trying to install anything using PackageKit +plugin leads to an "Unsupported" error. +--- + plugins/packagekit/gs-plugin-packagekit.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/plugins/packagekit/gs-plugin-packagekit.c b/plugins/packagekit/gs-plugin-packagekit.c +index 58d627276..85f941648 100644 +--- a/plugins/packagekit/gs-plugin-packagekit.c ++++ b/plugins/packagekit/gs-plugin-packagekit.c +@@ -519,6 +519,7 @@ gs_plugin_app_install (GsPlugin *plugin, + switch (gs_app_get_state (app)) { + case GS_APP_STATE_AVAILABLE: + case GS_APP_STATE_UPDATABLE: ++ case GS_APP_STATE_QUEUED_FOR_INSTALL: + source_ids = gs_app_get_source_ids (app); + if (source_ids->len == 0) { + g_set_error_literal (error, +-- +GitLab + + +From 71ce53a21373670f32b936194d46ab073df77a63 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Wed, 10 Aug 2022 14:24:51 +0200 +Subject: [PATCH 2/2] gs-plugin-loader: Add not removed from the install-queue + file + +The plugin loader has two places, which maintain the pending queue, +but they do not agree on the update of the install-queue file. Let +the functions be re-used, to avoid the problem. +--- + lib/gs-plugin-loader.c | 27 +++++++++++++++++---------- + 1 file changed, 17 insertions(+), 10 deletions(-) + +diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c +index 073008d55..e3f48666a 100644 +--- a/lib/gs-plugin-loader.c ++++ b/lib/gs-plugin-loader.c +@@ -88,6 +88,7 @@ struct _GsPluginLoader + + static void gs_plugin_loader_monitor_network (GsPluginLoader *plugin_loader); + static void add_app_to_install_queue (GsPluginLoader *plugin_loader, GsApp *app); ++static gboolean remove_app_from_install_queue (GsPluginLoader *plugin_loader, GsApp *app); + static void gs_plugin_loader_process_in_thread_pool_cb (gpointer data, gpointer user_data); + static void gs_plugin_loader_status_changed_cb (GsPlugin *plugin, + GsApp *app, +@@ -1078,17 +1079,22 @@ gs_plugin_loader_pending_apps_add (GsPluginLoader *plugin_loader, + GsPluginLoaderHelper *helper) + { + GsAppList *list = gs_plugin_job_get_list (helper->plugin_job); +- g_autoptr(GMutexLocker) locker = g_mutex_locker_new (&plugin_loader->pending_apps_mutex); +- +- if (plugin_loader->pending_apps == NULL) +- plugin_loader->pending_apps = gs_app_list_new (); + + g_assert (gs_app_list_length (list) > 0); + for (guint i = 0; i < gs_app_list_length (list); i++) { + GsApp *app = gs_app_list_index (list, i); +- gs_app_list_add (plugin_loader->pending_apps, app); +- /* make sure the progress is properly initialized */ +- gs_app_set_progress (app, GS_APP_PROGRESS_UNKNOWN); ++ switch (gs_plugin_job_get_action (helper->plugin_job)) { ++ case GS_PLUGIN_ACTION_INSTALL: ++ add_app_to_install_queue (plugin_loader, app); ++ /* make sure the progress is properly initialized */ ++ gs_app_set_progress (app, GS_APP_PROGRESS_UNKNOWN); ++ break; ++ case GS_PLUGIN_ACTION_REMOVE: ++ remove_app_from_install_queue (plugin_loader, app); ++ break; ++ default: ++ break; ++ } + } + g_idle_add (emit_pending_apps_idle, g_object_ref (plugin_loader)); + } +@@ -1098,13 +1104,11 @@ gs_plugin_loader_pending_apps_remove (GsPluginLoader *plugin_loader, + GsPluginLoaderHelper *helper) + { + GsAppList *list = gs_plugin_job_get_list (helper->plugin_job); +- g_autoptr(GMutexLocker) locker = g_mutex_locker_new (&plugin_loader->pending_apps_mutex); + + g_assert (gs_app_list_length (list) > 0); + for (guint i = 0; i < gs_app_list_length (list); i++) { + GsApp *app = gs_app_list_index (list, i); +- if (plugin_loader->pending_apps != NULL) +- gs_app_list_remove (plugin_loader->pending_apps, app); ++ remove_app_from_install_queue (plugin_loader, app); + + /* check the app is not still in an action helper */ + switch (gs_app_get_state (app)) { +@@ -1272,6 +1276,9 @@ remove_app_from_install_queue (GsPluginLoader *plugin_loader, GsApp *app) + g_mutex_unlock (&plugin_loader->pending_apps_mutex); + + if (ret) { ++ if (gs_app_get_state (app) == GS_APP_STATE_QUEUED_FOR_INSTALL) ++ gs_app_set_state (app, GS_APP_STATE_UNKNOWN); ++ + id = g_idle_add (emit_pending_apps_idle, g_object_ref (plugin_loader)); + g_source_set_name_by_id (id, "[gnome-software] emit_pending_apps_idle"); + save_install_queue (plugin_loader); +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index 59d9ebe..e141c89 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -18,7 +18,7 @@ Name: gnome-software Version: 43.beta -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -26,6 +26,7 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/43/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +Patch02: 0002-install-queue.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -212,6 +213,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Mon Aug 15 2022 Milan Crha - 43.beta-2 +- Add patch for install-queue + * Fri Aug 05 2022 Milan Crha - 43.beta-1 - Update to 43.beta From 6a61ae4b2d97cf5a3905bd6da6efc88538a9087d Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Wed, 17 Aug 2022 15:52:58 +0200 Subject: [PATCH 064/163] Resolves: #2119089 (No enough apps to show for the "Editor's Choice" section) --- gnome-software.spec | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index e141c89..cd0dec2 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -18,7 +18,7 @@ Name: gnome-software Version: 43.beta -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -130,9 +130,6 @@ This package includes the rpm-ostree backend. # remove unneeded dpkg plugin rm %{buildroot}%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dpkg.so -# not meant to be installed by the distros -rm %{buildroot}%{_datadir}/swcatalog/xml/org.gnome.Software.Curated.xml - # make the software center load faster desktop-file-edit %{buildroot}%{_datadir}/applications/org.gnome.Software.desktop \ --set-key=X-AppInstall-Package --set-value=%{name} @@ -191,6 +188,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %dir %{_datadir}/swcatalog %dir %{_datadir}/swcatalog/xml %{_datadir}/swcatalog/xml/gnome-pwa-list-foss.xml +%{_datadir}/swcatalog/xml/org.gnome.Software.Curated.xml %{_datadir}/swcatalog/xml/org.gnome.Software.Featured.xml %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service %{_datadir}/dbus-1/services/org.gnome.Software.service @@ -213,6 +211,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Wed Aug 17 2022 Milan Crha - 43.beta-3 +- Resolves: #2119089 (No enough apps to show for the "Editor's Choice" section) + * Mon Aug 15 2022 Milan Crha - 43.beta-2 - Add patch for install-queue From f744223b09eef29afe8c6084e973bc4c99d43110 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Thu, 18 Aug 2022 07:37:04 +0200 Subject: [PATCH 065/163] Add rpminspect.yaml (settings for the RUNPATH test) --- rpminspect.yaml | 7 +++++++ 1 file changed, 7 insertions(+) create mode 100644 rpminspect.yaml diff --git a/rpminspect.yaml b/rpminspect.yaml new file mode 100644 index 0000000..ef70fcd --- /dev/null +++ b/rpminspect.yaml @@ -0,0 +1,7 @@ +--- +runpath: + allowed_paths: + - /usr/lib/gnome-software + - /usr/lib/rpm-ostree + - /usr/lib64/gnome-software + - /usr/lib64/rpm-ostree From 17177232497d1c236a81f7d699853b5e2cb4f3b2 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 2 Sep 2022 10:51:15 +0200 Subject: [PATCH 066/163] Update to 43.rc --- 0002-install-queue.patch | 112 --------------------------------------- gnome-software.spec | 13 +++-- sources | 2 +- 3 files changed, 9 insertions(+), 118 deletions(-) delete mode 100644 0002-install-queue.patch diff --git a/0002-install-queue.patch b/0002-install-queue.patch deleted file mode 100644 index 698d1d0..0000000 --- a/0002-install-queue.patch +++ /dev/null @@ -1,112 +0,0 @@ -From d9e28b8cb59c805f2df8954637f2056467ff1be3 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 10 Aug 2022 13:41:46 +0200 -Subject: [PATCH 1/2] packagekit: Allow install of apps in the "queued for - install" state - -Treat the "queued for install" state the same as if "available/updatable" -state is set. Without that trying to install anything using PackageKit -plugin leads to an "Unsupported" error. ---- - plugins/packagekit/gs-plugin-packagekit.c | 1 + - 1 file changed, 1 insertion(+) - -diff --git a/plugins/packagekit/gs-plugin-packagekit.c b/plugins/packagekit/gs-plugin-packagekit.c -index 58d627276..85f941648 100644 ---- a/plugins/packagekit/gs-plugin-packagekit.c -+++ b/plugins/packagekit/gs-plugin-packagekit.c -@@ -519,6 +519,7 @@ gs_plugin_app_install (GsPlugin *plugin, - switch (gs_app_get_state (app)) { - case GS_APP_STATE_AVAILABLE: - case GS_APP_STATE_UPDATABLE: -+ case GS_APP_STATE_QUEUED_FOR_INSTALL: - source_ids = gs_app_get_source_ids (app); - if (source_ids->len == 0) { - g_set_error_literal (error, --- -GitLab - - -From 71ce53a21373670f32b936194d46ab073df77a63 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Wed, 10 Aug 2022 14:24:51 +0200 -Subject: [PATCH 2/2] gs-plugin-loader: Add not removed from the install-queue - file - -The plugin loader has two places, which maintain the pending queue, -but they do not agree on the update of the install-queue file. Let -the functions be re-used, to avoid the problem. ---- - lib/gs-plugin-loader.c | 27 +++++++++++++++++---------- - 1 file changed, 17 insertions(+), 10 deletions(-) - -diff --git a/lib/gs-plugin-loader.c b/lib/gs-plugin-loader.c -index 073008d55..e3f48666a 100644 ---- a/lib/gs-plugin-loader.c -+++ b/lib/gs-plugin-loader.c -@@ -88,6 +88,7 @@ struct _GsPluginLoader - - static void gs_plugin_loader_monitor_network (GsPluginLoader *plugin_loader); - static void add_app_to_install_queue (GsPluginLoader *plugin_loader, GsApp *app); -+static gboolean remove_app_from_install_queue (GsPluginLoader *plugin_loader, GsApp *app); - static void gs_plugin_loader_process_in_thread_pool_cb (gpointer data, gpointer user_data); - static void gs_plugin_loader_status_changed_cb (GsPlugin *plugin, - GsApp *app, -@@ -1078,17 +1079,22 @@ gs_plugin_loader_pending_apps_add (GsPluginLoader *plugin_loader, - GsPluginLoaderHelper *helper) - { - GsAppList *list = gs_plugin_job_get_list (helper->plugin_job); -- g_autoptr(GMutexLocker) locker = g_mutex_locker_new (&plugin_loader->pending_apps_mutex); -- -- if (plugin_loader->pending_apps == NULL) -- plugin_loader->pending_apps = gs_app_list_new (); - - g_assert (gs_app_list_length (list) > 0); - for (guint i = 0; i < gs_app_list_length (list); i++) { - GsApp *app = gs_app_list_index (list, i); -- gs_app_list_add (plugin_loader->pending_apps, app); -- /* make sure the progress is properly initialized */ -- gs_app_set_progress (app, GS_APP_PROGRESS_UNKNOWN); -+ switch (gs_plugin_job_get_action (helper->plugin_job)) { -+ case GS_PLUGIN_ACTION_INSTALL: -+ add_app_to_install_queue (plugin_loader, app); -+ /* make sure the progress is properly initialized */ -+ gs_app_set_progress (app, GS_APP_PROGRESS_UNKNOWN); -+ break; -+ case GS_PLUGIN_ACTION_REMOVE: -+ remove_app_from_install_queue (plugin_loader, app); -+ break; -+ default: -+ break; -+ } - } - g_idle_add (emit_pending_apps_idle, g_object_ref (plugin_loader)); - } -@@ -1098,13 +1104,11 @@ gs_plugin_loader_pending_apps_remove (GsPluginLoader *plugin_loader, - GsPluginLoaderHelper *helper) - { - GsAppList *list = gs_plugin_job_get_list (helper->plugin_job); -- g_autoptr(GMutexLocker) locker = g_mutex_locker_new (&plugin_loader->pending_apps_mutex); - - g_assert (gs_app_list_length (list) > 0); - for (guint i = 0; i < gs_app_list_length (list); i++) { - GsApp *app = gs_app_list_index (list, i); -- if (plugin_loader->pending_apps != NULL) -- gs_app_list_remove (plugin_loader->pending_apps, app); -+ remove_app_from_install_queue (plugin_loader, app); - - /* check the app is not still in an action helper */ - switch (gs_app_get_state (app)) { -@@ -1272,6 +1276,9 @@ remove_app_from_install_queue (GsPluginLoader *plugin_loader, GsApp *app) - g_mutex_unlock (&plugin_loader->pending_apps_mutex); - - if (ret) { -+ if (gs_app_get_state (app) == GS_APP_STATE_QUEUED_FOR_INSTALL) -+ gs_app_set_state (app, GS_APP_STATE_UNKNOWN); -+ - id = g_idle_add (emit_pending_apps_idle, g_object_ref (plugin_loader)); - g_source_set_name_by_id (id, "[gnome-software] emit_pending_apps_idle"); - save_install_queue (plugin_loader); --- -GitLab - diff --git a/gnome-software.spec b/gnome-software.spec index cd0dec2..9545378 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -17,8 +17,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 43.beta -Release: 3%{?dist} +Version: 43.rc +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -26,7 +26,6 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/43/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -Patch02: 0002-install-queue.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -56,7 +55,6 @@ BuildRequires: pkgconfig(polkit-gobject-1) BuildRequires: pkgconfig(rpm) BuildRequires: pkgconfig(rpm-ostree-1) BuildRequires: pkgconfig(sysprof-capture-4) -BuildRequires: pkgconfig(valgrind) BuildRequires: pkgconfig(xmlb) >= %{libxmlb_version} Requires: appstream-data @@ -154,7 +152,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %doc AUTHORS README.md %license COPYING %{_bindir}/gnome-software -%{_datadir}/applications/gnome-software-local-file.desktop +%{_datadir}/applications/gnome-software-local-file-flatpak.desktop +%{_datadir}/applications/gnome-software-local-file-fwupd.desktop +%{_datadir}/applications/gnome-software-local-file-packagekit.desktop %{_datadir}/applications/org.gnome.Software.desktop %{_mandir}/man1/gnome-software.1* %{_datadir}/icons/hicolor/*/apps/org.gnome.Software.svg @@ -211,6 +211,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Sep 02 2022 Milan Crha - 43.rc-1 +- Update to 43.rc + * Wed Aug 17 2022 Milan Crha - 43.beta-3 - Resolves: #2119089 (No enough apps to show for the "Editor's Choice" section) diff --git a/sources b/sources index 27a6c41..edd91e5 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-43.beta.tar.xz) = 9dd2d1f3bebf4715dfbe4db636ca068ac53ae4d463d20f02421eb2990edc75e3b29b78436b8539027056042b6dda2ff55e9d6add1c5c9f8693899ce7a80065de +SHA512 (gnome-software-43.rc.tar.xz) = b843e30ad842500cbab19ce32566162961ce50d7ef2e4a9f7cdf969acb2ce074de6928dfa8c3813a1e89fb91868d7fc17daa6e9c36db7c45255e6e8b80552340 From d1659f7e1159459e1a2ea168bd4f1519d231b133 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Tue, 13 Sep 2022 09:11:57 +0200 Subject: [PATCH 067/163] Resolves: #2124869 (Cannot install RPM package file) --- 0002-install-rpm-file.patch | 108 ++++++++++++++++++++++++++++++++++++ gnome-software.spec | 6 +- 2 files changed, 113 insertions(+), 1 deletion(-) create mode 100644 0002-install-rpm-file.patch diff --git a/0002-install-rpm-file.patch b/0002-install-rpm-file.patch new file mode 100644 index 0000000..745ceb7 --- /dev/null +++ b/0002-install-rpm-file.patch @@ -0,0 +1,108 @@ +From e706a530aeeba360fd60fa7ccde63a147f1e14d4 Mon Sep 17 00:00:00 2001 +Date: Wed, 7 Sep 2022 16:18:50 +0200 +Subject: [PATCH 1/2] gs-details-page: Filter out alternatives without origin + +When an alternative app has no origin set, it cannot be installed or +even shown in the GUI, thus filter such alternatives out. + +Helps https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1895 +--- + src/gs-details-page.c | 11 +++++++++++ + 1 file changed, 11 insertions(+) + +diff --git a/src/gs-details-page.c b/src/gs-details-page.c +index cfe3cc797..d35ee0a98 100644 +--- a/src/gs-details-page.c ++++ b/src/gs-details-page.c +@@ -1637,6 +1637,16 @@ _set_app (GsDetailsPage *self, GsApp *app) + self, 0); + } + ++static gboolean ++gs_details_page_filter_origin (GsApp *app, ++ gpointer user_data) ++{ ++ /* Keep only local apps or those, which have an origin set */ ++ return gs_app_get_state (app) == GS_APP_STATE_AVAILABLE_LOCAL || ++ gs_app_get_local_file (app) != NULL || ++ gs_app_get_origin (app) != NULL; ++} ++ + /* show the UI and do operations that should not block page load */ + static void + gs_details_page_load_stage2 (GsDetailsPage *self, +@@ -1676,6 +1686,7 @@ gs_details_page_load_stage2 (GsDetailsPage *self, + query = gs_app_query_new ("alternate-of", self->app, + "refine-flags", GS_DETAILS_PAGE_REFINE_FLAGS, + "dedupe-flags", GS_APP_LIST_FILTER_FLAG_NONE, ++ "filter-func", gs_details_page_filter_origin, + "sort-func", gs_utils_app_sort_priority, + NULL); + plugin_job2 = gs_plugin_job_list_apps_new (query, GS_PLUGIN_LIST_APPS_FLAGS_INTERACTIVE); +-- +GitLab + + +From 7962414c7ef62494512a93df5855249debc39415 Mon Sep 17 00:00:00 2001 +Date: Wed, 7 Sep 2022 16:58:34 +0200 +Subject: [PATCH 2/2] gs-details-page: Include local file as an alternative + when not installed + +It's not enough to add the local file to the GsAppList, because it can +contain an app with the same ID, thus the local file app won't be added +to the list. + +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1895 +--- + src/gs-details-page.c | 14 ++++++++++++-- + 1 file changed, 12 insertions(+), 2 deletions(-) + +diff --git a/src/gs-details-page.c b/src/gs-details-page.c +index d35ee0a98..50b80e159 100644 +--- a/src/gs-details-page.c ++++ b/src/gs-details-page.c +@@ -645,6 +645,7 @@ gs_details_page_get_alternates_cb (GObject *source_object, + GtkWidget *select_row = NULL; + GtkWidget *origin_row_by_packaging_format = NULL; + gint origin_row_by_packaging_format_index = 0; ++ guint n_rows = 0; + + self->origin_by_packaging_format = FALSE; + gs_widget_remove_all (self->origin_popover_list_box, (GsRemoveFunc) gtk_list_box_remove); +@@ -699,7 +700,15 @@ gs_details_page_get_alternates_cb (GObject *source_object, + /* add the local file to the list so that we can carry it over when + * switching between alternates */ + if (self->app_local_file != NULL) { +- gs_app_list_add (list, self->app_local_file); ++ if (gs_app_get_state (self->app_local_file) != GS_APP_STATE_INSTALLED) { ++ GtkWidget *row = gs_origin_popover_row_new (self->app_local_file); ++ gtk_widget_show (row); ++ gtk_list_box_append (GTK_LIST_BOX (self->origin_popover_list_box), row); ++ first_row = row; ++ select_row = row; ++ n_rows++; ++ } ++ + /* Do not allow change of the app by the packaging format when it's a local file */ + origin_by_packaging_format = FALSE; + } +@@ -716,6 +725,7 @@ gs_details_page_get_alternates_cb (GObject *source_object, + GsApp *app = gs_app_list_index (list, i); + GtkWidget *row = gs_origin_popover_row_new (app); + gtk_widget_show (row); ++ n_rows++; + if (first_row == NULL) + first_row = row; + if (app == self->app || ( +@@ -766,7 +776,7 @@ gs_details_page_get_alternates_cb (GObject *source_object, + } + + /* Do not show the "selected" check when there's only one app in the list */ +- if (select_row && gs_app_list_length (list) > 1) ++ if (select_row && n_rows > 1) + gs_origin_popover_row_set_selected (GS_ORIGIN_POPOVER_ROW (select_row), TRUE); + else if (select_row) + gtk_list_box_row_set_activatable (GTK_LIST_BOX_ROW (select_row), FALSE); +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index 9545378..6979b0c 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -18,7 +18,7 @@ Name: gnome-software Version: 43.rc -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -26,6 +26,7 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/43/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +Patch02: 0002-install-rpm-file.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -211,6 +212,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Tue Sep 13 2022 Milan Crha - 43.rc-2 +- Resolves: #2124869 (Cannot install RPM package file) + * Fri Sep 02 2022 Milan Crha - 43.rc-1 - Update to 43.rc From ddac1027ad5b1180b1dfdf2e62694a778c48cb4e Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 16 Sep 2022 08:39:15 +0200 Subject: [PATCH 068/163] Update to 43.0 --- gnome-software.spec | 7 +++++-- sources | 2 +- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 6979b0c..063211e 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -17,8 +17,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 43.rc -Release: 2%{?dist} +Version: 43.0 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -212,6 +212,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Sep 16 2022 Milan Crha - 43.0-1 +- Update to 43.0 + * Tue Sep 13 2022 Milan Crha - 43.rc-2 - Resolves: #2124869 (Cannot install RPM package file) diff --git a/sources b/sources index edd91e5..2cc3ac4 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-43.rc.tar.xz) = b843e30ad842500cbab19ce32566162961ce50d7ef2e4a9f7cdf969acb2ce074de6928dfa8c3813a1e89fb91868d7fc17daa6e9c36db7c45255e6e8b80552340 +SHA512 (gnome-software-43.0.tar.xz) = bcf64e4d3d847c660fd1c1a2356235569560bc315fb6b0d2e459dfb1bbee7bf97d9a14f7c8ef1129e01241385cd1540d1499f9cc9ad99a996965feb48e698d6a From 89923f63dcf1b2c9456f02bdd94db47c7b36a037 Mon Sep 17 00:00:00 2001 From: Kalev Lember Date: Tue, 27 Sep 2022 18:53:43 +0200 Subject: [PATCH 069/163] Rebuild to fix sysprof-capture symbols leaking into libraries consuming it --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 063211e..ffcafcf 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -18,7 +18,7 @@ Name: gnome-software Version: 43.0 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -212,6 +212,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Tue Sep 27 2022 Kalev Lember - 43.0-2 +- Rebuild to fix sysprof-capture symbols leaking into libraries consuming it + * Fri Sep 16 2022 Milan Crha - 43.0-1 - Update to 43.0 From 1cc4989f9873aeccb514af0dd102a34a1954e96e Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Wed, 5 Oct 2022 18:52:53 +0200 Subject: [PATCH 070/163] Resolves: #2132292 (rpm-ostree plugin refuses to update) --- 0003-rpm-ostree-download-size.patch | 38 +++++++++++++++++++++++++++++ gnome-software.spec | 6 ++++- 2 files changed, 43 insertions(+), 1 deletion(-) create mode 100644 0003-rpm-ostree-download-size.patch diff --git a/0003-rpm-ostree-download-size.patch b/0003-rpm-ostree-download-size.patch new file mode 100644 index 0000000..e353dd1 --- /dev/null +++ b/0003-rpm-ostree-download-size.patch @@ -0,0 +1,38 @@ +From 823f49dc59eb1a6a00c80084a8ac37782df124fa Mon Sep 17 00:00:00 2001 +Date: Mon, 26 Sep 2022 15:11:25 +0200 +Subject: [PATCH] rpm-ostree: Mark apps as downloaded + +There was a typo in the changes of the gs_app_set_size_download() API, +the `0` meant the app is downloaded, not that the size is unknown. +With this fixed, the Updates page offers to `Restart & Update`, instead +of `Download`, which does nothing, because the rpm-stree plugin +does not implement corresponding GsPlugin function. +--- + plugins/rpm-ostree/gs-plugin-rpm-ostree.c | 4 ++-- + 1 file changed, 2 insertions(+), 2 deletions(-) + +diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +index 6984ff95b..1b4f758da 100644 +--- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c ++++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +@@ -749,7 +749,7 @@ app_from_modified_pkg_variant (GsPlugin *plugin, GVariant *variant) + gs_app_set_management_plugin (app, plugin); + gs_app_add_quirk (app, GS_APP_QUIRK_NEEDS_REBOOT); + app_set_rpm_ostree_packaging_format (app); +- gs_app_set_size_download (app, GS_SIZE_TYPE_UNKNOWN, 0); ++ gs_app_set_size_download (app, GS_SIZE_TYPE_VALID, 0); + gs_app_set_kind (app, AS_COMPONENT_KIND_GENERIC); + gs_app_set_bundle_kind (app, AS_BUNDLE_KIND_PACKAGE); + gs_app_set_scope (app, AS_COMPONENT_SCOPE_SYSTEM); +@@ -788,7 +788,7 @@ app_from_single_pkg_variant (GsPlugin *plugin, GVariant *variant, gboolean addit + gs_app_set_management_plugin (app, plugin); + gs_app_add_quirk (app, GS_APP_QUIRK_NEEDS_REBOOT); + app_set_rpm_ostree_packaging_format (app); +- gs_app_set_size_download (app, GS_SIZE_TYPE_UNKNOWN, 0); ++ gs_app_set_size_download (app, GS_SIZE_TYPE_VALID, 0); + gs_app_set_kind (app, AS_COMPONENT_KIND_GENERIC); + gs_app_set_bundle_kind (app, AS_BUNDLE_KIND_PACKAGE); + gs_app_set_scope (app, AS_COMPONENT_SCOPE_SYSTEM); +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index ffcafcf..40d50e3 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -18,7 +18,7 @@ Name: gnome-software Version: 43.0 -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -27,6 +27,7 @@ Source0: https://download.gnome.org/sources/gnome-software/43/%{name}-%{tarbal Patch01: 0001-crash-with-broken-theme.patch Patch02: 0002-install-rpm-file.patch +Patch03: 0003-rpm-ostree-download-size.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -212,6 +213,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Wed Oct 05 2022 Milan Crha - 43.0-3 +- Resolves: #2132292 (rpm-ostree plugin refuses to update) + * Tue Sep 27 2022 Kalev Lember - 43.0-2 - Rebuild to fix sysprof-capture symbols leaking into libraries consuming it From aca6555662c7b01db55fed0b1e42500c657acc3c Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 24 Oct 2022 07:53:55 +0200 Subject: [PATCH 071/163] Update to 43.1 --- 0002-install-rpm-file.patch | 108 ---------------------------- 0003-rpm-ostree-download-size.patch | 38 ---------- gnome-software.spec | 9 +-- sources | 2 +- 4 files changed, 6 insertions(+), 151 deletions(-) delete mode 100644 0002-install-rpm-file.patch delete mode 100644 0003-rpm-ostree-download-size.patch diff --git a/0002-install-rpm-file.patch b/0002-install-rpm-file.patch deleted file mode 100644 index 745ceb7..0000000 --- a/0002-install-rpm-file.patch +++ /dev/null @@ -1,108 +0,0 @@ -From e706a530aeeba360fd60fa7ccde63a147f1e14d4 Mon Sep 17 00:00:00 2001 -Date: Wed, 7 Sep 2022 16:18:50 +0200 -Subject: [PATCH 1/2] gs-details-page: Filter out alternatives without origin - -When an alternative app has no origin set, it cannot be installed or -even shown in the GUI, thus filter such alternatives out. - -Helps https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1895 ---- - src/gs-details-page.c | 11 +++++++++++ - 1 file changed, 11 insertions(+) - -diff --git a/src/gs-details-page.c b/src/gs-details-page.c -index cfe3cc797..d35ee0a98 100644 ---- a/src/gs-details-page.c -+++ b/src/gs-details-page.c -@@ -1637,6 +1637,16 @@ _set_app (GsDetailsPage *self, GsApp *app) - self, 0); - } - -+static gboolean -+gs_details_page_filter_origin (GsApp *app, -+ gpointer user_data) -+{ -+ /* Keep only local apps or those, which have an origin set */ -+ return gs_app_get_state (app) == GS_APP_STATE_AVAILABLE_LOCAL || -+ gs_app_get_local_file (app) != NULL || -+ gs_app_get_origin (app) != NULL; -+} -+ - /* show the UI and do operations that should not block page load */ - static void - gs_details_page_load_stage2 (GsDetailsPage *self, -@@ -1676,6 +1686,7 @@ gs_details_page_load_stage2 (GsDetailsPage *self, - query = gs_app_query_new ("alternate-of", self->app, - "refine-flags", GS_DETAILS_PAGE_REFINE_FLAGS, - "dedupe-flags", GS_APP_LIST_FILTER_FLAG_NONE, -+ "filter-func", gs_details_page_filter_origin, - "sort-func", gs_utils_app_sort_priority, - NULL); - plugin_job2 = gs_plugin_job_list_apps_new (query, GS_PLUGIN_LIST_APPS_FLAGS_INTERACTIVE); --- -GitLab - - -From 7962414c7ef62494512a93df5855249debc39415 Mon Sep 17 00:00:00 2001 -Date: Wed, 7 Sep 2022 16:58:34 +0200 -Subject: [PATCH 2/2] gs-details-page: Include local file as an alternative - when not installed - -It's not enough to add the local file to the GsAppList, because it can -contain an app with the same ID, thus the local file app won't be added -to the list. - -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1895 ---- - src/gs-details-page.c | 14 ++++++++++++-- - 1 file changed, 12 insertions(+), 2 deletions(-) - -diff --git a/src/gs-details-page.c b/src/gs-details-page.c -index d35ee0a98..50b80e159 100644 ---- a/src/gs-details-page.c -+++ b/src/gs-details-page.c -@@ -645,6 +645,7 @@ gs_details_page_get_alternates_cb (GObject *source_object, - GtkWidget *select_row = NULL; - GtkWidget *origin_row_by_packaging_format = NULL; - gint origin_row_by_packaging_format_index = 0; -+ guint n_rows = 0; - - self->origin_by_packaging_format = FALSE; - gs_widget_remove_all (self->origin_popover_list_box, (GsRemoveFunc) gtk_list_box_remove); -@@ -699,7 +700,15 @@ gs_details_page_get_alternates_cb (GObject *source_object, - /* add the local file to the list so that we can carry it over when - * switching between alternates */ - if (self->app_local_file != NULL) { -- gs_app_list_add (list, self->app_local_file); -+ if (gs_app_get_state (self->app_local_file) != GS_APP_STATE_INSTALLED) { -+ GtkWidget *row = gs_origin_popover_row_new (self->app_local_file); -+ gtk_widget_show (row); -+ gtk_list_box_append (GTK_LIST_BOX (self->origin_popover_list_box), row); -+ first_row = row; -+ select_row = row; -+ n_rows++; -+ } -+ - /* Do not allow change of the app by the packaging format when it's a local file */ - origin_by_packaging_format = FALSE; - } -@@ -716,6 +725,7 @@ gs_details_page_get_alternates_cb (GObject *source_object, - GsApp *app = gs_app_list_index (list, i); - GtkWidget *row = gs_origin_popover_row_new (app); - gtk_widget_show (row); -+ n_rows++; - if (first_row == NULL) - first_row = row; - if (app == self->app || ( -@@ -766,7 +776,7 @@ gs_details_page_get_alternates_cb (GObject *source_object, - } - - /* Do not show the "selected" check when there's only one app in the list */ -- if (select_row && gs_app_list_length (list) > 1) -+ if (select_row && n_rows > 1) - gs_origin_popover_row_set_selected (GS_ORIGIN_POPOVER_ROW (select_row), TRUE); - else if (select_row) - gtk_list_box_row_set_activatable (GTK_LIST_BOX_ROW (select_row), FALSE); --- -GitLab - diff --git a/0003-rpm-ostree-download-size.patch b/0003-rpm-ostree-download-size.patch deleted file mode 100644 index e353dd1..0000000 --- a/0003-rpm-ostree-download-size.patch +++ /dev/null @@ -1,38 +0,0 @@ -From 823f49dc59eb1a6a00c80084a8ac37782df124fa Mon Sep 17 00:00:00 2001 -Date: Mon, 26 Sep 2022 15:11:25 +0200 -Subject: [PATCH] rpm-ostree: Mark apps as downloaded - -There was a typo in the changes of the gs_app_set_size_download() API, -the `0` meant the app is downloaded, not that the size is unknown. -With this fixed, the Updates page offers to `Restart & Update`, instead -of `Download`, which does nothing, because the rpm-stree plugin -does not implement corresponding GsPlugin function. ---- - plugins/rpm-ostree/gs-plugin-rpm-ostree.c | 4 ++-- - 1 file changed, 2 insertions(+), 2 deletions(-) - -diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -index 6984ff95b..1b4f758da 100644 ---- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -+++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -@@ -749,7 +749,7 @@ app_from_modified_pkg_variant (GsPlugin *plugin, GVariant *variant) - gs_app_set_management_plugin (app, plugin); - gs_app_add_quirk (app, GS_APP_QUIRK_NEEDS_REBOOT); - app_set_rpm_ostree_packaging_format (app); -- gs_app_set_size_download (app, GS_SIZE_TYPE_UNKNOWN, 0); -+ gs_app_set_size_download (app, GS_SIZE_TYPE_VALID, 0); - gs_app_set_kind (app, AS_COMPONENT_KIND_GENERIC); - gs_app_set_bundle_kind (app, AS_BUNDLE_KIND_PACKAGE); - gs_app_set_scope (app, AS_COMPONENT_SCOPE_SYSTEM); -@@ -788,7 +788,7 @@ app_from_single_pkg_variant (GsPlugin *plugin, GVariant *variant, gboolean addit - gs_app_set_management_plugin (app, plugin); - gs_app_add_quirk (app, GS_APP_QUIRK_NEEDS_REBOOT); - app_set_rpm_ostree_packaging_format (app); -- gs_app_set_size_download (app, GS_SIZE_TYPE_UNKNOWN, 0); -+ gs_app_set_size_download (app, GS_SIZE_TYPE_VALID, 0); - gs_app_set_kind (app, AS_COMPONENT_KIND_GENERIC); - gs_app_set_bundle_kind (app, AS_BUNDLE_KIND_PACKAGE); - gs_app_set_scope (app, AS_COMPONENT_SCOPE_SYSTEM); --- -GitLab - diff --git a/gnome-software.spec b/gnome-software.spec index 40d50e3..885915d 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -17,8 +17,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 43.0 -Release: 3%{?dist} +Version: 43.1 +Release: 1%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -26,8 +26,6 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/43/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -Patch02: 0002-install-rpm-file.patch -Patch03: 0003-rpm-ostree-download-size.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -213,6 +211,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Mon Oct 24 2022 Milan Crha - 43.1-1 +- Update to 43.1 + * Wed Oct 05 2022 Milan Crha - 43.0-3 - Resolves: #2132292 (rpm-ostree plugin refuses to update) diff --git a/sources b/sources index 2cc3ac4..d76eee5 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-43.0.tar.xz) = bcf64e4d3d847c660fd1c1a2356235569560bc315fb6b0d2e459dfb1bbee7bf97d9a14f7c8ef1129e01241385cd1540d1499f9cc9ad99a996965feb48e698d6a +SHA512 (gnome-software-43.1.tar.xz) = 5494622e1c52bcf660df8ab83cd73720ccab3c767f8870b6a23bd83c396972c508beb365e6df143055e3a7d9e77b42f01ea73a49d8dcdcf97aaeada0fe9f03e5 From a6313db9a145ae25b99ece3db717393f7c75a59d Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Tue, 8 Nov 2022 17:09:16 +0100 Subject: [PATCH 072/163] Disable WebApps for RHEL builds --- gnome-software.spec | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 885915d..7670999 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -9,6 +9,9 @@ %global libxmlb_version 0.1.7 %global packagekit_version 1.1.1 +# Disable WebApps for RHEL builds +%{!?with_webapps: %global with_webapps !0%{?rhel}} + # this is not a library version %define gs_plugin_version 19 @@ -18,7 +21,7 @@ Name: gnome-software Version: 43.1 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -59,7 +62,9 @@ BuildRequires: pkgconfig(xmlb) >= %{libxmlb_version} Requires: appstream-data Requires: appstream%{?_isa} >= %{appstream_version} +%if %{with_webapps} Requires: epiphany-runtime%{?_isa} +%endif Requires: flatpak%{?_isa} >= %{flatpak_version} Requires: flatpak-libs%{?_isa} >= %{flatpak_version} Requires: fwupd%{?_isa} >= %{fwupd_version} @@ -116,9 +121,15 @@ This package includes the rpm-ostree backend. -Dpackagekit_autoremove=true \ -Dexternal_appstream=false \ -Drpm_ostree=true \ +%if %{with_webapps} -Dwebapps=true \ -Dhardcoded_foss_webapps=true \ -Dhardcoded_proprietary_webapps=false \ +%else + -Dwebapps=false \ + -Dhardcoded_foss_webapps=false \ + -Dhardcoded_proprietary_webapps=false \ +%endif -Dtests=false %meson_build @@ -161,14 +172,18 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/icons/hicolor/symbolic/apps/org.gnome.Software-symbolic.svg %{_datadir}/icons/hicolor/scalable/actions/app-remove-symbolic.svg %{_datadir}/metainfo/org.gnome.Software.metainfo.xml +%if %{with_webapps} %{_datadir}/metainfo/org.gnome.Software.Plugin.Epiphany.metainfo.xml +%endif %{_datadir}/metainfo/org.gnome.Software.Plugin.Flatpak.metainfo.xml %{_datadir}/metainfo/org.gnome.Software.Plugin.Fwupd.metainfo.xml %dir %{_libdir}/gnome-software/plugins-%{gs_plugin_version} %{_libdir}/gnome-software/libgnomesoftware.so.%{gs_plugin_version} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_appstream.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dummy.so +%if %{with_webapps} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_epiphany.so +%endif %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-pkgdb-collections.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_flatpak.so @@ -211,6 +226,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Tue Nov 08 2022 Milan Crha - 43.1-2 +- Disable WebApps for RHEL builds + * Mon Oct 24 2022 Milan Crha - 43.1-1 - Update to 43.1 From 7cb12d79d3c23319198252ca98191231ef2838d3 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Tue, 8 Nov 2022 18:41:35 +0100 Subject: [PATCH 073/163] Also skip gnome-pwa-list-foss.xml when building without WebApps --- gnome-software.spec | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 7670999..6db479d 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -21,7 +21,7 @@ Name: gnome-software Version: 43.1 -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPLv2+ @@ -202,7 +202,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_sysconfdir}/xdg/autostart/org.gnome.Software.desktop %dir %{_datadir}/swcatalog %dir %{_datadir}/swcatalog/xml +%if %{with_webapps} %{_datadir}/swcatalog/xml/gnome-pwa-list-foss.xml +%endif %{_datadir}/swcatalog/xml/org.gnome.Software.Curated.xml %{_datadir}/swcatalog/xml/org.gnome.Software.Featured.xml %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service @@ -226,6 +228,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Tue Nov 08 2022 Milan Crha - 43.1-3 +- Also skip gnome-pwa-list-foss.xml when building without WebApps + * Tue Nov 08 2022 Milan Crha - 43.1-2 - Disable WebApps for RHEL builds From 082bd5162c14a42cefe791af2c507ad0f49d61fb Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Thu, 10 Nov 2022 11:13:20 +0100 Subject: [PATCH 074/163] Update License tag to SPDX --- gnome-software.spec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 6db479d..d0bec88 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -24,7 +24,7 @@ Version: 43.1 Release: 3%{?dist} Summary: A software center for GNOME -License: GPLv2+ +License: GPL-2.0-or-later URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/43/%{name}-%{tarball_version}.tar.xz From b692d2f960bce0a6e87906fad5f146bfdf6de9fe Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 2 Dec 2022 12:56:50 +0100 Subject: [PATCH 075/163] Update to 43.2 --- gnome-software.spec | 7 +++++-- sources | 2 +- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index d0bec88..4ffb38d 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -20,8 +20,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 43.1 -Release: 3%{?dist} +Version: 43.2 +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -228,6 +228,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Dec 02 2022 Milan Crha - 43.2-1 +- Update to 43.2 + * Tue Nov 08 2022 Milan Crha - 43.1-3 - Also skip gnome-pwa-list-foss.xml when building without WebApps diff --git a/sources b/sources index d76eee5..9799f5b 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-43.1.tar.xz) = 5494622e1c52bcf660df8ab83cd73720ccab3c767f8870b6a23bd83c396972c508beb365e6df143055e3a7d9e77b42f01ea73a49d8dcdcf97aaeada0fe9f03e5 +SHA512 (gnome-software-43.2.tar.xz) = d011418536706d2c5693581bd322008b5eb0fdf766ec96f1775135efb0fecec42dbc126ea2a66465b2169afb38b48fed1246516197e3bbf9d75b96e339d6ba33 From de5f7834c219407b8f6426076e2453285f2c7d48 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 9 Jan 2023 09:52:04 +0100 Subject: [PATCH 076/163] Update to 44.alpha --- 0001-crash-with-broken-theme.patch | 27 +++++++++++---------------- gnome-software.spec | 7 +++++-- sources | 2 +- 3 files changed, 17 insertions(+), 19 deletions(-) diff --git a/0001-crash-with-broken-theme.patch b/0001-crash-with-broken-theme.patch index ddbef4a..d41a916 100644 --- a/0001-crash-with-broken-theme.patch +++ b/0001-crash-with-broken-theme.patch @@ -1,25 +1,20 @@ -Subject: [PATCH] gs-feature-tile: Do not abort when the theme is broken - -Just print a warning when the theme doesn't provide 'theme_fg_color' and -fallback to black color. - -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1228 - -diff -up gnome-software-42.rc/src/gs-feature-tile.c.1 gnome-software-42.rc/src/gs-feature-tile.c ---- gnome-software-42.rc/src/gs-feature-tile.c.1 2022-03-04 16:23:58.566735700 +0100 -+++ gnome-software-42.rc/src/gs-feature-tile.c 2022-03-07 08:06:29.046595524 +0100 -@@ -411,7 +411,6 @@ gs_feature_tile_refresh (GsAppTile *self +diff -up gnome-software-devel/src/gs-feature-tile.c.1 gnome-software-devel/src/gs-feature-tile.c +--- gnome-software-devel/src/gs-feature-tile.c.1 2023-01-02 17:08:54.157641969 +0100 ++++ gnome-software-devel/src/gs-feature-tile.c 2023-01-02 17:09:36.881632780 +0100 +@@ -397,9 +397,6 @@ gs_feature_tile_refresh (GsAppTile *self if (key_colors != tile->key_colors_cache) { g_autoptr(GArray) colors = NULL; GdkRGBA fg_rgba; +-#if !GTK_CHECK_VERSION(4, 9, 2) - gboolean fg_rgba_valid; +-#endif GsHSBC fg_hsbc; const GsHSBC *chosen_hsbc; GsHSBC chosen_hsbc_modified; -@@ -429,8 +428,17 @@ gs_feature_tile_refresh (GsAppTile *self - * @min_abs_contrast contrast with the foreground, so - * that the text is legible. - */ +@@ -424,8 +421,17 @@ gs_feature_tile_refresh (GsAppTile *self + gtk_widget_get_color (GTK_WIDGET (self), &fg_rgba); + #else + context = gtk_widget_get_style_context (GTK_WIDGET (self)); - fg_rgba_valid = gtk_style_context_lookup_color (context, "theme_fg_color", &fg_rgba); - g_assert (fg_rgba_valid); + if (!gtk_style_context_lookup_color (context, "theme_fg_color", &fg_rgba)) { @@ -33,6 +28,6 @@ diff -up gnome-software-42.rc/src/gs-feature-tile.c.1 gnome-software-42.rc/src/g + fg_rgba.blue = 0.0; + fg_rgba.alpha = 1.0; + } + #endif gtk_rgb_to_hsv (fg_rgba.red, fg_rgba.green, fg_rgba.blue, - &fg_hsbc.hue, &fg_hsbc.saturation, &fg_hsbc.brightness); diff --git a/gnome-software.spec b/gnome-software.spec index 4ffb38d..7ec95f7 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -20,13 +20,13 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 43.2 +Version: 44~alpha Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://wiki.gnome.org/Apps/Software -Source0: https://download.gnome.org/sources/gnome-software/43/%{name}-%{tarball_version}.tar.xz +Source0: https://download.gnome.org/sources/gnome-software/44/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch @@ -228,6 +228,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Mon Jan 09 2023 Milan Crha - 44.alpha-1 +- Update to 44.alpha + * Fri Dec 02 2022 Milan Crha - 43.2-1 - Update to 43.2 diff --git a/sources b/sources index 9799f5b..15996c7 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-43.2.tar.xz) = d011418536706d2c5693581bd322008b5eb0fdf766ec96f1775135efb0fecec42dbc126ea2a66465b2169afb38b48fed1246516197e3bbf9d75b96e339d6ba33 +SHA512 (gnome-software-44.alpha.tar.xz) = 4c6d71bca4c5f17d34b1d1c6083ade966ac0f43c9ae00fff1f05a51faca117647d71e48045ebbc697e1e4106dedfe45ce442973dad5f4a947c5dfe416232a776 From db9647bdbd42e908b965b0066c3c6f35d15f98f6 Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Thu, 19 Jan 2023 05:39:31 +0000 Subject: [PATCH 077/163] Rebuilt for https://fedoraproject.org/wiki/Fedora_38_Mass_Rebuild Signed-off-by: Fedora Release Engineering --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 7ec95f7..090dad5 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -21,7 +21,7 @@ Name: gnome-software Version: 44~alpha -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -228,6 +228,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Jan 19 2023 Fedora Release Engineering - 44~alpha-2 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_38_Mass_Rebuild + * Mon Jan 09 2023 Milan Crha - 44.alpha-1 - Update to 44.alpha From 203bf248ec3b693f18770e6eb32e7cc70a4284e0 Mon Sep 17 00:00:00 2001 From: Michael Catanzaro Date: Thu, 9 Feb 2023 11:03:29 -0600 Subject: [PATCH 078/163] Switch to libsoup 3 --- gnome-software.spec | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 090dad5..e0a9fa6 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -21,7 +21,7 @@ Name: gnome-software Version: 44~alpha -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -50,7 +50,7 @@ BuildRequires: pkgconfig(gudev-1.0) BuildRequires: pkgconfig(json-glib-1.0) >= %{json_glib_version} BuildRequires: pkgconfig(libadwaita-1) >= %{libadwaita_version} BuildRequires: pkgconfig(libdnf) -BuildRequires: pkgconfig(libsoup-2.4) +BuildRequires: pkgconfig(libsoup-3.0) BuildRequires: pkgconfig(malcontent-0) BuildRequires: pkgconfig(ostree-1) BuildRequires: pkgconfig(packagekit-glib2) >= %{packagekit_version} @@ -113,7 +113,7 @@ This package includes the rpm-ostree backend. %build %meson \ - -Dsoup2=true \ + -Dsoup2=false \ -Dsnap=false \ -Dmalcontent=true \ -Dgudev=true \ @@ -228,6 +228,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Feb 09 2023 Michael Catanzaro - 44~alpha-3 +- Switch to libsoup 3 + * Thu Jan 19 2023 Fedora Release Engineering - 44~alpha-2 - Rebuilt for https://fedoraproject.org/wiki/Fedora_38_Mass_Rebuild From e710d3931e8db0f904b040d1638a53b2f3e986cf Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Tue, 14 Feb 2023 08:09:00 +0100 Subject: [PATCH 079/163] Update to 44.beta --- gnome-software.spec | 13 ++++++++----- sources | 2 +- 2 files changed, 9 insertions(+), 6 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index e0a9fa6..a8e2a96 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -2,9 +2,9 @@ %global flatpak_version 1.5.1 %global fwupd_version 1.3.3 %global glib2_version 2.61.1 -%global gtk4_version 4.4.0 +%global gtk4_version 4.9.2 %global json_glib_version 1.2.0 -%global libadwaita_version 1.0.1 +%global libadwaita_version 1.3~alpha %global libsoup_version 2.52.0 %global libxmlb_version 0.1.7 %global packagekit_version 1.1.1 @@ -13,15 +13,15 @@ %{!?with_webapps: %global with_webapps !0%{?rhel}} # this is not a library version -%define gs_plugin_version 19 +%define gs_plugin_version 20 %global tarball_version %%(echo %{version} | tr '~' '.') %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 44~alpha -Release: 3%{?dist} +Version: 44~beta +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -228,6 +228,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Tue Feb 14 2023 Milan Crha - 44.beta-1 +- Update to 44.beta + * Thu Feb 09 2023 Michael Catanzaro - 44~alpha-3 - Switch to libsoup 3 diff --git a/sources b/sources index 15996c7..57a6efa 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-44.alpha.tar.xz) = 4c6d71bca4c5f17d34b1d1c6083ade966ac0f43c9ae00fff1f05a51faca117647d71e48045ebbc697e1e4106dedfe45ce442973dad5f4a947c5dfe416232a776 +SHA512 (gnome-software-44.beta.tar.xz) = 0d5f65f513e10d2db2590a9f0a9a5f0eb911ef8ae3a823115cbbc79e08c347faa0f7d07bac3bab0e9fc26b32bc2e60e35b2c7263a9cffb89c5a4c156623657d7 From 6e1e4a25c991a12ddb81da4c1cb3a3c8c27d44c6 Mon Sep 17 00:00:00 2001 From: Adam Williamson Date: Thu, 23 Feb 2023 13:19:04 -0800 Subject: [PATCH 080/163] Backport MR #1635 to fix update notifications --- ...r-No-notification-of-prepared-update.patch | 45 +++++++++++++++++++ gnome-software.spec | 9 +++- 2 files changed, 53 insertions(+), 1 deletion(-) create mode 100644 0001-gs-update-monitor-No-notification-of-prepared-update.patch diff --git a/0001-gs-update-monitor-No-notification-of-prepared-update.patch b/0001-gs-update-monitor-No-notification-of-prepared-update.patch new file mode 100644 index 0000000..bbb2276 --- /dev/null +++ b/0001-gs-update-monitor-No-notification-of-prepared-update.patch @@ -0,0 +1,45 @@ +From f6594bb461617a92801cfbe5dd4017898119b72d Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Thu, 23 Feb 2023 16:10:33 +0100 +Subject: [PATCH] gs-update-monitor: No notification of prepared updates + +This is a regression in 44.beta, the job returns empty list of apps, +because its existence only indicates success or failure. Due to that +there was not recognized any online nor offline update, thus no notification +was done afterwards. Check the app list used in the update job instead. +--- + src/gs-update-monitor.c | 8 +++++--- + 1 file changed, 5 insertions(+), 3 deletions(-) + +diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c +index 6361ddbbb..b7ed2c344 100644 +--- a/src/gs-update-monitor.c ++++ b/src/gs-update-monitor.c +@@ -486,8 +486,9 @@ download_finished_cb (GObject *object, GAsyncResult *res, gpointer user_data) + g_autoptr(GsAppList) list = NULL; + g_autoptr(GsAppList) update_online = NULL; + g_autoptr(GsAppList) update_offline = NULL; ++ GsAppList *job_apps; + +- /* get result */ ++ /* the returned list is always empty, the existence indicates success */ + list = gs_plugin_loader_job_process_finish (plugin_loader, res, &error); + if (list == NULL) { + gs_plugin_loader_claim_job_error (plugin_loader, +@@ -497,10 +498,11 @@ download_finished_cb (GObject *object, GAsyncResult *res, gpointer user_data) + return; + } + ++ job_apps = gs_plugin_job_update_apps_get_apps (GS_PLUGIN_JOB_UPDATE_APPS (data->job)); + update_online = gs_app_list_new (); + update_offline = gs_app_list_new (); +- for (guint i = 0; i < gs_app_list_length (list); i++) { +- GsApp *app = gs_app_list_index (list, i); ++ for (guint i = 0; i < gs_app_list_length (job_apps); i++) { ++ GsApp *app = gs_app_list_index (job_apps, i); + if (_should_auto_update (app)) { + g_debug ("auto-updating %s", gs_app_get_unique_id (app)); + gs_app_list_add (update_online, app); +-- +2.39.2 + diff --git a/gnome-software.spec b/gnome-software.spec index a8e2a96..0cd68f2 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -21,7 +21,7 @@ Name: gnome-software Version: 44~beta -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -29,6 +29,10 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/44/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/1635 +# https://bugzilla.redhat.com/show_bug.cgi?id=2172662 +# Fix update notifications +Patch02: 0001-gs-update-monitor-No-notification-of-prepared-update.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -228,6 +232,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Feb 23 2023 Adam Williamson - 44~beta-2 +- Backport MR #1635 to fix update notifications + * Tue Feb 14 2023 Milan Crha - 44.beta-1 - Update to 44.beta From cb6e4371958d1a7dc595dec68606acc89a458a24 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 3 Mar 2023 13:59:50 +0100 Subject: [PATCH 081/163] Update to 44.rc --- ...r-No-notification-of-prepared-update.patch | 45 ------------------- gnome-software.spec | 13 +++--- sources | 2 +- 3 files changed, 7 insertions(+), 53 deletions(-) delete mode 100644 0001-gs-update-monitor-No-notification-of-prepared-update.patch diff --git a/0001-gs-update-monitor-No-notification-of-prepared-update.patch b/0001-gs-update-monitor-No-notification-of-prepared-update.patch deleted file mode 100644 index bbb2276..0000000 --- a/0001-gs-update-monitor-No-notification-of-prepared-update.patch +++ /dev/null @@ -1,45 +0,0 @@ -From f6594bb461617a92801cfbe5dd4017898119b72d Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Thu, 23 Feb 2023 16:10:33 +0100 -Subject: [PATCH] gs-update-monitor: No notification of prepared updates - -This is a regression in 44.beta, the job returns empty list of apps, -because its existence only indicates success or failure. Due to that -there was not recognized any online nor offline update, thus no notification -was done afterwards. Check the app list used in the update job instead. ---- - src/gs-update-monitor.c | 8 +++++--- - 1 file changed, 5 insertions(+), 3 deletions(-) - -diff --git a/src/gs-update-monitor.c b/src/gs-update-monitor.c -index 6361ddbbb..b7ed2c344 100644 ---- a/src/gs-update-monitor.c -+++ b/src/gs-update-monitor.c -@@ -486,8 +486,9 @@ download_finished_cb (GObject *object, GAsyncResult *res, gpointer user_data) - g_autoptr(GsAppList) list = NULL; - g_autoptr(GsAppList) update_online = NULL; - g_autoptr(GsAppList) update_offline = NULL; -+ GsAppList *job_apps; - -- /* get result */ -+ /* the returned list is always empty, the existence indicates success */ - list = gs_plugin_loader_job_process_finish (plugin_loader, res, &error); - if (list == NULL) { - gs_plugin_loader_claim_job_error (plugin_loader, -@@ -497,10 +498,11 @@ download_finished_cb (GObject *object, GAsyncResult *res, gpointer user_data) - return; - } - -+ job_apps = gs_plugin_job_update_apps_get_apps (GS_PLUGIN_JOB_UPDATE_APPS (data->job)); - update_online = gs_app_list_new (); - update_offline = gs_app_list_new (); -- for (guint i = 0; i < gs_app_list_length (list); i++) { -- GsApp *app = gs_app_list_index (list, i); -+ for (guint i = 0; i < gs_app_list_length (job_apps); i++) { -+ GsApp *app = gs_app_list_index (job_apps, i); - if (_should_auto_update (app)) { - g_debug ("auto-updating %s", gs_app_get_unique_id (app)); - gs_app_list_add (update_online, app); --- -2.39.2 - diff --git a/gnome-software.spec b/gnome-software.spec index 0cd68f2..d525c64 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -4,7 +4,7 @@ %global glib2_version 2.61.1 %global gtk4_version 4.9.2 %global json_glib_version 1.2.0 -%global libadwaita_version 1.3~alpha +%global libadwaita_version 1.3.alpha %global libsoup_version 2.52.0 %global libxmlb_version 0.1.7 %global packagekit_version 1.1.1 @@ -20,8 +20,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 44~beta -Release: 2%{?dist} +Version: 44~rc +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -29,10 +29,6 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/44/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/1635 -# https://bugzilla.redhat.com/show_bug.cgi?id=2172662 -# Fix update notifications -Patch02: 0001-gs-update-monitor-No-notification-of-prepared-update.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -232,6 +228,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Mar 03 2023 Milan Crha - 44~rc-1 +- Update to 44.rc + * Thu Feb 23 2023 Adam Williamson - 44~beta-2 - Backport MR #1635 to fix update notifications diff --git a/sources b/sources index 57a6efa..0ad486a 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-44.beta.tar.xz) = 0d5f65f513e10d2db2590a9f0a9a5f0eb911ef8ae3a823115cbbc79e08c347faa0f7d07bac3bab0e9fc26b32bc2e60e35b2c7263a9cffb89c5a4c156623657d7 +SHA512 (gnome-software-44.rc.tar.xz) = 15d40987a001af58dd0a671c8aa7399a1397a21bcd62ff5850e5dde4cee67cb64d53408492d8da0990cee301bf535b5c1954257d8dcbb0f49ba74ee1347ec843 From 1293c4db156be33d8bf471de4a1617903a23cd06 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 17 Mar 2023 07:44:25 +0100 Subject: [PATCH 082/163] Update to 44.0 --- 0002-update-czech-translation.patch | 4889 +++++++++++++++++++++++++++ gnome-software.spec | 6 +- sources | 2 +- 3 files changed, 4895 insertions(+), 2 deletions(-) create mode 100644 0002-update-czech-translation.patch diff --git a/0002-update-czech-translation.patch b/0002-update-czech-translation.patch new file mode 100644 index 0000000..86b6304 --- /dev/null +++ b/0002-update-czech-translation.patch @@ -0,0 +1,4889 @@ +diff --git a/po/cs.po b/po/cs.po +index 3301fcaf4..b532ac8a9 100644 +--- a/po/cs.po ++++ b/po/cs.po +@@ -4,22 +4,23 @@ + # + # Petr Kovar , 2015. + # Marek Černocký , 2013, 2014, 2015, 2016, 2017, 2018, 2019, 2020, 2021, 2022. +-# Vojtěch Perník , 2021-2022. ++# Vojtěch Perník , 2021-2023. ++# Daniel Rusek , 2023. + # + msgid "" + msgstr "" + "Project-Id-Version: gnome-software\n" + "Report-Msgid-Bugs-To: https://gitlab.gnome.org/GNOME/gnome-software/issues\n" +-"POT-Creation-Date: 2022-11-10 08:39+0000\n" +-"PO-Revision-Date: 2022-08-28 11:45+0200\n" +-"Last-Translator: Vojtěch Perník \n" ++"POT-Creation-Date: 2023-03-16 13:07+0000\n" ++"PO-Revision-Date: 2023-03-16 12:54+0100\n" ++"Last-Translator: Daniel Rusek \n" + "Language-Team: Czech \n" + "Language: cs\n" + "MIME-Version: 1.0\n" + "Content-Type: text/plain; charset=UTF-8\n" + "Content-Transfer-Encoding: 8bit\n" + "Plural-Forms: nplurals=3; plural=(n==1) ? 0 : (n>=2 && n<=4) ? 1 : 2;\n" +-"X-Generator: Poedit 3.1.1\n" ++"X-Generator: Poedit 3.2.2\n" + "X-Project-Style: gnome\n" + + #: data/metainfo/org.gnome.Software.metainfo.xml.in:7 src/gs-shell.ui:21 +@@ -33,18 +34,18 @@ msgstr "Instalujte a aktualizujte aplikace" + + #: data/metainfo/org.gnome.Software.metainfo.xml.in:10 + msgid "" +-"Software allows you to find and install new applications and system " +-"extensions and remove existing installed applications." ++"Software allows you to find and install new apps and system extensions and " ++"remove existing installed apps." + msgstr "" + "Aplikace Software umožňuje vyhledávat a instalovat aplikace a systémová " + "rozšíření a odebírat stávající nainstalované aplikace." + + #: data/metainfo/org.gnome.Software.metainfo.xml.in:14 + msgid "" +-"Software showcases featured and popular applications with useful " +-"descriptions and multiple screenshots per application. Applications can be " +-"found either through browsing the list of categories or by searching. It " +-"also allows you to update your system using an offline update." ++"Software showcases featured and popular apps with useful descriptions and " ++"multiple screenshots per app. Apps can be found either through browsing the " ++"list of categories or by searching. It also allows you to update your system " ++"using an offline update." + msgstr "" + "Aplikace Software vám představí významné a oblíbené aplikace pomocí " + "srozumitelného popisu a několika snímků obrazovky. Aplikace můžete najít buď " +@@ -73,7 +74,7 @@ msgstr "Panel s aktualizacemi" + msgid "The update details" + msgstr "Podrobnosti o aktualizaci" + +-#: data/metainfo/org.gnome.Software.metainfo.xml.in:2076 ++#: data/metainfo/org.gnome.Software.metainfo.xml.in:2222 + #: src/gs-application.c:264 + msgid "The GNOME Project" + msgstr "Projekt GNOME" +@@ -195,17 +196,12 @@ msgid "The last update timestamp" + msgstr "Datum a čas poslední aktualizace" + + #: data/org.gnome.software.gschema.xml:67 +-msgid "The last timestamp when the system was online and got any updates" +-msgstr "" +-"Datum a čas, kdy byl systém naposledy on-line a dostal nějaké aktualizace" +- +-#: data/org.gnome.software.gschema.xml:71 + msgid "The age in seconds to verify the upstream screenshot is still valid" + msgstr "" + "Doba v sekundách, po které se má ověřit, jestli je snímek obrazovky z " + "hlavního zdroje stále platný" + +-#: data/org.gnome.software.gschema.xml:72 ++#: data/org.gnome.software.gschema.xml:68 + msgid "" + "Choosing a larger value will mean less round-trips to the remote server but " + "updates to the screenshots may take longer to show to the user. A value of 0 " +@@ -216,75 +212,75 @@ msgstr "" + "znamená, že se kontroly na serveru nemají provádět vůbec, pokud je již " + "snímek v mezipaměti." + +-#: data/org.gnome.software.gschema.xml:81 ++#: data/org.gnome.software.gschema.xml:77 + msgid "The server to use for application reviews" + msgstr "Server, který se má používat pro recenze aktualizací" + +-#: data/org.gnome.software.gschema.xml:85 ++#: data/org.gnome.software.gschema.xml:81 + msgid "The minimum karma score for reviews" + msgstr "Minimální karma pro recenze" + +-#: data/org.gnome.software.gschema.xml:86 ++#: data/org.gnome.software.gschema.xml:82 + msgid "Reviews with karma less than this number will not be shown." + msgstr "Recenze s karmou nižší než toto číslo nebudou zobrazovány." + +-#: data/org.gnome.software.gschema.xml:90 ++#: data/org.gnome.software.gschema.xml:86 + msgid "A list of official repositories that should not be considered 3rd party" + msgstr "" + "Seznam oficiálních repozitářů, které by neměly být považovány za třetí stranu" + +-#: data/org.gnome.software.gschema.xml:94 ++#: data/org.gnome.software.gschema.xml:90 + msgid "A list of required repositories that cannot be disabled or removed" + msgstr "" + "Seznam vyžadovaných repozitářů, které nemohou být zakázány nebo odebrány" + +-#: data/org.gnome.software.gschema.xml:98 ++#: data/org.gnome.software.gschema.xml:94 + msgid "A list of official repositories that should be considered free software" + msgstr "" + "Seznam oficiálních repozitářů, které by měly být považovány za svobodný " + "software" + +-#: data/org.gnome.software.gschema.xml:102 ++#: data/org.gnome.software.gschema.xml:98 + msgid "" + "The licence URL to use when an application should be considered free software" + msgstr "" + "Adresa URL licence, která se má použít, když má aplikace považována za " + "svobodný software" + +-#: data/org.gnome.software.gschema.xml:106 ++#: data/org.gnome.software.gschema.xml:102 + msgid "Install bundled applications for all users on the system where possible" + msgstr "" + "Kde je to možné, instalovat všem uživatelům v systému přibalené aplikace" + +-#: data/org.gnome.software.gschema.xml:110 ++#: data/org.gnome.software.gschema.xml:106 + msgid "Allow access to the Software Repositories dialog" + msgstr "Umožnit přístup k dialogovému oknu s repozitáři softwaru" + +-#: data/org.gnome.software.gschema.xml:114 ++#: data/org.gnome.software.gschema.xml:110 + msgid "Offer upgrades for pre-releases" + msgstr "Nabízet povýšení na předběžná vydání" + +-#: data/org.gnome.software.gschema.xml:118 ++#: data/org.gnome.software.gschema.xml:114 + msgid "Show some UI elements informing the user that an app is non-free" + msgstr "" + "Zobrazovat v rozhraní prvky, které informují uživatele, že aplikace není " + "svobodná" + +-#: data/org.gnome.software.gschema.xml:122 ++#: data/org.gnome.software.gschema.xml:118 + msgid "Show the installed size for apps in the list of installed applications" + msgstr "" + "Zobrazovat velikost instalace pro aplikace v seznamu nainstalovaných aplikací" + + #. Translators: Replace the link with a version in your language, e.g. 'https://de.wikipedia.org/wiki/Proprietäre_Software'. Remember to include ''. +-#: data/org.gnome.software.gschema.xml:126 ++#: data/org.gnome.software.gschema.xml:122 + msgid "'https://en.wikipedia.org/wiki/Proprietary_software'" + msgstr "'https://cs.wikipedia.org/wiki/Propriet%C3%A1rn%C3%AD_software'" + +-#: data/org.gnome.software.gschema.xml:127 ++#: data/org.gnome.software.gschema.xml:123 + msgid "The URI that explains nonfree and proprietary software" + msgstr "Adresa URI, která vysvětluje nesvobodný a komerční software" + +-#: data/org.gnome.software.gschema.xml:131 ++#: data/org.gnome.software.gschema.xml:127 + msgid "" + "A list of URLs pointing to appstream files that will be downloaded into an " + "swcatalog folder" +@@ -292,7 +288,7 @@ msgstr "" + "Seznam adres URL ukazujících na soubory appstream, které byly stažené do " + "složky swcatalog" + +-#: data/org.gnome.software.gschema.xml:135 ++#: data/org.gnome.software.gschema.xml:131 + msgid "" + "Install the AppStream files to a system-wide location for all users. If " + "false, files are installed in non-standard $XDG_DATA_HOME/swcatalog/xml " +@@ -302,13 +298,7 @@ msgstr "" + "uživatele. Pokud je vypnuto, budou soubory instalovány do nestandardní " + "složky $XDG_DATA_HOME/swcatalog/xmls" + +-#: data/org.gnome.software.gschema.xml:139 +-#, fuzzy +-#| msgid "" +-#| "Priority order of packaging formats to prefer, with more important " +-#| "formats listed first. An empty array means the default order. Omitted " +-#| "formats are assumed to be listed last. Example packaging formats are: " +-#| "deb, flatpak, rpm, snap." ++#: data/org.gnome.software.gschema.xml:135 + msgid "" + "Priority order of packaging formats to prefer, with more important formats " + "listed first. An empty array means the default order. Omitted formats are " +@@ -319,9 +309,24 @@ msgstr "" + "Prioritní pořadí formátů balíčků, kterým dáváte přednost, přičemž " + "důležitější formáty jsou uvedeny na prvním místě. Prázdné pole znamená " + "výchozí pořadí. Předpokládá se, že vynechané formáty budou uvedeny jako " +-"poslední. Příklady balíčkovacích formátů: deb, flatpak, rpm, snap." ++"poslední. Příklady balíčkovacích formátů: deb, flatpak, rpm, snap. Formáty " ++"mohou být nepovinně specifikovány s názvem původu odděleného dvojtečkou, " ++"například „flatpak:flathub“." ++ ++#: data/org.gnome.software.gschema.xml:139 ++msgid "The timestamp of the last attempt to remove unused Flatpak runtimes" ++msgstr "" ++"Datum a čas posledního pokusu odebrat nepoužívaná běhová prostředí Flatpak" ++ ++#: data/org.gnome.software.gschema.xml:143 ++msgid "" ++"Set to 'true' to show only freely licensed apps and hide any proprietary " ++"apps." ++msgstr "" ++"Nastavte na „true“, chcete-li zobrazit pouze aplikace s otevřenou licencí a " ++"skrýt všechny proprietární aplikace." + +-#: data/org.gnome.software.gschema.xml:146 ++#: data/org.gnome.software.gschema.xml:150 + msgid "A string storing the gnome-online-account id used to login" + msgstr "Řetězec uchovávající ID gnome-online-account pro přihlášení" + +@@ -710,7 +715,7 @@ msgstr "%s • %s" + + #. Translators: The app is considered suitable to be run by all ages of people. + #. * This is displayed in a context tile, so the string should be short. +-#: src/gs-age-rating-context-dialog.c:936 ++#: src/gs-age-rating-context-dialog.c:935 + msgctxt "Age rating" + msgid "All" + msgstr "Vše" +@@ -719,44 +724,44 @@ msgstr "Vše" + #. * app’s context tile if the size is unknown. It should be short + #. * (at most a couple of characters wide). + #. Translators: This is shown in a bubble if the storage +-#. * size of an application is not known. The bubble is small, ++#. * size of an app is not known. The bubble is small, + #. * so the string should be as short as possible. +-#: src/gs-age-rating-context-dialog.c:949 src/gs-app-context-bar.c:206 ++#: src/gs-age-rating-context-dialog.c:948 src/gs-app-context-bar.c:206 + #: src/gs-storage-context-dialog.c:89 + msgid "?" + msgstr "?" + + #. Translators: This is a dialogue title which indicates that an app is suitable + #. * for all ages. The placeholder is the app name. +-#: src/gs-age-rating-context-dialog.c:1023 ++#: src/gs-age-rating-context-dialog.c:1020 + #, c-format + msgid "%s is suitable for everyone" + msgstr "Aplikace %s je vhodná pro každého" + + #. Translators: This is a dialogue title which indicates that an app is suitable + #. * for children up to around age 3. The placeholder is the app name. +-#: src/gs-age-rating-context-dialog.c:1027 ++#: src/gs-age-rating-context-dialog.c:1024 + #, c-format + msgid "%s is suitable for toddlers" + msgstr "Aplikace %s je vhodná pro batolata" + + #. Translators: This is a dialogue title which indicates that an app is suitable + #. * for children up to around age 5. The placeholder is the app name. +-#: src/gs-age-rating-context-dialog.c:1031 ++#: src/gs-age-rating-context-dialog.c:1028 + #, c-format + msgid "%s is suitable for young children" + msgstr "Aplikace %s je vhodná pro malé děti" + + #. Translators: This is a dialogue title which indicates that an app is suitable + #. * for people up to around age 18. The placeholder is the app name. +-#: src/gs-age-rating-context-dialog.c:1039 ++#: src/gs-age-rating-context-dialog.c:1036 + #, c-format + msgid "%s is suitable for teenagers" + msgstr "Aplikace %s je vhodná pro dospívající mládež" + + #. Translators: This is a dialogue title which indicates that an app is suitable + #. * for people aged up to and over 18. The placeholder is the app name. +-#: src/gs-age-rating-context-dialog.c:1043 ++#: src/gs-age-rating-context-dialog.c:1040 + #, c-format + msgid "%s is suitable for adults" + msgstr "Aplikace %s je vhodná pro dospělé" +@@ -764,14 +769,14 @@ msgstr "Aplikace %s je vhodná pro dospělé" + #. Translators: This is a dialogue title which indicates that an app is suitable + #. * for a specified age group. The first placeholder is the app name, the second + #. * is the age group. +-#: src/gs-age-rating-context-dialog.c:1048 ++#: src/gs-age-rating-context-dialog.c:1045 + #, c-format + msgid "%s is suitable for %s" + msgstr "Aplikace %s je vhodná pro %s" + + #. Translators: This is the title of the dialog which contains information about the suitability of an app for different ages. + #. this one’s not a placeholder +-#: src/gs-age-rating-context-dialog.ui:5 src/gs-app-context-bar.ui:211 ++#: src/gs-age-rating-context-dialog.ui:5 src/gs-app-context-bar.ui:217 + msgid "Age Rating" + msgstr "Vhodné od věku" + +@@ -781,7 +786,7 @@ msgstr "Vhodné od věku" + msgid "How to contribute missing information" + msgstr "Jak přidat chybějící informace" + +-#: lib/gs-app.c:6178 ++#: lib/gs-app.c:6256 + msgid "Local file" + msgstr "Místní soubor" + +@@ -790,44 +795,51 @@ msgstr "Místní soubor" + #. Example string: "Local file (RPM)" + #. Translators: The first placeholder is an app runtime + #. * name, the second is its version number. +-#: lib/gs-app.c:6197 src/gs-safety-context-dialog.c:439 ++#: lib/gs-app.c:6275 src/gs-safety-context-dialog.c:443 + #, c-format + msgid "%s (%s)" + msgstr "%s (%s)" + +-#: lib/gs-app.c:6274 ++#: lib/gs-app.c:6352 + msgid "Package" + msgstr "Balíček" + +-#: src/gs-app-addon-row.c:97 src/gs-app-row.c:460 ++#: src/gs-app-addon-row.c:95 src/gs-app-row.c:452 + msgid "Pending" + msgstr "Čeká na zpracování" + +-#: src/gs-app-addon-row.c:101 src/gs-app-row.c:464 src/gs-details-page.c:369 ++#: src/gs-app-addon-row.c:99 src/gs-app-row.c:456 src/gs-details-page.c:379 + msgid "Pending install" + msgstr "Čeká na instalaci" + +-#: src/gs-app-addon-row.c:105 src/gs-app-row.c:468 src/gs-details-page.c:376 ++#: src/gs-app-addon-row.c:103 src/gs-app-row.c:460 src/gs-details-page.c:386 + msgid "Pending remove" + msgstr "Čeká na odebrání" + +-#: src/gs-app-addon-row.c:111 src/gs-app-row.ui:197 src/gs-app-tile.ui:50 +-#: src/gs-feature-tile.c:535 +-msgctxt "Single app" +-msgid "Installed" +-msgstr "Nainstalováno" +- + #. TRANSLATORS: this is a button next to the search results that +-#. * shows the status of an application being installed +-#: src/gs-app-addon-row.c:115 src/gs-app-row.c:208 src/gs-details-page.c:362 ++#. * shows the status of an app being installed ++#: src/gs-app-addon-row.c:107 src/gs-app-row.c:207 src/gs-details-page.c:372 + msgid "Installing" + msgstr "Instaluje se" + +-#: src/gs-app-addon-row.c:119 ++#: src/gs-app-addon-row.c:111 + msgid "Removing" + msgstr "Odebírá se" + +-#: src/gs-app-addon-row.ui:64 src/gs-details-page.c:1015 ++#. TRANSLATORS: button text ++#. TRANSLATORS: button text in the header when an app ++#. * can be installed ++#. TRANSLATORS: button text in the header when firmware ++#. * can be live-installed ++#. TRANSLATORS: update the fw ++#: src/gs-app-addon-row.ui:66 src/gs-common.c:303 src/gs-details-page.c:924 ++#: src/gs-details-page.c:950 src/gs-details-page.ui:209 src/gs-page.c:412 ++#: plugins/packagekit/gs-packagekit-task.c:149 ++msgid "_Install" ++msgstr "_Instalovat" ++ ++#. TRANSLATORS: this is button text to remove the app ++#: src/gs-app-addon-row.ui:73 src/gs-page.c:551 + msgid "_Uninstall" + msgstr "_Odinstalovat" + +@@ -855,116 +867,120 @@ msgstr "Služby sezení" + msgid "Can access D-Bus services on the session bus" + msgstr "Může přistupovat k službám D-Bus na sběrnici sezení" + +-#: src/gs-app-details-page.c:71 ++#: src/gs-app-details-page.c:71 src/gs-app-details-page.c:72 + msgid "Devices" + msgstr "Zařízení" + + #: src/gs-app-details-page.c:71 ++msgid "Can access arbitrary devices such as webcams" ++msgstr "Může přistupovat k libovolným zařízením, například webovým kamerám" ++ ++#: src/gs-app-details-page.c:72 + msgid "Can access system device files" + msgstr "Může přistupovat k souborům na systémovém zařízení" + +-#: src/gs-app-details-page.c:72 src/gs-app-details-page.c:73 ++#: src/gs-app-details-page.c:73 src/gs-app-details-page.c:74 + msgid "Home folder" + msgstr "Domovská složka" + +-#: src/gs-app-details-page.c:72 src/gs-app-details-page.c:74 +-#: src/gs-app-details-page.c:77 src/gs-app-details-page.c:150 ++#: src/gs-app-details-page.c:73 src/gs-app-details-page.c:75 ++#: src/gs-app-details-page.c:78 src/gs-app-details-page.c:151 + msgid "Can view, edit and create files" + msgstr "Může zobrazovat, upravovat a vytvářet soubory" + +-#: src/gs-app-details-page.c:73 src/gs-app-details-page.c:75 +-#: src/gs-app-details-page.c:78 src/gs-app-details-page.c:145 ++#: src/gs-app-details-page.c:74 src/gs-app-details-page.c:76 ++#: src/gs-app-details-page.c:79 src/gs-app-details-page.c:146 + msgid "Can view files" + msgstr "Může zobrazovat soubory" + +-#: src/gs-app-details-page.c:74 src/gs-app-details-page.c:75 ++#: src/gs-app-details-page.c:75 src/gs-app-details-page.c:76 + msgid "File system" + msgstr "Souborový systém" + + #. The GS_APP_PERMISSIONS_FLAGS_FILESYSTEM_OTHER is used only as a flag, with actual files being part of the read/full lists +-#: src/gs-app-details-page.c:77 src/gs-app-details-page.c:78 ++#: src/gs-app-details-page.c:78 src/gs-app-details-page.c:79 + msgid "Downloads folder" + msgstr "Složka se staženými soubory" + +-#: src/gs-app-details-page.c:79 ++#: src/gs-app-details-page.c:80 + msgid "Settings" + msgstr "Nastavení" + +-#: src/gs-app-details-page.c:79 ++#: src/gs-app-details-page.c:80 + msgid "Can view and change any settings" + msgstr "Může zobrazovat a měnit libovolná nastavení" + +-#: src/gs-app-details-page.c:80 ++#: src/gs-app-details-page.c:81 + msgid "Legacy display system" + msgstr "Zastaralý zobrazovací systém" + +-#: src/gs-app-details-page.c:80 ++#: src/gs-app-details-page.c:81 + msgid "Uses an old, insecure display system" + msgstr "Používá starý, ne zcela bezpečný, zobrazovací systém" + +-#: src/gs-app-details-page.c:81 ++#: src/gs-app-details-page.c:82 + msgid "Sandbox escape" + msgstr "Opuštění izolovaného prostředí" + +-#: src/gs-app-details-page.c:81 ++#: src/gs-app-details-page.c:82 + msgid "Can escape the sandbox and circumvent any other restrictions" + msgstr "Může opustit izolované prostředí a obejít další omezení" + + #. FIXME support app == NULL + #. set window title +-#: src/gs-app-details-page.c:166 ++#: src/gs-app-details-page.c:167 + msgid "Update Details" + msgstr "Podrobnosti o aktualizaci" + + #. TRANSLATORS: this is where the packager did not write + #. * a description for the update +-#: src/gs-app-details-page.c:174 ++#: src/gs-app-details-page.c:175 + msgid "No update description available." + msgstr "Není k dispozici žádný popis aktualizace." + + #: src/gs-app-details-page.ui:25 src/gs-os-update-page.ui:25 +-#: src/gs-shell.ui:369 src/gs-shell.ui:460 ++#: src/gs-shell.ui:348 src/gs-shell.ui:439 + msgid "Go back" + msgstr "Přejít zpět" + +-#: src/gs-app-details-page.ui:48 src/gs-app-row.c:523 ++#: src/gs-app-details-page.ui:48 src/gs-app-row.c:515 + msgid "Requires additional permissions" + msgstr "Vyžaduje dodatečná oprávnění" + + #. Translators: Header of the section with other users' opinions about the app. +-#: src/gs-app-reviews-dialog.ui:6 src/gs-details-page.ui:867 ++#: src/gs-app-reviews-dialog.ui:6 src/gs-details-page.ui:930 + msgid "Reviews" + msgstr "Recenze" + + #: src/gs-app-reviews-dialog.ui:25 +-msgid "No reviews were found for this application." ++msgid "No reviews were found for this app." + msgstr "Pro tuto aplikaci nebyly nalezeny žádné recenze." + + #: src/gs-app-reviews-dialog.ui:27 + msgid "No Reviews" + msgstr "Bez recenzí" + +-#: src/gs-app-version-history-dialog.ui:6 src/gs-details-page.ui:545 ++#: src/gs-app-version-history-dialog.ui:6 src/gs-details-page.ui:529 + msgid "Version History" + msgstr "Historie verzí" + +-#: src/gs-app-version-history-row.c:71 ++#: src/gs-app-version-history-row.c:133 + #, c-format + msgid "New in Version %s" + msgstr "Novinky ve verzi %s" + +-#: src/gs-app-version-history-row.c:78 ++#: src/gs-app-version-history-row.c:140 + #, c-format + msgid "Version %s" + msgstr "Verze %s" + +-#: src/gs-app-version-history-row.c:80 ++#: src/gs-app-version-history-row.c:142 + msgid "No details for this release" + msgstr "K tomuto vydání nejsou k dispozici žádné podrobnosti." + + #. TRANSLATORS: This is the date string with: day number, month name, year. + #. i.e. "25 May 2012" +-#: src/gs-app-version-history-row.c:94 src/gs-review-row.c:63 ++#: src/gs-app-version-history-row.c:156 src/gs-review-row.c:67 + msgid "%e %B %Y" + msgstr "%e. %B %Y" + +@@ -1040,8 +1056,8 @@ msgid "Installs any pending updates in the background" + msgstr "Nainstalovat na pozadí případné čekající aktualizace" + + #: src/gs-application.c:147 +-msgid "Show update preferences" +-msgstr "Zobrazit předvolby aktualizací" ++msgid "Show preferences" ++msgstr "Zobrazit předvolby" + + #: src/gs-application.c:149 + msgid "Quit the running instance" +@@ -1056,8 +1072,8 @@ msgid "Show version number" + msgstr "Zobrazit číslo verze" + + #: src/gs-application.c:271 src/gs-application.c:279 +-msgid "Copyright © 2016–2022 GNOME Software contributors" +-msgstr "Copyright © 2016 – 2022 přispěvatelé Softwaru GNOME" ++msgid "Copyright © 2016–2023 GNOME Software contributors" ++msgstr "Copyright © 2016 – 2023 přispěvatelé Softwaru GNOME" + + #: src/gs-application.c:273 src/gs-application.c:282 + msgid "translator-credits" +@@ -1067,7 +1083,7 @@ msgstr "" + + #. TRANSLATORS: this is the title of the about window + #. TRANSLATORS: this is the menu item that opens the about window +-#: src/gs-application.c:287 src/gs-shell.c:2163 ++#: src/gs-application.c:287 src/gs-shell.c:2127 + msgid "About Software" + msgstr "O aplikaci Software" + +@@ -1077,11 +1093,11 @@ msgid "A nice way to manage the software on your system." + msgstr "Elegantní způsob správy softwaru ve vašem počítači." + + #. TRANSLATORS: we tried to show an app that did not exist +-#: src/gs-application.c:478 ++#: src/gs-application.c:507 + msgid "Sorry! There are no details for that application." + msgstr "Omlouváme se, ale pro tuto aplikaci nejsou k dispozici detaily." + +-#. Translators: The disk usage of an application when installed. ++#. Translators: The disk usage of an app when installed. + #. * This is displayed in a context tile, so the string should be short. + #: src/gs-app-context-bar.c:162 src/gs-storage-context-dialog.c:133 + msgid "Installed Size" +@@ -1106,7 +1122,7 @@ msgstr "Obsahuje %s mezipaměti" + msgid "Cache and data usage unknown" + msgstr "Využití mezipaměti a dat není známo" + +-#. Translators: The download size of an application. ++#. Translators: The download size of an app. + #. * This is displayed in a context tile, so the string should be short. + #: src/gs-app-context-bar.c:187 src/gs-storage-context-dialog.c:165 + msgid "Download Size" +@@ -1136,117 +1152,123 @@ msgstr "Velikost je neznámá" + + #. Translators: This indicates an app requires no permissions to run. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:282 ++#: src/gs-app-context-bar.c:281 + msgid "No permissions" + msgstr "Žádná oprávnění" + + #. Translators: This indicates an app uses the network. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:293 ++#: src/gs-app-context-bar.c:292 + msgid "Has network access" + msgstr "Má přístup k síti" + + #. Translators: This indicates an app uses D-Bus system services. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:300 ++#: src/gs-app-context-bar.c:299 + msgid "Uses system services" + msgstr "Využívá služby systému" + + #. Translators: This indicates an app uses D-Bus session services. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:307 ++#: src/gs-app-context-bar.c:306 + msgid "Uses session services" + msgstr "Využívá služby sezení" + + #. Translators: This indicates an app can access arbitrary hardware devices. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:314 ++#: src/gs-app-context-bar.c:313 + msgid "Can access hardware devices" + msgstr "Může přistupovat k hardwarovým zařízením" + ++#. Translators: This indicates an app can access system devices such as /dev/shm. ++#. * It’s used in a context tile, so should be short. ++#: src/gs-app-context-bar.c:320 ++msgid "Can access system devices" ++msgstr "Může přistupovat k systémovým zařízením" ++ + #. Translators: This indicates an app can read/write to the user’s home or the entire filesystem. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:326 ++#: src/gs-app-context-bar.c:332 + msgid "Can read/write all your data" + msgstr "Může číst/zapisovat všechna vaše data" + + #. Translators: This indicates an app can read (but not write) from the user’s home or the entire filesystem. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:338 ++#: src/gs-app-context-bar.c:344 + msgid "Can read all your data" + msgstr "Může číst všechna vaše data" + + #. Translators: This indicates an app can read/write to the user’s Downloads directory. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:345 ++#: src/gs-app-context-bar.c:351 + msgid "Can read/write your downloads" + msgstr "Může zapisovat do všech vašich dat" + + #. Translators: This indicates an app can read (but not write) from the user’s Downloads directory. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:352 ++#: src/gs-app-context-bar.c:358 + msgid "Can read your downloads" + msgstr "Může číst vaše stažené soubory" + + #. Translators: This indicates an app can access data in the system unknown to the Software. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:359 ++#: src/gs-app-context-bar.c:365 + msgid "Can access arbitrary files" + msgstr "Může přistupovat k libovolným souborům" + + #. Translators: This indicates an app can access or change user settings. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:366 src/gs-safety-context-dialog.c:227 ++#: src/gs-app-context-bar.c:372 src/gs-safety-context-dialog.c:234 + msgid "Can access and change user settings" + msgstr "Může zobrazovat a měnit uživatelská nastavení" + + #. Translators: This indicates an app uses the X11 windowing system. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:373 src/gs-safety-context-dialog.c:211 ++#: src/gs-app-context-bar.c:379 src/gs-safety-context-dialog.c:218 + msgid "Uses a legacy windowing system" + msgstr "Používá starý zobrazovací systém" + + #. Translators: This indicates an app can escape its sandbox. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:380 src/gs-safety-context-dialog.c:219 ++#: src/gs-app-context-bar.c:386 src/gs-safety-context-dialog.c:226 + msgid "Can acquire arbitrary permissions" + msgstr "Může získat libovolná oprávnění" + +-#. Translators: This indicates that an application has been packaged ++#. Translators: This indicates that an app has been packaged + #. * by the user’s distribution and is safe. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:406 src/gs-safety-context-dialog.c:146 ++#: src/gs-app-context-bar.c:412 src/gs-safety-context-dialog.c:145 + msgid "Reviewed by your distribution" + msgstr "Zkontrolováno vaší distribucí" + +-#. Translators: This indicates that an application has been packaged ++#. Translators: This indicates that an app has been packaged + #. * by someone other than the user’s distribution, so might not be safe. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:413 src/gs-safety-context-dialog.c:143 ++#: src/gs-app-context-bar.c:419 src/gs-safety-context-dialog.c:142 + msgid "Provided by a third party" + msgstr "Poskytováno třetí stranou" + + #. Translators: This indicates an app is not licensed under a free software license. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:425 ++#: src/gs-app-context-bar.c:431 + msgid "Proprietary code" + msgstr "Uzavřený kód" + + #. Translators: This indicates an app’s source code is freely available, so can be audited for security. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:431 ++#: src/gs-app-context-bar.c:437 + msgid "Auditable code" + msgstr "Otevřený kód" + + #. Translators: This indicates an app was written and released by a developer who has been verified. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:438 ++#: src/gs-app-context-bar.c:444 + msgid "Software developer is verified" + msgstr "Vývojář softwaru je ověřený" + + #. Translators: This indicates an app or its runtime reached its end of life. + #. * It’s used in a context tile, so should be short. +-#: src/gs-app-context-bar.c:447 ++#: src/gs-app-context-bar.c:453 + msgid "Software no longer supported" + msgstr "Software není nadále podporován" + +@@ -1264,180 +1286,180 @@ msgstr "Software není nadále podporován" + #. * If concatenating strings as a list using a separator like this is not + #. * possible in your language, please file an issue against gnome-software: + #. * https://gitlab.gnome.org/GNOME/gnome-software/-/issues/new +-#: src/gs-app-context-bar.c:459 src/gs-app-context-bar.c:730 ++#: src/gs-app-context-bar.c:465 src/gs-app-context-bar.c:731 + msgid "; " + msgstr "; " + + #. Translators: The app is considered safe to install and run. + #. * This is displayed in a context tile, so the string should be short. +-#: src/gs-app-context-bar.c:467 ++#: src/gs-app-context-bar.c:473 + msgid "Safe" + msgstr "Bezpečné" + + #. Translators: The app is considered potentially unsafe to install and run. + #. * This is displayed in a context tile, so the string should be short. +-#: src/gs-app-context-bar.c:474 ++#: src/gs-app-context-bar.c:480 + msgid "Potentially Unsafe" + msgstr "Potenciálně nebezpečné" + + #. Translators: The app is considered unsafe to install and run. + #. * This is displayed in a context tile, so the string should be short. +-#: src/gs-app-context-bar.c:481 ++#: src/gs-app-context-bar.c:487 + msgid "Unsafe" + msgstr "Nebezpečné" + +-#: src/gs-app-context-bar.c:560 src/gs-app-context-bar.c:592 +-#: src/gs-hardware-support-context-dialog.c:603 ++#: src/gs-app-context-bar.c:563 src/gs-app-context-bar.c:595 ++#: src/gs-hardware-support-context-dialog.c:602 + msgid "Mobile Only" + msgstr "Jen pro mobilní zařízení" + +-#: src/gs-app-context-bar.c:561 ++#: src/gs-app-context-bar.c:564 + msgid "Only works on a small screen" + msgstr "Funguje pouze na malé obrazovce" + +-#: src/gs-app-context-bar.c:566 src/gs-app-context-bar.c:599 +-#: src/gs-app-context-bar.c:606 src/gs-app-context-bar.c:656 +-#: src/gs-app-context-bar.c:661 src/gs-hardware-support-context-dialog.c:583 ++#: src/gs-app-context-bar.c:569 src/gs-app-context-bar.c:602 ++#: src/gs-app-context-bar.c:609 src/gs-app-context-bar.c:659 ++#: src/gs-app-context-bar.c:664 src/gs-hardware-support-context-dialog.c:582 + msgid "Desktop Only" + msgstr "Pouze pro PC" + +-#: src/gs-app-context-bar.c:567 ++#: src/gs-app-context-bar.c:570 + msgid "Only works on a large screen" + msgstr "Funguje pouze na velké obrazovce" + +-#: src/gs-app-context-bar.c:571 src/gs-hardware-support-context-dialog.c:621 ++#: src/gs-app-context-bar.c:574 src/gs-hardware-support-context-dialog.c:620 + msgid "Screen Size Mismatch" + msgstr "Nesoulad velikosti obrazovky" + +-#: src/gs-app-context-bar.c:572 src/gs-hardware-support-context-dialog.c:622 ++#: src/gs-app-context-bar.c:575 src/gs-hardware-support-context-dialog.c:621 + msgid "Doesn’t support your current screen size" + msgstr "Nepodporuje vaši současnou velikost obrazovky" + +-#: src/gs-app-context-bar.c:593 src/gs-hardware-support-context-dialog.c:674 +-#: src/gs-hardware-support-context-dialog.c:680 ++#: src/gs-app-context-bar.c:596 src/gs-hardware-support-context-dialog.c:673 ++#: src/gs-hardware-support-context-dialog.c:679 + msgid "Requires a touchscreen" + msgstr "Vyžaduje dotykovou obrazovku" + +-#: src/gs-app-context-bar.c:600 src/gs-hardware-support-context-dialog.c:634 +-#: src/gs-hardware-support-context-dialog.c:640 ++#: src/gs-app-context-bar.c:603 src/gs-hardware-support-context-dialog.c:633 ++#: src/gs-hardware-support-context-dialog.c:639 + msgid "Requires a keyboard" + msgstr "Vyžaduje klávesnici" + +-#: src/gs-app-context-bar.c:607 ++#: src/gs-app-context-bar.c:610 + msgid "Requires a mouse" + msgstr "Vyžaduje myš" + +-#: src/gs-app-context-bar.c:618 ++#: src/gs-app-context-bar.c:621 + msgid "Gamepad Needed" + msgstr "Vyžaduje herní ovladač" + +-#: src/gs-app-context-bar.c:619 ++#: src/gs-app-context-bar.c:622 + msgid "Requires a gamepad to play" + msgstr "Ke hraní vyžaduje herní ovladač" + + #. Translators: This is used in a context tile to indicate that + #. * an app works on phones, tablets *and* desktops. It should be + #. * short and in title case. +-#: src/gs-app-context-bar.c:643 ++#: src/gs-app-context-bar.c:646 + msgid "Adaptive" + msgstr "Adaptivní" + +-#: src/gs-app-context-bar.c:644 ++#: src/gs-app-context-bar.c:647 + msgid "Works on phones, tablets and desktops" + msgstr "Funguje na telefonech, tabletech a PC" + +-#: src/gs-app-context-bar.c:657 ++#: src/gs-app-context-bar.c:660 + msgid "Probably requires a keyboard or mouse" + msgstr "Pravděpodobně vyžaduje klávesnici nebo myš" + +-#: src/gs-app-context-bar.c:662 ++#: src/gs-app-context-bar.c:665 + msgid "Works on desktops and laptops" + msgstr "Funguje na PC a laptopech" + + #. Translators: This indicates that the content rating for an + #. * app says it can be used by all ages of people, as it contains + #. * no objectionable content. +-#: src/gs-app-context-bar.c:705 ++#: src/gs-app-context-bar.c:706 + msgid "Contains no age-inappropriate content" + msgstr "Neobsahuje žádný věkově nevhodný obsah" + +-#: src/gs-app-context-bar.c:753 ++#: src/gs-app-context-bar.c:754 + msgid "No age rating information available" + msgstr "Informace o věkové kategorii nejsou k dispozici" + + #. TRANSLATORS: this is a button next to the search results that +-#. * allows the application to be easily installed +-#: src/gs-app-row.c:155 ++#. * allows the app to be easily installed ++#: src/gs-app-row.c:154 + msgid "Visit Website" + msgstr "Navštívit webové stránky" + + #. TRANSLATORS: this is a button next to the search results that +-#. * allows the application to be easily installed. ++#. * allows the app to be easily installed. + #. * The ellipsis indicates that further steps are required +-#: src/gs-app-row.c:161 ++#: src/gs-app-row.c:160 + msgid "Install…" + msgstr "Instalovat…" + + #. TRANSLATORS: this is a button next to the search results that +-#. * allows to cancel a queued install of the application +-#: src/gs-app-row.c:169 src/gs-updates-section.ui:62 ++#. * allows to cancel a queued install of the app ++#: src/gs-app-row.c:168 src/gs-updates-section.ui:63 + msgid "Cancel" + msgstr "Zrušit" + + #. TRANSLATORS: this is a button next to the search results that +-#. * allows the application to be easily installed +-#. TRANSLATORS: button text +-#. TRANSLATORS: update the fw +-#: src/gs-app-row.c:177 src/gs-common.c:307 src/gs-page.c:374 ++#. * allows the app to be easily installed ++#: src/gs-app-row.c:176 + msgid "Install" + msgstr "Instalovat" + + #. TRANSLATORS: this is a button in the updates panel + #. * that allows the app to be easily updated live +-#: src/gs-app-row.c:185 ++#: src/gs-app-row.c:184 + msgid "Update" + msgstr "Aktualizovat" + + #. TRANSLATORS: this is a button next to the search results that +-#. * allows the application to be easily removed +-#. TRANSLATORS: button text in the header when an application can be erased +-#. TRANSLATORS: this is button text to remove the application +-#: src/gs-app-row.c:191 src/gs-app-row.c:201 src/gs-details-page.ui:280 +-#: src/gs-details-page.ui:290 src/gs-page.c:549 +-msgid "Uninstall" +-msgstr "Odinstalovat" ++#. * allows the app to be easily removed ++#: src/gs-app-row.c:190 src/gs-app-row.c:200 ++msgid "Uninstall…" ++msgstr "Odinstalovat…" + + #. TRANSLATORS: this is a button next to the search results that +-#. * shows the status of an application being erased +-#: src/gs-app-row.c:215 ++#. * shows the status of an app being erased ++#: src/gs-app-row.c:214 + msgid "Uninstalling" + msgstr "Odinstalovává se" + + #. TRANSLATORS: during the update the device + #. * will restart into a special update-only mode +-#: src/gs-app-row.c:330 ++#: src/gs-app-row.c:327 + msgid "Device cannot be used during update." + msgstr "Zařízení nelze během aktualizace používat." + + #. TRANSLATORS: this refers to where the app came from +-#: src/gs-app-row.c:340 src/gs-shell-search-provider.c:264 ++#: src/gs-app-row.c:337 src/gs-shell-search-provider.c:268 + #, c-format + msgid "Source: %s" + msgstr "Zdroj: %s" + + #. Translators: A message to indicate that an app has been renamed. The placeholder is the old human-readable name. +-#: src/gs-app-row.c:530 ++#: src/gs-app-row.c:522 + #, c-format + msgid "Renamed from %s" + msgstr "Přejmenováno z %s" + +-#. Translators: The placeholder is an application name ++#: src/gs-app-row.ui:197 src/gs-app-tile.ui:50 src/gs-feature-tile.c:543 ++msgctxt "Single app" ++msgid "Installed" ++msgstr "Nainstalováno" ++ ++#. Translators: The placeholder is an app name + #: src/gs-app-translation-dialog.c:67 + #, c-format + msgid "Help Translate %s" + msgstr "Pomozte přeložit %s" + +-#. Translators: The placeholder is an application name ++#. Translators: The placeholder is an app name + #: src/gs-app-translation-dialog.c:70 + #, c-format + msgid "" +@@ -1451,7 +1473,7 @@ msgstr "" + "dobrovolníků.\n" + "\n" + "To znamená, že i když ještě není k dispozici ve vašem jazyce, můžete se " +-"zapojit a pomoci s jeho překladem." ++"zapojit a pomoci s jejím překladem." + + #: src/gs-app-translation-dialog.ui:5 + msgid "Translations" +@@ -1467,29 +1489,35 @@ msgstr "_Stránka překladu" + msgid "Login required remote %s (realm %s)" + msgstr "Vyžadováno přihlášení vzdáleným %s (sféra %s)" + +-#: src/gs-basic-auth-dialog.ui:13 ++#: src/gs-basic-auth-dialog.ui:6 + msgid "Login Required" + msgstr "Vyžadováno přihlášení" + +-#: src/gs-basic-auth-dialog.ui:21 src/gs-common.c:721 +-#: src/gs-details-page.ui:306 src/gs-removal-dialog.ui:28 +-#: src/gs-review-dialog.ui:18 ++#. TRANSLATORS: button text ++#: src/gs-basic-auth-dialog.ui:12 src/gs-common.c:296 src/gs-common.c:697 ++#: src/gs-details-page.ui:297 src/gs-page.c:410 src/gs-page.c:549 ++#: src/gs-removal-dialog.ui:28 src/gs-repos-dialog.c:171 ++#: src/gs-repos-dialog.c:249 src/gs-review-dialog.ui:18 src/gs-review-row.c:237 ++#: src/gs-updates-page.c:847 src/gs-updates-page.c:864 + msgid "_Cancel" + msgstr "_Zrušit" + +-#: src/gs-basic-auth-dialog.ui:35 ++#: src/gs-basic-auth-dialog.ui:24 + msgid "_Login" + msgstr "Přih_lásit" + +-#: src/gs-basic-auth-dialog.ui:88 +-msgid "_User" +-msgstr "_Uživatel" ++#. Translators: Placeholder text for a login entry. ++#. Translators: It's an origin scope, 'User' or 'System' installation ++#: src/gs-basic-auth-dialog.ui:60 src/gs-origin-popover-row.ui:138 ++msgid "User" ++msgstr "Uživatel" + +-#: src/gs-basic-auth-dialog.ui:107 +-msgid "_Password" +-msgstr "_Heslo" ++#. Translators: Placeholder text for a login entry. ++#: src/gs-basic-auth-dialog.ui:73 ++msgid "Password" ++msgstr "Heslo" + +-#. TRANSLATORS: this is where all applications that don't ++#. TRANSLATORS: this is where all apps that don't + #. * fit in other groups are put + #: lib/gs-category.c:209 + msgid "Other" +@@ -1509,13 +1537,13 @@ msgstr "Významné" + + #. Heading for featured apps on a category page + #. Translators: This is a heading for software which has been featured ('picked') by the distribution. +-#: src/gs-category-page.ui:41 src/gs-overview-page.ui:106 ++#: src/gs-category-page.ui:41 src/gs-overview-page.ui:69 + msgid "Editor’s Choice" + msgstr "Výběr od distribuce" + + #. Heading for recently updated apps on a category page + #. Translators: This is a heading for software which has been recently released upstream. +-#: src/gs-category-page.ui:69 src/gs-overview-page.ui:129 ++#: src/gs-category-page.ui:69 src/gs-overview-page.ui:92 + msgid "New & Updated" + msgstr "Nové a aktualizované" + +@@ -1530,14 +1558,14 @@ msgid "Other Software" + msgstr "Ostatní" + + #. TRANSLATORS: the user isn't reading the question +-#: lib/gs-cmd.c:194 ++#: lib/gs-cmd.c:195 + #, c-format + msgid "Please enter a number from 1 to %u: " + msgstr "Zadejte prosím číslo od 1 do %u: " + + #. TRANSLATORS: asking the user to choose an app from a list +-#: lib/gs-cmd.c:266 +-msgid "Choose an application:" ++#: lib/gs-cmd.c:283 ++msgid "Choose an app:" + msgstr "Vyberte aplikaci:" + + #: lib/gs-desktop-data.c:16 +@@ -1910,7 +1938,7 @@ msgstr "Jazykové balíčky" + msgid "Localization" + msgstr "Lokalizace" + +-#. TRANSLATORS: this is the summary of a notification that an application ++#. TRANSLATORS: this is the summary of a notification that an app + #. * has been successfully installed + #. TRANSLATORS: this is the summary of a notification that a component + #. * has been successfully installed +@@ -1919,16 +1947,16 @@ msgstr "Lokalizace" + msgid "%s is now installed" + msgstr "Aplikace %s je nyní nainstalována" + +-#. TRANSLATORS: an application has been installed, but ++#. TRANSLATORS: an app has been installed, but + #. * needs a reboot to complete the installation + #: src/gs-common.c:73 src/gs-common.c:96 + msgid "A restart is required for the changes to take effect." + msgstr "Aby se změny projevily, je zapotřebí provést restart." + +-#. TRANSLATORS: this is the body of a notification that an application ++#. TRANSLATORS: this is the body of a notification that an app + #. * has been successfully installed + #: src/gs-common.c:77 +-msgid "Application is ready to be used." ++msgid "App is ready to be used." + msgstr "Aplikace je připravená k použití." + + #. TRANSLATORS: this is the summary of a notification that OS updates +@@ -1944,7 +1972,7 @@ msgid "Recently installed updates are available to review" + msgstr "Nedávno nainstalované aktualizace jsou k dispozici pro recenze" + + #. TRANSLATORS: button text +-#: src/gs-common.c:107 src/gs-common.c:884 ++#: src/gs-common.c:107 src/gs-common.c:860 + msgid "Restart" + msgstr "Restartovat" + +@@ -1953,97 +1981,98 @@ msgid "Launch" + msgstr "Spustit" + + #. TRANSLATORS: window title +-#: src/gs-common.c:234 +-#, fuzzy +-#| msgid "Install Unsigned Software?" ++#: src/gs-common.c:230 + msgid "Install Software?" +-msgstr "Nainstalovat nepodepsaný software?" ++msgstr "Nainstalovat software?" + + #. TRANSLATORS: window title +-#: src/gs-common.c:236 ++#: src/gs-common.c:232 + msgid "Install Third-Party Software?" + msgstr "Instalovat software třetí strany?" + + #. TRANSLATORS: window title +-#: src/gs-common.c:241 +-#, fuzzy +-#| msgid "Enable Third-Party Software Repository?" ++#: src/gs-common.c:236 + msgid "Enable Software Repository?" +-msgstr "Povolit repozitář softwaru třetí strany?" ++msgstr "Povolit repozitář softwaru?" + + #. TRANSLATORS: window title +-#: src/gs-common.c:243 src/gs-repos-dialog.c:168 ++#: src/gs-common.c:238 src/gs-repos-dialog.c:168 + msgid "Enable Third-Party Software Repository?" + msgstr "Povolit repozitář softwaru třetí strany?" + + #. TRANSLATORS: the replacements are as follows: +-#. * 1. Application name, e.g. "Firefox" ++#. * 1. App name, e.g. "Firefox" + #. * 2. Software repository name, e.g. fedora-optional + #. +-#: src/gs-common.c:261 ++#: src/gs-common.c:250 + #, c-format + msgid "" + "%s is not free and open source software, and is provided by “%s”." + msgstr "" +-"%s není svobodný a otevřený software a poskytuje jej „%s“." ++"%s není svobodný a otevřený software a poskytuje jej „%s“." + + #. TRANSLATORS: the replacements are as follows: +-#. * 1. Application name, e.g. "Firefox" ++#. * 1. App name, e.g. "Firefox" + #. * 2. Software repository name, e.g. fedora-optional +-#: src/gs-common.c:271 ++#: src/gs-common.c:260 + #, c-format + msgid "%s is provided by “%s”." + msgstr "%s poskytuje „%s“." + +-#: src/gs-common.c:280 ++#: src/gs-common.c:269 + msgid "This software repository must be enabled to continue installation." + msgstr "" + "Aby bylo možné pokračovat v instalaci, je nutné povolit tento repozitář " + "softwaru." + + #. TRANSLATORS: Laws are geographical, urgh... +-#: src/gs-common.c:290 ++#: src/gs-common.c:279 + #, c-format + msgid "It may be illegal to install or use %s in some countries." + msgstr "" + "V některých zemích nemusí být instalace a používání softwaru %s legální." + + #. TRANSLATORS: Laws are geographical, urgh... +-#: src/gs-common.c:296 ++#: src/gs-common.c:285 + msgid "It may be illegal to install or use this codec in some countries." + msgstr "" + "V některých zemích nemusí být instalace a používání tohoto kodeku legální." + + #. TRANSLATORS: this is button text to not ask about non-free content again +-#: src/gs-common.c:303 +-msgid "Don’t Warn Again" +-msgstr "Příště nevarovat" ++#: src/gs-common.c:299 ++msgid "Don’t _Warn Again" ++msgstr "Příště _nevarovat" + + #. TRANSLATORS: button text +-#: src/gs-common.c:312 +-msgid "Enable and Install" +-msgstr "Povolit a nainstalovat" ++#: src/gs-common.c:308 ++msgid "Enable and _Install" ++msgstr "Povolit a na_instalovat" + + #. TRANSLATORS: these are show_detailed_error messages from the + #. * package manager no mortal is supposed to understand, + #. * but google might know what they mean +-#: src/gs-common.c:514 ++#: src/gs-common.c:511 + msgid "Detailed errors from the package manager follow:" + msgstr "Dále jsou uvedeny podrobnosti o chybě získané od správy balíčků:" + +-#: src/gs-common.c:530 src/gs-safety-context-dialog.ui:72 ++#: src/gs-common.c:518 src/gs-safety-context-dialog.ui:72 + msgid "Details" + msgstr "Podrobnosti" + ++#. TRANSLATORS: button text ++#: src/gs-common.c:567 ++msgid "_Close" ++msgstr "_Zavřít" ++ + #. Translators: an accept button label, in a Cancel/Accept dialog +-#: src/gs-common.c:709 ++#: src/gs-common.c:689 + msgid "_Accept" + msgstr "_Přijmout" + + #. TRANSLATORS: we've just live-updated some apps +-#: src/gs-common.c:859 ++#: src/gs-common.c:835 + msgid "An update has been installed" + msgid_plural "Updates have been installed" + msgstr[0] "Aktualizace byla nainstalována" +@@ -2051,15 +2080,15 @@ msgstr[1] "Aktualizace byly nainstalovány" + msgstr[2] "Aktualizace byly nainstalovány" + + #. TRANSLATORS: we've just removed some apps +-#: src/gs-common.c:869 +-msgid "An application has been removed" +-msgid_plural "Applications have been removed" ++#: src/gs-common.c:845 ++msgid "An app has been removed" ++msgid_plural "Apps have been removed" + msgstr[0] "Aplikace byla odebrána" + msgstr[1] "Aplikace byly odebrány" + msgstr[2] "Aplikace byly odebrány" + + #. TRANSLATORS: the new apps will not be run until we restart +-#: src/gs-common.c:875 ++#: src/gs-common.c:851 + msgid "A restart is required for it to take effect." + msgid_plural "A restart is required for them to take effect." + msgstr[0] "Aby se projevila, je zapotřebí provést restart." +@@ -2067,16 +2096,16 @@ msgstr[1] "Aby se projevily, je zapotřebí provést restart." + msgstr[2] "Aby se projevily, je zapotřebí provést restart." + + #. TRANSLATORS: button text +-#: src/gs-common.c:882 ++#: src/gs-common.c:858 + msgid "Not Now" + msgstr "Nyní ne" + + #. TRANSLATORS: something happened less than 5 minutes ago +-#: src/gs-common.c:978 ++#: src/gs-common.c:954 + msgid "Just now" + msgstr "právě teď" + +-#: src/gs-common.c:980 ++#: src/gs-common.c:956 + #, c-format + msgid "%d minute ago" + msgid_plural "%d minutes ago" +@@ -2084,7 +2113,7 @@ msgstr[0] "před %d minutou" + msgstr[1] "před %d minutami" + msgstr[2] "před %d minutami" + +-#: src/gs-common.c:984 ++#: src/gs-common.c:960 + #, c-format + msgid "%d hour ago" + msgid_plural "%d hours ago" +@@ -2092,7 +2121,7 @@ msgstr[0] "před %d hodinou" + msgstr[1] "před %d hodinami" + msgstr[2] "před %d hodinami" + +-#: src/gs-common.c:988 ++#: src/gs-common.c:964 + #, c-format + msgid "%d day ago" + msgid_plural "%d days ago" +@@ -2100,7 +2129,7 @@ msgstr[0] "před %d dnem" + msgstr[1] "před %d dny" + msgstr[2] "před %d dny" + +-#: src/gs-common.c:992 ++#: src/gs-common.c:968 + #, c-format + msgid "%d week ago" + msgid_plural "%d weeks ago" +@@ -2108,7 +2137,7 @@ msgstr[0] "před %d týdnem" + msgstr[1] "před %d týdny" + msgstr[2] "před %d týdny" + +-#: src/gs-common.c:996 ++#: src/gs-common.c:972 + #, c-format + msgid "%d month ago" + msgid_plural "%d months ago" +@@ -2116,7 +2145,7 @@ msgstr[0] "před %d měsícem" + msgstr[1] "před %d měsíci" + msgstr[2] "před %d měsíci" + +-#: src/gs-common.c:1000 ++#: src/gs-common.c:976 + #, c-format + msgid "%d year ago" + msgid_plural "%d years ago" +@@ -2128,7 +2157,7 @@ msgstr[2] "před %d lety" + #. * the unit is drawn with a smaller font. If you need to flip the order, then you can use "%2$s %1$s". + #. * Make sure you'll preserve the no break space between the values. + #. * Example result: "13.0 MB" +-#: src/gs-common.c:1364 ++#: src/gs-common.c:1340 + #, c-format + msgctxt "format-size" + msgid "%s %s" +@@ -2136,7 +2165,7 @@ msgstr "%s %s" + + #. TRANSLATORS: this is a what we use in notifications if the app's name is unknown + #: src/gs-dbus-helper.c:291 +-msgid "An application" ++msgid "An app" + msgstr "Nějaká aplikace" + + #. TRANSLATORS: this is a notification displayed when an app needs additional MIME types. +@@ -2199,58 +2228,49 @@ msgstr "Požadavek na dodatečné balíčky" + msgid "Find in Software" + msgstr "Najít v aplikaci Software" + +-#: src/gs-description-box.c:67 src/gs-description-box.c:269 ++#: src/gs-description-box.c:87 src/gs-description-box.c:335 + msgid "_Show More" + msgstr "Zobrazit _více" + +-#: src/gs-description-box.c:67 ++#: src/gs-description-box.c:87 + msgid "_Show Less" + msgstr "Zobrazit _méně" + +-#: src/gs-details-page.c:357 ++#: src/gs-details-page.c:367 + msgid "Removing…" + msgstr "Odebírá se…" + +-#: src/gs-details-page.c:367 ++#: src/gs-details-page.c:377 + msgid "Requires restart to finish install" + msgstr "Vyžaduje restart k dokončení instalace" + +-#: src/gs-details-page.c:374 ++#: src/gs-details-page.c:384 + msgid "Requires restart to finish remove" + msgstr "Vyžaduje restart k dokončení odebírání" + + #. TRANSLATORS: This is a label on top of the app's progress + #. * bar to inform the user that the app should be installed soon +-#: src/gs-details-page.c:391 ++#: src/gs-details-page.c:401 + msgid "Pending installation…" + msgstr "Probíhá instalace…" + + #. TRANSLATORS: This is a label on top of the app's progress + #. * bar to inform the user that the app should be updated soon +-#: src/gs-details-page.c:398 ++#: src/gs-details-page.c:407 + msgid "Pending update…" + msgstr "Probíhá aktualizace…" + + #. Translators: This string is shown when preparing to download and install an app. +-#: src/gs-details-page.c:414 ++#: src/gs-details-page.c:421 + msgid "Preparing…" + msgstr "Připravuje se…" + + #. Translators: This string is shown when uninstalling an app. +-#: src/gs-details-page.c:417 ++#: src/gs-details-page.c:424 + msgid "Uninstalling…" + msgstr "Odinstalovává se…" + +-#. TRANSLATORS: button text in the header when an application +-#. * can be installed +-#. TRANSLATORS: button text in the header when firmware +-#. * can be live-installed +-#: src/gs-details-page.c:908 src/gs-details-page.c:934 +-#: src/gs-details-page.ui:229 plugins/packagekit/gs-packagekit-task.c:150 +-msgid "_Install" +-msgstr "_Instalovat" +- +-#: src/gs-details-page.c:924 ++#: src/gs-details-page.c:940 + msgid "_Restart" + msgstr "_Restartovat" + +@@ -2258,22 +2278,40 @@ msgstr "_Restartovat" + #. * be installed. + #. * The ellipsis indicates that further steps are required, + #. * e.g. enabling software repositories or the like +-#: src/gs-details-page.c:948 ++#: src/gs-details-page.c:964 + msgid "_Install…" + msgstr "_Instalovat…" + ++#: src/gs-details-page.c:1031 ++msgid "_Uninstall…" ++msgstr "_Odinstalovat…" ++ ++#. Translators: %s is the user-visible app name ++#: src/gs-details-page.c:1175 ++#, c-format ++msgid "%s will appear in US English" ++msgstr "Aplikace %s se zobrazí v americké angličtině" ++ ++#: src/gs-details-page.c:1181 ++msgid "This app will appear in US English" ++msgstr "Tato aplikace se zobrazí v americké angličtině" ++ ++#: src/gs-details-page.c:1196 src/gs-details-page.ui:59 ++msgid "Help _Translate" ++msgstr "_Pomoci přeložit" ++ + #. Translators: the '%s' is replaced with a developer name or a project group +-#: src/gs-details-page.c:1237 ++#: src/gs-details-page.c:1260 + #, c-format + msgid "Other Apps by %s" + msgstr "Co dalšího nabízí %s" + + #. TRANSLATORS: we need a remote server to process +-#: src/gs-details-page.c:1620 ++#: src/gs-details-page.c:1637 + msgid "You need internet access to write a review" + msgstr "Abyste mohli napsat recenzi, musíte být připojeni k Internetu" + +-#: src/gs-details-page.c:1790 src/gs-details-page.c:1806 ++#: src/gs-details-page.c:1822 src/gs-details-page.c:1838 + #, c-format + msgid "Unable to find “%s”" + msgstr "Nelze najít „%s“" +@@ -2283,74 +2321,61 @@ msgid "Details page" + msgstr "Stránka s podrobnostmi" + + #: src/gs-details-page.ui:39 +-msgid "Loading application details…" ++msgid "Loading app details…" + msgstr "Načítají se podrobnosti o aplikaci…" + +-#: src/gs-details-page.ui:77 +-msgid "" +-"This software is not available in your language and will appear in US " +-"English." +-msgstr "" +-"Tento software není dostupný ve vašem jazyce a zobrazí se v americké " +-"angličtině." +- +-#: src/gs-details-page.ui:83 +-msgid "Help _Translate" +-msgstr "_Pomoci přeložit" +- +-#. TRANSLATORS: A label for a button to execute the selected application. +-#: src/gs-details-page.ui:246 ++#. TRANSLATORS: A label for a button to execute the selected app. ++#: src/gs-details-page.ui:226 + msgid "_Open" + msgstr "_Otevřít" + +-#: src/gs-details-page.ui:262 plugins/packagekit/gs-packagekit-task.c:160 ++#: src/gs-details-page.ui:242 plugins/packagekit/gs-packagekit-task.c:159 + msgid "_Update" + msgstr "_Aktualizovat" + +-#: src/gs-details-page.ui:331 ++#. TRANSLATORS: button text in the header when an app can be erased ++#: src/gs-details-page.ui:260 src/gs-details-page.ui:270 ++msgid "Uninstall" ++msgstr "Odinstalovat" ++ ++#: src/gs-details-page.ui:322 + msgid "Downloading" + msgstr "Stahuje se" + +-#: src/gs-details-page.ui:468 src/gs-installed-page.ui:135 ++#: src/gs-details-page.ui:459 src/gs-installed-page.ui:135 + msgid "Add-ons" + msgstr "Doplňky" + +-#: src/gs-details-page.ui:479 +-msgid "Selected add-ons will be installed with the application." +-msgstr "Vybrané doplňky budou nainstalovány spolu s aplikací." +- +-#: src/gs-details-page.ui:579 +-msgid "" +-"This application can only be used when there is an active internet " +-"connection." ++#: src/gs-details-page.ui:563 ++msgid "This app can only be used when there is an active internet connection." + msgstr "" + "Tuto aplikaci je možné používat, jen když je funkční připojení k Internetu." + +-#: src/gs-details-page.ui:599 ++#: src/gs-details-page.ui:586 + msgid "Software Repository Included" + msgstr "Součástí je repozitář softwaru" + +-#: src/gs-details-page.ui:600 ++#: src/gs-details-page.ui:596 + msgid "" +-"This application includes a software repository which provides updates, as " +-"well as access to other software." ++"This app includes a software repository which provides updates, as well as " ++"access to other software." + msgstr "" + "Součástí této aplikace je repozitář softwaru, který poskytuje aktualizace a " + "přístup k dalšímu softwaru." + +-#: src/gs-details-page.ui:617 ++#: src/gs-details-page.ui:624 + msgid "No Software Repository Included" + msgstr "Součástí není žádný repozitář softwaru" + +-#: src/gs-details-page.ui:618 ++#: src/gs-details-page.ui:634 + msgid "" +-"This application does not include a software repository. It will not be " +-"updated with new versions." ++"This app does not include a software repository. It will not be updated with " ++"new versions." + msgstr "" + "Součástí této aplikace není žádný repozitář softwaru. Nebude tak průběžně " + "aktualizována na novější verze." + +-#: src/gs-details-page.ui:636 ++#: src/gs-details-page.ui:662 + msgid "" + "This software is already provided by your distribution and should not be " + "replaced." +@@ -2358,11 +2383,11 @@ msgstr "" + "Tento software již poskytuje vaše distribuce a neměli byste jej nahrazovat." + + #. Translators: a repository file used for installing software has been discovered. +-#: src/gs-details-page.ui:653 ++#: src/gs-details-page.ui:693 + msgid "Software Repository Identified" + msgstr "Rozpoznán repozitář softwaru" + +-#: src/gs-details-page.ui:654 ++#: src/gs-details-page.ui:703 + msgid "" + "Adding this software repository will give you access to additional software " + "and upgrades." +@@ -2370,15 +2395,15 @@ msgstr "" + "Přídáním tohoto repozitáře softwaru získáte přístup k dalšímu softwaru a " + "aktualizacím." + +-#: src/gs-details-page.ui:655 ++#: src/gs-details-page.ui:710 + msgid "Only use software repositories that you trust." + msgstr "Používejte pouze repozitáře softwaru, kterým věříte." + +-#: src/gs-details-page.ui:720 ++#: src/gs-details-page.ui:783 + msgid "No Metadata" + msgstr "Žádná metadata" + +-#: src/gs-details-page.ui:729 ++#: src/gs-details-page.ui:792 + msgid "" + "This software doesn’t provide any links to a website, code repository or " + "issue tracker." +@@ -2386,33 +2411,33 @@ msgstr "" + "Tento software neposkytuje žádné odkazy na webové stránky, repozitáře kódu " + "ani nástroj pro sledování problémů." + +-#: src/gs-details-page.ui:757 ++#: src/gs-details-page.ui:820 + msgid "Project _Website" + msgstr "_Webové stránky projektu" + +-#: src/gs-details-page.ui:774 ++#: src/gs-details-page.ui:837 + msgid "_Donate" + msgstr "Věnovat _dar" + +-#: src/gs-details-page.ui:791 ++#: src/gs-details-page.ui:854 + msgid "Contribute _Translations" + msgstr "_Přispět k překladu" + +-#: src/gs-details-page.ui:808 ++#: src/gs-details-page.ui:871 + msgid "_Report an Issue" + msgstr "_Nahlásit chybu" + +-#: src/gs-details-page.ui:825 ++#: src/gs-details-page.ui:888 + msgid "_Help" + msgstr "_Nápověda" + + #. Translators: Button opening a dialog where the users can write and publish their opinions about the apps. +-#: src/gs-details-page.ui:919 +-msgid "_Write Review" ++#: src/gs-details-page.ui:982 ++msgid "Write R_eview" + msgstr "Nap_sat recenzi" + + #. Translators: Button opening a dialog showing all reviews for an app. +-#: src/gs-details-page.ui:956 ++#: src/gs-details-page.ui:1019 + msgid "All Reviews" + msgstr "Všechny recenze" + +@@ -2431,7 +2456,7 @@ msgstr " a " + msgid ", " + msgstr ", " + +-#. TRANSLATORS: Application window title for fonts installation. ++#. TRANSLATORS: App window title for fonts installation. + #. %s will be replaced by name of the script we're searching for. + #: src/gs-extras-page.c:171 + #, c-format +@@ -2441,7 +2466,7 @@ msgstr[0] "Dostupné fonty pro písmo %s" + msgstr[1] "Dostupné fonty pro písma %s" + msgstr[2] "Dostupné fonty pro písma %s" + +-#. TRANSLATORS: Application window title for codec installation. ++#. TRANSLATORS: App window title for codec installation. + #. %s will be replaced by actual codec name(s) + #: src/gs-extras-page.c:179 + #, c-format +@@ -2470,11 +2495,11 @@ msgstr "%s nebyl nalezen" + msgid "on the website" + msgstr "na webových stránkách" + +-#. TRANSLATORS: this is when we know about an application or ++#. TRANSLATORS: this is when we know about an app or + #. * addon, but it can't be listed for some reason + #: src/gs-extras-page.c:354 + #, c-format +-msgid "No applications are available that provide the file %s." ++msgid "No apps are available that provide the file %s." + msgstr "Nejsou k dispozici žádné aplikace, které by poskytovaly soubor %s." + + #. TRANSLATORS: first %s is the codec name, and second %s is a +@@ -2482,20 +2507,20 @@ msgstr "Nejsou k dispozici žádné aplikace, které by poskytovaly soubor %s." + #: src/gs-extras-page.c:358 src/gs-extras-page.c:369 src/gs-extras-page.c:380 + #, c-format + msgid "" +-"Information about %s, as well as options for how to get missing applications " +-"might be found %s." ++"Information about %s, as well as options for how to get missing apps might " ++"be found %s." + msgstr "" + "Informace o formátu %s, včetně toho, jak získat chybějící aplikace, najdete " + "%s." + +-#. TRANSLATORS: this is when we know about an application or ++#. TRANSLATORS: this is when we know about an app or + #. * addon, but it can't be listed for some reason + #: src/gs-extras-page.c:365 src/gs-extras-page.c:387 + #, c-format +-msgid "No applications are available for %s support." ++msgid "No apps are available for %s support." + msgstr "Pro podporu %s nejsou k dispozici žádné aplikace." + +-#. TRANSLATORS: this is when we know about an application or ++#. TRANSLATORS: this is when we know about an app or + #. * addon, but it can't be listed for some reason + #: src/gs-extras-page.c:376 + #, c-format +@@ -2507,13 +2532,13 @@ msgstr "%s není k dispozici." + #: src/gs-extras-page.c:391 + #, c-format + msgid "" +-"Information about %s, as well as options for how to get an application that " +-"can support this format might be found %s." ++"Information about %s, as well as options for how to get an app that can " ++"support this format might be found %s." + msgstr "" +-"Informace o formátu %s, včetně toho, jak získat aplikaci, který umí tento " +-"tento formát podporovat, najdete %s." ++"Informace o formátu %s, včetně toho, jak získat aplikaci, který tento tento " ++"formát podporuje, najdete %s." + +-#. TRANSLATORS: this is when we know about an application or ++#. TRANSLATORS: this is when we know about an app or + #. * addon, but it can't be listed for some reason + #: src/gs-extras-page.c:398 + #, c-format +@@ -2530,7 +2555,7 @@ msgid "" + msgstr "" + "Informace o písmu %s, včetně toho, jak získat dodatečná písma, najdete %s." + +-#. TRANSLATORS: this is when we know about an application or ++#. TRANSLATORS: this is when we know about an app or + #. * addon, but it can't be listed for some reason + #: src/gs-extras-page.c:409 + #, c-format +@@ -2548,7 +2573,7 @@ msgstr "" + "Informace o kodeku %s, včetně toho, jak získat kodek, který umí tento formát " + "přehrát, najdete %s." + +-#. TRANSLATORS: this is when we know about an application or ++#. TRANSLATORS: this is when we know about an app or + #. * addon, but it can't be listed for some reason + #: src/gs-extras-page.c:420 + #, c-format +@@ -2566,7 +2591,7 @@ msgstr "" + "Informace o kodeku %s, včetně toho, jak získat dodatečné prostředky Plasma, " + "najdete %s." + +-#. TRANSLATORS: this is when we know about an application or ++#. TRANSLATORS: this is when we know about an app or + #. * addon, but it can't be listed for some reason + #: src/gs-extras-page.c:431 + #, c-format +@@ -2590,7 +2615,7 @@ msgid "the documentation" + msgstr "dokumentace" + + #. TRANSLATORS: no codecs were found. The first %s will be replaced by actual codec name(s), +-#. the second %s is the application name, which requested the codecs, the third %s is a link titled "the documentation" ++#. the second %s is the app name, which requested the codecs, the third %s is a link titled "the documentation" + #: src/gs-extras-page.c:487 + #, c-format + msgid "" +@@ -2631,12 +2656,12 @@ msgstr[2] "" + msgid "Failed to find any search results: %s" + msgstr "Selhalo získání jakýchkoliv výsledků hledání: %s" + +-#: src/gs-extras-page.c:874 ++#: src/gs-extras-page.c:878 + #, c-format + msgid "%s file format" + msgstr "formát souboru %s" + +-#: src/gs-extras-page.c:1254 ++#: src/gs-extras-page.c:1258 + msgid "Unable to Find Requested Software" + msgstr "Nelze najít požadovaný software" + +@@ -2656,206 +2681,206 @@ msgstr "Další" + msgid "Featured Apps List" + msgstr "Seznam významných aplikací" + +-#: src/gs-hardware-support-context-dialog.c:577 +-#: src/gs-hardware-support-context-dialog.c:586 ++#: src/gs-hardware-support-context-dialog.c:576 ++#: src/gs-hardware-support-context-dialog.c:585 + msgid "Desktop Support" + msgstr "Podpora pro PC" + +-#: src/gs-hardware-support-context-dialog.c:578 +-#: src/gs-hardware-support-context-dialog.c:587 ++#: src/gs-hardware-support-context-dialog.c:577 ++#: src/gs-hardware-support-context-dialog.c:586 + msgid "Supports being used on a large screen" + msgstr "Podporuje použití na velké obrazovce" + +-#: src/gs-hardware-support-context-dialog.c:580 ++#: src/gs-hardware-support-context-dialog.c:579 + msgid "Desktop Support Unknown" + msgstr "Neznámá podpora pro PC" + +-#: src/gs-hardware-support-context-dialog.c:581 ++#: src/gs-hardware-support-context-dialog.c:580 + msgid "Not enough information to know if large screens are supported" + msgstr "" + "Není dostatek informací, abychom věděli, zda jsou podporovány velké obrazovky" + +-#: src/gs-hardware-support-context-dialog.c:584 ++#: src/gs-hardware-support-context-dialog.c:583 + msgid "Requires a large screen" + msgstr "Vyžaduje velkou obrazovku" + +-#: src/gs-hardware-support-context-dialog.c:589 ++#: src/gs-hardware-support-context-dialog.c:588 + msgid "Desktop Not Supported" + msgstr "Nepodporuje stolní počítače" + +-#: src/gs-hardware-support-context-dialog.c:590 ++#: src/gs-hardware-support-context-dialog.c:589 + msgid "Cannot be used on a large screen" + msgstr "Nelze použít na velké obrazovce" + +-#: src/gs-hardware-support-context-dialog.c:597 +-#: src/gs-hardware-support-context-dialog.c:606 ++#: src/gs-hardware-support-context-dialog.c:596 ++#: src/gs-hardware-support-context-dialog.c:605 + msgid "Mobile Support" + msgstr "Podpora pro mobilní zařízení" + +-#: src/gs-hardware-support-context-dialog.c:598 +-#: src/gs-hardware-support-context-dialog.c:607 ++#: src/gs-hardware-support-context-dialog.c:597 ++#: src/gs-hardware-support-context-dialog.c:606 + msgid "Supports being used on a small screen" + msgstr "Podporuje použití na malé obrazovce" + +-#: src/gs-hardware-support-context-dialog.c:600 ++#: src/gs-hardware-support-context-dialog.c:599 + msgid "Mobile Support Unknown" + msgstr "Neznámá podpora pro mobilní zařízení" + +-#: src/gs-hardware-support-context-dialog.c:601 ++#: src/gs-hardware-support-context-dialog.c:600 + msgid "Not enough information to know if small screens are supported" + msgstr "" + "Není dostatek informací, abychom věděli, zda jsou podporovány malé obrazovky" + +-#: src/gs-hardware-support-context-dialog.c:604 ++#: src/gs-hardware-support-context-dialog.c:603 + msgid "Requires a small screen" + msgstr "Vyžaduje malou obrazovku" + +-#: src/gs-hardware-support-context-dialog.c:609 ++#: src/gs-hardware-support-context-dialog.c:608 + msgid "Mobile Not Supported" + msgstr "Nepodporuje mobily" + +-#: src/gs-hardware-support-context-dialog.c:610 ++#: src/gs-hardware-support-context-dialog.c:609 + msgid "Cannot be used on a small screen" + msgstr "Nelze použít na malé obrazovce" + +-#: src/gs-hardware-support-context-dialog.c:633 +-#: src/gs-hardware-support-context-dialog.c:642 ++#: src/gs-hardware-support-context-dialog.c:632 ++#: src/gs-hardware-support-context-dialog.c:641 + msgid "Keyboard Support" + msgstr "Podpora klávesnice" + +-#: src/gs-hardware-support-context-dialog.c:636 ++#: src/gs-hardware-support-context-dialog.c:635 + msgid "Keyboard Support Unknown" + msgstr "Neznámá podpora klávesnice" + +-#: src/gs-hardware-support-context-dialog.c:637 ++#: src/gs-hardware-support-context-dialog.c:636 + msgid "Not enough information to know if keyboards are supported" + msgstr "" + "Není dostatek informací, abychom věděli, zda jsou podporovány klávesnice" + +-#: src/gs-hardware-support-context-dialog.c:639 ++#: src/gs-hardware-support-context-dialog.c:638 + msgid "Keyboard Required" + msgstr "Vyžaduje klávesnici" + +-#: src/gs-hardware-support-context-dialog.c:643 ++#: src/gs-hardware-support-context-dialog.c:642 + msgid "Supports keyboards" + msgstr "Podporuje klávesnice" + +-#: src/gs-hardware-support-context-dialog.c:645 ++#: src/gs-hardware-support-context-dialog.c:644 + msgid "Keyboard Not Supported" + msgstr "Nepodporuje klávesnici" + +-#: src/gs-hardware-support-context-dialog.c:646 ++#: src/gs-hardware-support-context-dialog.c:645 + msgid "Cannot be used with a keyboard" + msgstr "Nelze použít s klávesnicí" + +-#: src/gs-hardware-support-context-dialog.c:653 +-#: src/gs-hardware-support-context-dialog.c:662 ++#: src/gs-hardware-support-context-dialog.c:652 ++#: src/gs-hardware-support-context-dialog.c:661 + msgid "Mouse Support" + msgstr "Podpora myši" + +-#: src/gs-hardware-support-context-dialog.c:654 +-#: src/gs-hardware-support-context-dialog.c:660 ++#: src/gs-hardware-support-context-dialog.c:653 ++#: src/gs-hardware-support-context-dialog.c:659 + msgid "Requires a mouse or pointing device" + msgstr "Vyžaduje myš nebo ukazovátko" + +-#: src/gs-hardware-support-context-dialog.c:656 ++#: src/gs-hardware-support-context-dialog.c:655 + msgid "Mouse Support Unknown" + msgstr "Neznámá podpora myši" + +-#: src/gs-hardware-support-context-dialog.c:657 ++#: src/gs-hardware-support-context-dialog.c:656 + msgid "" + "Not enough information to know if mice or pointing devices are supported" + msgstr "" + "Není dostatek informací, abychom věděli, zda jsou podporovány myši nebo " + "ukazovátka" + +-#: src/gs-hardware-support-context-dialog.c:659 ++#: src/gs-hardware-support-context-dialog.c:658 + msgid "Mouse Required" + msgstr "Vyžaduje myš" + +-#: src/gs-hardware-support-context-dialog.c:663 ++#: src/gs-hardware-support-context-dialog.c:662 + msgid "Supports mice and pointing devices" + msgstr "Podporuje myši a ukazovátka" + +-#: src/gs-hardware-support-context-dialog.c:665 ++#: src/gs-hardware-support-context-dialog.c:664 + msgid "Mouse Not Supported" + msgstr "Nepodporuje myš" + +-#: src/gs-hardware-support-context-dialog.c:666 ++#: src/gs-hardware-support-context-dialog.c:665 + msgid "Cannot be used with a mouse or pointing device" + msgstr "Nelze použít s myší nebo ukazovátkem" + +-#: src/gs-hardware-support-context-dialog.c:673 +-#: src/gs-hardware-support-context-dialog.c:682 ++#: src/gs-hardware-support-context-dialog.c:672 ++#: src/gs-hardware-support-context-dialog.c:681 + msgid "Touchscreen Support" + msgstr "Podpora dotykové obrazovky" + +-#: src/gs-hardware-support-context-dialog.c:676 ++#: src/gs-hardware-support-context-dialog.c:675 + msgid "Touchscreen Support Unknown" + msgstr "Neznámá podpora dotykové obrazovky" + +-#: src/gs-hardware-support-context-dialog.c:677 ++#: src/gs-hardware-support-context-dialog.c:676 + msgid "Not enough information to know if touchscreens are supported" + msgstr "" + "Není dostatek informací, abychom věděli, zda jsou podporovány dotykové " + "obrazovky" + +-#: src/gs-hardware-support-context-dialog.c:679 ++#: src/gs-hardware-support-context-dialog.c:678 + msgid "Touchscreen Required" + msgstr "Vyžaduje dotykovou obrazovku" + +-#: src/gs-hardware-support-context-dialog.c:683 ++#: src/gs-hardware-support-context-dialog.c:682 + msgid "Supports touchscreens" + msgstr "Podporuje dotykové obrazovky" + +-#: src/gs-hardware-support-context-dialog.c:685 ++#: src/gs-hardware-support-context-dialog.c:684 + msgid "Touchscreen Not Supported" + msgstr "Nepodporuje dotykovou obrazovku" + +-#: src/gs-hardware-support-context-dialog.c:686 ++#: src/gs-hardware-support-context-dialog.c:685 + msgid "Cannot be used with a touchscreen" + msgstr "Nelze použít s dotykovou obrazovkou" + +-#: src/gs-hardware-support-context-dialog.c:699 ++#: src/gs-hardware-support-context-dialog.c:698 + msgid "Gamepad Required" + msgstr "Vyžadován herní ovladač" + +-#: src/gs-hardware-support-context-dialog.c:700 ++#: src/gs-hardware-support-context-dialog.c:699 + msgid "Requires a gamepad" + msgstr "Vyžaduje herní ovladač" + +-#: src/gs-hardware-support-context-dialog.c:702 ++#: src/gs-hardware-support-context-dialog.c:701 + msgid "Gamepad Support" + msgstr "Podpora herního ovladače" + +-#: src/gs-hardware-support-context-dialog.c:703 ++#: src/gs-hardware-support-context-dialog.c:702 + msgid "Supports gamepads" + msgstr "Podporuje herní ovladače" + + #. Translators: It’s unknown whether this app is supported on + #. * the current hardware. The placeholder is the app name. +-#: src/gs-hardware-support-context-dialog.c:712 ++#: src/gs-hardware-support-context-dialog.c:711 + #, c-format + msgid "%s probably works on this device" + msgstr "Aplikace %s na tomto zařízení pravděpodobně funguje" + + #. Translators: The app will work on the current hardware. + #. * The placeholder is the app name. +-#: src/gs-hardware-support-context-dialog.c:719 ++#: src/gs-hardware-support-context-dialog.c:718 + #, c-format + msgid "%s works on this device" + msgstr "Aplikace %s na tomto zařízení funguje" + + #. Translators: The app may not work fully on the current hardware. + #. * The placeholder is the app name. +-#: src/gs-hardware-support-context-dialog.c:726 ++#: src/gs-hardware-support-context-dialog.c:725 + #, c-format + msgid "%s will not work properly on this device" + msgstr "Aplikace %s na tomto zařízení nebude fungovat správně" + + #. Translators: The app will not work properly on the current hardware. + #. * The placeholder is the app name. +-#: src/gs-hardware-support-context-dialog.c:733 ++#: src/gs-hardware-support-context-dialog.c:732 + #, c-format + msgid "%s will not work on this device" + msgstr "Aplikace %s na tomto zařízení nebude fungovat" +@@ -2866,8 +2891,7 @@ msgid "Hardware Support" + msgstr "Podpora hardwaru" + + #. Translators: This is in the context of a list of apps which are installed on the system. +-#. Translators: A label for a button to show only software which is already installed. +-#: src/gs-installed-page.c:813 src/gs-shell.ui:309 ++#: src/gs-installed-page.c:813 + msgctxt "List of installed apps" + msgid "Installed" + msgstr "Nainstalováno" +@@ -2883,27 +2907,27 @@ msgstr "S probíhající změnou" + #. origin_ui on a remote is the repo dialogue section name, + #. * not the remote title + #: src/gs-installed-page.ui:75 plugins/flatpak/gs-flatpak-utils.c:107 +-msgid "Applications" ++msgid "Apps" + msgstr "Aplikace" + + #: src/gs-installed-page.ui:95 +-msgid "Web Applications" ++msgid "Web Apps" + msgstr "Webové aplikace" + + #: src/gs-installed-page.ui:115 +-msgid "System Applications" ++msgid "System Apps" + msgstr "Systémové aplikace" + +-#: src/gs-license-tile.c:96 ++#: src/gs-license-tile.c:97 + msgid "Community Built" + msgstr "Vybudováno komunitou" + +-#: src/gs-license-tile.c:107 src/gs-license-tile.ui:98 ++#: src/gs-license-tile.c:108 src/gs-license-tile.ui:98 + msgid "_Get Involved" + msgstr "_Zapojit se" + + #. Translators: The first placeholder here is a link to information about the license, and the second placeholder here is the name of a software license. +-#: src/gs-license-tile.c:114 ++#: src/gs-license-tile.c:115 + #, c-format + msgid "" + "This software is developed in the open by a community of volunteers, and " +@@ -2917,7 +2941,7 @@ msgstr "" + "Můžete přispět a pomoci jej ještě vylepšit." + + #. Translators: The placeholder here is the name of a software license. +-#: src/gs-license-tile.c:121 ++#: src/gs-license-tile.c:122 + #, c-format + msgid "" + "This software is developed in the open by a community of volunteers, and " +@@ -2930,15 +2954,15 @@ msgstr "" + "\n" + "Můžete přispět a pomoci jej ještě vylepšit." + +-#: src/gs-license-tile.c:127 ++#: src/gs-license-tile.c:128 + msgid "Proprietary" + msgstr "Uzavřený software" + +-#: src/gs-license-tile.c:133 ++#: src/gs-license-tile.c:134 + msgid "_Learn More" + msgstr "Zjistit _více" + +-#: src/gs-license-tile.c:135 ++#: src/gs-license-tile.c:136 + msgid "" + "This software is not developed in the open, so only its developers know how " + "it works. It may be insecure in ways that are hard to detect, and it may " +@@ -2965,7 +2989,7 @@ msgstr "Načítá se stránka" + msgid "Starting up…" + msgstr "Spouští se…" + +-#: src/gs-metered-data-dialog.ui:5 src/gs-shell.ui:258 ++#: src/gs-metered-data-dialog.ui:5 + msgid "Automatic Updates Paused" + msgstr "Automatické aktualizace jsou pozastaveny" + +@@ -3012,62 +3036,72 @@ msgstr "Neznámý zdroj" + msgid "Beta" + msgstr "Beta" + +-#. Translators: It's an origin scope, 'User' or 'System' installation +-#: src/gs-origin-popover-row.ui:138 +-msgid "User" +-msgstr "Uživatel" +- + #. TRANSLATORS: This is the header for package additions during + #. * a system update +-#: src/gs-os-update-page.c:250 ++#: src/gs-os-update-page.c:249 + msgid "Additions" + msgstr "Přidávání" + + #. TRANSLATORS: This is the header for package removals during + #. * a system update +-#: src/gs-os-update-page.c:254 ++#: src/gs-os-update-page.c:253 + msgid "Removals" + msgstr "Odstraňování" + + #. TRANSLATORS: This is the header for package updates during + #. * a system update +-#: src/gs-os-update-page.c:258 ++#: src/gs-os-update-page.c:257 + msgctxt "Packages to be updated during a system upgrade" + msgid "Updates" + msgstr "Aktualizace" + + #. TRANSLATORS: This is the header for package downgrades during + #. * a system update +-#: src/gs-os-update-page.c:262 ++#: src/gs-os-update-page.c:261 + msgid "Downgrades" + msgstr "Ponižování" + +-#. Translators: This is a clickable link on the third party repositories info bar. It's ++#. Translators: This is a clickable link on the third party repositories message dialog. It's + #. part of a constructed sentence: "Provides access to additional software from [selected external sources]. + #. Some proprietary software is included." +-#: src/gs-overview-page.c:876 ++#: src/gs-overview-page.c:475 + msgid "selected external sources" + msgstr "vybraných externích zdrojů" + +-#. Translators: This is the third party repositories info bar. The %s is replaced with "selected external sources" link. +-#: src/gs-overview-page.c:878 ++#. Translators: This is the third party repositories message dialog. ++#. The %s is replaced with "selected external sources" link. ++#. Repositories Preferences is an item from Software's main menu. ++#: src/gs-overview-page.c:479 + #, c-format + msgid "" + "Provides access to additional software from %s. Some proprietary software is " +-"included." ++"included.\n" ++"\n" ++"You can enable those repositories later in Software Repositories preferences." + msgstr "" + "Poskytuje přístup k dalšímu softwaru z %s. Součástí je i některý uzavřený " +-"software." ++"software.\n" ++"\n" ++"Tyto repozitáře můžete později povolit v předvolbách Softwarových repozitářů." ++ ++#. TRANSLATORS: Heading asking whether to turn third party software repositories on of off. ++#: src/gs-overview-page.c:485 ++msgid "Enable Third Party Software Repositories?" ++msgstr "Povolit repozitáře softwaru třetích stran?" ++ ++#. TRANSLATORS: button to keep the third party software repositories off ++#: src/gs-overview-page.c:490 ++msgid "_Ignore" ++msgstr "_Ignorovat" + + #. TRANSLATORS: button to turn on third party software repositories + #. TRANSLATORS: button to accept the agreement +-#: src/gs-overview-page.c:887 src/gs-repos-dialog.c:173 +-msgid "Enable" +-msgstr "Povolit" ++#: src/gs-overview-page.c:492 src/gs-repos-dialog.c:173 ++msgid "_Enable" ++msgstr "_Povolit" + + #. Translators: This is the title of the main page of the UI. +-#. Translators: A label for a button to show all available software. +-#: src/gs-overview-page.c:946 src/gs-shell.ui:296 ++#: src/gs-overview-page.c:985 + msgid "Explore" + msgstr "Procházet" + +@@ -3075,61 +3109,62 @@ msgstr "Procházet" + msgid "Overview page" + msgstr "Stránka s přehledem" + +-#: src/gs-overview-page.ui:35 +-msgid "Enable Third Party Software Repositories?" +-msgstr "Povolit repozitáře softwaru třetích stran?" +- + #. Translators: This is a heading for a list of categories. +-#: src/gs-overview-page.ui:180 ++#: src/gs-overview-page.ui:143 + msgid "Other Categories" + msgstr "Ostatní kategorie" + +-#: src/gs-overview-page.ui:221 +-msgid "No Application Data Found" ++#: src/gs-overview-page.ui:184 ++msgid "No App Data Found" + msgstr "O aplikaci nebyly nalezeny žádné informace" + +-#: lib/gs-plugin-loader.c:2836 ++#: lib/gs-plugin-loader.c:2771 + msgctxt "Distribution name" + msgid "Unknown" + msgstr "neznámá" + +-#: src/gs-page.c:274 ++#. TRANSLATORS: button text ++#: src/gs-page.c:92 ++msgid "_OK" ++msgstr "_Budiž" ++ ++#: src/gs-page.c:271 + msgid "User declined installation" + msgstr "Uživatel odmítl instalaci" + + #. TRANSLATORS: this is a prompt message, and +-#. * '%s' is an application summary, e.g. 'GNOME Clocks' +-#: src/gs-page.c:365 ++#. * '%s' is an app summary, e.g. 'GNOME Clocks' ++#: src/gs-page.c:404 + #, c-format + msgid "Prepare %s" + msgstr "Příprava aplikace %s" + + #. TRANSLATORS: this is a prompt message, and '%s' is an + #. * repository name, e.g. 'GNOME Nightly' +-#: src/gs-page.c:518 ++#: src/gs-page.c:523 + #, c-format + msgid "Are you sure you want to remove the %s repository?" + msgstr "Opravdu chcete odebrat repozitář %s?" + + #. TRANSLATORS: longer dialog text +-#: src/gs-page.c:522 ++#: src/gs-page.c:527 + #, c-format + msgid "" +-"All applications from %s will be uninstalled, and you will have to re-" +-"install the repository to use them again." ++"All apps from %s will be uninstalled, and you will have to re-install the " ++"repository to use them again." + msgstr "" +-"Všechny aplikace pocházející ze repozitáře %s budou odinstalovány. Abyste je " ++"Všechny aplikace pocházející z repozitáře %s budou odinstalovány. Abyste je " + "mohli znovu použít, budete muset repozitář znovu nainstalovat." + + #. TRANSLATORS: this is a prompt message, and '%s' is an +-#. * application summary, e.g. 'GNOME Clocks' +-#: src/gs-page.c:530 ++#. * app summary, e.g. 'GNOME Clocks' ++#: src/gs-page.c:535 + #, c-format + msgid "Are you sure you want to uninstall %s?" + msgstr "Opravdu chcete odinstalovat %s?" + + #. TRANSLATORS: longer dialog text +-#: src/gs-page.c:533 ++#: src/gs-page.c:538 + #, c-format + msgid "" + "%s will be uninstalled, and you will have to install it to use it again." +@@ -3138,8 +3173,8 @@ msgstr "" + "muset provést novou instalaci." + + #: src/gs-prefs-dialog.ui:5 +-msgid "Update Preferences" +-msgstr "Předvolby aktualizací" ++msgid "Preferences" ++msgstr "Předvolby" + + #: src/gs-prefs-dialog.ui:16 + msgid "" +@@ -3150,65 +3185,69 @@ msgstr "" + "automaticky stahovány na mobilních nebo měřených připojeních." + + #: src/gs-prefs-dialog.ui:19 +-msgid "Automatic Updates" +-msgstr "Automatické aktualizace" ++msgid "Automatic _Updates" ++msgstr "Automatické _aktualizace" + + #: src/gs-prefs-dialog.ui:20 + msgid "" +-"Downloads and installs software updates in the background, when possible." ++"Downloads and installs software updates in the background, when possible" + msgstr "Stahuje a instaluje aktualizace softwaru na pozadí, pokud je to možné." + +-#: src/gs-prefs-dialog.ui:32 +-msgid "Automatic Update Notifications" +-msgstr "Oznamovat automatické aktualizace" +- + #: src/gs-prefs-dialog.ui:33 +-msgid "Show notifications when updates have been automatically installed." ++msgid "Automatic Update _Notifications" ++msgstr "_Oznamovat automatické aktualizace" ++ ++#: src/gs-prefs-dialog.ui:34 ++msgid "Show notifications when updates have been automatically installed" + msgstr "Zobrazovat oznámení, když jsou automaticky nainstalovány aplikace." + ++#: src/gs-prefs-dialog.ui:47 ++msgid "Show Only _Free Apps" ++msgstr "Zobrazit _pouze svobodné aplikace" ++ ++#: src/gs-prefs-dialog.ui:48 ++msgid "Show only freely licensed apps and hide any proprietary apps" ++msgstr "" ++"Zobrazit pouze aplikace se svobodnou licencí a skrýt všechny proprietární " ++"aplikace." ++ + #. TRANSLATORS: This is a text displayed during a distro upgrade. %s + #. will be replaced by the name and version of distro, e.g. 'Fedora 23'. + #: src/gs-removal-dialog.c:96 +-#, fuzzy, c-format +-#| msgid "" +-#| "Some of the currently installed software is not compatible with %s. If " +-#| "you continue, the following will be automatically removed during the " +-#| "upgrade:" ++#, c-format + msgid "" + "Installed software is incompatible with %s, and will be automatically " + "removed during upgrade." + msgstr "" + "Některý z právě instalovaného softwaru není kompatibilní s distribucí %s. " +-"Pokud budete pokračovat, následujíc se během povýšení odstraní:" ++"Pokud budete pokračovat, během povýšení se odstraní." + + #: src/gs-removal-dialog.ui:7 + msgid "Incompatible Software" + msgstr "Nekompatibilní software" + + #: src/gs-removal-dialog.ui:37 +-#, fuzzy +-#| msgid "_Restart & Upgrade" + msgid "_Upgrade" +-msgstr "_Restartovat a aktualizovat" ++msgstr "_Aktualizovat" + + #. TRANSLATORS: The '%s' is replaced with a repository name, like "Fedora Modular - x86_64" +-#: src/gs-repos-dialog.c:239 ++#: src/gs-repos-dialog.c:241 + #, c-format + msgid "" + "Software that has been installed from “%s” will cease to receive updates." + msgstr "" + "Software, který byl nainstalován z „%s“, přestane dostávat aktualizace." + +-#: src/gs-repos-dialog.c:248 ++#: src/gs-repos-dialog.c:246 + msgid "Disable Repository?" + msgstr "Zakázat repozitář?" + +-#: src/gs-repos-dialog.c:248 ++#: src/gs-repos-dialog.c:246 + msgid "Remove Repository?" + msgstr "Odebrat repozitář?" + + #. TRANSLATORS: this is button text to disable a repo +-#: src/gs-repos-dialog.c:254 ++#: src/gs-repos-dialog.c:253 + msgid "_Disable" + msgstr "_Zakázat" + +@@ -3217,41 +3256,41 @@ msgstr "_Zakázat" + msgid "_Remove" + msgstr "_Odebrat" + +-#: src/gs-repos-dialog.c:508 ++#: src/gs-repos-dialog.c:507 + msgid "Enable New Repositories" + msgstr "Povolit nové repozitáře" + +-#: src/gs-repos-dialog.c:509 ++#: src/gs-repos-dialog.c:508 + msgid "Turn on new repositories when they are added." + msgstr "Zapnout nové repozitáře při jejich přidání." + + #. TRANSLATORS: this is the clickable + #. * link on the third party repositories info bar +-#: src/gs-repos-dialog.c:518 ++#: src/gs-repos-dialog.c:517 + msgid "more information" + msgstr "více informací" + + #. TRANSLATORS: this is the third party repositories info bar. The '%s' is replaced + #. with a link consisting a text "more information", which constructs a sentence: + #. "Additional repositories from selected third parties - more information." +-#: src/gs-repos-dialog.c:523 ++#: src/gs-repos-dialog.c:522 + #, c-format + msgid "Additional repositories from selected third parties — %s." + msgstr "Další repozitáře od vybraných třetích stran — %s." + +-#: src/gs-repos-dialog.c:528 ++#: src/gs-repos-dialog.c:527 + msgid "Fedora Third Party Repositories" + msgstr "Repozitáře třetích stran Fedory" + + #. TRANSLATORS: this is the fallback text we use if we can't + #. figure out the name of the operating system +-#: src/gs-repos-dialog.c:670 ++#: src/gs-repos-dialog.c:669 + msgid "the operating system" + msgstr "operačního systému" + + #. TRANSLATORS: This is the description text displayed in the Software Repositories dialog. + #. %s gets replaced by the name of the actual distro, e.g. Fedora. +-#: src/gs-repos-dialog.c:728 ++#: src/gs-repos-dialog.c:727 + #, c-format + msgid "These repositories supplement the default software provided by %s." + msgstr "" +@@ -3259,7 +3298,7 @@ msgstr "" + "%s." + + #. button in the info bar +-#: src/gs-repos-dialog.ui:8 src/gs-shell.ui:88 ++#: src/gs-repos-dialog.ui:8 src/gs-shell.ui:99 + msgid "Software Repositories" + msgstr "Softwarové repozitáře" + +@@ -3267,19 +3306,21 @@ msgstr "Softwarové repozitáře" + msgid "No Repositories" + msgstr "Žádné repozitáře" + +-#. TRANSLATORS: This string is used to construct the 'X applications +-#. installed' sentence, describing a software repository. +-#: src/gs-repo-row.c:160 ++#. TRANSLATORS: This string states how many apps have been ++#. * installed from a particular repo, and is displayed on a row ++#. * describing that repo. The placeholder is the number of apps. ++#: src/gs-repo-row.c:161 + #, c-format +-msgid "%u application installed" +-msgid_plural "%u applications installed" ++msgid "%u app installed" ++msgid_plural "%u apps installed" + msgstr[0] "Nainstalována %u aplikace" + msgstr[1] "Nainstalovány %u aplikace" + msgstr[2] "Nainstalováno %u aplikací" + +-#. TRANSLATORS: This string is used to construct the 'X add-ons +-#. installed' sentence, describing a software repository. +-#: src/gs-repo-row.c:167 ++#. TRANSLATORS: This string states how many add-ons have been ++#. * installed from a particular repo, and is displayed on a row ++#. * describing that repo. The placeholder is the number of add-ons. ++#: src/gs-repo-row.c:169 + #, c-format + msgid "%u add-on installed" + msgid_plural "%u add-ons installed" +@@ -3287,21 +3328,27 @@ msgstr[0] "Nainstalován %u doplněk" + msgstr[1] "Nainstalovány %u doplňky" + msgstr[2] "Nainstalováno %u doplňků" + +-#. TRANSLATORS: This string is used to construct the 'X applications +-#. and y add-ons installed' sentence, describing a software repository. +-#. The correct form here depends on the number of applications. +-#: src/gs-repo-row.c:175 ++#. TRANSLATORS: This string is used to construct the 'X apps ++#. and Y add-ons installed' sentence, stating how many things have been ++#. * installed from a particular repo. It’s displayed on a row describing ++#. * that repo. The placeholder is the number of apps, and the translated ++#. * string will be substituted in for the first placeholder in the ++#. * string “%s and %s installed”. ++#: src/gs-repo-row.c:180 + #, c-format +-msgid "%u application" +-msgid_plural "%u applications" ++msgid "%u app" ++msgid_plural "%u apps" + msgstr[0] "%u aplikace" + msgstr[1] "%u aplikace" + msgstr[2] "%u aplikací" + +-#. TRANSLATORS: This string is used to construct the 'X applications +-#. and y add-ons installed' sentence, describing a software repository. +-#. The correct form here depends on the number of add-ons. +-#: src/gs-repo-row.c:181 ++#. TRANSLATORS: This string is used to construct the 'X apps ++#. and Y add-ons installed' sentence, stating how many things have been ++#. * installed from a particular repo. It’s displayed on a row describing ++#. * that repo. The placeholder is the number of add-ons, and the translated ++#. * string will be substituted in for the second placeholder in the ++#. * string “%s and %s installed”. ++#: src/gs-repo-row.c:189 + #, c-format + msgid "%u add-on" + msgid_plural "%u add-ons" +@@ -3309,11 +3356,20 @@ msgstr[0] "%u doplněk" + msgstr[1] "%u doplňky" + msgstr[2] "%u doplňků" + +-#. TRANSLATORS: This string is used to construct the 'X applications +-#. and y add-ons installed' sentence, describing a software repository. +-#. The correct form here depends on the total number of +-#. applications and add-ons. +-#: src/gs-repo-row.c:188 ++#. TRANSLATORS: This string is used to construct the 'X apps ++#. and Y add-ons installed' sentence, stating how many things have been ++#. * installed from a particular repo. It’s displayed on a row describing ++#. * that repo. The first placeholder is the translated string “%u app” or ++#. * “%u apps”. The second placeholder is the translated string “%u add-on” ++#. * or “%u add-ons”. ++#. * ++#. * The choice of plural form for this string is determined by the total ++#. * number of apps plus add-ons. For example, ++#. * - “1 app and 2 add-ons installed” - uses count 3 ++#. * - “2 apps and 1 add-on installed” - uses count 3 ++#. * - “4 apps and 5 add-ons installed” - uses count 9 ++#. ++#: src/gs-repo-row.c:205 + #, c-format + msgid "%s and %s installed" + msgid_plural "%s and %s installed" +@@ -3321,120 +3377,117 @@ msgstr[0] "%s a %s" + msgstr[1] "%s a %s" + msgstr[2] "%s a %s" + +-#. Translators: The first '%s' is replaced with a text like '10 applications installed', ++#. Translators: The first '%s' is replaced with a text like '10 apps installed', + #. the second '%s' is replaced with installation kind, like in case of Flatpak 'User Installation'. +-#: src/gs-repo-row.c:243 ++#: src/gs-repo-row.c:260 + #, c-format + msgctxt "repo-row" + msgid "%s • %s" + msgstr "%s • %s" + +-#: src/gs-repo-row.c:314 +-#, fuzzy +-#| msgid "_Remove" ++#: src/gs-repo-row.c:331 + msgid "Remove" +-msgstr "_Odebrat" ++msgstr "Odebrat" + + #. TRANSLATORS: lighthearted star rating description; +-#. * A really bad application ++#. * A really bad app + #: src/gs-review-dialog.c:78 + msgid "Hate it" + msgstr "Nenávidím ji" + + #. TRANSLATORS: lighthearted star rating description; +-#. * Not a great application ++#. * Not a great app + #: src/gs-review-dialog.c:82 + msgid "Don’t like it" + msgstr "Nemám ji rád" + + #. TRANSLATORS: lighthearted star rating description; +-#. * A fairly-good application ++#. * A fairly-good app + #: src/gs-review-dialog.c:86 + msgid "It’s OK" + msgstr "Běžná aplikace" + + #. TRANSLATORS: lighthearted star rating description; +-#. * A good application ++#. * A good app + #: src/gs-review-dialog.c:90 + msgid "Like it" + msgstr "Mám ji rád" + + #. TRANSLATORS: lighthearted star rating description; +-#. * A really awesome application ++#. * A really awesome app + #: src/gs-review-dialog.c:94 + msgid "Love it" + msgstr "Zbožňuji ji" + ++#. TRANSLATORS: lighthearted star rating description; ++#. * No star has been clicked yet ++#: src/gs-review-dialog.c:98 ++msgid "Select a Star to Leave a Rating" ++msgstr "Chcete-li zanechat hodnocení, vyberte hvězdičku" ++ + #. TRANSLATORS: the review can't just be copied and pasted +-#: src/gs-review-dialog.c:118 ++#: src/gs-review-dialog.c:119 + msgid "Please take more time writing the review" + msgstr "Věnujte prosím trochu času napsaní recenze" + + #. TRANSLATORS: the review is not acceptable +-#: src/gs-review-dialog.c:122 ++#: src/gs-review-dialog.c:123 + msgid "Please choose a star rating" + msgstr "Ohodnoťte prosím hvězdičkami" + + #. TRANSLATORS: the review is not acceptable +-#: src/gs-review-dialog.c:126 ++#: src/gs-review-dialog.c:127 + msgid "The summary is too short" + msgstr "Celkové hodnocení je příliš krátké" + + #. TRANSLATORS: the review is not acceptable +-#: src/gs-review-dialog.c:130 ++#: src/gs-review-dialog.c:131 + msgid "The summary is too long" + msgstr "Celkové hodnocení je příliš dlouhé" + + #. TRANSLATORS: the review is not acceptable +-#: src/gs-review-dialog.c:134 ++#: src/gs-review-dialog.c:135 + msgid "The description is too short" + msgstr "Recenze je příliš krátká" + + #. TRANSLATORS: the review is not acceptable +-#: src/gs-review-dialog.c:138 ++#: src/gs-review-dialog.c:139 + msgid "The description is too long" + msgstr "Recenze je příliš dlouhá" + + #. Translators: Title of the dialog box where the users can write and publish their opinions about the apps. + #: src/gs-review-dialog.ui:10 +-msgid "Post Review" +-msgstr "Příspěvek do recenzí" ++msgid "Write a Review" ++msgstr "Napsat recenzi" + + #. Translators: A button to publish the user's opinion about the app. + #: src/gs-review-dialog.ui:26 +-msgid "_Post" ++msgid "_Send" + msgstr "_Odeslat" + +-#: src/gs-review-dialog.ui:56 +-msgid "Rating" +-msgstr "Hodnocení" +- +-#: src/gs-review-dialog.ui:88 +-msgid "Summary" +-msgstr "Celkový dojem" +- +-#: src/gs-review-dialog.ui:97 ++#: src/gs-review-dialog.ui:71 + msgid "" +-"Give a short summary of your review, for example: “Great app, would " +-"recommend”." ++"What did you like about this app? Leaving your feedback along with your " ++"reasons for leaving a review is helpful for others." + msgstr "" +-"Uveďte krátké shrnutí své recenze, například: „Skvělá aplikace, doporučuji“." ++"Co se vám na této aplikaci líbilo? Zanechání zpětné vazby společně s důvody " ++"pro zanechání recenze je pro ostatní užitečné." ++ ++#: src/gs-review-dialog.ui:84 ++msgid "Review Summary" ++msgstr "Celkový dojem" + + #. Translators: This is where the users enter their opinions about the apps. +-#: src/gs-review-dialog.ui:119 ++#: src/gs-review-dialog.ui:116 + msgctxt "app review" +-msgid "Review" +-msgstr "Recenze" ++msgid "Write a short review" ++msgstr "Napište krátkou recenzi" + +-#: src/gs-review-dialog.ui:128 +-msgid "What do you think of the app? Try to give reasons for your views." +-msgstr "Co si o aplikaci myslíte? Snažte se uvést důvody svého hodnocení." +- +-#: src/gs-review-dialog.ui:156 ++#: src/gs-review-dialog.ui:160 + msgid "" +-"Find what data is sent in our privacy policy. The full name attached to your account will be shown " +-"publicly." ++"Find what data is sent in our privacy policy. The full name attached to your account will be " ++"shown publicly." + msgstr "" + "Najděte si v našich zásadách " + "soukromí, jaká data jsou odesílána. Celé jméno přiřazené k vašemu účtu " +@@ -3448,24 +3501,24 @@ msgstr[0] "celkem %u recenze" + msgstr[1] "celkem %u recenze" + msgstr[2] "celkem %u recenzí" + +-#: src/gs-review-histogram.ui:93 ++#: src/gs-review-histogram.ui:88 + msgid "out of 5 stars" + msgstr "z 5 hvězdiček" + + #. TRANSLATORS: this is when a user doesn't specify a name +-#: src/gs-review-row.c:56 ++#: src/gs-review-row.c:60 + msgctxt "Reviewer name" + msgid "Unknown" + msgstr "anonym" + + #. TRANSLATORS: we explain what the action is going to do +-#: src/gs-review-row.c:220 ++#: src/gs-review-row.c:222 + msgid "You can report reviews for abusive, rude, or discriminatory behavior." + msgstr "" + "Můžete nahlásit recenze, které jsou urážlivé, sprosté nebo diskriminační." + + #. TRANSLATORS: we ask the user if they really want to do this +-#: src/gs-review-row.c:225 ++#: src/gs-review-row.c:227 + msgid "" + "Once reported, a review will be hidden until it has been checked by an " + "administrator." +@@ -3474,15 +3527,15 @@ msgstr "Po nahlášení bude recenze skryta, dokud ji nezkontroluje správce." + #. TRANSLATORS: window title when + #. * reporting a user-submitted review + #. * for moderation +-#: src/gs-review-row.c:239 ++#: src/gs-review-row.c:235 + msgid "Report Review?" + msgstr "Nahlásit recenzi?" + + #. TRANSLATORS: button text when + #. * sending a review for moderation +-#: src/gs-review-row.c:243 +-msgid "Report" +-msgstr "Nahlásit" ++#: src/gs-review-row.c:240 ++msgid "_Report" ++msgstr "_Nahlásit" + + #. Translators: Users can express their opinions about other users' opinions about the apps. + #: src/gs-review-row.ui:84 +@@ -3510,175 +3563,184 @@ msgstr "Nahlásit…" + msgid "Remove…" + msgstr "Odebrat…" + +-#: src/gs-safety-context-dialog.c:144 +-msgid "Check that you trust the vendor, as the application isn’t sandboxed" ++#: src/gs-safety-context-dialog.c:143 ++msgid "Check that you trust the vendor, as the app isn’t sandboxed" + msgstr "" + "Zkontrolujte si, že důvěřujete dodavateli, protože aplikace není v " +-"izolovaném prostředí." ++"izolovaném prostředí" + +-#: src/gs-safety-context-dialog.c:147 ++#: src/gs-safety-context-dialog.c:146 + msgid "" +-"Application isn’t sandboxed but the distribution has checked that it is not " +-"malicious" ++"App isn’t sandboxed but the distribution has checked that it is not malicious" + msgstr "" + "Aplikace není v izolovaném prostředí, ale je prověřená v distribuci, že " +-"neobsahuje škodlivý kód." ++"neobsahuje škodlivý kód" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:160 ++#: src/gs-safety-context-dialog.c:159 + msgid "No Permissions" + msgstr "Žádná oprávnění" + +-#: src/gs-safety-context-dialog.c:161 ++#: src/gs-safety-context-dialog.c:160 + msgid "App is fully sandboxed" + msgstr "Aplikace je v plně izolovaném prostředí" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:172 ++#: src/gs-safety-context-dialog.c:171 + msgid "Network Access" + msgstr "Přístup k síti" + +-#: src/gs-safety-context-dialog.c:173 ++#: src/gs-safety-context-dialog.c:172 + msgid "Can access the internet" + msgstr "Může přistupovat k internetu" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:176 ++#: src/gs-safety-context-dialog.c:175 + msgid "No Network Access" + msgstr "Žádný přístup k síti" + +-#: src/gs-safety-context-dialog.c:177 ++#: src/gs-safety-context-dialog.c:176 + msgid "Cannot access the internet" + msgstr "Nemůže přistupovat k internetu" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:183 ++#: src/gs-safety-context-dialog.c:182 + msgid "Uses System Services" + msgstr "Využívá služby systému" + +-#: src/gs-safety-context-dialog.c:184 ++#: src/gs-safety-context-dialog.c:183 + msgid "Can request data from system services" + msgstr "Může si vyžádat data ze služeb systému" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:191 ++#: src/gs-safety-context-dialog.c:190 + msgid "Uses Session Services" + msgstr "Využívá služby sezení" + +-#: src/gs-safety-context-dialog.c:192 ++#: src/gs-safety-context-dialog.c:191 + msgid "Can request data from session services" + msgstr "Může si vyžádat data ze služeb sezení" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:199 +-msgid "Device Access" +-msgstr "Přístup k zařízení" ++#: src/gs-safety-context-dialog.c:198 ++msgid "User Device Access" ++msgstr "Přístup k uživatelským zařízením" + +-#: src/gs-safety-context-dialog.c:200 ++#: src/gs-safety-context-dialog.c:199 + msgid "Can access devices such as webcams or gaming controllers" + msgstr "Může přistupovat k zařízením jako jsou webkamery nebo herní ovladače" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:203 +-msgid "No Device Access" +-msgstr "Žádný přístup k zařízení" ++#: src/gs-safety-context-dialog.c:202 ++msgid "No User Device Access" ++msgstr "Žádný přístup k uživatelským zařízením" + +-#: src/gs-safety-context-dialog.c:204 ++#: src/gs-safety-context-dialog.c:203 + msgid "Cannot access devices such as webcams or gaming controllers" + msgstr "Nemůže přistupovat k zařízením jako jsou webkamery nebo herní ovladače" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. ++#: src/gs-safety-context-dialog.c:209 ++msgid "System Device Access" ++msgstr "Přístup k systémovým zařízením" ++ + #: src/gs-safety-context-dialog.c:210 ++msgid "Can access system devices which require elevated permissions" ++msgstr "" ++"Může přistupovat k systémovým zařízením, která vyžadují zvýšená oprávnění" ++ ++#. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. ++#: src/gs-safety-context-dialog.c:217 + msgid "Legacy Windowing System" + msgstr "Zastaralý zobrazovací systém" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:218 ++#: src/gs-safety-context-dialog.c:225 + msgid "Arbitrary Permissions" + msgstr "Libovolná oprávnění" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:226 ++#: src/gs-safety-context-dialog.c:233 + msgid "User Settings" + msgstr "Uživatelská nastavení" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:238 ++#: src/gs-safety-context-dialog.c:245 + msgid "Full File System Read/Write Access" + msgstr "Plný přístup k souborovému systému pro čtení/zápis" + +-#: src/gs-safety-context-dialog.c:239 ++#: src/gs-safety-context-dialog.c:246 + msgid "Can read and write all data on the file system" + msgstr "Může číst a zapisovat všechna data v souborovém systému" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:247 ++#: src/gs-safety-context-dialog.c:254 + msgid "Home Folder Read/Write Access" + msgstr "Přístup k domovské složce pro čtení/zápis" + +-#: src/gs-safety-context-dialog.c:248 ++#: src/gs-safety-context-dialog.c:255 + msgid "Can read and write all data in your home directory" + msgstr "Může číst a zapisovat všechna data ve vaší domovské složce" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:256 ++#: src/gs-safety-context-dialog.c:263 + msgid "Full File System Read Access" + msgstr "Plný přístup k souborovému systému pro čtení" + +-#: src/gs-safety-context-dialog.c:257 ++#: src/gs-safety-context-dialog.c:264 + msgid "Can read all data on the file system" + msgstr "Může číst všechna data v souborovém systému" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:266 ++#: src/gs-safety-context-dialog.c:273 + msgid "Home Folder Read Access" + msgstr "Přístup k domovské složce pro čtení" + +-#: src/gs-safety-context-dialog.c:267 ++#: src/gs-safety-context-dialog.c:274 + msgid "Can read all data in your home directory" + msgstr "Může číst všechna data ve vaší domovské složce" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:276 ++#: src/gs-safety-context-dialog.c:283 + msgid "Download Folder Read/Write Access" + msgstr "Přístup ke složce se staženými soubory pro čtení/zápis" + +-#: src/gs-safety-context-dialog.c:277 ++#: src/gs-safety-context-dialog.c:284 + msgid "Can read and write all data in your downloads directory" + msgstr "Může číst a zapisovat všechna data ve vaší složce se staženými soubory" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:288 ++#: src/gs-safety-context-dialog.c:295 + msgid "Download Folder Read Access" + msgstr "Přístup ke složce se staženými soubory pro čtení" + +-#: src/gs-safety-context-dialog.c:289 ++#: src/gs-safety-context-dialog.c:296 + msgid "Can read all data in your downloads directory" + msgstr "Může číst všechna data ve vaší složce se staženými soubory" + +-#: src/gs-safety-context-dialog.c:299 ++#: src/gs-safety-context-dialog.c:306 + msgid "Can read and write all data in the directory" + msgstr "Může číst a zapisovat všechna data ve složce" + +-#: src/gs-safety-context-dialog.c:310 ++#: src/gs-safety-context-dialog.c:317 + msgid "Can read all data in the directory" + msgstr "Může číst všechna data ve složce" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:326 ++#: src/gs-safety-context-dialog.c:333 + msgid "No File System Access" + msgstr "Žádný přístup k souborovému systému" + +-#: src/gs-safety-context-dialog.c:327 ++#: src/gs-safety-context-dialog.c:334 + msgid "Cannot access the file system at all" + msgstr "Vůbec nemůže přistupovat k souborovému systému" + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:341 ++#: src/gs-safety-context-dialog.c:348 + msgid "Proprietary Code" + msgstr "uzavřená" + +-#: src/gs-safety-context-dialog.c:342 ++#: src/gs-safety-context-dialog.c:349 + msgid "" + "The source code is not public, so it cannot be independently audited and " + "might be unsafe" +@@ -3687,11 +3749,11 @@ msgstr "" + "nebezpečný." + + #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. +-#: src/gs-safety-context-dialog.c:345 ++#: src/gs-safety-context-dialog.c:352 + msgid "Auditable Code" + msgstr "otevřený kód" + +-#: src/gs-safety-context-dialog.c:346 ++#: src/gs-safety-context-dialog.c:353 + msgid "" + "The source code is public and can be independently audited, which makes the " + "app more likely to be safe" +@@ -3701,21 +3763,21 @@ msgstr "" + + #. Translators: This indicates an app was written and released by a developer who has been verified. + #. * It’s used in a context tile, so should be short. +-#: src/gs-safety-context-dialog.c:354 ++#: src/gs-safety-context-dialog.c:361 + msgid "App developer is verified" + msgstr "Vývojář aplikace je ověřený" + +-#: src/gs-safety-context-dialog.c:355 ++#: src/gs-safety-context-dialog.c:362 + msgid "The developer of this app has been verified to be who they say they are" + msgstr "Bylo ověřeno, že vývojář této aplikace je tím, za koho se vydává" + + #. Translators: This indicates an app uses an outdated SDK. + #. * It’s used in a context tile, so should be short. +-#: src/gs-safety-context-dialog.c:366 ++#: src/gs-safety-context-dialog.c:373 + msgid "Insecure Dependencies" + msgstr "Bezpečnostní rizika v závislostech" + +-#: src/gs-safety-context-dialog.c:367 ++#: src/gs-safety-context-dialog.c:374 + msgid "" + "Software or its dependencies are no longer supported and may be insecure" + msgstr "" +@@ -3724,21 +3786,21 @@ msgstr "" + + #. Translators: The app is considered safe to install and run. + #. * The placeholder is the app name. +-#: src/gs-safety-context-dialog.c:376 ++#: src/gs-safety-context-dialog.c:383 + #, c-format + msgid "%s is safe" + msgstr "Aplikace %s je bezpečná" + + #. Translators: The app is considered potentially unsafe to install and run. + #. * The placeholder is the app name. +-#: src/gs-safety-context-dialog.c:383 ++#: src/gs-safety-context-dialog.c:390 + #, c-format + msgid "%s is potentially unsafe" + msgstr "Aplikace %s je potenciálně nebezpečná" + + #. Translators: The app is considered unsafe to install and run. + #. * The placeholder is the app name. +-#: src/gs-safety-context-dialog.c:390 ++#: src/gs-safety-context-dialog.c:397 + #, c-format + msgid "%s is unsafe" + msgstr "Aplikace %s je nebezpečná" +@@ -3775,42 +3837,43 @@ msgstr "Předchozí snímek obrazovky" + msgid "Next Screenshot" + msgstr "Následující snímek obrazovky" + +-#: src/gs-screenshot-carousel.ui:127 +-msgid "No screenshot provided" +-msgstr "Nemá snímek obrazovky" ++#. Translators: Shortened form of “no screenshots available” when showing an app’s details. ++#: src/gs-screenshot-carousel.ui:130 ++msgid "No Screenshots" ++msgstr "Žádné snímky obrazovky" + + #. TRANSLATORS: this is when we try to download a screenshot and + #. * we get back 404 +-#: src/gs-screenshot-image.c:362 src/gs-screenshot-image.c:419 +-#: src/gs-screenshot-image.c:623 ++#: src/gs-screenshot-image.c:359 src/gs-screenshot-image.c:416 ++#: src/gs-screenshot-image.c:620 + msgid "Screenshot not found" + msgstr "Snímek nebyl nalezen" + + #. TRANSLATORS: possibly image file corrupt or not an image +-#: src/gs-screenshot-image.c:438 ++#: src/gs-screenshot-image.c:435 + msgid "Failed to load image" + msgstr "Selhalo načtení obrázku" + + #. TRANSLATORS: this is when we request a screenshot size that + #. * the generator did not create or the parser did not add +-#: src/gs-screenshot-image.c:651 ++#: src/gs-screenshot-image.c:648 + msgid "Screenshot size not found" + msgstr "Velikost snímku nebyla nalezena" + + #. TRANSLATORS: this is when we try create the cache directory + #. * but we were out of space or permission was denied +-#: src/gs-screenshot-image.c:733 ++#: src/gs-screenshot-image.c:730 + msgid "Could not create cache" + msgstr "Nelze vytvoři mezipaměť" + + #. TRANSLATORS: this is when we try to download a screenshot + #. * that was not a valid URL +-#: src/gs-screenshot-image.c:747 ++#: src/gs-screenshot-image.c:744 + msgid "Screenshot not valid" + msgstr "Snímek není platný" + + #. TRANSLATORS: this is when networking is not available +-#: src/gs-screenshot-image.c:797 ++#: src/gs-screenshot-image.c:794 + msgid "Screenshot not available" + msgstr "Snímek není k dispozici" + +@@ -3820,7 +3883,7 @@ msgstr "Snímek" + + #. TRANSLATORS: this is when there are too many search results + #. * to show in in the search page +-#: src/gs-search-page.c:180 ++#: src/gs-search-page.c:179 + #, c-format + msgid "%u more match" + msgid_plural "%u more matches" +@@ -3837,7 +3900,7 @@ msgid "Search for Apps" + msgstr "Hledat aplikace" + + #: src/gs-search-page.ui:46 +-msgid "No Application Found" ++msgid "No App Found" + msgstr "Žádná aplikace nebyla nalezena" + + #. TRANSLATORS: this is part of the in-app notification, +@@ -3848,33 +3911,33 @@ msgstr "Žádná aplikace nebyla nalezena" + #. TRANSLATORS: this is part of the in-app notification, + #. * where the %s is a multi-word localised app name + #. * e.g. 'Getting things GNOME!" +-#: src/gs-shell.c:1209 src/gs-shell.c:1214 src/gs-shell.c:1229 +-#: src/gs-shell.c:1233 ++#: src/gs-shell.c:1170 src/gs-shell.c:1175 src/gs-shell.c:1190 ++#: src/gs-shell.c:1194 + #, c-format + msgid "“%s”" + msgstr "„%s“" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the source (e.g. "alt.fedoraproject.org") +-#: src/gs-shell.c:1285 ++#: src/gs-shell.c:1246 + #, c-format + msgid "Unable to download firmware updates from %s" + msgstr "Nelze stáhnout aktualizace firmwaru z %s" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the source (e.g. "alt.fedoraproject.org") +-#: src/gs-shell.c:1291 ++#: src/gs-shell.c:1252 + #, c-format + msgid "Unable to download updates from %s" + msgstr "Nelze stáhnout aktualizace z %s" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1298 src/gs-shell.c:1338 ++#: src/gs-shell.c:1259 src/gs-shell.c:1300 + msgid "Unable to download updates" + msgstr "Nelze stáhnout aktualizace" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1303 ++#: src/gs-shell.c:1264 + msgid "" + "Unable to download updates: internet access was required but wasn’t available" + msgstr "" +@@ -3883,124 +3946,124 @@ msgstr "" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the source (e.g. "alt.fedoraproject.org") +-#: src/gs-shell.c:1311 ++#: src/gs-shell.c:1272 + #, c-format + msgid "Unable to download updates from %s: not enough disk space" + msgstr "Nelze stáhnout aktualizace z %s: není dostatek místa na disku" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1316 ++#: src/gs-shell.c:1277 + msgid "Unable to download updates: not enough disk space" + msgstr "Nelze stáhnout aktualizace: není dostatek místa na disku" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1322 ++#: src/gs-shell.c:1283 + msgid "Unable to download updates: authentication was required" + msgstr "Nelze stáhnout aktualizace: je vyžadováno ověření" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1326 ++#: src/gs-shell.c:1287 + msgid "Unable to download updates: authentication was invalid" + msgstr "Nelze stáhnout aktualizace: ověření nebylo platné" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1330 ++#: src/gs-shell.c:1291 + msgid "" + "Unable to download updates: you do not have permission to install software" + msgstr "Nelze stáhnout aktualizace: nemáte oprávnění instalovat software" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1341 ++#: src/gs-shell.c:1303 + msgid "Unable to get list of updates" + msgstr "Nelze získat seznam aktualizací" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the first %s is the application name (e.g. "GIMP") and ++#. * where the first %s is the app name (e.g. "GIMP") and + #. * the second %s is the origin, e.g. "Fedora Project [fedoraproject.org]" +-#: src/gs-shell.c:1377 ++#: src/gs-shell.c:1339 + #, c-format + msgid "Unable to install %s as download failed from %s" + msgstr "Nelze nainstalovat balíček %s, protože selhalo jeho stažení z %s" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1383 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1345 + #, c-format + msgid "Unable to install %s as download failed" + msgstr "Nelze nainstalovat balíček %s, protože selhalo stažení" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the first %s is the application name (e.g. "GIMP") ++#. * where the first %s is the app name (e.g. "GIMP") + #. * and the second %s is the name of the runtime, e.g. + #. * "GNOME SDK [flatpak.gnome.org]" +-#: src/gs-shell.c:1395 ++#: src/gs-shell.c:1357 + #, c-format + msgid "Unable to install %s as runtime %s not available" + msgstr "" + "Nelze nainstalovat balíček %s, protože není k dispozici běhové prostředí %s" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1401 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1363 + #, c-format + msgid "Unable to install %s as not supported" + msgstr "Nelze nainstalovat balíček %s, protože není podporovaný" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1407 ++#: src/gs-shell.c:1369 + msgid "Unable to install: internet access was required but wasn’t available" + msgstr "" + "Nelze nainstalovat: přístup k internetu je nezbytný, ale není k dispozici" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1412 +-msgid "Unable to install: the application has an invalid format" ++#: src/gs-shell.c:1374 ++msgid "Unable to install: the app has an invalid format" + msgstr "Nelze nainstalovat: aplikace má neplatný formát" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1416 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1378 + #, c-format + msgid "Unable to install %s: not enough disk space" + msgstr "Nelze nainstalovat balíček %s: není dostatek místa na disku" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1422 ++#: src/gs-shell.c:1384 + #, c-format + msgid "Unable to install %s: authentication was required" + msgstr "Nelze nainstalovat balíček %s: je vyžadováno ověření" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1428 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1390 + #, c-format + msgid "Unable to install %s: authentication was invalid" + msgstr "Nelze nainstalovat balíček %s: ověření nebylo platné" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1434 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1396 + #, c-format + msgid "Unable to install %s: you do not have permission to install software" + msgstr "Nelze nainstalovat balíček %s: nemáte oprávnění k instalaci softwaru" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "Dell XPS 13") +-#: src/gs-shell.c:1441 ++#. * where the %s is the app name (e.g. "Dell XPS 13") ++#: src/gs-shell.c:1403 + #, c-format + msgid "Unable to install %s: AC power is required" + msgstr "Nelze nainstalovat balíček %s: je vyžadováno připojené napájení" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "Dell XPS 13") +-#: src/gs-shell.c:1447 ++#. * where the %s is the app name (e.g. "Dell XPS 13") ++#: src/gs-shell.c:1409 + #, c-format + msgid "Unable to install %s: The battery level is too low" + msgstr "Nelze nainstalovat balíček %s: úroveň nabití baterie je příliš nízká" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1456 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1418 + #, c-format + msgid "Unable to install %s" + msgstr "Nelze nainstalovat balíček %s" +@@ -4009,14 +4072,14 @@ msgstr "Nelze nainstalovat balíček %s" + #. * where the first %s is the app name (e.g. "GIMP") and + #. * the second %s is the origin, e.g. "Fedora" or + #. * "Fedora Project [fedoraproject.org]" +-#: src/gs-shell.c:1495 ++#: src/gs-shell.c:1457 + #, c-format + msgid "Unable to update %s from %s as download failed" + msgstr "Nelze aktualizovat balíček %s z %s, protože selhalo stažení" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1502 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1464 + #, c-format + msgid "Unable to update %s as download failed" + msgstr "Nelze aktualizovat balíček %s, protože selhalo stažení" +@@ -4024,71 +4087,71 @@ msgstr "Nelze aktualizovat balíček %s, protože selhalo stažení" + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the origin, e.g. "Fedora" or + #. * "Fedora Project [fedoraproject.org]" +-#: src/gs-shell.c:1509 ++#: src/gs-shell.c:1471 + #, c-format + msgid "Unable to install updates from %s as download failed" + msgstr "Nelze nainstalovat aktualizace z %s, protože selhalo stažení" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1513 ++#: src/gs-shell.c:1475 + #, c-format + msgid "Unable to install updates as download failed" + msgstr "Nelze nainstalovat aktualizace, protože selhalo stažení" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1518 ++#: src/gs-shell.c:1480 + msgid "Unable to update: internet access was required but wasn’t available" + msgstr "" + "Nelze aktualizovat: přístup k internetu je nezbytný, ale není k dispozici" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1527 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1489 + #, c-format + msgid "Unable to update %s: not enough disk space" + msgstr "Nelze aktualizovat balíček %s: nedostatek místa na disku" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1532 ++#: src/gs-shell.c:1494 + #, c-format + msgid "Unable to install updates: not enough disk space" + msgstr "Nelze nainstalovat aktualizace: nedostatek místa na disku" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1541 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1503 + #, c-format + msgid "Unable to update %s: authentication was required" + msgstr "Nelze aktualizovat balíček %s: je vyžadováno ověření" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1546 ++#: src/gs-shell.c:1508 + #, c-format + msgid "Unable to install updates: authentication was required" + msgstr "Nelze nainstalovat aktualizace: je vyžadováno ověření" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1554 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1516 + #, c-format + msgid "Unable to update %s: authentication was invalid" + msgstr "Nelze aktualizovat balíček %s: ověření bylo neplatné" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1559 ++#: src/gs-shell.c:1521 + #, c-format + msgid "Unable to install updates: authentication was invalid" + msgstr "Nelze nainstalovat aktualizace: ověření bylo neplatné" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1567 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1529 + #, c-format + msgid "Unable to update %s: you do not have permission to update software" + msgstr "Nelze aktualizovat balíček %s: nemáte oprávnění k aktualizaci softwaru" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1573 ++#: src/gs-shell.c:1535 + #, c-format + msgid "" + "Unable to install updates: you do not have permission to update software" +@@ -4096,44 +4159,44 @@ msgstr "" + "Nelze nainstalovat aktualizace: nemáte oprávnění k aktualizaci softwaru" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "Dell XPS 13") +-#: src/gs-shell.c:1582 ++#. * where the %s is the app name (e.g. "Dell XPS 13") ++#: src/gs-shell.c:1544 + #, c-format + msgid "Unable to update %s: AC power is required" + msgstr "" + "Nelze aktualizovat balíček %s: je vyžadováno napájení z elektrické sítě" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "Dell XPS 13") +-#: src/gs-shell.c:1588 ++#. * where the %s is the app name (e.g. "Dell XPS 13") ++#: src/gs-shell.c:1550 + #, c-format + msgid "Unable to install updates: AC power is required" + msgstr "" + "Nelze nainstalovat aktualizace: je vyžadováno napájení z elektrické sítě" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "Dell XPS 13") +-#: src/gs-shell.c:1596 ++#. * where the %s is the app name (e.g. "Dell XPS 13") ++#: src/gs-shell.c:1558 + #, c-format + msgid "Unable to update %s: The battery level is too low" + msgstr "Nelze aktualizovat balíček %s: úroveň nabití baterie je příliš nízká" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "Dell XPS 13") +-#: src/gs-shell.c:1602 ++#. * where the %s is the app name (e.g. "Dell XPS 13") ++#: src/gs-shell.c:1564 + #, c-format + msgid "Unable to install updates: The battery level is too low" + msgstr "Nelze nainstalovat aktualizace: úroveň nabití baterie je příliš nízká" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1613 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1575 + #, c-format + msgid "Unable to update %s" + msgstr "Nelze aktualizovat balíček %s" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1616 ++#: src/gs-shell.c:1578 + #, c-format + msgid "Unable to install updates" + msgstr "Nelze nainstalovat aktualizace" +@@ -4141,21 +4204,21 @@ msgstr "Nelze nainstalovat aktualizace" + #. TRANSLATORS: failure text for the in-app notification, + #. * where the first %s is the distro name (e.g. "Fedora 25") and + #. * the second %s is the origin, e.g. "Fedora Project [fedoraproject.org]" +-#: src/gs-shell.c:1652 ++#: src/gs-shell.c:1614 + #, c-format + msgid "Unable to upgrade to %s from %s" + msgstr "Nelze povýšit na %s z %s" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the app name (e.g. "GIMP") +-#: src/gs-shell.c:1657 ++#: src/gs-shell.c:1619 + #, c-format + msgid "Unable to upgrade to %s as download failed" + msgstr "Nelze povýšit na %s, protože selhalo stažení" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the distro name (e.g. "Fedora 25") +-#: src/gs-shell.c:1665 ++#: src/gs-shell.c:1627 + #, c-format + msgid "" + "Unable to upgrade to %s: internet access was required but wasn’t available" +@@ -4165,159 +4228,159 @@ msgstr "" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the distro name (e.g. "Fedora 25") +-#: src/gs-shell.c:1673 ++#: src/gs-shell.c:1635 + #, c-format + msgid "Unable to upgrade to %s: not enough disk space" + msgstr "Nelze povýšit na %s: není dostatek místa na disku" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the distro name (e.g. "Fedora 25") +-#: src/gs-shell.c:1680 ++#: src/gs-shell.c:1642 + #, c-format + msgid "Unable to upgrade to %s: authentication was required" + msgstr "Nelze povýšit na %s: je vyžadováno ověření" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the distro name (e.g. "Fedora 25") +-#: src/gs-shell.c:1686 ++#: src/gs-shell.c:1648 + #, c-format + msgid "Unable to upgrade to %s: authentication was invalid" + msgstr "Nelze povýšit na %s: ověření nebylo platné" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the distro name (e.g. "Fedora 25") +-#: src/gs-shell.c:1692 ++#: src/gs-shell.c:1654 + #, c-format + msgid "Unable to upgrade to %s: you do not have permission to upgrade" + msgstr "Nelze povýšit na %s: nemáte oprávnění k povyšování" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the distro name (e.g. "Fedora 25") +-#: src/gs-shell.c:1698 ++#: src/gs-shell.c:1660 + #, c-format + msgid "Unable to upgrade to %s: AC power is required" + msgstr "Nelze povýšit na %s: je vyžadováno připojené napájení" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the distro name (e.g. "Fedora 25") +-#: src/gs-shell.c:1704 ++#: src/gs-shell.c:1666 + #, c-format + msgid "Unable to upgrade to %s: The battery level is too low" + msgstr "Nelze povýšit na %s: úroveň nabití baterie je příliš nízká" + + #. TRANSLATORS: failure text for the in-app notification, + #. * where the %s is the distro name (e.g. "Fedora 25") +-#: src/gs-shell.c:1713 ++#: src/gs-shell.c:1675 + #, c-format + msgid "Unable to upgrade to %s" + msgstr "Nelze povýšit na %s" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1744 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1706 + #, c-format + msgid "Unable to remove %s: authentication was required" + msgstr "Nelze odstranit balíček %s: je vyžadováno ověření" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1749 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1711 + #, c-format + msgid "Unable to remove %s: authentication was invalid" + msgstr "Nelze odstranit balíček %s: ověření nebylo platné" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1754 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1716 + #, c-format + msgid "Unable to remove %s: you do not have permission to remove software" + msgstr "Nelze odstranit balíček %s: nemáte oprávnění k odstranění softwaru" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1760 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1722 + #, c-format + msgid "Unable to remove %s: AC power is required" + msgstr "Nelze odstranit balíček %s: je vyžadováno připojené napájení" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1766 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1728 + #, c-format + msgid "Unable to remove %s: The battery level is too low" + msgstr "Nelze odstranit balíček %s: úroveň nabití baterie je příliš nízká" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the %s is the application name (e.g. "GIMP") +-#: src/gs-shell.c:1778 ++#. * where the %s is the app name (e.g. "GIMP") ++#: src/gs-shell.c:1740 + #, c-format + msgid "Unable to remove %s" + msgstr "Nelze odstranit balíček %s" + + #. TRANSLATORS: failure text for the in-app notification, +-#. * where the first %s is the application name (e.g. "GIMP") ++#. * where the first %s is the app name (e.g. "GIMP") + #. * and the second %s is the name of the runtime, e.g. + #. * "GNOME SDK [flatpak.gnome.org]" +-#: src/gs-shell.c:1813 ++#: src/gs-shell.c:1775 + #, c-format + msgid "Unable to launch %s: %s is not installed" + msgstr "Nelze spustit aplikaci %s: balíček %s není nainstalovaný" + + #. TRANSLATORS: we failed to get a proper error code +-#: src/gs-shell.c:1821 src/gs-shell.c:1837 src/gs-shell.c:1879 +-#: src/gs-shell.c:1921 src/gs-shell.c:1978 ++#: src/gs-shell.c:1783 src/gs-shell.c:1799 src/gs-shell.c:1841 ++#: src/gs-shell.c:1883 src/gs-shell.c:1940 + msgid "Sorry, something went wrong" + msgstr "Litujeme, ale něco se stalo špatně" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1826 src/gs-shell.c:1868 src/gs-shell.c:1910 +-#: src/gs-shell.c:1957 ++#: src/gs-shell.c:1788 src/gs-shell.c:1830 src/gs-shell.c:1872 ++#: src/gs-shell.c:1919 + msgid "Not enough disk space — free up some space and try again" + msgstr "" + "Nebyl dostatek místa na disku – uvolněte nějaké místo a pak to zkuste znovu" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1862 ++#: src/gs-shell.c:1824 + msgid "Failed to install file: not supported" + msgstr "Selhala instalace souboru: není podporován" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1865 ++#: src/gs-shell.c:1827 + msgid "Failed to install file: authentication failed" + msgstr "Selhala instalace souboru: selhalo ověření" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1904 ++#: src/gs-shell.c:1866 + msgid "Failed to install: not supported" + msgstr "Selhala instalace: není podporováno" + + #. TRANSLATORS: failure text for the in-app notification +-#: src/gs-shell.c:1907 ++#: src/gs-shell.c:1869 + msgid "Failed to install: authentication failed" + msgstr "Selhala instalace: selhalo ověření" + + #. TRANSLATORS: failure text for the in-app notification, + #. * the %s is the origin, e.g. "Fedora" or + #. * "Fedora Project [fedoraproject.org]" +-#: src/gs-shell.c:1952 ++#: src/gs-shell.c:1914 + #, c-format + msgid "Unable to contact %s" + msgstr "Nelze kontaktovat %s" + +-#. TRANSLATORS: failure text for the in-app notification, where the 'Software' means this application, aka 'GNOME Software'. +-#: src/gs-shell.c:1962 ++#. TRANSLATORS: failure text for the in-app notification, where the 'Software' means this app, aka 'GNOME Software'. ++#: src/gs-shell.c:1924 + msgid "Software needs to be restarted to use new plugins." + msgstr "" + "Aplikace Software musí být restartována, aby mohla používat nový zásuvný " + "modul." + + #. TRANSLATORS: need to be connected to the AC power +-#: src/gs-shell.c:1966 ++#: src/gs-shell.c:1928 + msgid "AC power is required" + msgstr "Je vyžadováno připojené napájení" + + #. TRANSLATORS: not enough juice to do this safely +-#: src/gs-shell.c:1969 ++#: src/gs-shell.c:1931 + msgid "The battery level is too low" + msgstr "Úroveň nabití baterie je příliš nízká" + +@@ -4326,48 +4389,65 @@ msgid "_Software Repositories" + msgstr "_Softwarové repozitáře" + + #: src/gs-shell.ui:12 +-msgid "_Update Preferences" +-msgstr "Předvolby akt_ualizací" ++msgid "_Preferences" ++msgstr "_Předvolby" + + #. button in the info bar +-#: src/gs-shell.ui:98 ++#: src/gs-shell.ui:109 + msgid "Examine Disk" + msgstr "Prozkoumat disk" + + #. button in the info bar +-#. TRANSLATORS: this is a link to the +-#. * control-center network panel +-#: src/gs-shell.ui:108 src/gs-updates-page.c:885 ++#: src/gs-shell.ui:119 + msgid "Network Settings" + msgstr "Nastavení sítě" + + #. button in the info bar +-#: src/gs-shell.ui:118 +-msgid "Restart Now" +-msgstr "Restartovat hned" ++#: src/gs-shell.ui:129 ++msgid "_Restart Now…" ++msgstr "_Restartovat hned…" + + #. button in the info bar +-#: src/gs-shell.ui:128 ++#: src/gs-shell.ui:140 + msgid "More Information" + msgstr "Další informace" + +-#: src/gs-shell.ui:188 src/gs-shell.ui:190 ++#: src/gs-shell.ui:200 src/gs-shell.ui:202 + msgid "Search" + msgstr "Hledat" + +-#: src/gs-shell.ui:204 src/gs-shell.ui:206 +-msgid "Primary Menu" +-msgstr "Hlavní nabídky" ++#: src/gs-shell.ui:216 src/gs-shell.ui:218 ++msgid "Main Menu" ++msgstr "Hlavní nabídka" ++ ++#: src/gs-shell.ui:245 ++msgid "Search apps" ++msgstr "Hledat aplikace" ++ ++#: src/gs-shell.ui:257 ++msgid "Metered network ‒ automatic updates paused" ++msgstr "Měřená síť – automatické aktualizace jsou pozastaveny" + +-#: src/gs-shell.ui:276 ++#: src/gs-shell.ui:258 + msgid "Find Out _More" + msgstr "Dozvědět se _více…" + ++#. Translators: A label for a button to show all available software. ++#: src/gs-shell.ui:272 ++msgid "_Explore" ++msgstr "_Procházet" ++ ++#. Translators: A label for a button to show only software which is already installed. ++#: src/gs-shell.ui:286 ++msgctxt "List of installed apps" ++msgid "_Installed" ++msgstr "Na_instalováno" ++ + #. Translators: A label for a button to show only updates which are available to install. +-#: src/gs-shell.ui:330 ++#: src/gs-shell.ui:308 + msgctxt "Header bar button for list of apps to be updated" +-msgid "Updates" +-msgstr "Aktualizace" ++msgid "_Updates" ++msgstr "_Aktualizace" + + #. Translators: This is shown in a bubble to represent a 0 byte + #. * storage size, so its context is “storage size: none”. The +@@ -4378,11 +4458,11 @@ msgid "None" + msgstr "Žádná" + + #: src/gs-storage-context-dialog.c:139 +-msgid "Application Data" ++msgid "App Data" + msgstr "Data aplikace" + + #: src/gs-storage-context-dialog.c:140 +-msgid "Data needed for the application to run" ++msgid "Data needed for the app to run" + msgstr "Data potřebná ke spuštění aplikace" + + #: src/gs-storage-context-dialog.c:145 +@@ -4390,7 +4470,7 @@ msgid "User Data" + msgstr "Uživatelská data" + + #: src/gs-storage-context-dialog.c:146 +-msgid "Data created by you in the application" ++msgid "Data created by you in the app" + msgstr "Vámi vytvořená data v aplikaci" + + #: src/gs-storage-context-dialog.c:153 +@@ -4402,7 +4482,7 @@ msgid "Temporary cached data" + msgstr "Dočasná data v mezipaměti" + + #: src/gs-storage-context-dialog.c:172 +-msgid "The application itself" ++msgid "The app itself" + msgstr "Aplikace samotná" + + #: src/gs-storage-context-dialog.c:177 +@@ -4410,7 +4490,7 @@ msgid "Required Dependencies" + msgstr "Vyžadované závislosti" + + #: src/gs-storage-context-dialog.c:178 +-msgid "Shared system components required by this application" ++msgid "Shared system components required by this app" + msgstr "Sdílené systémové komponenty vyžadované touto aplikací" + + #: src/gs-storage-context-dialog.c:188 +@@ -4426,23 +4506,22 @@ msgstr "Úložiště" + #. Translators: Please do not translate the markup or link href + #: src/gs-storage-context-dialog.ui:69 + msgid "" +-"Cached data can be cleared from the _application settings." ++"Cached data can be cleared from the _app settings." + msgstr "" + "Data uložená v mezipaměti lze vymazat v _nastavení " + "aplikace." + +-#: src/gs-summary-tile.c:118 ++#: src/gs-summary-tile.c:139 + #, c-format + msgid "%s (Installed)" + msgstr "%s (nainstalováno)" + +-#: src/gs-summary-tile.c:123 ++#: src/gs-summary-tile.c:144 + #, c-format + msgid "%s (Installing)" + msgstr "%s (instaluje se)" + +-#: src/gs-summary-tile.c:128 ++#: src/gs-summary-tile.c:149 + #, c-format + msgid "%s (Removing)" + msgstr "%s (odebírá se)" +@@ -4508,8 +4587,8 @@ msgstr "Stáhněte prosím čekající aktualizace softwaru." + #. TRANSLATORS: apps were auto-updated and restart is required + #: src/gs-update-monitor.c:355 + #, c-format +-msgid "%u Application Updated — Restart Required" +-msgid_plural "%u Applications Updated — Restart Required" ++msgid "%u App Updated — Restart Required" ++msgid_plural "%u Apps Updated — Restart Required" + msgstr[0] "Byla aktualizována %u aplikace — vyžaduje restart" + msgstr[1] "Byly aktualizovány %u aplikace — vyžaduje restart" + msgstr[2] "Bylo aktualizováno %u aplikací — vyžaduje restart" +@@ -4517,13 +4596,13 @@ msgstr[2] "Bylo aktualizováno %u aplikací — vyžaduje restart" + #. TRANSLATORS: apps were auto-updated + #: src/gs-update-monitor.c:361 + #, c-format +-msgid "%u Application Updated" +-msgid_plural "%u Applications Updated" ++msgid "%u App Updated" ++msgid_plural "%u Apps Updated" + msgstr[0] "Byla aktualizována %u aplikace" + msgstr[1] "Byly aktualizovány %u aplikace" + msgstr[2] "Bylo aktualizováno %u aplikací" + +-#. TRANSLATORS: %1 is an application name, e.g. Firefox ++#. TRANSLATORS: %1 is an app name, e.g. Firefox + #: src/gs-update-monitor.c:372 + #, c-format + msgid "%s has been updated." +@@ -4531,81 +4610,81 @@ msgstr "Aplikace %s byla aktualizována." + + #. TRANSLATORS: the app needs restarting + #: src/gs-update-monitor.c:375 +-msgid "Please restart the application." ++msgid "Please restart the app." + msgstr "Restartujte ji prosím." + +-#. TRANSLATORS: %1 and %2 are both application names, e.g. Firefox ++#. TRANSLATORS: %1 and %2 are both app names, e.g. Firefox + #: src/gs-update-monitor.c:383 + #, c-format + msgid "%s and %s have been updated." + msgstr "Aplikace %s a %s byly aktualizovány." + +-#. TRANSLATORS: at least one application needs restarting ++#. TRANSLATORS: at least one app needs restarting + #: src/gs-update-monitor.c:389 src/gs-update-monitor.c:408 + #, c-format +-msgid "%u application requires a restart." +-msgid_plural "%u applications require a restart." ++msgid "%u app requires a restart." ++msgid_plural "%u apps require a restart." + msgstr[0] "%u aplikace vyžaduje restart." + msgstr[1] "%u aplikace vyžadují restart." + msgstr[2] "%u aplikací vyžaduje restart." + +-#. TRANSLATORS: %1, %2 and %3 are all application names, e.g. Firefox ++#. TRANSLATORS: %1, %2 and %3 are all app names, e.g. Firefox + #: src/gs-update-monitor.c:401 + #, c-format + msgid "Includes %s, %s and %s." + msgstr "Včetně %s, %s a %s." + + #. TRANSLATORS: this is when the current operating system version goes end-of-life +-#: src/gs-update-monitor.c:671 src/gs-updates-page.ui:20 ++#: src/gs-update-monitor.c:696 + msgid "Operating System Updates Unavailable" + msgstr "Aktualizace operačního systému nejsou dostupné" + + #. TRANSLATORS: this is the message dialog for the distro EOL notice +-#: src/gs-update-monitor.c:673 ++#: src/gs-update-monitor.c:698 + msgid "Upgrade to continue receiving security updates." + msgstr "Povýšit, aby byly nadále přijímány bezpečnostní aktualizace." + + #. TRANSLATORS: this is a distro upgrade, the replacement would be the + #. * distro name, e.g. 'Fedora' +-#: src/gs-update-monitor.c:728 ++#: src/gs-update-monitor.c:753 + #, c-format + msgid "A new version of %s is available to install" + msgstr "K instalaci je dostupná nová verze distribuce %s" + + #. TRANSLATORS: this is a distro upgrade +-#: src/gs-update-monitor.c:732 ++#: src/gs-update-monitor.c:757 + msgid "Software Upgrade Available" + msgstr "Dostupné povýšení softwaru" + + #. TRANSLATORS: title when we offline updates have failed +-#: src/gs-update-monitor.c:1137 ++#: src/gs-update-monitor.c:1162 + msgid "Software Updates Failed" + msgstr "Aktualizace softwaru selhaly" + + #. TRANSLATORS: message when we offline updates have failed +-#: src/gs-update-monitor.c:1139 ++#: src/gs-update-monitor.c:1164 + msgid "An important operating system update failed to be installed." + msgstr "Selhala instalace důležité aktualizace operačního systému." + +-#: src/gs-update-monitor.c:1140 ++#: src/gs-update-monitor.c:1165 + msgid "Show Details" + msgstr "Zobrazit podrobnosti" + + #. TRANSLATORS: Notification title when we've done a distro upgrade +-#: src/gs-update-monitor.c:1162 ++#: src/gs-update-monitor.c:1187 + msgid "System Upgrade Complete" + msgstr "Bylo dokončeno povýšení systému" + + #. TRANSLATORS: This is the notification body when we've done a + #. * distro upgrade. First %s is the distro name and the 2nd %s + #. * is the version, e.g. "Welcome to Fedora 28!" +-#: src/gs-update-monitor.c:1167 ++#: src/gs-update-monitor.c:1192 + #, c-format + msgid "Welcome to %s %s!" + msgstr "Vítejte ve vydání %s %s!" + + #. TRANSLATORS: title when we've done offline updates +-#: src/gs-update-monitor.c:1173 ++#: src/gs-update-monitor.c:1198 + msgid "Software Update Installed" + msgid_plural "Software Updates Installed" + msgstr[0] "Aktualizace softwaru nainstalována" +@@ -4613,7 +4692,7 @@ msgstr[1] "Aktualizace softwaru nainstalovány" + msgstr[2] "Aktualizace softwaru nainstalovány" + + #. TRANSLATORS: message when we've done offline updates +-#: src/gs-update-monitor.c:1177 ++#: src/gs-update-monitor.c:1202 + msgid "An important operating system update has been installed." + msgid_plural "Important operating system updates have been installed." + msgstr[0] "Byla nainstalována důležitá aktualizace operačního systému." +@@ -4621,34 +4700,34 @@ msgstr[1] "Byly nainstalovány důležité aktualizace operačního systému." + msgstr[2] "Byly nainstalovány důležité aktualizace operačního systému." + + #. TRANSLATORS: Button to look at the updates that were installed. +-#. * Note that it has nothing to do with the application reviews, the ++#. * Note that it has nothing to do with the app reviews, the + #. * users can't express their opinions here. In some languages + #. * "Review (evaluate) something" is a different translation than + #. * "Review (browse) something." +-#: src/gs-update-monitor.c:1188 ++#: src/gs-update-monitor.c:1213 + msgctxt "updates" + msgid "Review" + msgstr "Přehled" + + #. TRANSLATORS: this is when the offline update failed +-#: src/gs-update-monitor.c:1237 ++#: src/gs-update-monitor.c:1262 + msgid "Failed To Update" + msgstr "Aktualizace selhala" + + #. TRANSLATORS: the user must have updated manually after + #. * the updates were prepared +-#: src/gs-update-monitor.c:1242 ++#: src/gs-update-monitor.c:1267 + msgid "The system was already up to date." + msgstr "Systém již byl aktuální." + + #. TRANSLATORS: the user aborted the update manually +-#: src/gs-update-monitor.c:1247 ++#: src/gs-update-monitor.c:1272 + msgid "The update was cancelled." + msgstr "Aktualizace byla zrušena." + + #. TRANSLATORS: the package manager needed to download + #. * something with no network available +-#: src/gs-update-monitor.c:1252 ++#: src/gs-update-monitor.c:1277 + msgid "" + "Internet access was required but wasn’t available. Please make sure that you " + "have internet access and try again." +@@ -4657,7 +4736,7 @@ msgstr "" + "připojení k Internetu a zkuste to znovu." + + #. TRANSLATORS: if the package is not signed correctly +-#: src/gs-update-monitor.c:1257 ++#: src/gs-update-monitor.c:1282 + msgid "" + "There were security issues with the update. Please consult your software " + "provider for more details." +@@ -4666,7 +4745,7 @@ msgstr "" + "svým poskytovatelem softwaru." + + #. TRANSLATORS: we ran out of disk space +-#: src/gs-update-monitor.c:1262 ++#: src/gs-update-monitor.c:1287 + msgid "" + "There wasn’t enough disk space. Please free up some space and try again." + msgstr "" +@@ -4674,7 +4753,7 @@ msgstr "" + "znovu." + + #. TRANSLATORS: We didn't handle the error type +-#: src/gs-update-monitor.c:1266 ++#: src/gs-update-monitor.c:1291 + msgid "" + "We’re sorry: the update failed to install. Please wait for another update " + "and try again. If the problem persists, contact your software provider." +@@ -4684,49 +4763,39 @@ msgstr "" + "poskytovatele softwaru." + + #. TRANSLATORS: This is the time when we last checked for updates +-#: src/gs-updates-page.c:248 ++#: src/gs-updates-page.c:253 + #, c-format + msgid "Last checked: %s" + msgstr "Poslední kontrola: %s" + +-#: src/gs-updates-page.c:297 +-msgid "Stop Refreshing" +-msgstr "" ++#: src/gs-updates-page.c:302 ++msgid "Stop" ++msgstr "Zastavit" + +-#: src/gs-updates-page.c:306 src/gs-updates-page.c:318 +-msgid "Refresh" +-msgstr "" ++#: src/gs-updates-page.c:311 src/gs-updates-page.c:323 ++msgid "Check for Updates" ++msgstr "Zkontrolovat aktualizace" + + #. TRANSLATORS: the first %s is the distro name, e.g. 'Fedora' + #. * and the second %s is the distro version, e.g. '25' +-#: src/gs-updates-page.c:563 ++#: src/gs-updates-page.c:568 + #, c-format +-msgid "%s %s is no longer supported." +-msgstr "Systém %s %s již není podporován." +- +-#: src/gs-updates-page.c:567 +-msgid "Your operating system is no longer supported." +-msgstr "Váš operační systém není nadále podporován." +- +-#. TRANSLATORS: EOL distros do not get important updates +-#: src/gs-updates-page.c:572 +-msgid "This means that it does not receive security updates." +-msgstr "" +-"Znamená to, že pro něj již nadále nejsou poskytovány bezpečnostní opravy." ++msgid "%s %s has stopped receiving critical software updates" ++msgstr "Distribuce %s %s přestala dostávat kritické aktualizace softwaru" + +-#. TRANSLATORS: upgrade refers to a major update, e.g. Fedora 25 to 26 +-#: src/gs-updates-page.c:576 +-msgid "It is recommended that you upgrade to a more recent version." +-msgstr "Doporučuje se povýšit na nejnovější verzi." ++#. TRANSLATORS: This message is meant to tell users that they need to upgrade ++#. * or else their distro will not get important updates. ++#: src/gs-updates-page.c:574 ++msgid "Your operating system has stopped receiving critical software updates" ++msgstr "Váš operační systém přestal dostávat kritické aktualizace softwaru" + + #. TRANSLATORS: this is to explain that downloading updates may cost money +-#: src/gs-updates-page.c:853 ++#: src/gs-updates-page.c:843 + msgid "Charges May Apply" + msgstr "Možné zpoplatnění" + +-#. TRANSLATORS: we need network +-#. * to do the updates check +-#: src/gs-updates-page.c:857 ++#. TRANSLATORS: we need network to do the updates check ++#: src/gs-updates-page.c:845 + msgid "" + "Checking for updates while using mobile broadband could cause you to incur " + "charges." +@@ -4734,28 +4803,31 @@ msgstr "" + "Kontrola aktualizací přes mobilní připojení může být zpoplatněna vaším " + "operátorem." + +-#. TRANSLATORS: this is a link to the +-#. * control-center network panel +-#: src/gs-updates-page.c:861 ++#. TRANSLATORS: this is a link to the control-center network panel ++#: src/gs-updates-page.c:849 + msgid "Check _Anyway" + msgstr "_Přesto zkontrolovat" + + #. TRANSLATORS: can't do updates check +-#: src/gs-updates-page.c:877 ++#: src/gs-updates-page.c:860 + msgid "No Network" + msgstr "Žádné připojení k síti" + +-#. TRANSLATORS: we need network +-#. * to do the updates check +-#: src/gs-updates-page.c:881 ++#. TRANSLATORS: we need network to do the updates check ++#: src/gs-updates-page.c:862 + msgid "Internet access is required to check for updates." + msgstr "Přístup k internetu je nezbytný pro kontrolu aktualizací." + +-#: src/gs-updates-page.c:1254 ++#. TRANSLATORS: this is a link to the control-center network panel ++#: src/gs-updates-page.c:866 ++msgid "Network _Settings" ++msgstr "Nastavení _sítě" ++ ++#: src/gs-updates-page.c:1235 + msgid "Check for updates" + msgstr "Zkontrolovat aktualizace" + +-#: src/gs-updates-page.c:1290 ++#: src/gs-updates-page.c:1271 + msgctxt "Apps to be updated" + msgid "Updates" + msgstr "Aktualizace" +@@ -4765,25 +4837,25 @@ msgid "Updates page" + msgstr "Stránka s aktualizacemi" + + #. TRANSLATORS: the updates panel is starting up. +-#: src/gs-updates-page.ui:82 ++#: src/gs-updates-page.ui:58 + msgid "Loading Updates…" + msgstr "Načítají se aktualizace…" + + #. TRANSLATORS: the updates panel is starting up. +-#: src/gs-updates-page.ui:95 ++#: src/gs-updates-page.ui:71 + msgid "This could take a while." + msgstr "Může to chvilku trvat." + + #. TRANSLATORS: This means all software (plural) installed on this system is up to date. +-#: src/gs-updates-page.ui:203 ++#: src/gs-updates-page.ui:179 + msgid "Up to Date" + msgstr "Aktuální" + +-#: src/gs-updates-page.ui:242 ++#: src/gs-updates-page.ui:218 + msgid "Use Mobile Data?" + msgstr "Použít mobilní data?" + +-#: src/gs-updates-page.ui:243 ++#: src/gs-updates-page.ui:219 + msgid "" + "Checking for updates when using mobile broadband could cause you to incur " + "charges." +@@ -4791,68 +4863,68 @@ msgstr "" + "Kontrola aktualizací při používání mobilního širokopásmového připojení vám " + "může způsobit poplatky." + +-#: src/gs-updates-page.ui:246 ++#: src/gs-updates-page.ui:222 + msgid "_Check Anyway" + msgstr "_Přesto zkontrolovat" + +-#: src/gs-updates-page.ui:262 ++#: src/gs-updates-page.ui:238 + msgid "No Connection" + msgstr "Žádné připojení" + +-#: src/gs-updates-page.ui:263 ++#: src/gs-updates-page.ui:239 + msgid "Go online to check for updates." + msgstr "Kvůli kontrole aktualizací se musíte připojit k síti." + +-#: src/gs-updates-page.ui:266 ++#: src/gs-updates-page.ui:242 + msgid "_Network Settings" + msgstr "_Nastavení sítě" + +-#: src/gs-updates-page.ui:295 ++#: src/gs-updates-page.ui:275 + msgid "Error" + msgstr "Chyba" + +-#: src/gs-updates-page.ui:296 ++#: src/gs-updates-page.ui:276 + msgid "Updates are automatically managed." + msgstr "Aktualizace jsou spravovány automaticky." + + #. TRANSLATORS: This is the button for installing all + #. * offline updates +-#: src/gs-updates-section.c:312 +-msgid "Restart & Update" +-msgstr "Restartovat a aktualizovat" ++#: src/gs-updates-section.c:340 ++msgid "_Restart & Update…" ++msgstr "_Restartovat a aktualizovat…" + + #. TRANSLATORS: This is the button for upgrading all +-#. * online-updatable applications +-#: src/gs-updates-section.c:318 +-msgid "Update All" +-msgstr "Aktualizovat vše" ++#. * online-updatable apps ++#: src/gs-updates-section.c:346 ++msgid "U_pdate All" ++msgstr "_Aktualizovat vše" + + #. TRANSLATORS: This is the header for system firmware that + #. * requires a reboot to apply +-#: src/gs-updates-section.c:450 ++#: src/gs-updates-section.c:474 + msgid "Integrated Firmware" + msgstr "Integrovaný Firmware" + + #. TRANSLATORS: This is the header for offline OS and offline + #. * app updates that require a reboot to apply +-#: src/gs-updates-section.c:455 ++#: src/gs-updates-section.c:479 + msgid "Requires Restart" + msgstr "Vyžaduje restart" + + #. TRANSLATORS: This is the header for online runtime and + #. * app updates, typically flatpaks or snaps +-#: src/gs-updates-section.c:460 +-msgid "Application Updates" ++#: src/gs-updates-section.c:484 ++msgid "App Updates" + msgstr "Aktualizace aplikací" + + #. TRANSLATORS: This is the header for device firmware that can + #. * be installed online +-#: src/gs-updates-section.c:465 ++#: src/gs-updates-section.c:489 + msgid "Device Firmware" + msgstr "Firmware zařízení" + + #: src/gs-updates-section.ui:33 src/gs-upgrade-banner.ui:72 +-#: plugins/packagekit/gs-packagekit-task.c:155 ++#: plugins/packagekit/gs-packagekit-task.c:154 + msgid "_Download" + msgstr "S_táhnout" + +@@ -4899,8 +4971,8 @@ msgid "A major upgrade, with new features and added polish." + msgstr "Povýšení na novou verzi s novými funkcemi a vylepšeními." + + #: src/gs-upgrade-banner.ui:187 +-msgid "_Restart & Upgrade" +-msgstr "_Restartovat a aktualizovat" ++msgid "_Restart & Upgrade…" ++msgstr "_Restartovat a aktualizovat…" + + #: src/gs-upgrade-banner.ui:201 + msgid "Remember to back up data and files before upgrading." +@@ -4910,7 +4982,7 @@ msgstr "Nezapomeňte zazálohovat si před povýšením svá data a soubory." + msgid "Add, remove or update software on this computer" + msgstr "Přidat, odebrat nebo aktualizovat software v tomto počítači" + +-#. Translators: Search terms to find this application. Do NOT translate or localize the semicolons! The list MUST also end with a semicolon! ++#. Translators: Search terms to find this app. Do NOT translate or localize the semicolons! The list MUST also end with a semicolon! + #: src/org.gnome.Software.desktop.in:12 + msgid "" + "Updates;Upgrade;Sources;Repositories;Preferences;Install;Uninstall;Program;" +@@ -4922,14 +4994,14 @@ msgstr "" + #. TRANSLATORS: this is a group of updates that are not + #. * packages and are not shown in the main list + #: plugins/core/gs-plugin-generic-updates.c:67 +-#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:2975 ++#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:3049 + msgid "System Updates" + msgstr "Aktualizace systému" + + #. TRANSLATORS: this is a longer description of the + #. * "System Updates" string + #: plugins/core/gs-plugin-generic-updates.c:72 +-#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:2980 ++#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:3054 + msgid "" + "General system updates, such as security or bug fixes, and performance " + "improvements." +@@ -4943,21 +5015,19 @@ msgid "Downloading featured images…" + msgstr "Stahují se obrázky k významným aplikacím…" + + #. Translators: The '%s' is replaced with the OS name, like "Endless OS" +-#: plugins/eos-updater/gs-plugin-eos-updater.c:637 ++#: plugins/eos-updater/gs-plugin-eos-updater.c:684 + #, c-format + msgid "%s update with new features and fixes." + msgstr "Aktualizace %s s novými funkcemi a opravami." + +-#: plugins/eos-updater/gs-plugin-eos-updater.c:970 ++#: plugins/eos-updater/gs-plugin-eos-updater.c:1267 + msgid "EOS update service could not fetch and apply the update." + msgstr "Aktualizační služba EOS nemohla stáhnout a nasadit aktualizaci." + + #: plugins/epiphany/gs-plugin-epiphany.c:499 + #: plugins/epiphany/gs-plugin-epiphany.c:503 +-#, fuzzy +-#| msgid "Web Applications" + msgid "Web App" +-msgstr "Webové aplikace" ++msgstr "Webová aplikace" + + #: plugins/epiphany/org.gnome.Software.Plugin.Epiphany.metainfo.xml.in:6 + msgid "Web Apps Support" +@@ -4985,139 +5055,139 @@ msgid "Flatpak Support" + msgstr "Podpora pro Flatpak" + + #: plugins/flatpak/org.gnome.Software.Plugin.Flatpak.metainfo.xml.in:7 +-msgid "Flatpak is a framework for desktop applications on Linux" ++msgid "Flatpak is a framework for desktop apps on Linux" + msgstr "Flatpak je systém pro provozování aplikací na Linuxu" + + #. Reference: https://docs.flatpak.org/en/latest/flatpak-command-reference.html#idm45858571325264 +-#: plugins/flatpak/gs-flatpak.c:313 ++#: plugins/flatpak/gs-flatpak.c:318 + #, c-format + msgid "System folder %s" + msgstr "Systémová složka %s" + +-#: plugins/flatpak/gs-flatpak.c:314 plugins/flatpak/gs-flatpak.c:315 ++#: plugins/flatpak/gs-flatpak.c:319 plugins/flatpak/gs-flatpak.c:320 + #, c-format + msgid "Home subfolder %s" + msgstr "Podsložka %s v domovské složce" + +-#: plugins/flatpak/gs-flatpak.c:316 ++#: plugins/flatpak/gs-flatpak.c:321 + msgid "Host system folders" + msgstr "Složky hostitelského systému" + +-#: plugins/flatpak/gs-flatpak.c:317 ++#: plugins/flatpak/gs-flatpak.c:322 + msgid "Host system configuration from /etc" + msgstr "Konfigurace hostitelského systému z /etc" + +-#: plugins/flatpak/gs-flatpak.c:318 ++#: plugins/flatpak/gs-flatpak.c:323 + msgid "Desktop folder" + msgstr "Složka plochy" + +-#: plugins/flatpak/gs-flatpak.c:318 ++#: plugins/flatpak/gs-flatpak.c:323 + #, c-format + msgid "Desktop subfolder %s" + msgstr "Podsložka %s ve složce plochy" + +-#: plugins/flatpak/gs-flatpak.c:319 ++#: plugins/flatpak/gs-flatpak.c:324 + msgid "Documents folder" + msgstr "Složka dokumentů" + +-#: plugins/flatpak/gs-flatpak.c:319 ++#: plugins/flatpak/gs-flatpak.c:324 + #, c-format + msgid "Documents subfolder %s" + msgstr "Podsložka %s ve složce dokumentů" + +-#: plugins/flatpak/gs-flatpak.c:320 ++#: plugins/flatpak/gs-flatpak.c:325 + msgid "Music folder" + msgstr "Složka hudby" + +-#: plugins/flatpak/gs-flatpak.c:320 ++#: plugins/flatpak/gs-flatpak.c:325 + #, c-format + msgid "Music subfolder %s" + msgstr "Podsložka %s ve složce hudby" + +-#: plugins/flatpak/gs-flatpak.c:321 ++#: plugins/flatpak/gs-flatpak.c:326 + msgid "Pictures folder" + msgstr "Složka obrázků" + +-#: plugins/flatpak/gs-flatpak.c:321 ++#: plugins/flatpak/gs-flatpak.c:326 + #, c-format + msgid "Pictures subfolder %s" + msgstr "Podsložka %s ve složce obrázků" + +-#: plugins/flatpak/gs-flatpak.c:322 ++#: plugins/flatpak/gs-flatpak.c:327 + msgid "Public Share folder" + msgstr "Složka veřejně sdílených" + +-#: plugins/flatpak/gs-flatpak.c:322 ++#: plugins/flatpak/gs-flatpak.c:327 + #, c-format + msgid "Public Share subfolder %s" + msgstr "Podsložka %s ve složce veřejně sdílených" + +-#: plugins/flatpak/gs-flatpak.c:323 ++#: plugins/flatpak/gs-flatpak.c:328 + msgid "Videos folder" + msgstr "Složka videí" + +-#: plugins/flatpak/gs-flatpak.c:323 ++#: plugins/flatpak/gs-flatpak.c:328 + #, c-format + msgid "Videos subfolder %s" + msgstr "Podsložka %s ve složce videí" + +-#: plugins/flatpak/gs-flatpak.c:324 ++#: plugins/flatpak/gs-flatpak.c:329 + msgid "Templates folder" + msgstr "Složka šablon" + +-#: plugins/flatpak/gs-flatpak.c:324 ++#: plugins/flatpak/gs-flatpak.c:329 + #, c-format + msgid "Templates subfolder %s" + msgstr "Podsložka %s ve složce šablon" + +-#: plugins/flatpak/gs-flatpak.c:325 ++#: plugins/flatpak/gs-flatpak.c:330 + msgid "User cache folder" + msgstr "Složka uživatelské mezipaměti" + +-#: plugins/flatpak/gs-flatpak.c:325 ++#: plugins/flatpak/gs-flatpak.c:330 + #, c-format + msgid "User cache subfolder %s" + msgstr "Podsložka %s ve složce uživatelské mezipaměti" + +-#: plugins/flatpak/gs-flatpak.c:326 ++#: plugins/flatpak/gs-flatpak.c:331 + msgid "User configuration folder" + msgstr "Složka uživatelské konfigurace" + +-#: plugins/flatpak/gs-flatpak.c:326 ++#: plugins/flatpak/gs-flatpak.c:331 + #, c-format + msgid "User configuration subfolder %s" + msgstr "Podsložka %s ve složce uživatelské konfigurace" + +-#: plugins/flatpak/gs-flatpak.c:327 ++#: plugins/flatpak/gs-flatpak.c:332 + msgid "User data folder" + msgstr "Složka uživatelských dat" + +-#: plugins/flatpak/gs-flatpak.c:327 ++#: plugins/flatpak/gs-flatpak.c:332 + #, c-format + msgid "User data subfolder %s" + msgstr "Podsložka %s ve složce uživatelských dat" + +-#: plugins/flatpak/gs-flatpak.c:328 ++#: plugins/flatpak/gs-flatpak.c:333 + msgid "User runtime folder" + msgstr "Uživatelská složka pro běh aplikací" + +-#: plugins/flatpak/gs-flatpak.c:328 ++#: plugins/flatpak/gs-flatpak.c:333 + #, c-format + msgid "User runtime subfolder %s" + msgstr "Podsložka %s v uživatelské složce pro běh aplikací" + +-#: plugins/flatpak/gs-flatpak.c:386 ++#: plugins/flatpak/gs-flatpak.c:391 + #, c-format + msgid "Filesystem access to %s" + msgstr "Přístup k souborovému systému v %s" + + #. TRANSLATORS: status text when downloading new metadata +-#: plugins/flatpak/gs-flatpak.c:1403 ++#: plugins/flatpak/gs-flatpak.c:1408 + #, c-format + msgid "Getting flatpak metadata for %s…" + msgstr "Získávají se metadata Flatpak pro %s…" + +-#: plugins/flatpak/gs-flatpak.c:3580 ++#: plugins/flatpak/gs-flatpak.c:3589 + #, c-format + msgid "Failed to refine addon ‘%s’: %s" + msgstr "Selhalo vylepšení doplňku „%s“: %s" +@@ -5130,17 +5200,17 @@ msgstr "Uživatelská instalace" + msgid "System Installation" + msgstr "Systémová instalace" + +-#: plugins/flatpak/gs-plugin-flatpak.c:1038 ++#: plugins/flatpak/gs-plugin-flatpak.c:1320 + #, c-format + msgid "Failed to add to install for addon ‘%s’: %s" + msgstr "Selhalo přídání doplňku „%s“ k nainstalování: %s" + +-#: plugins/flatpak/gs-plugin-flatpak.c:1052 ++#: plugins/flatpak/gs-plugin-flatpak.c:1334 + #, c-format + msgid "Failed to add to uninstall for addon ‘%s’: %s" + msgstr "Selhalo přidání doplňku „%s“ k odinstalování: %s" + +-#: plugins/flatpak/gs-plugin-flatpak.c:1318 ++#: plugins/flatpak/gs-plugin-flatpak.c:1601 + #, c-format + msgid "" + "Remote “%s” doesn't allow install of “%s”, possibly due to its filter. " +@@ -5152,87 +5222,85 @@ msgstr "" + #. TRANSLATORS: as in laptop battery power + #: plugins/fwupd/gs-fwupd-app.c:66 + msgid "System power is too low to perform the update" +-msgstr "" ++msgstr "Systém nemá dostatek energie, aby provedl aktualizaci" + + #. TRANSLATORS: as in laptop battery power + #: plugins/fwupd/gs-fwupd-app.c:70 + #, c-format + msgid "System power is too low to perform the update (%u%%, requires %u%%)" + msgstr "" ++"Systém nemá dostatek energie, aby provedl aktualizaci (%u%%, vyžaduje %u%%)" + + #. TRANSLATORS: for example, a Bluetooth mouse that is in powersave mode + #: plugins/fwupd/gs-fwupd-app.c:76 + msgid "Device is unreachable, or out of wireless range" +-msgstr "" ++msgstr "Zařízení je nedostupné nebo mimo dosah bezdrátové sítě" + + #. TRANSLATORS: for example the batteries *inside* the Bluetooth mouse + #: plugins/fwupd/gs-fwupd-app.c:82 +-#, fuzzy, c-format +-#| msgid "The battery level is too low" ++#, c-format + msgid "Device battery power is too low" +-msgstr "Úroveň nabití baterie je příliš nízká" ++msgstr "Úroveň nabití baterie zařízení je příliš nízká" + + #. TRANSLATORS: for example the batteries *inside* the Bluetooth mouse + #: plugins/fwupd/gs-fwupd-app.c:85 + #, c-format + msgid "Device battery power is too low (%u%%, requires %u%%)" +-msgstr "" ++msgstr "Úroveň nabití baterie zařízení je příliš nízká (%u%%, vyžaduje %u%%)" + + #. TRANSLATORS: usually this is when we're waiting for a reboot + #: plugins/fwupd/gs-fwupd-app.c:91 + msgid "Device is waiting for the update to be applied" +-msgstr "" ++msgstr "Zařízení čeká na aplikování aktualizace" + + #. TRANSLATORS: as in, wired mains power for a laptop + #: plugins/fwupd/gs-fwupd-app.c:95 + msgid "Device requires AC power to be connected" +-msgstr "" ++msgstr "Zařízení vyžaduje připojené napájení za sítě" + + #. TRANSLATORS: lid means "laptop top cover" + #: plugins/fwupd/gs-fwupd-app.c:99 +-#, fuzzy +-#| msgid "Device cannot be used during update." + msgid "Device cannot be used while the lid is closed" +-msgstr "Zařízení nelze během aktualizace používat." ++msgstr "Zařízení nelze používat, pokud je víko notebooku zavřené" + + #. TRANSLATORS: a specific part of hardware, + #. * the first %s is the device name, e.g. 'Unifying Receiver` +-#: plugins/fwupd/gs-fwupd-app.c:218 ++#: plugins/fwupd/gs-fwupd-app.c:219 + #, c-format + msgid "%s Device Update" + msgstr "Aktualizace zařízení %s" + + #. TRANSLATORS: the entire system, e.g. all internal devices, + #. * the first %s is the device name, e.g. 'ThinkPad P50` +-#: plugins/fwupd/gs-fwupd-app.c:223 ++#: plugins/fwupd/gs-fwupd-app.c:224 + #, c-format + msgid "%s System Update" + msgstr "Aktualizace systému pro %s" + + #. TRANSLATORS: the EC is typically the keyboard controller chip, + #. * the first %s is the device name, e.g. 'ThinkPad P50` +-#: plugins/fwupd/gs-fwupd-app.c:228 ++#: plugins/fwupd/gs-fwupd-app.c:229 + #, c-format + msgid "%s Embedded Controller Update" + msgstr "Aktualizace vestavěného řadiče pro %s" + + #. TRANSLATORS: ME stands for Management Engine, the Intel AMT thing, + #. * the first %s is the device name, e.g. 'ThinkPad P50` +-#: plugins/fwupd/gs-fwupd-app.c:233 ++#: plugins/fwupd/gs-fwupd-app.c:234 + #, c-format + msgid "%s ME Update" + msgstr "Aktualizace ME pro %s" + + #. TRANSLATORS: ME stands for Management Engine (with Intel AMT), + #. * where the first %s is the device name, e.g. 'ThinkPad P50` +-#: plugins/fwupd/gs-fwupd-app.c:238 ++#: plugins/fwupd/gs-fwupd-app.c:239 + #, c-format + msgid "%s Corporate ME Update" + msgstr "Aktualizace ME pro firmy pro %s" + + #. TRANSLATORS: ME stands for Management Engine, where + #. * the first %s is the device name, e.g. 'ThinkPad P50` +-#: plugins/fwupd/gs-fwupd-app.c:243 ++#: plugins/fwupd/gs-fwupd-app.c:244 + #, c-format + msgid "%s Consumer ME Update" + msgstr "Aktualizace ME pro běžné spotřebitele pro %s" +@@ -5240,7 +5308,7 @@ msgstr "Aktualizace ME pro běžné spotřebitele pro %s" + #. TRANSLATORS: the controller is a device that has other devices + #. * plugged into it, for example ThunderBolt, FireWire or USB, + #. * the first %s is the device name, e.g. 'Intel ThunderBolt` +-#: plugins/fwupd/gs-fwupd-app.c:249 ++#: plugins/fwupd/gs-fwupd-app.c:250 + #, c-format + msgid "%s Controller Update" + msgstr "Aktualizace řadiče pro %s" +@@ -5248,97 +5316,137 @@ msgstr "Aktualizace řadiče pro %s" + #. TRANSLATORS: the Thunderbolt controller is a device that + #. * has other high speed Thunderbolt devices plugged into it; + #. * the first %s is the system name, e.g. 'ThinkPad P50` +-#: plugins/fwupd/gs-fwupd-app.c:255 ++#: plugins/fwupd/gs-fwupd-app.c:256 + #, c-format + msgid "%s Thunderbolt Controller Update" + msgstr "Aktualizace řadiče Thunderbolt pro %s" + + #. TRANSLATORS: the CPU microcode is firmware loaded onto the CPU + #. * at system bootup +-#: plugins/fwupd/gs-fwupd-app.c:260 ++#: plugins/fwupd/gs-fwupd-app.c:261 + #, c-format + msgid "%s CPU Microcode Update" + msgstr "Aktualizace mikrokódu CPU pro %s" + + #. TRANSLATORS: configuration refers to hardware state, + #. * e.g. a security database or a default power value +-#: plugins/fwupd/gs-fwupd-app.c:265 ++#: plugins/fwupd/gs-fwupd-app.c:266 + #, c-format + msgid "%s Configuration Update" + msgstr "Aktualizace nastavení pro %s" + + #. TRANSLATORS: battery refers to the system power source +-#: plugins/fwupd/gs-fwupd-app.c:269 ++#: plugins/fwupd/gs-fwupd-app.c:270 + #, c-format + msgid "%s Battery Update" + msgstr "Aktualizace baterie pro %s" + + #. TRANSLATORS: camera can refer to the laptop internal + #. * camera in the bezel or external USB webcam +-#: plugins/fwupd/gs-fwupd-app.c:274 ++#: plugins/fwupd/gs-fwupd-app.c:275 + #, c-format + msgid "%s Camera Update" + msgstr "Aktualizace kamery pro %s" + + #. TRANSLATORS: TPM refers to a Trusted Platform Module +-#: plugins/fwupd/gs-fwupd-app.c:278 ++#: plugins/fwupd/gs-fwupd-app.c:279 + #, c-format + msgid "%s TPM Update" + msgstr "Aktualizace TPM pro %s" + + #. TRANSLATORS: TouchPad refers to a flat input device +-#: plugins/fwupd/gs-fwupd-app.c:282 ++#: plugins/fwupd/gs-fwupd-app.c:283 + #, c-format + msgid "%s Touchpad Update" + msgstr "Aktualizace touchpadu pro %s" + + #. TRANSLATORS: Mouse refers to a handheld input device +-#: plugins/fwupd/gs-fwupd-app.c:286 ++#: plugins/fwupd/gs-fwupd-app.c:287 + #, c-format + msgid "%s Mouse Update" + msgstr "Aktualizace myši pro %s" + + #. TRANSLATORS: Keyboard refers to an input device for typing +-#: plugins/fwupd/gs-fwupd-app.c:290 ++#: plugins/fwupd/gs-fwupd-app.c:291 + #, c-format + msgid "%s Keyboard Update" + msgstr "Aktualizace klávesnice pro %s" + + #. TRANSLATORS: Storage Controller is typically a RAID or SAS adapter +-#: plugins/fwupd/gs-fwupd-app.c:294 ++#: plugins/fwupd/gs-fwupd-app.c:295 + #, c-format + msgid "%s Storage Controller Update" + msgstr "Aktualizace řadiče disků pro %s" + + #. TRANSLATORS: Network Interface refers to the physical + #. * PCI card, not the logical wired connection +-#: plugins/fwupd/gs-fwupd-app.c:299 ++#: plugins/fwupd/gs-fwupd-app.c:300 + #, c-format + msgid "%s Network Interface Update" + msgstr "Aktualizace síťové karty pro %s" + + #. TRANSLATORS: Video Display refers to the laptop internal display or + #. * external monitor +-#: plugins/fwupd/gs-fwupd-app.c:304 ++#: plugins/fwupd/gs-fwupd-app.c:305 + #, c-format + msgid "%s Display Update" + msgstr "Aktualizace displeje pro %s" + + #. TRANSLATORS: BMC refers to baseboard management controller which + #. * is the device that updates all the other firmware on the system +-#: plugins/fwupd/gs-fwupd-app.c:309 ++#: plugins/fwupd/gs-fwupd-app.c:310 + #, c-format + msgid "%s BMC Update" + msgstr "Aktualizace BMC pro %s" + + #. TRANSLATORS: Receiver refers to a radio device, e.g. a tiny Bluetooth + #. * device that stays in the USB port so the wireless peripheral works +-#: plugins/fwupd/gs-fwupd-app.c:314 ++#: plugins/fwupd/gs-fwupd-app.c:315 + #, c-format + msgid "%s USB Receiver Update" + msgstr "Aktualizace přijímače USB pro %s" + +-#: plugins/fwupd/gs-plugin-fwupd.c:1244 ++#. TRANSLATORS: drive refers to a storage device, e.g. SATA disk ++#: plugins/fwupd/gs-fwupd-app.c:319 ++#, c-format ++msgid "%s Drive Update" ++msgstr "Aktualizace disku pro %s" ++ ++#. TRANSLATORS: flash refers to solid state storage, e.g. UFS or eMMC ++#: plugins/fwupd/gs-fwupd-app.c:323 ++#, c-format ++msgid "%s Flash Drive Update" ++msgstr "Aktualizace flash disku pro %s" ++ ++#. TRANSLATORS: SSD refers to a Solid State Drive, e.g. non-rotating ++#. * SATA or NVMe disk ++#: plugins/fwupd/gs-fwupd-app.c:328 ++#, c-format ++msgid "%s SSD Update" ++msgstr "Aktualizace SSD pro %s" ++ ++#. TRANSLATORS: GPU refers to a Graphics Processing Unit, e.g. ++#. * the "video card" ++#: plugins/fwupd/gs-fwupd-app.c:333 ++#, c-format ++msgid "%s GPU Update" ++msgstr "Aktualizace grafické karty pro %s" ++ ++#. TRANSLATORS: Dock refers to the port replicator hardware laptops are ++#. * cradled in, or lowered onto ++#: plugins/fwupd/gs-fwupd-app.c:338 ++#, c-format ++msgid "%s Dock Update" ++msgstr "Aktualizace dokovacího zařízení pro %s" ++ ++#. TRANSLATORS: Dock refers to the port replicator device connected ++#. * by plugging in a USB cable -- which may or may not also provide power ++#: plugins/fwupd/gs-fwupd-app.c:343 ++#, c-format ++msgid "%s USB Dock Update" ++msgstr "Aktualizace USB dokovacího zařízení pro %s" ++ ++#: plugins/fwupd/gs-plugin-fwupd.c:1763 + msgid "Firmware" + msgstr "Firmware" + +@@ -5350,11 +5458,11 @@ msgstr "Podpora aktualizací firmwaru" + msgid "Provides support for firmware upgrades" + msgstr "Poskytuje podporu pro povyšování verzí firmwaru" + +-#: plugins/packagekit/gs-packagekit-task.c:148 ++#: plugins/packagekit/gs-packagekit-task.c:147 + msgid "Install Unsigned Software?" + msgstr "Nainstalovat nepodepsaný software?" + +-#: plugins/packagekit/gs-packagekit-task.c:149 ++#: plugins/packagekit/gs-packagekit-task.c:148 + msgid "" + "Software that is to be installed is not signed. It will not be possible to " + "verify the origin of updates to this software, or whether updates have been " +@@ -5363,11 +5471,11 @@ msgstr "" + "Software, který se chystáte nainstalovat, není podepsaný. Nebude tak možné " + "ověřit původ jeho aktualizací, nebo zda aktualizace nebyly zmanipulovány." + +-#: plugins/packagekit/gs-packagekit-task.c:153 ++#: plugins/packagekit/gs-packagekit-task.c:152 + msgid "Download Unsigned Software?" + msgstr "Stáhnout nepodepsaný software?" + +-#: plugins/packagekit/gs-packagekit-task.c:154 ++#: plugins/packagekit/gs-packagekit-task.c:153 + msgid "" + "Unsigned updates are available. Without a signature, it is not possible to " + "verify the origin of the update, or whether it has been tampered with." +@@ -5375,11 +5483,11 @@ msgstr "" + "Jsou k dispozici nepodepsané aktualizace. Bez podpisu není možné ověřit " + "původ aktualizace, nebo zda nebyla zmanipulována." + +-#: plugins/packagekit/gs-packagekit-task.c:158 ++#: plugins/packagekit/gs-packagekit-task.c:157 + msgid "Update Unsigned Software?" + msgstr "Aktualizovat nepodepsaný software?" + +-#: plugins/packagekit/gs-packagekit-task.c:159 ++#: plugins/packagekit/gs-packagekit-task.c:158 + msgid "" + "Unsigned updates are available. Without a signature, it is not possible to " + "verify the origin of the update, or whether it has been tampered with. " +@@ -5391,11 +5499,11 @@ msgstr "" + "zakázány, dokud nebudou nepodepsané aktualizace buďto odstraněny nebo " + "nahrazeny jinými." + +-#: plugins/packagekit/gs-plugin-packagekit.c:367 ++#: plugins/packagekit/gs-plugin-packagekit.c:416 + msgid "Packages" + msgstr "Balíčky" + +-#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:2696 ++#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:2764 + msgid "Operating System (OSTree)" + msgstr "Operační systém (OSTree)" + +@@ -5412,6 +5520,76 @@ msgstr "Podpora pro Snap" + msgid "A snap is a universal Linux package" + msgstr "Snap je univerzální linuxový balíček" + ++#~ msgid "Selected add-ons will be installed with the app." ++#~ msgstr "Vybrané doplňky budou nainstalovány spolu s aplikací." ++ ++#~ msgid "The last timestamp when the system was online and got any updates" ++#~ msgstr "" ++#~ "Datum a čas, kdy byl systém naposledy on-line a dostal nějaké aktualizace" ++ ++#~ msgid "_User" ++#~ msgstr "_Uživatel" ++ ++#~ msgid "" ++#~ "This software is not available in your language and will appear in US " ++#~ "English." ++#~ msgstr "" ++#~ "Tento software není dostupný ve vašem jazyce a zobrazí se v americké " ++#~ "angličtině." ++ ++#~ msgid "Applications" ++#~ msgstr "Aplikace" ++ ++#~ msgid "Web Applications" ++#~ msgstr "Webové aplikace" ++ ++#~ msgid "Post Review" ++#~ msgstr "Příspěvek do recenzí" ++ ++#~ msgid "_Post" ++#~ msgstr "_Odeslat" ++ ++#~ msgid "Rating" ++#~ msgstr "Hodnocení" ++ ++#~ msgid "" ++#~ "Give a short summary of your review, for example: “Great app, would " ++#~ "recommend”." ++#~ msgstr "" ++#~ "Uveďte krátké shrnutí své recenze, například: „Skvělá aplikace, " ++#~ "doporučuji“." ++ ++#~ msgctxt "app review" ++#~ msgid "Review" ++#~ msgstr "Recenze" ++ ++#~ msgid "What do you think of the app? Try to give reasons for your views." ++#~ msgstr "Co si o aplikaci myslíte? Snažte se uvést důvody svého hodnocení." ++ ++#~ msgid "No screenshot provided" ++#~ msgstr "Nemá snímek obrazovky" ++ ++#~ msgid "Primary Menu" ++#~ msgstr "Hlavní nabídky" ++ ++#~ msgctxt "Header bar button for list of apps to be updated" ++#~ msgid "Updates" ++#~ msgstr "Aktualizace" ++ ++#, c-format ++#~ msgid "%s %s is no longer supported." ++#~ msgstr "Systém %s %s již není podporován." ++ ++#~ msgid "This means that it does not receive security updates." ++#~ msgstr "" ++#~ "Znamená to, že pro něj již nadále nejsou poskytovány bezpečnostní opravy." ++ ++#~ msgid "It is recommended that you upgrade to a more recent version." ++#~ msgstr "Doporučuje se povýšit na nejnovější verzi." ++ ++#~ msgid "Application Updates" ++#~ msgstr "Aktualizace aplikací" ++ + #~ msgid "_Continue" + #~ msgstr "_Pokračovat" + diff --git a/gnome-software.spec b/gnome-software.spec index d525c64..746ce38 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -20,7 +20,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 44~rc +Version: 44.0 Release: 1%{?dist} Summary: A software center for GNOME @@ -29,6 +29,7 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/44/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch +Patch02: 0002-update-czech-translation.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -228,6 +229,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Mar 17 2023 Milan Crha - 44.0-1 +- Update to 44.0 + * Fri Mar 03 2023 Milan Crha - 44~rc-1 - Update to 44.rc diff --git a/sources b/sources index 0ad486a..91637d7 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-44.rc.tar.xz) = 15d40987a001af58dd0a671c8aa7399a1397a21bcd62ff5850e5dde4cee67cb64d53408492d8da0990cee301bf535b5c1954257d8dcbb0f49ba74ee1347ec843 +SHA512 (gnome-software-44.0.tar.xz) = 592a88fd3488d7d9cd573eff99e8ec503169b52354d672263d7e514846c666c56f87fcbdb31fb8c497ed048808ec223646c247326af76a7e4a361084fd1b180e From 5babfff9d73355c6239465c7beac70fa499727a4 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 24 Mar 2023 07:17:17 +0100 Subject: [PATCH 083/163] Resolves: #2181367 (Prefer Fedora Flatpaks before RPM before other sources for apps) --- gnome-software.spec | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 746ce38..ddb80ca 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -21,7 +21,7 @@ Name: gnome-software Version: 44.0 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -152,6 +152,7 @@ official-repos = [ 'rhel-%{?rhel}' ] %else official-repos = [ 'anaconda', 'fedora', 'fedora-debuginfo', 'fedora-source', 'koji-override-0', 'koji-override-1', 'rawhide', 'rawhide-debuginfo', 'rawhide-source', 'updates', 'updates-debuginfo', 'updates-source', 'updates-testing', 'updates-testing-debuginfo', 'updates-testing-source', 'fedora-modular', 'fedora-modular-debuginfo', 'fedora-modular-source', 'rawhide-modular', 'rawhide-modular-debuginfo', 'rawhide-modular-source', 'fedora-cisco-openh264', 'fedora-cisco-openh264-debuginfo' ] required-repos = [ 'fedora', 'updates' ] +packaging-format-preference = [ 'flatpak:fedora', 'rpm' ] %endif FOE @@ -229,6 +230,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Mar 24 2023 Milan Crha - 44.0-2 +- Resolves: #2181367 (Prefer Fedora Flatpaks before RPM before other sources for apps) + * Fri Mar 17 2023 Milan Crha - 44.0-1 - Update to 44.0 From ba20db05e79a803486c744d7886b834bd4564d80 Mon Sep 17 00:00:00 2001 From: Yaakov Selkowitz Date: Sun, 26 Mar 2023 12:30:05 -0400 Subject: [PATCH 084/163] Fix libsoup runtime dependency This was switched to libsoup3 in 44~alpha but the runtime dependency was not switched to match. With the switch, there is no particular version constraint, so just rely on the dynamic link dependency. --- gnome-software.spec | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index ddb80ca..42a59ce 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -5,7 +5,6 @@ %global gtk4_version 4.9.2 %global json_glib_version 1.2.0 %global libadwaita_version 1.3.alpha -%global libsoup_version 2.52.0 %global libxmlb_version 0.1.7 %global packagekit_version 1.1.1 @@ -21,7 +20,7 @@ Name: gnome-software Version: 44.0 -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -77,7 +76,6 @@ Requires: json-glib%{?_isa} >= %{json_glib_version} Requires: iso-codes # librsvg2 is needed for gdk-pixbuf svg loader Requires: librsvg2%{?_isa} -Requires: libsoup%{?_isa} >= %{libsoup_version} Requires: libxmlb%{?_isa} >= %{libxmlb_version} Recommends: PackageKit%{?_isa} >= %{packagekit_version} @@ -230,6 +228,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Sun Mar 26 2023 Yaakov Selkowitz - 44.0-3 +- Fix libsoup runtime dependency + * Fri Mar 24 2023 Milan Crha - 44.0-2 - Resolves: #2181367 (Prefer Fedora Flatpaks before RPM before other sources for apps) From 248c8dbdc8defa97548be91e1abca25df0f644da Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 27 Mar 2023 08:46:48 +0200 Subject: [PATCH 085/163] Added 'flatpak:fedora-testing' into packaging-format-preference --- gnome-software.spec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 42a59ce..79fd305 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -150,7 +150,7 @@ official-repos = [ 'rhel-%{?rhel}' ] %else official-repos = [ 'anaconda', 'fedora', 'fedora-debuginfo', 'fedora-source', 'koji-override-0', 'koji-override-1', 'rawhide', 'rawhide-debuginfo', 'rawhide-source', 'updates', 'updates-debuginfo', 'updates-source', 'updates-testing', 'updates-testing-debuginfo', 'updates-testing-source', 'fedora-modular', 'fedora-modular-debuginfo', 'fedora-modular-source', 'rawhide-modular', 'rawhide-modular-debuginfo', 'rawhide-modular-source', 'fedora-cisco-openh264', 'fedora-cisco-openh264-debuginfo' ] required-repos = [ 'fedora', 'updates' ] -packaging-format-preference = [ 'flatpak:fedora', 'rpm' ] +packaging-format-preference = [ 'flatpak:fedora-testing', 'flatpak:fedora', 'rpm' ] %endif FOE From 487ab393e18ebb579e3ae21643ed57cb560b6669 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 21 Apr 2023 08:55:05 +0200 Subject: [PATCH 086/163] Update to 44.1 --- 0002-update-czech-translation.patch | 4889 --------------------------- gnome-software.spec | 8 +- sources | 2 +- 3 files changed, 6 insertions(+), 4893 deletions(-) delete mode 100644 0002-update-czech-translation.patch diff --git a/0002-update-czech-translation.patch b/0002-update-czech-translation.patch deleted file mode 100644 index 86b6304..0000000 --- a/0002-update-czech-translation.patch +++ /dev/null @@ -1,4889 +0,0 @@ -diff --git a/po/cs.po b/po/cs.po -index 3301fcaf4..b532ac8a9 100644 ---- a/po/cs.po -+++ b/po/cs.po -@@ -4,22 +4,23 @@ - # - # Petr Kovar , 2015. - # Marek Černocký , 2013, 2014, 2015, 2016, 2017, 2018, 2019, 2020, 2021, 2022. --# Vojtěch Perník , 2021-2022. -+# Vojtěch Perník , 2021-2023. -+# Daniel Rusek , 2023. - # - msgid "" - msgstr "" - "Project-Id-Version: gnome-software\n" - "Report-Msgid-Bugs-To: https://gitlab.gnome.org/GNOME/gnome-software/issues\n" --"POT-Creation-Date: 2022-11-10 08:39+0000\n" --"PO-Revision-Date: 2022-08-28 11:45+0200\n" --"Last-Translator: Vojtěch Perník \n" -+"POT-Creation-Date: 2023-03-16 13:07+0000\n" -+"PO-Revision-Date: 2023-03-16 12:54+0100\n" -+"Last-Translator: Daniel Rusek \n" - "Language-Team: Czech \n" - "Language: cs\n" - "MIME-Version: 1.0\n" - "Content-Type: text/plain; charset=UTF-8\n" - "Content-Transfer-Encoding: 8bit\n" - "Plural-Forms: nplurals=3; plural=(n==1) ? 0 : (n>=2 && n<=4) ? 1 : 2;\n" --"X-Generator: Poedit 3.1.1\n" -+"X-Generator: Poedit 3.2.2\n" - "X-Project-Style: gnome\n" - - #: data/metainfo/org.gnome.Software.metainfo.xml.in:7 src/gs-shell.ui:21 -@@ -33,18 +34,18 @@ msgstr "Instalujte a aktualizujte aplikace" - - #: data/metainfo/org.gnome.Software.metainfo.xml.in:10 - msgid "" --"Software allows you to find and install new applications and system " --"extensions and remove existing installed applications." -+"Software allows you to find and install new apps and system extensions and " -+"remove existing installed apps." - msgstr "" - "Aplikace Software umožňuje vyhledávat a instalovat aplikace a systémová " - "rozšíření a odebírat stávající nainstalované aplikace." - - #: data/metainfo/org.gnome.Software.metainfo.xml.in:14 - msgid "" --"Software showcases featured and popular applications with useful " --"descriptions and multiple screenshots per application. Applications can be " --"found either through browsing the list of categories or by searching. It " --"also allows you to update your system using an offline update." -+"Software showcases featured and popular apps with useful descriptions and " -+"multiple screenshots per app. Apps can be found either through browsing the " -+"list of categories or by searching. It also allows you to update your system " -+"using an offline update." - msgstr "" - "Aplikace Software vám představí významné a oblíbené aplikace pomocí " - "srozumitelného popisu a několika snímků obrazovky. Aplikace můžete najít buď " -@@ -73,7 +74,7 @@ msgstr "Panel s aktualizacemi" - msgid "The update details" - msgstr "Podrobnosti o aktualizaci" - --#: data/metainfo/org.gnome.Software.metainfo.xml.in:2076 -+#: data/metainfo/org.gnome.Software.metainfo.xml.in:2222 - #: src/gs-application.c:264 - msgid "The GNOME Project" - msgstr "Projekt GNOME" -@@ -195,17 +196,12 @@ msgid "The last update timestamp" - msgstr "Datum a čas poslední aktualizace" - - #: data/org.gnome.software.gschema.xml:67 --msgid "The last timestamp when the system was online and got any updates" --msgstr "" --"Datum a čas, kdy byl systém naposledy on-line a dostal nějaké aktualizace" -- --#: data/org.gnome.software.gschema.xml:71 - msgid "The age in seconds to verify the upstream screenshot is still valid" - msgstr "" - "Doba v sekundách, po které se má ověřit, jestli je snímek obrazovky z " - "hlavního zdroje stále platný" - --#: data/org.gnome.software.gschema.xml:72 -+#: data/org.gnome.software.gschema.xml:68 - msgid "" - "Choosing a larger value will mean less round-trips to the remote server but " - "updates to the screenshots may take longer to show to the user. A value of 0 " -@@ -216,75 +212,75 @@ msgstr "" - "znamená, že se kontroly na serveru nemají provádět vůbec, pokud je již " - "snímek v mezipaměti." - --#: data/org.gnome.software.gschema.xml:81 -+#: data/org.gnome.software.gschema.xml:77 - msgid "The server to use for application reviews" - msgstr "Server, který se má používat pro recenze aktualizací" - --#: data/org.gnome.software.gschema.xml:85 -+#: data/org.gnome.software.gschema.xml:81 - msgid "The minimum karma score for reviews" - msgstr "Minimální karma pro recenze" - --#: data/org.gnome.software.gschema.xml:86 -+#: data/org.gnome.software.gschema.xml:82 - msgid "Reviews with karma less than this number will not be shown." - msgstr "Recenze s karmou nižší než toto číslo nebudou zobrazovány." - --#: data/org.gnome.software.gschema.xml:90 -+#: data/org.gnome.software.gschema.xml:86 - msgid "A list of official repositories that should not be considered 3rd party" - msgstr "" - "Seznam oficiálních repozitářů, které by neměly být považovány za třetí stranu" - --#: data/org.gnome.software.gschema.xml:94 -+#: data/org.gnome.software.gschema.xml:90 - msgid "A list of required repositories that cannot be disabled or removed" - msgstr "" - "Seznam vyžadovaných repozitářů, které nemohou být zakázány nebo odebrány" - --#: data/org.gnome.software.gschema.xml:98 -+#: data/org.gnome.software.gschema.xml:94 - msgid "A list of official repositories that should be considered free software" - msgstr "" - "Seznam oficiálních repozitářů, které by měly být považovány za svobodný " - "software" - --#: data/org.gnome.software.gschema.xml:102 -+#: data/org.gnome.software.gschema.xml:98 - msgid "" - "The licence URL to use when an application should be considered free software" - msgstr "" - "Adresa URL licence, která se má použít, když má aplikace považována za " - "svobodný software" - --#: data/org.gnome.software.gschema.xml:106 -+#: data/org.gnome.software.gschema.xml:102 - msgid "Install bundled applications for all users on the system where possible" - msgstr "" - "Kde je to možné, instalovat všem uživatelům v systému přibalené aplikace" - --#: data/org.gnome.software.gschema.xml:110 -+#: data/org.gnome.software.gschema.xml:106 - msgid "Allow access to the Software Repositories dialog" - msgstr "Umožnit přístup k dialogovému oknu s repozitáři softwaru" - --#: data/org.gnome.software.gschema.xml:114 -+#: data/org.gnome.software.gschema.xml:110 - msgid "Offer upgrades for pre-releases" - msgstr "Nabízet povýšení na předběžná vydání" - --#: data/org.gnome.software.gschema.xml:118 -+#: data/org.gnome.software.gschema.xml:114 - msgid "Show some UI elements informing the user that an app is non-free" - msgstr "" - "Zobrazovat v rozhraní prvky, které informují uživatele, že aplikace není " - "svobodná" - --#: data/org.gnome.software.gschema.xml:122 -+#: data/org.gnome.software.gschema.xml:118 - msgid "Show the installed size for apps in the list of installed applications" - msgstr "" - "Zobrazovat velikost instalace pro aplikace v seznamu nainstalovaných aplikací" - - #. Translators: Replace the link with a version in your language, e.g. 'https://de.wikipedia.org/wiki/Proprietäre_Software'. Remember to include ''. --#: data/org.gnome.software.gschema.xml:126 -+#: data/org.gnome.software.gschema.xml:122 - msgid "'https://en.wikipedia.org/wiki/Proprietary_software'" - msgstr "'https://cs.wikipedia.org/wiki/Propriet%C3%A1rn%C3%AD_software'" - --#: data/org.gnome.software.gschema.xml:127 -+#: data/org.gnome.software.gschema.xml:123 - msgid "The URI that explains nonfree and proprietary software" - msgstr "Adresa URI, která vysvětluje nesvobodný a komerční software" - --#: data/org.gnome.software.gschema.xml:131 -+#: data/org.gnome.software.gschema.xml:127 - msgid "" - "A list of URLs pointing to appstream files that will be downloaded into an " - "swcatalog folder" -@@ -292,7 +288,7 @@ msgstr "" - "Seznam adres URL ukazujících na soubory appstream, které byly stažené do " - "složky swcatalog" - --#: data/org.gnome.software.gschema.xml:135 -+#: data/org.gnome.software.gschema.xml:131 - msgid "" - "Install the AppStream files to a system-wide location for all users. If " - "false, files are installed in non-standard $XDG_DATA_HOME/swcatalog/xml " -@@ -302,13 +298,7 @@ msgstr "" - "uživatele. Pokud je vypnuto, budou soubory instalovány do nestandardní " - "složky $XDG_DATA_HOME/swcatalog/xmls" - --#: data/org.gnome.software.gschema.xml:139 --#, fuzzy --#| msgid "" --#| "Priority order of packaging formats to prefer, with more important " --#| "formats listed first. An empty array means the default order. Omitted " --#| "formats are assumed to be listed last. Example packaging formats are: " --#| "deb, flatpak, rpm, snap." -+#: data/org.gnome.software.gschema.xml:135 - msgid "" - "Priority order of packaging formats to prefer, with more important formats " - "listed first. An empty array means the default order. Omitted formats are " -@@ -319,9 +309,24 @@ msgstr "" - "Prioritní pořadí formátů balíčků, kterým dáváte přednost, přičemž " - "důležitější formáty jsou uvedeny na prvním místě. Prázdné pole znamená " - "výchozí pořadí. Předpokládá se, že vynechané formáty budou uvedeny jako " --"poslední. Příklady balíčkovacích formátů: deb, flatpak, rpm, snap." -+"poslední. Příklady balíčkovacích formátů: deb, flatpak, rpm, snap. Formáty " -+"mohou být nepovinně specifikovány s názvem původu odděleného dvojtečkou, " -+"například „flatpak:flathub“." -+ -+#: data/org.gnome.software.gschema.xml:139 -+msgid "The timestamp of the last attempt to remove unused Flatpak runtimes" -+msgstr "" -+"Datum a čas posledního pokusu odebrat nepoužívaná běhová prostředí Flatpak" -+ -+#: data/org.gnome.software.gschema.xml:143 -+msgid "" -+"Set to 'true' to show only freely licensed apps and hide any proprietary " -+"apps." -+msgstr "" -+"Nastavte na „true“, chcete-li zobrazit pouze aplikace s otevřenou licencí a " -+"skrýt všechny proprietární aplikace." - --#: data/org.gnome.software.gschema.xml:146 -+#: data/org.gnome.software.gschema.xml:150 - msgid "A string storing the gnome-online-account id used to login" - msgstr "Řetězec uchovávající ID gnome-online-account pro přihlášení" - -@@ -710,7 +715,7 @@ msgstr "%s • %s" - - #. Translators: The app is considered suitable to be run by all ages of people. - #. * This is displayed in a context tile, so the string should be short. --#: src/gs-age-rating-context-dialog.c:936 -+#: src/gs-age-rating-context-dialog.c:935 - msgctxt "Age rating" - msgid "All" - msgstr "Vše" -@@ -719,44 +724,44 @@ msgstr "Vše" - #. * app’s context tile if the size is unknown. It should be short - #. * (at most a couple of characters wide). - #. Translators: This is shown in a bubble if the storage --#. * size of an application is not known. The bubble is small, -+#. * size of an app is not known. The bubble is small, - #. * so the string should be as short as possible. --#: src/gs-age-rating-context-dialog.c:949 src/gs-app-context-bar.c:206 -+#: src/gs-age-rating-context-dialog.c:948 src/gs-app-context-bar.c:206 - #: src/gs-storage-context-dialog.c:89 - msgid "?" - msgstr "?" - - #. Translators: This is a dialogue title which indicates that an app is suitable - #. * for all ages. The placeholder is the app name. --#: src/gs-age-rating-context-dialog.c:1023 -+#: src/gs-age-rating-context-dialog.c:1020 - #, c-format - msgid "%s is suitable for everyone" - msgstr "Aplikace %s je vhodná pro každého" - - #. Translators: This is a dialogue title which indicates that an app is suitable - #. * for children up to around age 3. The placeholder is the app name. --#: src/gs-age-rating-context-dialog.c:1027 -+#: src/gs-age-rating-context-dialog.c:1024 - #, c-format - msgid "%s is suitable for toddlers" - msgstr "Aplikace %s je vhodná pro batolata" - - #. Translators: This is a dialogue title which indicates that an app is suitable - #. * for children up to around age 5. The placeholder is the app name. --#: src/gs-age-rating-context-dialog.c:1031 -+#: src/gs-age-rating-context-dialog.c:1028 - #, c-format - msgid "%s is suitable for young children" - msgstr "Aplikace %s je vhodná pro malé děti" - - #. Translators: This is a dialogue title which indicates that an app is suitable - #. * for people up to around age 18. The placeholder is the app name. --#: src/gs-age-rating-context-dialog.c:1039 -+#: src/gs-age-rating-context-dialog.c:1036 - #, c-format - msgid "%s is suitable for teenagers" - msgstr "Aplikace %s je vhodná pro dospívající mládež" - - #. Translators: This is a dialogue title which indicates that an app is suitable - #. * for people aged up to and over 18. The placeholder is the app name. --#: src/gs-age-rating-context-dialog.c:1043 -+#: src/gs-age-rating-context-dialog.c:1040 - #, c-format - msgid "%s is suitable for adults" - msgstr "Aplikace %s je vhodná pro dospělé" -@@ -764,14 +769,14 @@ msgstr "Aplikace %s je vhodná pro dospělé" - #. Translators: This is a dialogue title which indicates that an app is suitable - #. * for a specified age group. The first placeholder is the app name, the second - #. * is the age group. --#: src/gs-age-rating-context-dialog.c:1048 -+#: src/gs-age-rating-context-dialog.c:1045 - #, c-format - msgid "%s is suitable for %s" - msgstr "Aplikace %s je vhodná pro %s" - - #. Translators: This is the title of the dialog which contains information about the suitability of an app for different ages. - #. this one’s not a placeholder --#: src/gs-age-rating-context-dialog.ui:5 src/gs-app-context-bar.ui:211 -+#: src/gs-age-rating-context-dialog.ui:5 src/gs-app-context-bar.ui:217 - msgid "Age Rating" - msgstr "Vhodné od věku" - -@@ -781,7 +786,7 @@ msgstr "Vhodné od věku" - msgid "How to contribute missing information" - msgstr "Jak přidat chybějící informace" - --#: lib/gs-app.c:6178 -+#: lib/gs-app.c:6256 - msgid "Local file" - msgstr "Místní soubor" - -@@ -790,44 +795,51 @@ msgstr "Místní soubor" - #. Example string: "Local file (RPM)" - #. Translators: The first placeholder is an app runtime - #. * name, the second is its version number. --#: lib/gs-app.c:6197 src/gs-safety-context-dialog.c:439 -+#: lib/gs-app.c:6275 src/gs-safety-context-dialog.c:443 - #, c-format - msgid "%s (%s)" - msgstr "%s (%s)" - --#: lib/gs-app.c:6274 -+#: lib/gs-app.c:6352 - msgid "Package" - msgstr "Balíček" - --#: src/gs-app-addon-row.c:97 src/gs-app-row.c:460 -+#: src/gs-app-addon-row.c:95 src/gs-app-row.c:452 - msgid "Pending" - msgstr "Čeká na zpracování" - --#: src/gs-app-addon-row.c:101 src/gs-app-row.c:464 src/gs-details-page.c:369 -+#: src/gs-app-addon-row.c:99 src/gs-app-row.c:456 src/gs-details-page.c:379 - msgid "Pending install" - msgstr "Čeká na instalaci" - --#: src/gs-app-addon-row.c:105 src/gs-app-row.c:468 src/gs-details-page.c:376 -+#: src/gs-app-addon-row.c:103 src/gs-app-row.c:460 src/gs-details-page.c:386 - msgid "Pending remove" - msgstr "Čeká na odebrání" - --#: src/gs-app-addon-row.c:111 src/gs-app-row.ui:197 src/gs-app-tile.ui:50 --#: src/gs-feature-tile.c:535 --msgctxt "Single app" --msgid "Installed" --msgstr "Nainstalováno" -- - #. TRANSLATORS: this is a button next to the search results that --#. * shows the status of an application being installed --#: src/gs-app-addon-row.c:115 src/gs-app-row.c:208 src/gs-details-page.c:362 -+#. * shows the status of an app being installed -+#: src/gs-app-addon-row.c:107 src/gs-app-row.c:207 src/gs-details-page.c:372 - msgid "Installing" - msgstr "Instaluje se" - --#: src/gs-app-addon-row.c:119 -+#: src/gs-app-addon-row.c:111 - msgid "Removing" - msgstr "Odebírá se" - --#: src/gs-app-addon-row.ui:64 src/gs-details-page.c:1015 -+#. TRANSLATORS: button text -+#. TRANSLATORS: button text in the header when an app -+#. * can be installed -+#. TRANSLATORS: button text in the header when firmware -+#. * can be live-installed -+#. TRANSLATORS: update the fw -+#: src/gs-app-addon-row.ui:66 src/gs-common.c:303 src/gs-details-page.c:924 -+#: src/gs-details-page.c:950 src/gs-details-page.ui:209 src/gs-page.c:412 -+#: plugins/packagekit/gs-packagekit-task.c:149 -+msgid "_Install" -+msgstr "_Instalovat" -+ -+#. TRANSLATORS: this is button text to remove the app -+#: src/gs-app-addon-row.ui:73 src/gs-page.c:551 - msgid "_Uninstall" - msgstr "_Odinstalovat" - -@@ -855,116 +867,120 @@ msgstr "Služby sezení" - msgid "Can access D-Bus services on the session bus" - msgstr "Může přistupovat k službám D-Bus na sběrnici sezení" - --#: src/gs-app-details-page.c:71 -+#: src/gs-app-details-page.c:71 src/gs-app-details-page.c:72 - msgid "Devices" - msgstr "Zařízení" - - #: src/gs-app-details-page.c:71 -+msgid "Can access arbitrary devices such as webcams" -+msgstr "Může přistupovat k libovolným zařízením, například webovým kamerám" -+ -+#: src/gs-app-details-page.c:72 - msgid "Can access system device files" - msgstr "Může přistupovat k souborům na systémovém zařízení" - --#: src/gs-app-details-page.c:72 src/gs-app-details-page.c:73 -+#: src/gs-app-details-page.c:73 src/gs-app-details-page.c:74 - msgid "Home folder" - msgstr "Domovská složka" - --#: src/gs-app-details-page.c:72 src/gs-app-details-page.c:74 --#: src/gs-app-details-page.c:77 src/gs-app-details-page.c:150 -+#: src/gs-app-details-page.c:73 src/gs-app-details-page.c:75 -+#: src/gs-app-details-page.c:78 src/gs-app-details-page.c:151 - msgid "Can view, edit and create files" - msgstr "Může zobrazovat, upravovat a vytvářet soubory" - --#: src/gs-app-details-page.c:73 src/gs-app-details-page.c:75 --#: src/gs-app-details-page.c:78 src/gs-app-details-page.c:145 -+#: src/gs-app-details-page.c:74 src/gs-app-details-page.c:76 -+#: src/gs-app-details-page.c:79 src/gs-app-details-page.c:146 - msgid "Can view files" - msgstr "Může zobrazovat soubory" - --#: src/gs-app-details-page.c:74 src/gs-app-details-page.c:75 -+#: src/gs-app-details-page.c:75 src/gs-app-details-page.c:76 - msgid "File system" - msgstr "Souborový systém" - - #. The GS_APP_PERMISSIONS_FLAGS_FILESYSTEM_OTHER is used only as a flag, with actual files being part of the read/full lists --#: src/gs-app-details-page.c:77 src/gs-app-details-page.c:78 -+#: src/gs-app-details-page.c:78 src/gs-app-details-page.c:79 - msgid "Downloads folder" - msgstr "Složka se staženými soubory" - --#: src/gs-app-details-page.c:79 -+#: src/gs-app-details-page.c:80 - msgid "Settings" - msgstr "Nastavení" - --#: src/gs-app-details-page.c:79 -+#: src/gs-app-details-page.c:80 - msgid "Can view and change any settings" - msgstr "Může zobrazovat a měnit libovolná nastavení" - --#: src/gs-app-details-page.c:80 -+#: src/gs-app-details-page.c:81 - msgid "Legacy display system" - msgstr "Zastaralý zobrazovací systém" - --#: src/gs-app-details-page.c:80 -+#: src/gs-app-details-page.c:81 - msgid "Uses an old, insecure display system" - msgstr "Používá starý, ne zcela bezpečný, zobrazovací systém" - --#: src/gs-app-details-page.c:81 -+#: src/gs-app-details-page.c:82 - msgid "Sandbox escape" - msgstr "Opuštění izolovaného prostředí" - --#: src/gs-app-details-page.c:81 -+#: src/gs-app-details-page.c:82 - msgid "Can escape the sandbox and circumvent any other restrictions" - msgstr "Může opustit izolované prostředí a obejít další omezení" - - #. FIXME support app == NULL - #. set window title --#: src/gs-app-details-page.c:166 -+#: src/gs-app-details-page.c:167 - msgid "Update Details" - msgstr "Podrobnosti o aktualizaci" - - #. TRANSLATORS: this is where the packager did not write - #. * a description for the update --#: src/gs-app-details-page.c:174 -+#: src/gs-app-details-page.c:175 - msgid "No update description available." - msgstr "Není k dispozici žádný popis aktualizace." - - #: src/gs-app-details-page.ui:25 src/gs-os-update-page.ui:25 --#: src/gs-shell.ui:369 src/gs-shell.ui:460 -+#: src/gs-shell.ui:348 src/gs-shell.ui:439 - msgid "Go back" - msgstr "Přejít zpět" - --#: src/gs-app-details-page.ui:48 src/gs-app-row.c:523 -+#: src/gs-app-details-page.ui:48 src/gs-app-row.c:515 - msgid "Requires additional permissions" - msgstr "Vyžaduje dodatečná oprávnění" - - #. Translators: Header of the section with other users' opinions about the app. --#: src/gs-app-reviews-dialog.ui:6 src/gs-details-page.ui:867 -+#: src/gs-app-reviews-dialog.ui:6 src/gs-details-page.ui:930 - msgid "Reviews" - msgstr "Recenze" - - #: src/gs-app-reviews-dialog.ui:25 --msgid "No reviews were found for this application." -+msgid "No reviews were found for this app." - msgstr "Pro tuto aplikaci nebyly nalezeny žádné recenze." - - #: src/gs-app-reviews-dialog.ui:27 - msgid "No Reviews" - msgstr "Bez recenzí" - --#: src/gs-app-version-history-dialog.ui:6 src/gs-details-page.ui:545 -+#: src/gs-app-version-history-dialog.ui:6 src/gs-details-page.ui:529 - msgid "Version History" - msgstr "Historie verzí" - --#: src/gs-app-version-history-row.c:71 -+#: src/gs-app-version-history-row.c:133 - #, c-format - msgid "New in Version %s" - msgstr "Novinky ve verzi %s" - --#: src/gs-app-version-history-row.c:78 -+#: src/gs-app-version-history-row.c:140 - #, c-format - msgid "Version %s" - msgstr "Verze %s" - --#: src/gs-app-version-history-row.c:80 -+#: src/gs-app-version-history-row.c:142 - msgid "No details for this release" - msgstr "K tomuto vydání nejsou k dispozici žádné podrobnosti." - - #. TRANSLATORS: This is the date string with: day number, month name, year. - #. i.e. "25 May 2012" --#: src/gs-app-version-history-row.c:94 src/gs-review-row.c:63 -+#: src/gs-app-version-history-row.c:156 src/gs-review-row.c:67 - msgid "%e %B %Y" - msgstr "%e. %B %Y" - -@@ -1040,8 +1056,8 @@ msgid "Installs any pending updates in the background" - msgstr "Nainstalovat na pozadí případné čekající aktualizace" - - #: src/gs-application.c:147 --msgid "Show update preferences" --msgstr "Zobrazit předvolby aktualizací" -+msgid "Show preferences" -+msgstr "Zobrazit předvolby" - - #: src/gs-application.c:149 - msgid "Quit the running instance" -@@ -1056,8 +1072,8 @@ msgid "Show version number" - msgstr "Zobrazit číslo verze" - - #: src/gs-application.c:271 src/gs-application.c:279 --msgid "Copyright © 2016–2022 GNOME Software contributors" --msgstr "Copyright © 2016 – 2022 přispěvatelé Softwaru GNOME" -+msgid "Copyright © 2016–2023 GNOME Software contributors" -+msgstr "Copyright © 2016 – 2023 přispěvatelé Softwaru GNOME" - - #: src/gs-application.c:273 src/gs-application.c:282 - msgid "translator-credits" -@@ -1067,7 +1083,7 @@ msgstr "" - - #. TRANSLATORS: this is the title of the about window - #. TRANSLATORS: this is the menu item that opens the about window --#: src/gs-application.c:287 src/gs-shell.c:2163 -+#: src/gs-application.c:287 src/gs-shell.c:2127 - msgid "About Software" - msgstr "O aplikaci Software" - -@@ -1077,11 +1093,11 @@ msgid "A nice way to manage the software on your system." - msgstr "Elegantní způsob správy softwaru ve vašem počítači." - - #. TRANSLATORS: we tried to show an app that did not exist --#: src/gs-application.c:478 -+#: src/gs-application.c:507 - msgid "Sorry! There are no details for that application." - msgstr "Omlouváme se, ale pro tuto aplikaci nejsou k dispozici detaily." - --#. Translators: The disk usage of an application when installed. -+#. Translators: The disk usage of an app when installed. - #. * This is displayed in a context tile, so the string should be short. - #: src/gs-app-context-bar.c:162 src/gs-storage-context-dialog.c:133 - msgid "Installed Size" -@@ -1106,7 +1122,7 @@ msgstr "Obsahuje %s mezipaměti" - msgid "Cache and data usage unknown" - msgstr "Využití mezipaměti a dat není známo" - --#. Translators: The download size of an application. -+#. Translators: The download size of an app. - #. * This is displayed in a context tile, so the string should be short. - #: src/gs-app-context-bar.c:187 src/gs-storage-context-dialog.c:165 - msgid "Download Size" -@@ -1136,117 +1152,123 @@ msgstr "Velikost je neznámá" - - #. Translators: This indicates an app requires no permissions to run. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:282 -+#: src/gs-app-context-bar.c:281 - msgid "No permissions" - msgstr "Žádná oprávnění" - - #. Translators: This indicates an app uses the network. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:293 -+#: src/gs-app-context-bar.c:292 - msgid "Has network access" - msgstr "Má přístup k síti" - - #. Translators: This indicates an app uses D-Bus system services. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:300 -+#: src/gs-app-context-bar.c:299 - msgid "Uses system services" - msgstr "Využívá služby systému" - - #. Translators: This indicates an app uses D-Bus session services. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:307 -+#: src/gs-app-context-bar.c:306 - msgid "Uses session services" - msgstr "Využívá služby sezení" - - #. Translators: This indicates an app can access arbitrary hardware devices. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:314 -+#: src/gs-app-context-bar.c:313 - msgid "Can access hardware devices" - msgstr "Může přistupovat k hardwarovým zařízením" - -+#. Translators: This indicates an app can access system devices such as /dev/shm. -+#. * It’s used in a context tile, so should be short. -+#: src/gs-app-context-bar.c:320 -+msgid "Can access system devices" -+msgstr "Může přistupovat k systémovým zařízením" -+ - #. Translators: This indicates an app can read/write to the user’s home or the entire filesystem. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:326 -+#: src/gs-app-context-bar.c:332 - msgid "Can read/write all your data" - msgstr "Může číst/zapisovat všechna vaše data" - - #. Translators: This indicates an app can read (but not write) from the user’s home or the entire filesystem. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:338 -+#: src/gs-app-context-bar.c:344 - msgid "Can read all your data" - msgstr "Může číst všechna vaše data" - - #. Translators: This indicates an app can read/write to the user’s Downloads directory. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:345 -+#: src/gs-app-context-bar.c:351 - msgid "Can read/write your downloads" - msgstr "Může zapisovat do všech vašich dat" - - #. Translators: This indicates an app can read (but not write) from the user’s Downloads directory. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:352 -+#: src/gs-app-context-bar.c:358 - msgid "Can read your downloads" - msgstr "Může číst vaše stažené soubory" - - #. Translators: This indicates an app can access data in the system unknown to the Software. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:359 -+#: src/gs-app-context-bar.c:365 - msgid "Can access arbitrary files" - msgstr "Může přistupovat k libovolným souborům" - - #. Translators: This indicates an app can access or change user settings. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:366 src/gs-safety-context-dialog.c:227 -+#: src/gs-app-context-bar.c:372 src/gs-safety-context-dialog.c:234 - msgid "Can access and change user settings" - msgstr "Může zobrazovat a měnit uživatelská nastavení" - - #. Translators: This indicates an app uses the X11 windowing system. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:373 src/gs-safety-context-dialog.c:211 -+#: src/gs-app-context-bar.c:379 src/gs-safety-context-dialog.c:218 - msgid "Uses a legacy windowing system" - msgstr "Používá starý zobrazovací systém" - - #. Translators: This indicates an app can escape its sandbox. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:380 src/gs-safety-context-dialog.c:219 -+#: src/gs-app-context-bar.c:386 src/gs-safety-context-dialog.c:226 - msgid "Can acquire arbitrary permissions" - msgstr "Může získat libovolná oprávnění" - --#. Translators: This indicates that an application has been packaged -+#. Translators: This indicates that an app has been packaged - #. * by the user’s distribution and is safe. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:406 src/gs-safety-context-dialog.c:146 -+#: src/gs-app-context-bar.c:412 src/gs-safety-context-dialog.c:145 - msgid "Reviewed by your distribution" - msgstr "Zkontrolováno vaší distribucí" - --#. Translators: This indicates that an application has been packaged -+#. Translators: This indicates that an app has been packaged - #. * by someone other than the user’s distribution, so might not be safe. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:413 src/gs-safety-context-dialog.c:143 -+#: src/gs-app-context-bar.c:419 src/gs-safety-context-dialog.c:142 - msgid "Provided by a third party" - msgstr "Poskytováno třetí stranou" - - #. Translators: This indicates an app is not licensed under a free software license. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:425 -+#: src/gs-app-context-bar.c:431 - msgid "Proprietary code" - msgstr "Uzavřený kód" - - #. Translators: This indicates an app’s source code is freely available, so can be audited for security. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:431 -+#: src/gs-app-context-bar.c:437 - msgid "Auditable code" - msgstr "Otevřený kód" - - #. Translators: This indicates an app was written and released by a developer who has been verified. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:438 -+#: src/gs-app-context-bar.c:444 - msgid "Software developer is verified" - msgstr "Vývojář softwaru je ověřený" - - #. Translators: This indicates an app or its runtime reached its end of life. - #. * It’s used in a context tile, so should be short. --#: src/gs-app-context-bar.c:447 -+#: src/gs-app-context-bar.c:453 - msgid "Software no longer supported" - msgstr "Software není nadále podporován" - -@@ -1264,180 +1286,180 @@ msgstr "Software není nadále podporován" - #. * If concatenating strings as a list using a separator like this is not - #. * possible in your language, please file an issue against gnome-software: - #. * https://gitlab.gnome.org/GNOME/gnome-software/-/issues/new --#: src/gs-app-context-bar.c:459 src/gs-app-context-bar.c:730 -+#: src/gs-app-context-bar.c:465 src/gs-app-context-bar.c:731 - msgid "; " - msgstr "; " - - #. Translators: The app is considered safe to install and run. - #. * This is displayed in a context tile, so the string should be short. --#: src/gs-app-context-bar.c:467 -+#: src/gs-app-context-bar.c:473 - msgid "Safe" - msgstr "Bezpečné" - - #. Translators: The app is considered potentially unsafe to install and run. - #. * This is displayed in a context tile, so the string should be short. --#: src/gs-app-context-bar.c:474 -+#: src/gs-app-context-bar.c:480 - msgid "Potentially Unsafe" - msgstr "Potenciálně nebezpečné" - - #. Translators: The app is considered unsafe to install and run. - #. * This is displayed in a context tile, so the string should be short. --#: src/gs-app-context-bar.c:481 -+#: src/gs-app-context-bar.c:487 - msgid "Unsafe" - msgstr "Nebezpečné" - --#: src/gs-app-context-bar.c:560 src/gs-app-context-bar.c:592 --#: src/gs-hardware-support-context-dialog.c:603 -+#: src/gs-app-context-bar.c:563 src/gs-app-context-bar.c:595 -+#: src/gs-hardware-support-context-dialog.c:602 - msgid "Mobile Only" - msgstr "Jen pro mobilní zařízení" - --#: src/gs-app-context-bar.c:561 -+#: src/gs-app-context-bar.c:564 - msgid "Only works on a small screen" - msgstr "Funguje pouze na malé obrazovce" - --#: src/gs-app-context-bar.c:566 src/gs-app-context-bar.c:599 --#: src/gs-app-context-bar.c:606 src/gs-app-context-bar.c:656 --#: src/gs-app-context-bar.c:661 src/gs-hardware-support-context-dialog.c:583 -+#: src/gs-app-context-bar.c:569 src/gs-app-context-bar.c:602 -+#: src/gs-app-context-bar.c:609 src/gs-app-context-bar.c:659 -+#: src/gs-app-context-bar.c:664 src/gs-hardware-support-context-dialog.c:582 - msgid "Desktop Only" - msgstr "Pouze pro PC" - --#: src/gs-app-context-bar.c:567 -+#: src/gs-app-context-bar.c:570 - msgid "Only works on a large screen" - msgstr "Funguje pouze na velké obrazovce" - --#: src/gs-app-context-bar.c:571 src/gs-hardware-support-context-dialog.c:621 -+#: src/gs-app-context-bar.c:574 src/gs-hardware-support-context-dialog.c:620 - msgid "Screen Size Mismatch" - msgstr "Nesoulad velikosti obrazovky" - --#: src/gs-app-context-bar.c:572 src/gs-hardware-support-context-dialog.c:622 -+#: src/gs-app-context-bar.c:575 src/gs-hardware-support-context-dialog.c:621 - msgid "Doesn’t support your current screen size" - msgstr "Nepodporuje vaši současnou velikost obrazovky" - --#: src/gs-app-context-bar.c:593 src/gs-hardware-support-context-dialog.c:674 --#: src/gs-hardware-support-context-dialog.c:680 -+#: src/gs-app-context-bar.c:596 src/gs-hardware-support-context-dialog.c:673 -+#: src/gs-hardware-support-context-dialog.c:679 - msgid "Requires a touchscreen" - msgstr "Vyžaduje dotykovou obrazovku" - --#: src/gs-app-context-bar.c:600 src/gs-hardware-support-context-dialog.c:634 --#: src/gs-hardware-support-context-dialog.c:640 -+#: src/gs-app-context-bar.c:603 src/gs-hardware-support-context-dialog.c:633 -+#: src/gs-hardware-support-context-dialog.c:639 - msgid "Requires a keyboard" - msgstr "Vyžaduje klávesnici" - --#: src/gs-app-context-bar.c:607 -+#: src/gs-app-context-bar.c:610 - msgid "Requires a mouse" - msgstr "Vyžaduje myš" - --#: src/gs-app-context-bar.c:618 -+#: src/gs-app-context-bar.c:621 - msgid "Gamepad Needed" - msgstr "Vyžaduje herní ovladač" - --#: src/gs-app-context-bar.c:619 -+#: src/gs-app-context-bar.c:622 - msgid "Requires a gamepad to play" - msgstr "Ke hraní vyžaduje herní ovladač" - - #. Translators: This is used in a context tile to indicate that - #. * an app works on phones, tablets *and* desktops. It should be - #. * short and in title case. --#: src/gs-app-context-bar.c:643 -+#: src/gs-app-context-bar.c:646 - msgid "Adaptive" - msgstr "Adaptivní" - --#: src/gs-app-context-bar.c:644 -+#: src/gs-app-context-bar.c:647 - msgid "Works on phones, tablets and desktops" - msgstr "Funguje na telefonech, tabletech a PC" - --#: src/gs-app-context-bar.c:657 -+#: src/gs-app-context-bar.c:660 - msgid "Probably requires a keyboard or mouse" - msgstr "Pravděpodobně vyžaduje klávesnici nebo myš" - --#: src/gs-app-context-bar.c:662 -+#: src/gs-app-context-bar.c:665 - msgid "Works on desktops and laptops" - msgstr "Funguje na PC a laptopech" - - #. Translators: This indicates that the content rating for an - #. * app says it can be used by all ages of people, as it contains - #. * no objectionable content. --#: src/gs-app-context-bar.c:705 -+#: src/gs-app-context-bar.c:706 - msgid "Contains no age-inappropriate content" - msgstr "Neobsahuje žádný věkově nevhodný obsah" - --#: src/gs-app-context-bar.c:753 -+#: src/gs-app-context-bar.c:754 - msgid "No age rating information available" - msgstr "Informace o věkové kategorii nejsou k dispozici" - - #. TRANSLATORS: this is a button next to the search results that --#. * allows the application to be easily installed --#: src/gs-app-row.c:155 -+#. * allows the app to be easily installed -+#: src/gs-app-row.c:154 - msgid "Visit Website" - msgstr "Navštívit webové stránky" - - #. TRANSLATORS: this is a button next to the search results that --#. * allows the application to be easily installed. -+#. * allows the app to be easily installed. - #. * The ellipsis indicates that further steps are required --#: src/gs-app-row.c:161 -+#: src/gs-app-row.c:160 - msgid "Install…" - msgstr "Instalovat…" - - #. TRANSLATORS: this is a button next to the search results that --#. * allows to cancel a queued install of the application --#: src/gs-app-row.c:169 src/gs-updates-section.ui:62 -+#. * allows to cancel a queued install of the app -+#: src/gs-app-row.c:168 src/gs-updates-section.ui:63 - msgid "Cancel" - msgstr "Zrušit" - - #. TRANSLATORS: this is a button next to the search results that --#. * allows the application to be easily installed --#. TRANSLATORS: button text --#. TRANSLATORS: update the fw --#: src/gs-app-row.c:177 src/gs-common.c:307 src/gs-page.c:374 -+#. * allows the app to be easily installed -+#: src/gs-app-row.c:176 - msgid "Install" - msgstr "Instalovat" - - #. TRANSLATORS: this is a button in the updates panel - #. * that allows the app to be easily updated live --#: src/gs-app-row.c:185 -+#: src/gs-app-row.c:184 - msgid "Update" - msgstr "Aktualizovat" - - #. TRANSLATORS: this is a button next to the search results that --#. * allows the application to be easily removed --#. TRANSLATORS: button text in the header when an application can be erased --#. TRANSLATORS: this is button text to remove the application --#: src/gs-app-row.c:191 src/gs-app-row.c:201 src/gs-details-page.ui:280 --#: src/gs-details-page.ui:290 src/gs-page.c:549 --msgid "Uninstall" --msgstr "Odinstalovat" -+#. * allows the app to be easily removed -+#: src/gs-app-row.c:190 src/gs-app-row.c:200 -+msgid "Uninstall…" -+msgstr "Odinstalovat…" - - #. TRANSLATORS: this is a button next to the search results that --#. * shows the status of an application being erased --#: src/gs-app-row.c:215 -+#. * shows the status of an app being erased -+#: src/gs-app-row.c:214 - msgid "Uninstalling" - msgstr "Odinstalovává se" - - #. TRANSLATORS: during the update the device - #. * will restart into a special update-only mode --#: src/gs-app-row.c:330 -+#: src/gs-app-row.c:327 - msgid "Device cannot be used during update." - msgstr "Zařízení nelze během aktualizace používat." - - #. TRANSLATORS: this refers to where the app came from --#: src/gs-app-row.c:340 src/gs-shell-search-provider.c:264 -+#: src/gs-app-row.c:337 src/gs-shell-search-provider.c:268 - #, c-format - msgid "Source: %s" - msgstr "Zdroj: %s" - - #. Translators: A message to indicate that an app has been renamed. The placeholder is the old human-readable name. --#: src/gs-app-row.c:530 -+#: src/gs-app-row.c:522 - #, c-format - msgid "Renamed from %s" - msgstr "Přejmenováno z %s" - --#. Translators: The placeholder is an application name -+#: src/gs-app-row.ui:197 src/gs-app-tile.ui:50 src/gs-feature-tile.c:543 -+msgctxt "Single app" -+msgid "Installed" -+msgstr "Nainstalováno" -+ -+#. Translators: The placeholder is an app name - #: src/gs-app-translation-dialog.c:67 - #, c-format - msgid "Help Translate %s" - msgstr "Pomozte přeložit %s" - --#. Translators: The placeholder is an application name -+#. Translators: The placeholder is an app name - #: src/gs-app-translation-dialog.c:70 - #, c-format - msgid "" -@@ -1451,7 +1473,7 @@ msgstr "" - "dobrovolníků.\n" - "\n" - "To znamená, že i když ještě není k dispozici ve vašem jazyce, můžete se " --"zapojit a pomoci s jeho překladem." -+"zapojit a pomoci s jejím překladem." - - #: src/gs-app-translation-dialog.ui:5 - msgid "Translations" -@@ -1467,29 +1489,35 @@ msgstr "_Stránka překladu" - msgid "Login required remote %s (realm %s)" - msgstr "Vyžadováno přihlášení vzdáleným %s (sféra %s)" - --#: src/gs-basic-auth-dialog.ui:13 -+#: src/gs-basic-auth-dialog.ui:6 - msgid "Login Required" - msgstr "Vyžadováno přihlášení" - --#: src/gs-basic-auth-dialog.ui:21 src/gs-common.c:721 --#: src/gs-details-page.ui:306 src/gs-removal-dialog.ui:28 --#: src/gs-review-dialog.ui:18 -+#. TRANSLATORS: button text -+#: src/gs-basic-auth-dialog.ui:12 src/gs-common.c:296 src/gs-common.c:697 -+#: src/gs-details-page.ui:297 src/gs-page.c:410 src/gs-page.c:549 -+#: src/gs-removal-dialog.ui:28 src/gs-repos-dialog.c:171 -+#: src/gs-repos-dialog.c:249 src/gs-review-dialog.ui:18 src/gs-review-row.c:237 -+#: src/gs-updates-page.c:847 src/gs-updates-page.c:864 - msgid "_Cancel" - msgstr "_Zrušit" - --#: src/gs-basic-auth-dialog.ui:35 -+#: src/gs-basic-auth-dialog.ui:24 - msgid "_Login" - msgstr "Přih_lásit" - --#: src/gs-basic-auth-dialog.ui:88 --msgid "_User" --msgstr "_Uživatel" -+#. Translators: Placeholder text for a login entry. -+#. Translators: It's an origin scope, 'User' or 'System' installation -+#: src/gs-basic-auth-dialog.ui:60 src/gs-origin-popover-row.ui:138 -+msgid "User" -+msgstr "Uživatel" - --#: src/gs-basic-auth-dialog.ui:107 --msgid "_Password" --msgstr "_Heslo" -+#. Translators: Placeholder text for a login entry. -+#: src/gs-basic-auth-dialog.ui:73 -+msgid "Password" -+msgstr "Heslo" - --#. TRANSLATORS: this is where all applications that don't -+#. TRANSLATORS: this is where all apps that don't - #. * fit in other groups are put - #: lib/gs-category.c:209 - msgid "Other" -@@ -1509,13 +1537,13 @@ msgstr "Významné" - - #. Heading for featured apps on a category page - #. Translators: This is a heading for software which has been featured ('picked') by the distribution. --#: src/gs-category-page.ui:41 src/gs-overview-page.ui:106 -+#: src/gs-category-page.ui:41 src/gs-overview-page.ui:69 - msgid "Editor’s Choice" - msgstr "Výběr od distribuce" - - #. Heading for recently updated apps on a category page - #. Translators: This is a heading for software which has been recently released upstream. --#: src/gs-category-page.ui:69 src/gs-overview-page.ui:129 -+#: src/gs-category-page.ui:69 src/gs-overview-page.ui:92 - msgid "New & Updated" - msgstr "Nové a aktualizované" - -@@ -1530,14 +1558,14 @@ msgid "Other Software" - msgstr "Ostatní" - - #. TRANSLATORS: the user isn't reading the question --#: lib/gs-cmd.c:194 -+#: lib/gs-cmd.c:195 - #, c-format - msgid "Please enter a number from 1 to %u: " - msgstr "Zadejte prosím číslo od 1 do %u: " - - #. TRANSLATORS: asking the user to choose an app from a list --#: lib/gs-cmd.c:266 --msgid "Choose an application:" -+#: lib/gs-cmd.c:283 -+msgid "Choose an app:" - msgstr "Vyberte aplikaci:" - - #: lib/gs-desktop-data.c:16 -@@ -1910,7 +1938,7 @@ msgstr "Jazykové balíčky" - msgid "Localization" - msgstr "Lokalizace" - --#. TRANSLATORS: this is the summary of a notification that an application -+#. TRANSLATORS: this is the summary of a notification that an app - #. * has been successfully installed - #. TRANSLATORS: this is the summary of a notification that a component - #. * has been successfully installed -@@ -1919,16 +1947,16 @@ msgstr "Lokalizace" - msgid "%s is now installed" - msgstr "Aplikace %s je nyní nainstalována" - --#. TRANSLATORS: an application has been installed, but -+#. TRANSLATORS: an app has been installed, but - #. * needs a reboot to complete the installation - #: src/gs-common.c:73 src/gs-common.c:96 - msgid "A restart is required for the changes to take effect." - msgstr "Aby se změny projevily, je zapotřebí provést restart." - --#. TRANSLATORS: this is the body of a notification that an application -+#. TRANSLATORS: this is the body of a notification that an app - #. * has been successfully installed - #: src/gs-common.c:77 --msgid "Application is ready to be used." -+msgid "App is ready to be used." - msgstr "Aplikace je připravená k použití." - - #. TRANSLATORS: this is the summary of a notification that OS updates -@@ -1944,7 +1972,7 @@ msgid "Recently installed updates are available to review" - msgstr "Nedávno nainstalované aktualizace jsou k dispozici pro recenze" - - #. TRANSLATORS: button text --#: src/gs-common.c:107 src/gs-common.c:884 -+#: src/gs-common.c:107 src/gs-common.c:860 - msgid "Restart" - msgstr "Restartovat" - -@@ -1953,97 +1981,98 @@ msgid "Launch" - msgstr "Spustit" - - #. TRANSLATORS: window title --#: src/gs-common.c:234 --#, fuzzy --#| msgid "Install Unsigned Software?" -+#: src/gs-common.c:230 - msgid "Install Software?" --msgstr "Nainstalovat nepodepsaný software?" -+msgstr "Nainstalovat software?" - - #. TRANSLATORS: window title --#: src/gs-common.c:236 -+#: src/gs-common.c:232 - msgid "Install Third-Party Software?" - msgstr "Instalovat software třetí strany?" - - #. TRANSLATORS: window title --#: src/gs-common.c:241 --#, fuzzy --#| msgid "Enable Third-Party Software Repository?" -+#: src/gs-common.c:236 - msgid "Enable Software Repository?" --msgstr "Povolit repozitář softwaru třetí strany?" -+msgstr "Povolit repozitář softwaru?" - - #. TRANSLATORS: window title --#: src/gs-common.c:243 src/gs-repos-dialog.c:168 -+#: src/gs-common.c:238 src/gs-repos-dialog.c:168 - msgid "Enable Third-Party Software Repository?" - msgstr "Povolit repozitář softwaru třetí strany?" - - #. TRANSLATORS: the replacements are as follows: --#. * 1. Application name, e.g. "Firefox" -+#. * 1. App name, e.g. "Firefox" - #. * 2. Software repository name, e.g. fedora-optional - #. --#: src/gs-common.c:261 -+#: src/gs-common.c:250 - #, c-format - msgid "" - "%s is not free and open source software, and is provided by “%s”." - msgstr "" --"%s není svobodný a otevřený software a poskytuje jej „%s“." -+"%s není svobodný a otevřený software a poskytuje jej „%s“." - - #. TRANSLATORS: the replacements are as follows: --#. * 1. Application name, e.g. "Firefox" -+#. * 1. App name, e.g. "Firefox" - #. * 2. Software repository name, e.g. fedora-optional --#: src/gs-common.c:271 -+#: src/gs-common.c:260 - #, c-format - msgid "%s is provided by “%s”." - msgstr "%s poskytuje „%s“." - --#: src/gs-common.c:280 -+#: src/gs-common.c:269 - msgid "This software repository must be enabled to continue installation." - msgstr "" - "Aby bylo možné pokračovat v instalaci, je nutné povolit tento repozitář " - "softwaru." - - #. TRANSLATORS: Laws are geographical, urgh... --#: src/gs-common.c:290 -+#: src/gs-common.c:279 - #, c-format - msgid "It may be illegal to install or use %s in some countries." - msgstr "" - "V některých zemích nemusí být instalace a používání softwaru %s legální." - - #. TRANSLATORS: Laws are geographical, urgh... --#: src/gs-common.c:296 -+#: src/gs-common.c:285 - msgid "It may be illegal to install or use this codec in some countries." - msgstr "" - "V některých zemích nemusí být instalace a používání tohoto kodeku legální." - - #. TRANSLATORS: this is button text to not ask about non-free content again --#: src/gs-common.c:303 --msgid "Don’t Warn Again" --msgstr "Příště nevarovat" -+#: src/gs-common.c:299 -+msgid "Don’t _Warn Again" -+msgstr "Příště _nevarovat" - - #. TRANSLATORS: button text --#: src/gs-common.c:312 --msgid "Enable and Install" --msgstr "Povolit a nainstalovat" -+#: src/gs-common.c:308 -+msgid "Enable and _Install" -+msgstr "Povolit a na_instalovat" - - #. TRANSLATORS: these are show_detailed_error messages from the - #. * package manager no mortal is supposed to understand, - #. * but google might know what they mean --#: src/gs-common.c:514 -+#: src/gs-common.c:511 - msgid "Detailed errors from the package manager follow:" - msgstr "Dále jsou uvedeny podrobnosti o chybě získané od správy balíčků:" - --#: src/gs-common.c:530 src/gs-safety-context-dialog.ui:72 -+#: src/gs-common.c:518 src/gs-safety-context-dialog.ui:72 - msgid "Details" - msgstr "Podrobnosti" - -+#. TRANSLATORS: button text -+#: src/gs-common.c:567 -+msgid "_Close" -+msgstr "_Zavřít" -+ - #. Translators: an accept button label, in a Cancel/Accept dialog --#: src/gs-common.c:709 -+#: src/gs-common.c:689 - msgid "_Accept" - msgstr "_Přijmout" - - #. TRANSLATORS: we've just live-updated some apps --#: src/gs-common.c:859 -+#: src/gs-common.c:835 - msgid "An update has been installed" - msgid_plural "Updates have been installed" - msgstr[0] "Aktualizace byla nainstalována" -@@ -2051,15 +2080,15 @@ msgstr[1] "Aktualizace byly nainstalovány" - msgstr[2] "Aktualizace byly nainstalovány" - - #. TRANSLATORS: we've just removed some apps --#: src/gs-common.c:869 --msgid "An application has been removed" --msgid_plural "Applications have been removed" -+#: src/gs-common.c:845 -+msgid "An app has been removed" -+msgid_plural "Apps have been removed" - msgstr[0] "Aplikace byla odebrána" - msgstr[1] "Aplikace byly odebrány" - msgstr[2] "Aplikace byly odebrány" - - #. TRANSLATORS: the new apps will not be run until we restart --#: src/gs-common.c:875 -+#: src/gs-common.c:851 - msgid "A restart is required for it to take effect." - msgid_plural "A restart is required for them to take effect." - msgstr[0] "Aby se projevila, je zapotřebí provést restart." -@@ -2067,16 +2096,16 @@ msgstr[1] "Aby se projevily, je zapotřebí provést restart." - msgstr[2] "Aby se projevily, je zapotřebí provést restart." - - #. TRANSLATORS: button text --#: src/gs-common.c:882 -+#: src/gs-common.c:858 - msgid "Not Now" - msgstr "Nyní ne" - - #. TRANSLATORS: something happened less than 5 minutes ago --#: src/gs-common.c:978 -+#: src/gs-common.c:954 - msgid "Just now" - msgstr "právě teď" - --#: src/gs-common.c:980 -+#: src/gs-common.c:956 - #, c-format - msgid "%d minute ago" - msgid_plural "%d minutes ago" -@@ -2084,7 +2113,7 @@ msgstr[0] "před %d minutou" - msgstr[1] "před %d minutami" - msgstr[2] "před %d minutami" - --#: src/gs-common.c:984 -+#: src/gs-common.c:960 - #, c-format - msgid "%d hour ago" - msgid_plural "%d hours ago" -@@ -2092,7 +2121,7 @@ msgstr[0] "před %d hodinou" - msgstr[1] "před %d hodinami" - msgstr[2] "před %d hodinami" - --#: src/gs-common.c:988 -+#: src/gs-common.c:964 - #, c-format - msgid "%d day ago" - msgid_plural "%d days ago" -@@ -2100,7 +2129,7 @@ msgstr[0] "před %d dnem" - msgstr[1] "před %d dny" - msgstr[2] "před %d dny" - --#: src/gs-common.c:992 -+#: src/gs-common.c:968 - #, c-format - msgid "%d week ago" - msgid_plural "%d weeks ago" -@@ -2108,7 +2137,7 @@ msgstr[0] "před %d týdnem" - msgstr[1] "před %d týdny" - msgstr[2] "před %d týdny" - --#: src/gs-common.c:996 -+#: src/gs-common.c:972 - #, c-format - msgid "%d month ago" - msgid_plural "%d months ago" -@@ -2116,7 +2145,7 @@ msgstr[0] "před %d měsícem" - msgstr[1] "před %d měsíci" - msgstr[2] "před %d měsíci" - --#: src/gs-common.c:1000 -+#: src/gs-common.c:976 - #, c-format - msgid "%d year ago" - msgid_plural "%d years ago" -@@ -2128,7 +2157,7 @@ msgstr[2] "před %d lety" - #. * the unit is drawn with a smaller font. If you need to flip the order, then you can use "%2$s %1$s". - #. * Make sure you'll preserve the no break space between the values. - #. * Example result: "13.0 MB" --#: src/gs-common.c:1364 -+#: src/gs-common.c:1340 - #, c-format - msgctxt "format-size" - msgid "%s %s" -@@ -2136,7 +2165,7 @@ msgstr "%s %s" - - #. TRANSLATORS: this is a what we use in notifications if the app's name is unknown - #: src/gs-dbus-helper.c:291 --msgid "An application" -+msgid "An app" - msgstr "Nějaká aplikace" - - #. TRANSLATORS: this is a notification displayed when an app needs additional MIME types. -@@ -2199,58 +2228,49 @@ msgstr "Požadavek na dodatečné balíčky" - msgid "Find in Software" - msgstr "Najít v aplikaci Software" - --#: src/gs-description-box.c:67 src/gs-description-box.c:269 -+#: src/gs-description-box.c:87 src/gs-description-box.c:335 - msgid "_Show More" - msgstr "Zobrazit _více" - --#: src/gs-description-box.c:67 -+#: src/gs-description-box.c:87 - msgid "_Show Less" - msgstr "Zobrazit _méně" - --#: src/gs-details-page.c:357 -+#: src/gs-details-page.c:367 - msgid "Removing…" - msgstr "Odebírá se…" - --#: src/gs-details-page.c:367 -+#: src/gs-details-page.c:377 - msgid "Requires restart to finish install" - msgstr "Vyžaduje restart k dokončení instalace" - --#: src/gs-details-page.c:374 -+#: src/gs-details-page.c:384 - msgid "Requires restart to finish remove" - msgstr "Vyžaduje restart k dokončení odebírání" - - #. TRANSLATORS: This is a label on top of the app's progress - #. * bar to inform the user that the app should be installed soon --#: src/gs-details-page.c:391 -+#: src/gs-details-page.c:401 - msgid "Pending installation…" - msgstr "Probíhá instalace…" - - #. TRANSLATORS: This is a label on top of the app's progress - #. * bar to inform the user that the app should be updated soon --#: src/gs-details-page.c:398 -+#: src/gs-details-page.c:407 - msgid "Pending update…" - msgstr "Probíhá aktualizace…" - - #. Translators: This string is shown when preparing to download and install an app. --#: src/gs-details-page.c:414 -+#: src/gs-details-page.c:421 - msgid "Preparing…" - msgstr "Připravuje se…" - - #. Translators: This string is shown when uninstalling an app. --#: src/gs-details-page.c:417 -+#: src/gs-details-page.c:424 - msgid "Uninstalling…" - msgstr "Odinstalovává se…" - --#. TRANSLATORS: button text in the header when an application --#. * can be installed --#. TRANSLATORS: button text in the header when firmware --#. * can be live-installed --#: src/gs-details-page.c:908 src/gs-details-page.c:934 --#: src/gs-details-page.ui:229 plugins/packagekit/gs-packagekit-task.c:150 --msgid "_Install" --msgstr "_Instalovat" -- --#: src/gs-details-page.c:924 -+#: src/gs-details-page.c:940 - msgid "_Restart" - msgstr "_Restartovat" - -@@ -2258,22 +2278,40 @@ msgstr "_Restartovat" - #. * be installed. - #. * The ellipsis indicates that further steps are required, - #. * e.g. enabling software repositories or the like --#: src/gs-details-page.c:948 -+#: src/gs-details-page.c:964 - msgid "_Install…" - msgstr "_Instalovat…" - -+#: src/gs-details-page.c:1031 -+msgid "_Uninstall…" -+msgstr "_Odinstalovat…" -+ -+#. Translators: %s is the user-visible app name -+#: src/gs-details-page.c:1175 -+#, c-format -+msgid "%s will appear in US English" -+msgstr "Aplikace %s se zobrazí v americké angličtině" -+ -+#: src/gs-details-page.c:1181 -+msgid "This app will appear in US English" -+msgstr "Tato aplikace se zobrazí v americké angličtině" -+ -+#: src/gs-details-page.c:1196 src/gs-details-page.ui:59 -+msgid "Help _Translate" -+msgstr "_Pomoci přeložit" -+ - #. Translators: the '%s' is replaced with a developer name or a project group --#: src/gs-details-page.c:1237 -+#: src/gs-details-page.c:1260 - #, c-format - msgid "Other Apps by %s" - msgstr "Co dalšího nabízí %s" - - #. TRANSLATORS: we need a remote server to process --#: src/gs-details-page.c:1620 -+#: src/gs-details-page.c:1637 - msgid "You need internet access to write a review" - msgstr "Abyste mohli napsat recenzi, musíte být připojeni k Internetu" - --#: src/gs-details-page.c:1790 src/gs-details-page.c:1806 -+#: src/gs-details-page.c:1822 src/gs-details-page.c:1838 - #, c-format - msgid "Unable to find “%s”" - msgstr "Nelze najít „%s“" -@@ -2283,74 +2321,61 @@ msgid "Details page" - msgstr "Stránka s podrobnostmi" - - #: src/gs-details-page.ui:39 --msgid "Loading application details…" -+msgid "Loading app details…" - msgstr "Načítají se podrobnosti o aplikaci…" - --#: src/gs-details-page.ui:77 --msgid "" --"This software is not available in your language and will appear in US " --"English." --msgstr "" --"Tento software není dostupný ve vašem jazyce a zobrazí se v americké " --"angličtině." -- --#: src/gs-details-page.ui:83 --msgid "Help _Translate" --msgstr "_Pomoci přeložit" -- --#. TRANSLATORS: A label for a button to execute the selected application. --#: src/gs-details-page.ui:246 -+#. TRANSLATORS: A label for a button to execute the selected app. -+#: src/gs-details-page.ui:226 - msgid "_Open" - msgstr "_Otevřít" - --#: src/gs-details-page.ui:262 plugins/packagekit/gs-packagekit-task.c:160 -+#: src/gs-details-page.ui:242 plugins/packagekit/gs-packagekit-task.c:159 - msgid "_Update" - msgstr "_Aktualizovat" - --#: src/gs-details-page.ui:331 -+#. TRANSLATORS: button text in the header when an app can be erased -+#: src/gs-details-page.ui:260 src/gs-details-page.ui:270 -+msgid "Uninstall" -+msgstr "Odinstalovat" -+ -+#: src/gs-details-page.ui:322 - msgid "Downloading" - msgstr "Stahuje se" - --#: src/gs-details-page.ui:468 src/gs-installed-page.ui:135 -+#: src/gs-details-page.ui:459 src/gs-installed-page.ui:135 - msgid "Add-ons" - msgstr "Doplňky" - --#: src/gs-details-page.ui:479 --msgid "Selected add-ons will be installed with the application." --msgstr "Vybrané doplňky budou nainstalovány spolu s aplikací." -- --#: src/gs-details-page.ui:579 --msgid "" --"This application can only be used when there is an active internet " --"connection." -+#: src/gs-details-page.ui:563 -+msgid "This app can only be used when there is an active internet connection." - msgstr "" - "Tuto aplikaci je možné používat, jen když je funkční připojení k Internetu." - --#: src/gs-details-page.ui:599 -+#: src/gs-details-page.ui:586 - msgid "Software Repository Included" - msgstr "Součástí je repozitář softwaru" - --#: src/gs-details-page.ui:600 -+#: src/gs-details-page.ui:596 - msgid "" --"This application includes a software repository which provides updates, as " --"well as access to other software." -+"This app includes a software repository which provides updates, as well as " -+"access to other software." - msgstr "" - "Součástí této aplikace je repozitář softwaru, který poskytuje aktualizace a " - "přístup k dalšímu softwaru." - --#: src/gs-details-page.ui:617 -+#: src/gs-details-page.ui:624 - msgid "No Software Repository Included" - msgstr "Součástí není žádný repozitář softwaru" - --#: src/gs-details-page.ui:618 -+#: src/gs-details-page.ui:634 - msgid "" --"This application does not include a software repository. It will not be " --"updated with new versions." -+"This app does not include a software repository. It will not be updated with " -+"new versions." - msgstr "" - "Součástí této aplikace není žádný repozitář softwaru. Nebude tak průběžně " - "aktualizována na novější verze." - --#: src/gs-details-page.ui:636 -+#: src/gs-details-page.ui:662 - msgid "" - "This software is already provided by your distribution and should not be " - "replaced." -@@ -2358,11 +2383,11 @@ msgstr "" - "Tento software již poskytuje vaše distribuce a neměli byste jej nahrazovat." - - #. Translators: a repository file used for installing software has been discovered. --#: src/gs-details-page.ui:653 -+#: src/gs-details-page.ui:693 - msgid "Software Repository Identified" - msgstr "Rozpoznán repozitář softwaru" - --#: src/gs-details-page.ui:654 -+#: src/gs-details-page.ui:703 - msgid "" - "Adding this software repository will give you access to additional software " - "and upgrades." -@@ -2370,15 +2395,15 @@ msgstr "" - "Přídáním tohoto repozitáře softwaru získáte přístup k dalšímu softwaru a " - "aktualizacím." - --#: src/gs-details-page.ui:655 -+#: src/gs-details-page.ui:710 - msgid "Only use software repositories that you trust." - msgstr "Používejte pouze repozitáře softwaru, kterým věříte." - --#: src/gs-details-page.ui:720 -+#: src/gs-details-page.ui:783 - msgid "No Metadata" - msgstr "Žádná metadata" - --#: src/gs-details-page.ui:729 -+#: src/gs-details-page.ui:792 - msgid "" - "This software doesn’t provide any links to a website, code repository or " - "issue tracker." -@@ -2386,33 +2411,33 @@ msgstr "" - "Tento software neposkytuje žádné odkazy na webové stránky, repozitáře kódu " - "ani nástroj pro sledování problémů." - --#: src/gs-details-page.ui:757 -+#: src/gs-details-page.ui:820 - msgid "Project _Website" - msgstr "_Webové stránky projektu" - --#: src/gs-details-page.ui:774 -+#: src/gs-details-page.ui:837 - msgid "_Donate" - msgstr "Věnovat _dar" - --#: src/gs-details-page.ui:791 -+#: src/gs-details-page.ui:854 - msgid "Contribute _Translations" - msgstr "_Přispět k překladu" - --#: src/gs-details-page.ui:808 -+#: src/gs-details-page.ui:871 - msgid "_Report an Issue" - msgstr "_Nahlásit chybu" - --#: src/gs-details-page.ui:825 -+#: src/gs-details-page.ui:888 - msgid "_Help" - msgstr "_Nápověda" - - #. Translators: Button opening a dialog where the users can write and publish their opinions about the apps. --#: src/gs-details-page.ui:919 --msgid "_Write Review" -+#: src/gs-details-page.ui:982 -+msgid "Write R_eview" - msgstr "Nap_sat recenzi" - - #. Translators: Button opening a dialog showing all reviews for an app. --#: src/gs-details-page.ui:956 -+#: src/gs-details-page.ui:1019 - msgid "All Reviews" - msgstr "Všechny recenze" - -@@ -2431,7 +2456,7 @@ msgstr " a " - msgid ", " - msgstr ", " - --#. TRANSLATORS: Application window title for fonts installation. -+#. TRANSLATORS: App window title for fonts installation. - #. %s will be replaced by name of the script we're searching for. - #: src/gs-extras-page.c:171 - #, c-format -@@ -2441,7 +2466,7 @@ msgstr[0] "Dostupné fonty pro písmo %s" - msgstr[1] "Dostupné fonty pro písma %s" - msgstr[2] "Dostupné fonty pro písma %s" - --#. TRANSLATORS: Application window title for codec installation. -+#. TRANSLATORS: App window title for codec installation. - #. %s will be replaced by actual codec name(s) - #: src/gs-extras-page.c:179 - #, c-format -@@ -2470,11 +2495,11 @@ msgstr "%s nebyl nalezen" - msgid "on the website" - msgstr "na webových stránkách" - --#. TRANSLATORS: this is when we know about an application or -+#. TRANSLATORS: this is when we know about an app or - #. * addon, but it can't be listed for some reason - #: src/gs-extras-page.c:354 - #, c-format --msgid "No applications are available that provide the file %s." -+msgid "No apps are available that provide the file %s." - msgstr "Nejsou k dispozici žádné aplikace, které by poskytovaly soubor %s." - - #. TRANSLATORS: first %s is the codec name, and second %s is a -@@ -2482,20 +2507,20 @@ msgstr "Nejsou k dispozici žádné aplikace, které by poskytovaly soubor %s." - #: src/gs-extras-page.c:358 src/gs-extras-page.c:369 src/gs-extras-page.c:380 - #, c-format - msgid "" --"Information about %s, as well as options for how to get missing applications " --"might be found %s." -+"Information about %s, as well as options for how to get missing apps might " -+"be found %s." - msgstr "" - "Informace o formátu %s, včetně toho, jak získat chybějící aplikace, najdete " - "%s." - --#. TRANSLATORS: this is when we know about an application or -+#. TRANSLATORS: this is when we know about an app or - #. * addon, but it can't be listed for some reason - #: src/gs-extras-page.c:365 src/gs-extras-page.c:387 - #, c-format --msgid "No applications are available for %s support." -+msgid "No apps are available for %s support." - msgstr "Pro podporu %s nejsou k dispozici žádné aplikace." - --#. TRANSLATORS: this is when we know about an application or -+#. TRANSLATORS: this is when we know about an app or - #. * addon, but it can't be listed for some reason - #: src/gs-extras-page.c:376 - #, c-format -@@ -2507,13 +2532,13 @@ msgstr "%s není k dispozici." - #: src/gs-extras-page.c:391 - #, c-format - msgid "" --"Information about %s, as well as options for how to get an application that " --"can support this format might be found %s." -+"Information about %s, as well as options for how to get an app that can " -+"support this format might be found %s." - msgstr "" --"Informace o formátu %s, včetně toho, jak získat aplikaci, který umí tento " --"tento formát podporovat, najdete %s." -+"Informace o formátu %s, včetně toho, jak získat aplikaci, který tento tento " -+"formát podporuje, najdete %s." - --#. TRANSLATORS: this is when we know about an application or -+#. TRANSLATORS: this is when we know about an app or - #. * addon, but it can't be listed for some reason - #: src/gs-extras-page.c:398 - #, c-format -@@ -2530,7 +2555,7 @@ msgid "" - msgstr "" - "Informace o písmu %s, včetně toho, jak získat dodatečná písma, najdete %s." - --#. TRANSLATORS: this is when we know about an application or -+#. TRANSLATORS: this is when we know about an app or - #. * addon, but it can't be listed for some reason - #: src/gs-extras-page.c:409 - #, c-format -@@ -2548,7 +2573,7 @@ msgstr "" - "Informace o kodeku %s, včetně toho, jak získat kodek, který umí tento formát " - "přehrát, najdete %s." - --#. TRANSLATORS: this is when we know about an application or -+#. TRANSLATORS: this is when we know about an app or - #. * addon, but it can't be listed for some reason - #: src/gs-extras-page.c:420 - #, c-format -@@ -2566,7 +2591,7 @@ msgstr "" - "Informace o kodeku %s, včetně toho, jak získat dodatečné prostředky Plasma, " - "najdete %s." - --#. TRANSLATORS: this is when we know about an application or -+#. TRANSLATORS: this is when we know about an app or - #. * addon, but it can't be listed for some reason - #: src/gs-extras-page.c:431 - #, c-format -@@ -2590,7 +2615,7 @@ msgid "the documentation" - msgstr "dokumentace" - - #. TRANSLATORS: no codecs were found. The first %s will be replaced by actual codec name(s), --#. the second %s is the application name, which requested the codecs, the third %s is a link titled "the documentation" -+#. the second %s is the app name, which requested the codecs, the third %s is a link titled "the documentation" - #: src/gs-extras-page.c:487 - #, c-format - msgid "" -@@ -2631,12 +2656,12 @@ msgstr[2] "" - msgid "Failed to find any search results: %s" - msgstr "Selhalo získání jakýchkoliv výsledků hledání: %s" - --#: src/gs-extras-page.c:874 -+#: src/gs-extras-page.c:878 - #, c-format - msgid "%s file format" - msgstr "formát souboru %s" - --#: src/gs-extras-page.c:1254 -+#: src/gs-extras-page.c:1258 - msgid "Unable to Find Requested Software" - msgstr "Nelze najít požadovaný software" - -@@ -2656,206 +2681,206 @@ msgstr "Další" - msgid "Featured Apps List" - msgstr "Seznam významných aplikací" - --#: src/gs-hardware-support-context-dialog.c:577 --#: src/gs-hardware-support-context-dialog.c:586 -+#: src/gs-hardware-support-context-dialog.c:576 -+#: src/gs-hardware-support-context-dialog.c:585 - msgid "Desktop Support" - msgstr "Podpora pro PC" - --#: src/gs-hardware-support-context-dialog.c:578 --#: src/gs-hardware-support-context-dialog.c:587 -+#: src/gs-hardware-support-context-dialog.c:577 -+#: src/gs-hardware-support-context-dialog.c:586 - msgid "Supports being used on a large screen" - msgstr "Podporuje použití na velké obrazovce" - --#: src/gs-hardware-support-context-dialog.c:580 -+#: src/gs-hardware-support-context-dialog.c:579 - msgid "Desktop Support Unknown" - msgstr "Neznámá podpora pro PC" - --#: src/gs-hardware-support-context-dialog.c:581 -+#: src/gs-hardware-support-context-dialog.c:580 - msgid "Not enough information to know if large screens are supported" - msgstr "" - "Není dostatek informací, abychom věděli, zda jsou podporovány velké obrazovky" - --#: src/gs-hardware-support-context-dialog.c:584 -+#: src/gs-hardware-support-context-dialog.c:583 - msgid "Requires a large screen" - msgstr "Vyžaduje velkou obrazovku" - --#: src/gs-hardware-support-context-dialog.c:589 -+#: src/gs-hardware-support-context-dialog.c:588 - msgid "Desktop Not Supported" - msgstr "Nepodporuje stolní počítače" - --#: src/gs-hardware-support-context-dialog.c:590 -+#: src/gs-hardware-support-context-dialog.c:589 - msgid "Cannot be used on a large screen" - msgstr "Nelze použít na velké obrazovce" - --#: src/gs-hardware-support-context-dialog.c:597 --#: src/gs-hardware-support-context-dialog.c:606 -+#: src/gs-hardware-support-context-dialog.c:596 -+#: src/gs-hardware-support-context-dialog.c:605 - msgid "Mobile Support" - msgstr "Podpora pro mobilní zařízení" - --#: src/gs-hardware-support-context-dialog.c:598 --#: src/gs-hardware-support-context-dialog.c:607 -+#: src/gs-hardware-support-context-dialog.c:597 -+#: src/gs-hardware-support-context-dialog.c:606 - msgid "Supports being used on a small screen" - msgstr "Podporuje použití na malé obrazovce" - --#: src/gs-hardware-support-context-dialog.c:600 -+#: src/gs-hardware-support-context-dialog.c:599 - msgid "Mobile Support Unknown" - msgstr "Neznámá podpora pro mobilní zařízení" - --#: src/gs-hardware-support-context-dialog.c:601 -+#: src/gs-hardware-support-context-dialog.c:600 - msgid "Not enough information to know if small screens are supported" - msgstr "" - "Není dostatek informací, abychom věděli, zda jsou podporovány malé obrazovky" - --#: src/gs-hardware-support-context-dialog.c:604 -+#: src/gs-hardware-support-context-dialog.c:603 - msgid "Requires a small screen" - msgstr "Vyžaduje malou obrazovku" - --#: src/gs-hardware-support-context-dialog.c:609 -+#: src/gs-hardware-support-context-dialog.c:608 - msgid "Mobile Not Supported" - msgstr "Nepodporuje mobily" - --#: src/gs-hardware-support-context-dialog.c:610 -+#: src/gs-hardware-support-context-dialog.c:609 - msgid "Cannot be used on a small screen" - msgstr "Nelze použít na malé obrazovce" - --#: src/gs-hardware-support-context-dialog.c:633 --#: src/gs-hardware-support-context-dialog.c:642 -+#: src/gs-hardware-support-context-dialog.c:632 -+#: src/gs-hardware-support-context-dialog.c:641 - msgid "Keyboard Support" - msgstr "Podpora klávesnice" - --#: src/gs-hardware-support-context-dialog.c:636 -+#: src/gs-hardware-support-context-dialog.c:635 - msgid "Keyboard Support Unknown" - msgstr "Neznámá podpora klávesnice" - --#: src/gs-hardware-support-context-dialog.c:637 -+#: src/gs-hardware-support-context-dialog.c:636 - msgid "Not enough information to know if keyboards are supported" - msgstr "" - "Není dostatek informací, abychom věděli, zda jsou podporovány klávesnice" - --#: src/gs-hardware-support-context-dialog.c:639 -+#: src/gs-hardware-support-context-dialog.c:638 - msgid "Keyboard Required" - msgstr "Vyžaduje klávesnici" - --#: src/gs-hardware-support-context-dialog.c:643 -+#: src/gs-hardware-support-context-dialog.c:642 - msgid "Supports keyboards" - msgstr "Podporuje klávesnice" - --#: src/gs-hardware-support-context-dialog.c:645 -+#: src/gs-hardware-support-context-dialog.c:644 - msgid "Keyboard Not Supported" - msgstr "Nepodporuje klávesnici" - --#: src/gs-hardware-support-context-dialog.c:646 -+#: src/gs-hardware-support-context-dialog.c:645 - msgid "Cannot be used with a keyboard" - msgstr "Nelze použít s klávesnicí" - --#: src/gs-hardware-support-context-dialog.c:653 --#: src/gs-hardware-support-context-dialog.c:662 -+#: src/gs-hardware-support-context-dialog.c:652 -+#: src/gs-hardware-support-context-dialog.c:661 - msgid "Mouse Support" - msgstr "Podpora myši" - --#: src/gs-hardware-support-context-dialog.c:654 --#: src/gs-hardware-support-context-dialog.c:660 -+#: src/gs-hardware-support-context-dialog.c:653 -+#: src/gs-hardware-support-context-dialog.c:659 - msgid "Requires a mouse or pointing device" - msgstr "Vyžaduje myš nebo ukazovátko" - --#: src/gs-hardware-support-context-dialog.c:656 -+#: src/gs-hardware-support-context-dialog.c:655 - msgid "Mouse Support Unknown" - msgstr "Neznámá podpora myši" - --#: src/gs-hardware-support-context-dialog.c:657 -+#: src/gs-hardware-support-context-dialog.c:656 - msgid "" - "Not enough information to know if mice or pointing devices are supported" - msgstr "" - "Není dostatek informací, abychom věděli, zda jsou podporovány myši nebo " - "ukazovátka" - --#: src/gs-hardware-support-context-dialog.c:659 -+#: src/gs-hardware-support-context-dialog.c:658 - msgid "Mouse Required" - msgstr "Vyžaduje myš" - --#: src/gs-hardware-support-context-dialog.c:663 -+#: src/gs-hardware-support-context-dialog.c:662 - msgid "Supports mice and pointing devices" - msgstr "Podporuje myši a ukazovátka" - --#: src/gs-hardware-support-context-dialog.c:665 -+#: src/gs-hardware-support-context-dialog.c:664 - msgid "Mouse Not Supported" - msgstr "Nepodporuje myš" - --#: src/gs-hardware-support-context-dialog.c:666 -+#: src/gs-hardware-support-context-dialog.c:665 - msgid "Cannot be used with a mouse or pointing device" - msgstr "Nelze použít s myší nebo ukazovátkem" - --#: src/gs-hardware-support-context-dialog.c:673 --#: src/gs-hardware-support-context-dialog.c:682 -+#: src/gs-hardware-support-context-dialog.c:672 -+#: src/gs-hardware-support-context-dialog.c:681 - msgid "Touchscreen Support" - msgstr "Podpora dotykové obrazovky" - --#: src/gs-hardware-support-context-dialog.c:676 -+#: src/gs-hardware-support-context-dialog.c:675 - msgid "Touchscreen Support Unknown" - msgstr "Neznámá podpora dotykové obrazovky" - --#: src/gs-hardware-support-context-dialog.c:677 -+#: src/gs-hardware-support-context-dialog.c:676 - msgid "Not enough information to know if touchscreens are supported" - msgstr "" - "Není dostatek informací, abychom věděli, zda jsou podporovány dotykové " - "obrazovky" - --#: src/gs-hardware-support-context-dialog.c:679 -+#: src/gs-hardware-support-context-dialog.c:678 - msgid "Touchscreen Required" - msgstr "Vyžaduje dotykovou obrazovku" - --#: src/gs-hardware-support-context-dialog.c:683 -+#: src/gs-hardware-support-context-dialog.c:682 - msgid "Supports touchscreens" - msgstr "Podporuje dotykové obrazovky" - --#: src/gs-hardware-support-context-dialog.c:685 -+#: src/gs-hardware-support-context-dialog.c:684 - msgid "Touchscreen Not Supported" - msgstr "Nepodporuje dotykovou obrazovku" - --#: src/gs-hardware-support-context-dialog.c:686 -+#: src/gs-hardware-support-context-dialog.c:685 - msgid "Cannot be used with a touchscreen" - msgstr "Nelze použít s dotykovou obrazovkou" - --#: src/gs-hardware-support-context-dialog.c:699 -+#: src/gs-hardware-support-context-dialog.c:698 - msgid "Gamepad Required" - msgstr "Vyžadován herní ovladač" - --#: src/gs-hardware-support-context-dialog.c:700 -+#: src/gs-hardware-support-context-dialog.c:699 - msgid "Requires a gamepad" - msgstr "Vyžaduje herní ovladač" - --#: src/gs-hardware-support-context-dialog.c:702 -+#: src/gs-hardware-support-context-dialog.c:701 - msgid "Gamepad Support" - msgstr "Podpora herního ovladače" - --#: src/gs-hardware-support-context-dialog.c:703 -+#: src/gs-hardware-support-context-dialog.c:702 - msgid "Supports gamepads" - msgstr "Podporuje herní ovladače" - - #. Translators: It’s unknown whether this app is supported on - #. * the current hardware. The placeholder is the app name. --#: src/gs-hardware-support-context-dialog.c:712 -+#: src/gs-hardware-support-context-dialog.c:711 - #, c-format - msgid "%s probably works on this device" - msgstr "Aplikace %s na tomto zařízení pravděpodobně funguje" - - #. Translators: The app will work on the current hardware. - #. * The placeholder is the app name. --#: src/gs-hardware-support-context-dialog.c:719 -+#: src/gs-hardware-support-context-dialog.c:718 - #, c-format - msgid "%s works on this device" - msgstr "Aplikace %s na tomto zařízení funguje" - - #. Translators: The app may not work fully on the current hardware. - #. * The placeholder is the app name. --#: src/gs-hardware-support-context-dialog.c:726 -+#: src/gs-hardware-support-context-dialog.c:725 - #, c-format - msgid "%s will not work properly on this device" - msgstr "Aplikace %s na tomto zařízení nebude fungovat správně" - - #. Translators: The app will not work properly on the current hardware. - #. * The placeholder is the app name. --#: src/gs-hardware-support-context-dialog.c:733 -+#: src/gs-hardware-support-context-dialog.c:732 - #, c-format - msgid "%s will not work on this device" - msgstr "Aplikace %s na tomto zařízení nebude fungovat" -@@ -2866,8 +2891,7 @@ msgid "Hardware Support" - msgstr "Podpora hardwaru" - - #. Translators: This is in the context of a list of apps which are installed on the system. --#. Translators: A label for a button to show only software which is already installed. --#: src/gs-installed-page.c:813 src/gs-shell.ui:309 -+#: src/gs-installed-page.c:813 - msgctxt "List of installed apps" - msgid "Installed" - msgstr "Nainstalováno" -@@ -2883,27 +2907,27 @@ msgstr "S probíhající změnou" - #. origin_ui on a remote is the repo dialogue section name, - #. * not the remote title - #: src/gs-installed-page.ui:75 plugins/flatpak/gs-flatpak-utils.c:107 --msgid "Applications" -+msgid "Apps" - msgstr "Aplikace" - - #: src/gs-installed-page.ui:95 --msgid "Web Applications" -+msgid "Web Apps" - msgstr "Webové aplikace" - - #: src/gs-installed-page.ui:115 --msgid "System Applications" -+msgid "System Apps" - msgstr "Systémové aplikace" - --#: src/gs-license-tile.c:96 -+#: src/gs-license-tile.c:97 - msgid "Community Built" - msgstr "Vybudováno komunitou" - --#: src/gs-license-tile.c:107 src/gs-license-tile.ui:98 -+#: src/gs-license-tile.c:108 src/gs-license-tile.ui:98 - msgid "_Get Involved" - msgstr "_Zapojit se" - - #. Translators: The first placeholder here is a link to information about the license, and the second placeholder here is the name of a software license. --#: src/gs-license-tile.c:114 -+#: src/gs-license-tile.c:115 - #, c-format - msgid "" - "This software is developed in the open by a community of volunteers, and " -@@ -2917,7 +2941,7 @@ msgstr "" - "Můžete přispět a pomoci jej ještě vylepšit." - - #. Translators: The placeholder here is the name of a software license. --#: src/gs-license-tile.c:121 -+#: src/gs-license-tile.c:122 - #, c-format - msgid "" - "This software is developed in the open by a community of volunteers, and " -@@ -2930,15 +2954,15 @@ msgstr "" - "\n" - "Můžete přispět a pomoci jej ještě vylepšit." - --#: src/gs-license-tile.c:127 -+#: src/gs-license-tile.c:128 - msgid "Proprietary" - msgstr "Uzavřený software" - --#: src/gs-license-tile.c:133 -+#: src/gs-license-tile.c:134 - msgid "_Learn More" - msgstr "Zjistit _více" - --#: src/gs-license-tile.c:135 -+#: src/gs-license-tile.c:136 - msgid "" - "This software is not developed in the open, so only its developers know how " - "it works. It may be insecure in ways that are hard to detect, and it may " -@@ -2965,7 +2989,7 @@ msgstr "Načítá se stránka" - msgid "Starting up…" - msgstr "Spouští se…" - --#: src/gs-metered-data-dialog.ui:5 src/gs-shell.ui:258 -+#: src/gs-metered-data-dialog.ui:5 - msgid "Automatic Updates Paused" - msgstr "Automatické aktualizace jsou pozastaveny" - -@@ -3012,62 +3036,72 @@ msgstr "Neznámý zdroj" - msgid "Beta" - msgstr "Beta" - --#. Translators: It's an origin scope, 'User' or 'System' installation --#: src/gs-origin-popover-row.ui:138 --msgid "User" --msgstr "Uživatel" -- - #. TRANSLATORS: This is the header for package additions during - #. * a system update --#: src/gs-os-update-page.c:250 -+#: src/gs-os-update-page.c:249 - msgid "Additions" - msgstr "Přidávání" - - #. TRANSLATORS: This is the header for package removals during - #. * a system update --#: src/gs-os-update-page.c:254 -+#: src/gs-os-update-page.c:253 - msgid "Removals" - msgstr "Odstraňování" - - #. TRANSLATORS: This is the header for package updates during - #. * a system update --#: src/gs-os-update-page.c:258 -+#: src/gs-os-update-page.c:257 - msgctxt "Packages to be updated during a system upgrade" - msgid "Updates" - msgstr "Aktualizace" - - #. TRANSLATORS: This is the header for package downgrades during - #. * a system update --#: src/gs-os-update-page.c:262 -+#: src/gs-os-update-page.c:261 - msgid "Downgrades" - msgstr "Ponižování" - --#. Translators: This is a clickable link on the third party repositories info bar. It's -+#. Translators: This is a clickable link on the third party repositories message dialog. It's - #. part of a constructed sentence: "Provides access to additional software from [selected external sources]. - #. Some proprietary software is included." --#: src/gs-overview-page.c:876 -+#: src/gs-overview-page.c:475 - msgid "selected external sources" - msgstr "vybraných externích zdrojů" - --#. Translators: This is the third party repositories info bar. The %s is replaced with "selected external sources" link. --#: src/gs-overview-page.c:878 -+#. Translators: This is the third party repositories message dialog. -+#. The %s is replaced with "selected external sources" link. -+#. Repositories Preferences is an item from Software's main menu. -+#: src/gs-overview-page.c:479 - #, c-format - msgid "" - "Provides access to additional software from %s. Some proprietary software is " --"included." -+"included.\n" -+"\n" -+"You can enable those repositories later in Software Repositories preferences." - msgstr "" - "Poskytuje přístup k dalšímu softwaru z %s. Součástí je i některý uzavřený " --"software." -+"software.\n" -+"\n" -+"Tyto repozitáře můžete později povolit v předvolbách Softwarových repozitářů." -+ -+#. TRANSLATORS: Heading asking whether to turn third party software repositories on of off. -+#: src/gs-overview-page.c:485 -+msgid "Enable Third Party Software Repositories?" -+msgstr "Povolit repozitáře softwaru třetích stran?" -+ -+#. TRANSLATORS: button to keep the third party software repositories off -+#: src/gs-overview-page.c:490 -+msgid "_Ignore" -+msgstr "_Ignorovat" - - #. TRANSLATORS: button to turn on third party software repositories - #. TRANSLATORS: button to accept the agreement --#: src/gs-overview-page.c:887 src/gs-repos-dialog.c:173 --msgid "Enable" --msgstr "Povolit" -+#: src/gs-overview-page.c:492 src/gs-repos-dialog.c:173 -+msgid "_Enable" -+msgstr "_Povolit" - - #. Translators: This is the title of the main page of the UI. --#. Translators: A label for a button to show all available software. --#: src/gs-overview-page.c:946 src/gs-shell.ui:296 -+#: src/gs-overview-page.c:985 - msgid "Explore" - msgstr "Procházet" - -@@ -3075,61 +3109,62 @@ msgstr "Procházet" - msgid "Overview page" - msgstr "Stránka s přehledem" - --#: src/gs-overview-page.ui:35 --msgid "Enable Third Party Software Repositories?" --msgstr "Povolit repozitáře softwaru třetích stran?" -- - #. Translators: This is a heading for a list of categories. --#: src/gs-overview-page.ui:180 -+#: src/gs-overview-page.ui:143 - msgid "Other Categories" - msgstr "Ostatní kategorie" - --#: src/gs-overview-page.ui:221 --msgid "No Application Data Found" -+#: src/gs-overview-page.ui:184 -+msgid "No App Data Found" - msgstr "O aplikaci nebyly nalezeny žádné informace" - --#: lib/gs-plugin-loader.c:2836 -+#: lib/gs-plugin-loader.c:2771 - msgctxt "Distribution name" - msgid "Unknown" - msgstr "neznámá" - --#: src/gs-page.c:274 -+#. TRANSLATORS: button text -+#: src/gs-page.c:92 -+msgid "_OK" -+msgstr "_Budiž" -+ -+#: src/gs-page.c:271 - msgid "User declined installation" - msgstr "Uživatel odmítl instalaci" - - #. TRANSLATORS: this is a prompt message, and --#. * '%s' is an application summary, e.g. 'GNOME Clocks' --#: src/gs-page.c:365 -+#. * '%s' is an app summary, e.g. 'GNOME Clocks' -+#: src/gs-page.c:404 - #, c-format - msgid "Prepare %s" - msgstr "Příprava aplikace %s" - - #. TRANSLATORS: this is a prompt message, and '%s' is an - #. * repository name, e.g. 'GNOME Nightly' --#: src/gs-page.c:518 -+#: src/gs-page.c:523 - #, c-format - msgid "Are you sure you want to remove the %s repository?" - msgstr "Opravdu chcete odebrat repozitář %s?" - - #. TRANSLATORS: longer dialog text --#: src/gs-page.c:522 -+#: src/gs-page.c:527 - #, c-format - msgid "" --"All applications from %s will be uninstalled, and you will have to re-" --"install the repository to use them again." -+"All apps from %s will be uninstalled, and you will have to re-install the " -+"repository to use them again." - msgstr "" --"Všechny aplikace pocházející ze repozitáře %s budou odinstalovány. Abyste je " -+"Všechny aplikace pocházející z repozitáře %s budou odinstalovány. Abyste je " - "mohli znovu použít, budete muset repozitář znovu nainstalovat." - - #. TRANSLATORS: this is a prompt message, and '%s' is an --#. * application summary, e.g. 'GNOME Clocks' --#: src/gs-page.c:530 -+#. * app summary, e.g. 'GNOME Clocks' -+#: src/gs-page.c:535 - #, c-format - msgid "Are you sure you want to uninstall %s?" - msgstr "Opravdu chcete odinstalovat %s?" - - #. TRANSLATORS: longer dialog text --#: src/gs-page.c:533 -+#: src/gs-page.c:538 - #, c-format - msgid "" - "%s will be uninstalled, and you will have to install it to use it again." -@@ -3138,8 +3173,8 @@ msgstr "" - "muset provést novou instalaci." - - #: src/gs-prefs-dialog.ui:5 --msgid "Update Preferences" --msgstr "Předvolby aktualizací" -+msgid "Preferences" -+msgstr "Předvolby" - - #: src/gs-prefs-dialog.ui:16 - msgid "" -@@ -3150,65 +3185,69 @@ msgstr "" - "automaticky stahovány na mobilních nebo měřených připojeních." - - #: src/gs-prefs-dialog.ui:19 --msgid "Automatic Updates" --msgstr "Automatické aktualizace" -+msgid "Automatic _Updates" -+msgstr "Automatické _aktualizace" - - #: src/gs-prefs-dialog.ui:20 - msgid "" --"Downloads and installs software updates in the background, when possible." -+"Downloads and installs software updates in the background, when possible" - msgstr "Stahuje a instaluje aktualizace softwaru na pozadí, pokud je to možné." - --#: src/gs-prefs-dialog.ui:32 --msgid "Automatic Update Notifications" --msgstr "Oznamovat automatické aktualizace" -- - #: src/gs-prefs-dialog.ui:33 --msgid "Show notifications when updates have been automatically installed." -+msgid "Automatic Update _Notifications" -+msgstr "_Oznamovat automatické aktualizace" -+ -+#: src/gs-prefs-dialog.ui:34 -+msgid "Show notifications when updates have been automatically installed" - msgstr "Zobrazovat oznámení, když jsou automaticky nainstalovány aplikace." - -+#: src/gs-prefs-dialog.ui:47 -+msgid "Show Only _Free Apps" -+msgstr "Zobrazit _pouze svobodné aplikace" -+ -+#: src/gs-prefs-dialog.ui:48 -+msgid "Show only freely licensed apps and hide any proprietary apps" -+msgstr "" -+"Zobrazit pouze aplikace se svobodnou licencí a skrýt všechny proprietární " -+"aplikace." -+ - #. TRANSLATORS: This is a text displayed during a distro upgrade. %s - #. will be replaced by the name and version of distro, e.g. 'Fedora 23'. - #: src/gs-removal-dialog.c:96 --#, fuzzy, c-format --#| msgid "" --#| "Some of the currently installed software is not compatible with %s. If " --#| "you continue, the following will be automatically removed during the " --#| "upgrade:" -+#, c-format - msgid "" - "Installed software is incompatible with %s, and will be automatically " - "removed during upgrade." - msgstr "" - "Některý z právě instalovaného softwaru není kompatibilní s distribucí %s. " --"Pokud budete pokračovat, následujíc se během povýšení odstraní:" -+"Pokud budete pokračovat, během povýšení se odstraní." - - #: src/gs-removal-dialog.ui:7 - msgid "Incompatible Software" - msgstr "Nekompatibilní software" - - #: src/gs-removal-dialog.ui:37 --#, fuzzy --#| msgid "_Restart & Upgrade" - msgid "_Upgrade" --msgstr "_Restartovat a aktualizovat" -+msgstr "_Aktualizovat" - - #. TRANSLATORS: The '%s' is replaced with a repository name, like "Fedora Modular - x86_64" --#: src/gs-repos-dialog.c:239 -+#: src/gs-repos-dialog.c:241 - #, c-format - msgid "" - "Software that has been installed from “%s” will cease to receive updates." - msgstr "" - "Software, který byl nainstalován z „%s“, přestane dostávat aktualizace." - --#: src/gs-repos-dialog.c:248 -+#: src/gs-repos-dialog.c:246 - msgid "Disable Repository?" - msgstr "Zakázat repozitář?" - --#: src/gs-repos-dialog.c:248 -+#: src/gs-repos-dialog.c:246 - msgid "Remove Repository?" - msgstr "Odebrat repozitář?" - - #. TRANSLATORS: this is button text to disable a repo --#: src/gs-repos-dialog.c:254 -+#: src/gs-repos-dialog.c:253 - msgid "_Disable" - msgstr "_Zakázat" - -@@ -3217,41 +3256,41 @@ msgstr "_Zakázat" - msgid "_Remove" - msgstr "_Odebrat" - --#: src/gs-repos-dialog.c:508 -+#: src/gs-repos-dialog.c:507 - msgid "Enable New Repositories" - msgstr "Povolit nové repozitáře" - --#: src/gs-repos-dialog.c:509 -+#: src/gs-repos-dialog.c:508 - msgid "Turn on new repositories when they are added." - msgstr "Zapnout nové repozitáře při jejich přidání." - - #. TRANSLATORS: this is the clickable - #. * link on the third party repositories info bar --#: src/gs-repos-dialog.c:518 -+#: src/gs-repos-dialog.c:517 - msgid "more information" - msgstr "více informací" - - #. TRANSLATORS: this is the third party repositories info bar. The '%s' is replaced - #. with a link consisting a text "more information", which constructs a sentence: - #. "Additional repositories from selected third parties - more information." --#: src/gs-repos-dialog.c:523 -+#: src/gs-repos-dialog.c:522 - #, c-format - msgid "Additional repositories from selected third parties — %s." - msgstr "Další repozitáře od vybraných třetích stran — %s." - --#: src/gs-repos-dialog.c:528 -+#: src/gs-repos-dialog.c:527 - msgid "Fedora Third Party Repositories" - msgstr "Repozitáře třetích stran Fedory" - - #. TRANSLATORS: this is the fallback text we use if we can't - #. figure out the name of the operating system --#: src/gs-repos-dialog.c:670 -+#: src/gs-repos-dialog.c:669 - msgid "the operating system" - msgstr "operačního systému" - - #. TRANSLATORS: This is the description text displayed in the Software Repositories dialog. - #. %s gets replaced by the name of the actual distro, e.g. Fedora. --#: src/gs-repos-dialog.c:728 -+#: src/gs-repos-dialog.c:727 - #, c-format - msgid "These repositories supplement the default software provided by %s." - msgstr "" -@@ -3259,7 +3298,7 @@ msgstr "" - "%s." - - #. button in the info bar --#: src/gs-repos-dialog.ui:8 src/gs-shell.ui:88 -+#: src/gs-repos-dialog.ui:8 src/gs-shell.ui:99 - msgid "Software Repositories" - msgstr "Softwarové repozitáře" - -@@ -3267,19 +3306,21 @@ msgstr "Softwarové repozitáře" - msgid "No Repositories" - msgstr "Žádné repozitáře" - --#. TRANSLATORS: This string is used to construct the 'X applications --#. installed' sentence, describing a software repository. --#: src/gs-repo-row.c:160 -+#. TRANSLATORS: This string states how many apps have been -+#. * installed from a particular repo, and is displayed on a row -+#. * describing that repo. The placeholder is the number of apps. -+#: src/gs-repo-row.c:161 - #, c-format --msgid "%u application installed" --msgid_plural "%u applications installed" -+msgid "%u app installed" -+msgid_plural "%u apps installed" - msgstr[0] "Nainstalována %u aplikace" - msgstr[1] "Nainstalovány %u aplikace" - msgstr[2] "Nainstalováno %u aplikací" - --#. TRANSLATORS: This string is used to construct the 'X add-ons --#. installed' sentence, describing a software repository. --#: src/gs-repo-row.c:167 -+#. TRANSLATORS: This string states how many add-ons have been -+#. * installed from a particular repo, and is displayed on a row -+#. * describing that repo. The placeholder is the number of add-ons. -+#: src/gs-repo-row.c:169 - #, c-format - msgid "%u add-on installed" - msgid_plural "%u add-ons installed" -@@ -3287,21 +3328,27 @@ msgstr[0] "Nainstalován %u doplněk" - msgstr[1] "Nainstalovány %u doplňky" - msgstr[2] "Nainstalováno %u doplňků" - --#. TRANSLATORS: This string is used to construct the 'X applications --#. and y add-ons installed' sentence, describing a software repository. --#. The correct form here depends on the number of applications. --#: src/gs-repo-row.c:175 -+#. TRANSLATORS: This string is used to construct the 'X apps -+#. and Y add-ons installed' sentence, stating how many things have been -+#. * installed from a particular repo. It’s displayed on a row describing -+#. * that repo. The placeholder is the number of apps, and the translated -+#. * string will be substituted in for the first placeholder in the -+#. * string “%s and %s installed”. -+#: src/gs-repo-row.c:180 - #, c-format --msgid "%u application" --msgid_plural "%u applications" -+msgid "%u app" -+msgid_plural "%u apps" - msgstr[0] "%u aplikace" - msgstr[1] "%u aplikace" - msgstr[2] "%u aplikací" - --#. TRANSLATORS: This string is used to construct the 'X applications --#. and y add-ons installed' sentence, describing a software repository. --#. The correct form here depends on the number of add-ons. --#: src/gs-repo-row.c:181 -+#. TRANSLATORS: This string is used to construct the 'X apps -+#. and Y add-ons installed' sentence, stating how many things have been -+#. * installed from a particular repo. It’s displayed on a row describing -+#. * that repo. The placeholder is the number of add-ons, and the translated -+#. * string will be substituted in for the second placeholder in the -+#. * string “%s and %s installed”. -+#: src/gs-repo-row.c:189 - #, c-format - msgid "%u add-on" - msgid_plural "%u add-ons" -@@ -3309,11 +3356,20 @@ msgstr[0] "%u doplněk" - msgstr[1] "%u doplňky" - msgstr[2] "%u doplňků" - --#. TRANSLATORS: This string is used to construct the 'X applications --#. and y add-ons installed' sentence, describing a software repository. --#. The correct form here depends on the total number of --#. applications and add-ons. --#: src/gs-repo-row.c:188 -+#. TRANSLATORS: This string is used to construct the 'X apps -+#. and Y add-ons installed' sentence, stating how many things have been -+#. * installed from a particular repo. It’s displayed on a row describing -+#. * that repo. The first placeholder is the translated string “%u app” or -+#. * “%u apps”. The second placeholder is the translated string “%u add-on” -+#. * or “%u add-ons”. -+#. * -+#. * The choice of plural form for this string is determined by the total -+#. * number of apps plus add-ons. For example, -+#. * - “1 app and 2 add-ons installed” - uses count 3 -+#. * - “2 apps and 1 add-on installed” - uses count 3 -+#. * - “4 apps and 5 add-ons installed” - uses count 9 -+#. -+#: src/gs-repo-row.c:205 - #, c-format - msgid "%s and %s installed" - msgid_plural "%s and %s installed" -@@ -3321,120 +3377,117 @@ msgstr[0] "%s a %s" - msgstr[1] "%s a %s" - msgstr[2] "%s a %s" - --#. Translators: The first '%s' is replaced with a text like '10 applications installed', -+#. Translators: The first '%s' is replaced with a text like '10 apps installed', - #. the second '%s' is replaced with installation kind, like in case of Flatpak 'User Installation'. --#: src/gs-repo-row.c:243 -+#: src/gs-repo-row.c:260 - #, c-format - msgctxt "repo-row" - msgid "%s • %s" - msgstr "%s • %s" - --#: src/gs-repo-row.c:314 --#, fuzzy --#| msgid "_Remove" -+#: src/gs-repo-row.c:331 - msgid "Remove" --msgstr "_Odebrat" -+msgstr "Odebrat" - - #. TRANSLATORS: lighthearted star rating description; --#. * A really bad application -+#. * A really bad app - #: src/gs-review-dialog.c:78 - msgid "Hate it" - msgstr "Nenávidím ji" - - #. TRANSLATORS: lighthearted star rating description; --#. * Not a great application -+#. * Not a great app - #: src/gs-review-dialog.c:82 - msgid "Don’t like it" - msgstr "Nemám ji rád" - - #. TRANSLATORS: lighthearted star rating description; --#. * A fairly-good application -+#. * A fairly-good app - #: src/gs-review-dialog.c:86 - msgid "It’s OK" - msgstr "Běžná aplikace" - - #. TRANSLATORS: lighthearted star rating description; --#. * A good application -+#. * A good app - #: src/gs-review-dialog.c:90 - msgid "Like it" - msgstr "Mám ji rád" - - #. TRANSLATORS: lighthearted star rating description; --#. * A really awesome application -+#. * A really awesome app - #: src/gs-review-dialog.c:94 - msgid "Love it" - msgstr "Zbožňuji ji" - -+#. TRANSLATORS: lighthearted star rating description; -+#. * No star has been clicked yet -+#: src/gs-review-dialog.c:98 -+msgid "Select a Star to Leave a Rating" -+msgstr "Chcete-li zanechat hodnocení, vyberte hvězdičku" -+ - #. TRANSLATORS: the review can't just be copied and pasted --#: src/gs-review-dialog.c:118 -+#: src/gs-review-dialog.c:119 - msgid "Please take more time writing the review" - msgstr "Věnujte prosím trochu času napsaní recenze" - - #. TRANSLATORS: the review is not acceptable --#: src/gs-review-dialog.c:122 -+#: src/gs-review-dialog.c:123 - msgid "Please choose a star rating" - msgstr "Ohodnoťte prosím hvězdičkami" - - #. TRANSLATORS: the review is not acceptable --#: src/gs-review-dialog.c:126 -+#: src/gs-review-dialog.c:127 - msgid "The summary is too short" - msgstr "Celkové hodnocení je příliš krátké" - - #. TRANSLATORS: the review is not acceptable --#: src/gs-review-dialog.c:130 -+#: src/gs-review-dialog.c:131 - msgid "The summary is too long" - msgstr "Celkové hodnocení je příliš dlouhé" - - #. TRANSLATORS: the review is not acceptable --#: src/gs-review-dialog.c:134 -+#: src/gs-review-dialog.c:135 - msgid "The description is too short" - msgstr "Recenze je příliš krátká" - - #. TRANSLATORS: the review is not acceptable --#: src/gs-review-dialog.c:138 -+#: src/gs-review-dialog.c:139 - msgid "The description is too long" - msgstr "Recenze je příliš dlouhá" - - #. Translators: Title of the dialog box where the users can write and publish their opinions about the apps. - #: src/gs-review-dialog.ui:10 --msgid "Post Review" --msgstr "Příspěvek do recenzí" -+msgid "Write a Review" -+msgstr "Napsat recenzi" - - #. Translators: A button to publish the user's opinion about the app. - #: src/gs-review-dialog.ui:26 --msgid "_Post" -+msgid "_Send" - msgstr "_Odeslat" - --#: src/gs-review-dialog.ui:56 --msgid "Rating" --msgstr "Hodnocení" -- --#: src/gs-review-dialog.ui:88 --msgid "Summary" --msgstr "Celkový dojem" -- --#: src/gs-review-dialog.ui:97 -+#: src/gs-review-dialog.ui:71 - msgid "" --"Give a short summary of your review, for example: “Great app, would " --"recommend”." -+"What did you like about this app? Leaving your feedback along with your " -+"reasons for leaving a review is helpful for others." - msgstr "" --"Uveďte krátké shrnutí své recenze, například: „Skvělá aplikace, doporučuji“." -+"Co se vám na této aplikaci líbilo? Zanechání zpětné vazby společně s důvody " -+"pro zanechání recenze je pro ostatní užitečné." -+ -+#: src/gs-review-dialog.ui:84 -+msgid "Review Summary" -+msgstr "Celkový dojem" - - #. Translators: This is where the users enter their opinions about the apps. --#: src/gs-review-dialog.ui:119 -+#: src/gs-review-dialog.ui:116 - msgctxt "app review" --msgid "Review" --msgstr "Recenze" -+msgid "Write a short review" -+msgstr "Napište krátkou recenzi" - --#: src/gs-review-dialog.ui:128 --msgid "What do you think of the app? Try to give reasons for your views." --msgstr "Co si o aplikaci myslíte? Snažte se uvést důvody svého hodnocení." -- --#: src/gs-review-dialog.ui:156 -+#: src/gs-review-dialog.ui:160 - msgid "" --"Find what data is sent in our privacy policy. The full name attached to your account will be shown " --"publicly." -+"Find what data is sent in our privacy policy. The full name attached to your account will be " -+"shown publicly." - msgstr "" - "Najděte si v našich zásadách " - "soukromí, jaká data jsou odesílána. Celé jméno přiřazené k vašemu účtu " -@@ -3448,24 +3501,24 @@ msgstr[0] "celkem %u recenze" - msgstr[1] "celkem %u recenze" - msgstr[2] "celkem %u recenzí" - --#: src/gs-review-histogram.ui:93 -+#: src/gs-review-histogram.ui:88 - msgid "out of 5 stars" - msgstr "z 5 hvězdiček" - - #. TRANSLATORS: this is when a user doesn't specify a name --#: src/gs-review-row.c:56 -+#: src/gs-review-row.c:60 - msgctxt "Reviewer name" - msgid "Unknown" - msgstr "anonym" - - #. TRANSLATORS: we explain what the action is going to do --#: src/gs-review-row.c:220 -+#: src/gs-review-row.c:222 - msgid "You can report reviews for abusive, rude, or discriminatory behavior." - msgstr "" - "Můžete nahlásit recenze, které jsou urážlivé, sprosté nebo diskriminační." - - #. TRANSLATORS: we ask the user if they really want to do this --#: src/gs-review-row.c:225 -+#: src/gs-review-row.c:227 - msgid "" - "Once reported, a review will be hidden until it has been checked by an " - "administrator." -@@ -3474,15 +3527,15 @@ msgstr "Po nahlášení bude recenze skryta, dokud ji nezkontroluje správce." - #. TRANSLATORS: window title when - #. * reporting a user-submitted review - #. * for moderation --#: src/gs-review-row.c:239 -+#: src/gs-review-row.c:235 - msgid "Report Review?" - msgstr "Nahlásit recenzi?" - - #. TRANSLATORS: button text when - #. * sending a review for moderation --#: src/gs-review-row.c:243 --msgid "Report" --msgstr "Nahlásit" -+#: src/gs-review-row.c:240 -+msgid "_Report" -+msgstr "_Nahlásit" - - #. Translators: Users can express their opinions about other users' opinions about the apps. - #: src/gs-review-row.ui:84 -@@ -3510,175 +3563,184 @@ msgstr "Nahlásit…" - msgid "Remove…" - msgstr "Odebrat…" - --#: src/gs-safety-context-dialog.c:144 --msgid "Check that you trust the vendor, as the application isn’t sandboxed" -+#: src/gs-safety-context-dialog.c:143 -+msgid "Check that you trust the vendor, as the app isn’t sandboxed" - msgstr "" - "Zkontrolujte si, že důvěřujete dodavateli, protože aplikace není v " --"izolovaném prostředí." -+"izolovaném prostředí" - --#: src/gs-safety-context-dialog.c:147 -+#: src/gs-safety-context-dialog.c:146 - msgid "" --"Application isn’t sandboxed but the distribution has checked that it is not " --"malicious" -+"App isn’t sandboxed but the distribution has checked that it is not malicious" - msgstr "" - "Aplikace není v izolovaném prostředí, ale je prověřená v distribuci, že " --"neobsahuje škodlivý kód." -+"neobsahuje škodlivý kód" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:160 -+#: src/gs-safety-context-dialog.c:159 - msgid "No Permissions" - msgstr "Žádná oprávnění" - --#: src/gs-safety-context-dialog.c:161 -+#: src/gs-safety-context-dialog.c:160 - msgid "App is fully sandboxed" - msgstr "Aplikace je v plně izolovaném prostředí" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:172 -+#: src/gs-safety-context-dialog.c:171 - msgid "Network Access" - msgstr "Přístup k síti" - --#: src/gs-safety-context-dialog.c:173 -+#: src/gs-safety-context-dialog.c:172 - msgid "Can access the internet" - msgstr "Může přistupovat k internetu" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:176 -+#: src/gs-safety-context-dialog.c:175 - msgid "No Network Access" - msgstr "Žádný přístup k síti" - --#: src/gs-safety-context-dialog.c:177 -+#: src/gs-safety-context-dialog.c:176 - msgid "Cannot access the internet" - msgstr "Nemůže přistupovat k internetu" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:183 -+#: src/gs-safety-context-dialog.c:182 - msgid "Uses System Services" - msgstr "Využívá služby systému" - --#: src/gs-safety-context-dialog.c:184 -+#: src/gs-safety-context-dialog.c:183 - msgid "Can request data from system services" - msgstr "Může si vyžádat data ze služeb systému" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:191 -+#: src/gs-safety-context-dialog.c:190 - msgid "Uses Session Services" - msgstr "Využívá služby sezení" - --#: src/gs-safety-context-dialog.c:192 -+#: src/gs-safety-context-dialog.c:191 - msgid "Can request data from session services" - msgstr "Může si vyžádat data ze služeb sezení" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:199 --msgid "Device Access" --msgstr "Přístup k zařízení" -+#: src/gs-safety-context-dialog.c:198 -+msgid "User Device Access" -+msgstr "Přístup k uživatelským zařízením" - --#: src/gs-safety-context-dialog.c:200 -+#: src/gs-safety-context-dialog.c:199 - msgid "Can access devices such as webcams or gaming controllers" - msgstr "Může přistupovat k zařízením jako jsou webkamery nebo herní ovladače" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:203 --msgid "No Device Access" --msgstr "Žádný přístup k zařízení" -+#: src/gs-safety-context-dialog.c:202 -+msgid "No User Device Access" -+msgstr "Žádný přístup k uživatelským zařízením" - --#: src/gs-safety-context-dialog.c:204 -+#: src/gs-safety-context-dialog.c:203 - msgid "Cannot access devices such as webcams or gaming controllers" - msgstr "Nemůže přistupovat k zařízením jako jsou webkamery nebo herní ovladače" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. -+#: src/gs-safety-context-dialog.c:209 -+msgid "System Device Access" -+msgstr "Přístup k systémovým zařízením" -+ - #: src/gs-safety-context-dialog.c:210 -+msgid "Can access system devices which require elevated permissions" -+msgstr "" -+"Může přistupovat k systémovým zařízením, která vyžadují zvýšená oprávnění" -+ -+#. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. -+#: src/gs-safety-context-dialog.c:217 - msgid "Legacy Windowing System" - msgstr "Zastaralý zobrazovací systém" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:218 -+#: src/gs-safety-context-dialog.c:225 - msgid "Arbitrary Permissions" - msgstr "Libovolná oprávnění" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:226 -+#: src/gs-safety-context-dialog.c:233 - msgid "User Settings" - msgstr "Uživatelská nastavení" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:238 -+#: src/gs-safety-context-dialog.c:245 - msgid "Full File System Read/Write Access" - msgstr "Plný přístup k souborovému systému pro čtení/zápis" - --#: src/gs-safety-context-dialog.c:239 -+#: src/gs-safety-context-dialog.c:246 - msgid "Can read and write all data on the file system" - msgstr "Může číst a zapisovat všechna data v souborovém systému" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:247 -+#: src/gs-safety-context-dialog.c:254 - msgid "Home Folder Read/Write Access" - msgstr "Přístup k domovské složce pro čtení/zápis" - --#: src/gs-safety-context-dialog.c:248 -+#: src/gs-safety-context-dialog.c:255 - msgid "Can read and write all data in your home directory" - msgstr "Může číst a zapisovat všechna data ve vaší domovské složce" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:256 -+#: src/gs-safety-context-dialog.c:263 - msgid "Full File System Read Access" - msgstr "Plný přístup k souborovému systému pro čtení" - --#: src/gs-safety-context-dialog.c:257 -+#: src/gs-safety-context-dialog.c:264 - msgid "Can read all data on the file system" - msgstr "Může číst všechna data v souborovém systému" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:266 -+#: src/gs-safety-context-dialog.c:273 - msgid "Home Folder Read Access" - msgstr "Přístup k domovské složce pro čtení" - --#: src/gs-safety-context-dialog.c:267 -+#: src/gs-safety-context-dialog.c:274 - msgid "Can read all data in your home directory" - msgstr "Může číst všechna data ve vaší domovské složce" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:276 -+#: src/gs-safety-context-dialog.c:283 - msgid "Download Folder Read/Write Access" - msgstr "Přístup ke složce se staženými soubory pro čtení/zápis" - --#: src/gs-safety-context-dialog.c:277 -+#: src/gs-safety-context-dialog.c:284 - msgid "Can read and write all data in your downloads directory" - msgstr "Může číst a zapisovat všechna data ve vaší složce se staženými soubory" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:288 -+#: src/gs-safety-context-dialog.c:295 - msgid "Download Folder Read Access" - msgstr "Přístup ke složce se staženými soubory pro čtení" - --#: src/gs-safety-context-dialog.c:289 -+#: src/gs-safety-context-dialog.c:296 - msgid "Can read all data in your downloads directory" - msgstr "Může číst všechna data ve vaší složce se staženými soubory" - --#: src/gs-safety-context-dialog.c:299 -+#: src/gs-safety-context-dialog.c:306 - msgid "Can read and write all data in the directory" - msgstr "Může číst a zapisovat všechna data ve složce" - --#: src/gs-safety-context-dialog.c:310 -+#: src/gs-safety-context-dialog.c:317 - msgid "Can read all data in the directory" - msgstr "Může číst všechna data ve složce" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:326 -+#: src/gs-safety-context-dialog.c:333 - msgid "No File System Access" - msgstr "Žádný přístup k souborovému systému" - --#: src/gs-safety-context-dialog.c:327 -+#: src/gs-safety-context-dialog.c:334 - msgid "Cannot access the file system at all" - msgstr "Vůbec nemůže přistupovat k souborovému systému" - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:341 -+#: src/gs-safety-context-dialog.c:348 - msgid "Proprietary Code" - msgstr "uzavřená" - --#: src/gs-safety-context-dialog.c:342 -+#: src/gs-safety-context-dialog.c:349 - msgid "" - "The source code is not public, so it cannot be independently audited and " - "might be unsafe" -@@ -3687,11 +3749,11 @@ msgstr "" - "nebezpečný." - - #. Translators: This refers to permissions (for example, from flatpak) which an app requests from the user. --#: src/gs-safety-context-dialog.c:345 -+#: src/gs-safety-context-dialog.c:352 - msgid "Auditable Code" - msgstr "otevřený kód" - --#: src/gs-safety-context-dialog.c:346 -+#: src/gs-safety-context-dialog.c:353 - msgid "" - "The source code is public and can be independently audited, which makes the " - "app more likely to be safe" -@@ -3701,21 +3763,21 @@ msgstr "" - - #. Translators: This indicates an app was written and released by a developer who has been verified. - #. * It’s used in a context tile, so should be short. --#: src/gs-safety-context-dialog.c:354 -+#: src/gs-safety-context-dialog.c:361 - msgid "App developer is verified" - msgstr "Vývojář aplikace je ověřený" - --#: src/gs-safety-context-dialog.c:355 -+#: src/gs-safety-context-dialog.c:362 - msgid "The developer of this app has been verified to be who they say they are" - msgstr "Bylo ověřeno, že vývojář této aplikace je tím, za koho se vydává" - - #. Translators: This indicates an app uses an outdated SDK. - #. * It’s used in a context tile, so should be short. --#: src/gs-safety-context-dialog.c:366 -+#: src/gs-safety-context-dialog.c:373 - msgid "Insecure Dependencies" - msgstr "Bezpečnostní rizika v závislostech" - --#: src/gs-safety-context-dialog.c:367 -+#: src/gs-safety-context-dialog.c:374 - msgid "" - "Software or its dependencies are no longer supported and may be insecure" - msgstr "" -@@ -3724,21 +3786,21 @@ msgstr "" - - #. Translators: The app is considered safe to install and run. - #. * The placeholder is the app name. --#: src/gs-safety-context-dialog.c:376 -+#: src/gs-safety-context-dialog.c:383 - #, c-format - msgid "%s is safe" - msgstr "Aplikace %s je bezpečná" - - #. Translators: The app is considered potentially unsafe to install and run. - #. * The placeholder is the app name. --#: src/gs-safety-context-dialog.c:383 -+#: src/gs-safety-context-dialog.c:390 - #, c-format - msgid "%s is potentially unsafe" - msgstr "Aplikace %s je potenciálně nebezpečná" - - #. Translators: The app is considered unsafe to install and run. - #. * The placeholder is the app name. --#: src/gs-safety-context-dialog.c:390 -+#: src/gs-safety-context-dialog.c:397 - #, c-format - msgid "%s is unsafe" - msgstr "Aplikace %s je nebezpečná" -@@ -3775,42 +3837,43 @@ msgstr "Předchozí snímek obrazovky" - msgid "Next Screenshot" - msgstr "Následující snímek obrazovky" - --#: src/gs-screenshot-carousel.ui:127 --msgid "No screenshot provided" --msgstr "Nemá snímek obrazovky" -+#. Translators: Shortened form of “no screenshots available” when showing an app’s details. -+#: src/gs-screenshot-carousel.ui:130 -+msgid "No Screenshots" -+msgstr "Žádné snímky obrazovky" - - #. TRANSLATORS: this is when we try to download a screenshot and - #. * we get back 404 --#: src/gs-screenshot-image.c:362 src/gs-screenshot-image.c:419 --#: src/gs-screenshot-image.c:623 -+#: src/gs-screenshot-image.c:359 src/gs-screenshot-image.c:416 -+#: src/gs-screenshot-image.c:620 - msgid "Screenshot not found" - msgstr "Snímek nebyl nalezen" - - #. TRANSLATORS: possibly image file corrupt or not an image --#: src/gs-screenshot-image.c:438 -+#: src/gs-screenshot-image.c:435 - msgid "Failed to load image" - msgstr "Selhalo načtení obrázku" - - #. TRANSLATORS: this is when we request a screenshot size that - #. * the generator did not create or the parser did not add --#: src/gs-screenshot-image.c:651 -+#: src/gs-screenshot-image.c:648 - msgid "Screenshot size not found" - msgstr "Velikost snímku nebyla nalezena" - - #. TRANSLATORS: this is when we try create the cache directory - #. * but we were out of space or permission was denied --#: src/gs-screenshot-image.c:733 -+#: src/gs-screenshot-image.c:730 - msgid "Could not create cache" - msgstr "Nelze vytvoři mezipaměť" - - #. TRANSLATORS: this is when we try to download a screenshot - #. * that was not a valid URL --#: src/gs-screenshot-image.c:747 -+#: src/gs-screenshot-image.c:744 - msgid "Screenshot not valid" - msgstr "Snímek není platný" - - #. TRANSLATORS: this is when networking is not available --#: src/gs-screenshot-image.c:797 -+#: src/gs-screenshot-image.c:794 - msgid "Screenshot not available" - msgstr "Snímek není k dispozici" - -@@ -3820,7 +3883,7 @@ msgstr "Snímek" - - #. TRANSLATORS: this is when there are too many search results - #. * to show in in the search page --#: src/gs-search-page.c:180 -+#: src/gs-search-page.c:179 - #, c-format - msgid "%u more match" - msgid_plural "%u more matches" -@@ -3837,7 +3900,7 @@ msgid "Search for Apps" - msgstr "Hledat aplikace" - - #: src/gs-search-page.ui:46 --msgid "No Application Found" -+msgid "No App Found" - msgstr "Žádná aplikace nebyla nalezena" - - #. TRANSLATORS: this is part of the in-app notification, -@@ -3848,33 +3911,33 @@ msgstr "Žádná aplikace nebyla nalezena" - #. TRANSLATORS: this is part of the in-app notification, - #. * where the %s is a multi-word localised app name - #. * e.g. 'Getting things GNOME!" --#: src/gs-shell.c:1209 src/gs-shell.c:1214 src/gs-shell.c:1229 --#: src/gs-shell.c:1233 -+#: src/gs-shell.c:1170 src/gs-shell.c:1175 src/gs-shell.c:1190 -+#: src/gs-shell.c:1194 - #, c-format - msgid "“%s”" - msgstr "„%s“" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the source (e.g. "alt.fedoraproject.org") --#: src/gs-shell.c:1285 -+#: src/gs-shell.c:1246 - #, c-format - msgid "Unable to download firmware updates from %s" - msgstr "Nelze stáhnout aktualizace firmwaru z %s" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the source (e.g. "alt.fedoraproject.org") --#: src/gs-shell.c:1291 -+#: src/gs-shell.c:1252 - #, c-format - msgid "Unable to download updates from %s" - msgstr "Nelze stáhnout aktualizace z %s" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1298 src/gs-shell.c:1338 -+#: src/gs-shell.c:1259 src/gs-shell.c:1300 - msgid "Unable to download updates" - msgstr "Nelze stáhnout aktualizace" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1303 -+#: src/gs-shell.c:1264 - msgid "" - "Unable to download updates: internet access was required but wasn’t available" - msgstr "" -@@ -3883,124 +3946,124 @@ msgstr "" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the source (e.g. "alt.fedoraproject.org") --#: src/gs-shell.c:1311 -+#: src/gs-shell.c:1272 - #, c-format - msgid "Unable to download updates from %s: not enough disk space" - msgstr "Nelze stáhnout aktualizace z %s: není dostatek místa na disku" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1316 -+#: src/gs-shell.c:1277 - msgid "Unable to download updates: not enough disk space" - msgstr "Nelze stáhnout aktualizace: není dostatek místa na disku" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1322 -+#: src/gs-shell.c:1283 - msgid "Unable to download updates: authentication was required" - msgstr "Nelze stáhnout aktualizace: je vyžadováno ověření" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1326 -+#: src/gs-shell.c:1287 - msgid "Unable to download updates: authentication was invalid" - msgstr "Nelze stáhnout aktualizace: ověření nebylo platné" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1330 -+#: src/gs-shell.c:1291 - msgid "" - "Unable to download updates: you do not have permission to install software" - msgstr "Nelze stáhnout aktualizace: nemáte oprávnění instalovat software" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1341 -+#: src/gs-shell.c:1303 - msgid "Unable to get list of updates" - msgstr "Nelze získat seznam aktualizací" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the first %s is the application name (e.g. "GIMP") and -+#. * where the first %s is the app name (e.g. "GIMP") and - #. * the second %s is the origin, e.g. "Fedora Project [fedoraproject.org]" --#: src/gs-shell.c:1377 -+#: src/gs-shell.c:1339 - #, c-format - msgid "Unable to install %s as download failed from %s" - msgstr "Nelze nainstalovat balíček %s, protože selhalo jeho stažení z %s" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1383 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1345 - #, c-format - msgid "Unable to install %s as download failed" - msgstr "Nelze nainstalovat balíček %s, protože selhalo stažení" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the first %s is the application name (e.g. "GIMP") -+#. * where the first %s is the app name (e.g. "GIMP") - #. * and the second %s is the name of the runtime, e.g. - #. * "GNOME SDK [flatpak.gnome.org]" --#: src/gs-shell.c:1395 -+#: src/gs-shell.c:1357 - #, c-format - msgid "Unable to install %s as runtime %s not available" - msgstr "" - "Nelze nainstalovat balíček %s, protože není k dispozici běhové prostředí %s" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1401 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1363 - #, c-format - msgid "Unable to install %s as not supported" - msgstr "Nelze nainstalovat balíček %s, protože není podporovaný" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1407 -+#: src/gs-shell.c:1369 - msgid "Unable to install: internet access was required but wasn’t available" - msgstr "" - "Nelze nainstalovat: přístup k internetu je nezbytný, ale není k dispozici" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1412 --msgid "Unable to install: the application has an invalid format" -+#: src/gs-shell.c:1374 -+msgid "Unable to install: the app has an invalid format" - msgstr "Nelze nainstalovat: aplikace má neplatný formát" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1416 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1378 - #, c-format - msgid "Unable to install %s: not enough disk space" - msgstr "Nelze nainstalovat balíček %s: není dostatek místa na disku" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1422 -+#: src/gs-shell.c:1384 - #, c-format - msgid "Unable to install %s: authentication was required" - msgstr "Nelze nainstalovat balíček %s: je vyžadováno ověření" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1428 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1390 - #, c-format - msgid "Unable to install %s: authentication was invalid" - msgstr "Nelze nainstalovat balíček %s: ověření nebylo platné" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1434 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1396 - #, c-format - msgid "Unable to install %s: you do not have permission to install software" - msgstr "Nelze nainstalovat balíček %s: nemáte oprávnění k instalaci softwaru" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "Dell XPS 13") --#: src/gs-shell.c:1441 -+#. * where the %s is the app name (e.g. "Dell XPS 13") -+#: src/gs-shell.c:1403 - #, c-format - msgid "Unable to install %s: AC power is required" - msgstr "Nelze nainstalovat balíček %s: je vyžadováno připojené napájení" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "Dell XPS 13") --#: src/gs-shell.c:1447 -+#. * where the %s is the app name (e.g. "Dell XPS 13") -+#: src/gs-shell.c:1409 - #, c-format - msgid "Unable to install %s: The battery level is too low" - msgstr "Nelze nainstalovat balíček %s: úroveň nabití baterie je příliš nízká" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1456 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1418 - #, c-format - msgid "Unable to install %s" - msgstr "Nelze nainstalovat balíček %s" -@@ -4009,14 +4072,14 @@ msgstr "Nelze nainstalovat balíček %s" - #. * where the first %s is the app name (e.g. "GIMP") and - #. * the second %s is the origin, e.g. "Fedora" or - #. * "Fedora Project [fedoraproject.org]" --#: src/gs-shell.c:1495 -+#: src/gs-shell.c:1457 - #, c-format - msgid "Unable to update %s from %s as download failed" - msgstr "Nelze aktualizovat balíček %s z %s, protože selhalo stažení" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1502 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1464 - #, c-format - msgid "Unable to update %s as download failed" - msgstr "Nelze aktualizovat balíček %s, protože selhalo stažení" -@@ -4024,71 +4087,71 @@ msgstr "Nelze aktualizovat balíček %s, protože selhalo stažení" - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the origin, e.g. "Fedora" or - #. * "Fedora Project [fedoraproject.org]" --#: src/gs-shell.c:1509 -+#: src/gs-shell.c:1471 - #, c-format - msgid "Unable to install updates from %s as download failed" - msgstr "Nelze nainstalovat aktualizace z %s, protože selhalo stažení" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1513 -+#: src/gs-shell.c:1475 - #, c-format - msgid "Unable to install updates as download failed" - msgstr "Nelze nainstalovat aktualizace, protože selhalo stažení" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1518 -+#: src/gs-shell.c:1480 - msgid "Unable to update: internet access was required but wasn’t available" - msgstr "" - "Nelze aktualizovat: přístup k internetu je nezbytný, ale není k dispozici" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1527 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1489 - #, c-format - msgid "Unable to update %s: not enough disk space" - msgstr "Nelze aktualizovat balíček %s: nedostatek místa na disku" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1532 -+#: src/gs-shell.c:1494 - #, c-format - msgid "Unable to install updates: not enough disk space" - msgstr "Nelze nainstalovat aktualizace: nedostatek místa na disku" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1541 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1503 - #, c-format - msgid "Unable to update %s: authentication was required" - msgstr "Nelze aktualizovat balíček %s: je vyžadováno ověření" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1546 -+#: src/gs-shell.c:1508 - #, c-format - msgid "Unable to install updates: authentication was required" - msgstr "Nelze nainstalovat aktualizace: je vyžadováno ověření" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1554 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1516 - #, c-format - msgid "Unable to update %s: authentication was invalid" - msgstr "Nelze aktualizovat balíček %s: ověření bylo neplatné" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1559 -+#: src/gs-shell.c:1521 - #, c-format - msgid "Unable to install updates: authentication was invalid" - msgstr "Nelze nainstalovat aktualizace: ověření bylo neplatné" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1567 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1529 - #, c-format - msgid "Unable to update %s: you do not have permission to update software" - msgstr "Nelze aktualizovat balíček %s: nemáte oprávnění k aktualizaci softwaru" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1573 -+#: src/gs-shell.c:1535 - #, c-format - msgid "" - "Unable to install updates: you do not have permission to update software" -@@ -4096,44 +4159,44 @@ msgstr "" - "Nelze nainstalovat aktualizace: nemáte oprávnění k aktualizaci softwaru" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "Dell XPS 13") --#: src/gs-shell.c:1582 -+#. * where the %s is the app name (e.g. "Dell XPS 13") -+#: src/gs-shell.c:1544 - #, c-format - msgid "Unable to update %s: AC power is required" - msgstr "" - "Nelze aktualizovat balíček %s: je vyžadováno napájení z elektrické sítě" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "Dell XPS 13") --#: src/gs-shell.c:1588 -+#. * where the %s is the app name (e.g. "Dell XPS 13") -+#: src/gs-shell.c:1550 - #, c-format - msgid "Unable to install updates: AC power is required" - msgstr "" - "Nelze nainstalovat aktualizace: je vyžadováno napájení z elektrické sítě" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "Dell XPS 13") --#: src/gs-shell.c:1596 -+#. * where the %s is the app name (e.g. "Dell XPS 13") -+#: src/gs-shell.c:1558 - #, c-format - msgid "Unable to update %s: The battery level is too low" - msgstr "Nelze aktualizovat balíček %s: úroveň nabití baterie je příliš nízká" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "Dell XPS 13") --#: src/gs-shell.c:1602 -+#. * where the %s is the app name (e.g. "Dell XPS 13") -+#: src/gs-shell.c:1564 - #, c-format - msgid "Unable to install updates: The battery level is too low" - msgstr "Nelze nainstalovat aktualizace: úroveň nabití baterie je příliš nízká" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1613 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1575 - #, c-format - msgid "Unable to update %s" - msgstr "Nelze aktualizovat balíček %s" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1616 -+#: src/gs-shell.c:1578 - #, c-format - msgid "Unable to install updates" - msgstr "Nelze nainstalovat aktualizace" -@@ -4141,21 +4204,21 @@ msgstr "Nelze nainstalovat aktualizace" - #. TRANSLATORS: failure text for the in-app notification, - #. * where the first %s is the distro name (e.g. "Fedora 25") and - #. * the second %s is the origin, e.g. "Fedora Project [fedoraproject.org]" --#: src/gs-shell.c:1652 -+#: src/gs-shell.c:1614 - #, c-format - msgid "Unable to upgrade to %s from %s" - msgstr "Nelze povýšit na %s z %s" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the app name (e.g. "GIMP") --#: src/gs-shell.c:1657 -+#: src/gs-shell.c:1619 - #, c-format - msgid "Unable to upgrade to %s as download failed" - msgstr "Nelze povýšit na %s, protože selhalo stažení" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the distro name (e.g. "Fedora 25") --#: src/gs-shell.c:1665 -+#: src/gs-shell.c:1627 - #, c-format - msgid "" - "Unable to upgrade to %s: internet access was required but wasn’t available" -@@ -4165,159 +4228,159 @@ msgstr "" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the distro name (e.g. "Fedora 25") --#: src/gs-shell.c:1673 -+#: src/gs-shell.c:1635 - #, c-format - msgid "Unable to upgrade to %s: not enough disk space" - msgstr "Nelze povýšit na %s: není dostatek místa na disku" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the distro name (e.g. "Fedora 25") --#: src/gs-shell.c:1680 -+#: src/gs-shell.c:1642 - #, c-format - msgid "Unable to upgrade to %s: authentication was required" - msgstr "Nelze povýšit na %s: je vyžadováno ověření" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the distro name (e.g. "Fedora 25") --#: src/gs-shell.c:1686 -+#: src/gs-shell.c:1648 - #, c-format - msgid "Unable to upgrade to %s: authentication was invalid" - msgstr "Nelze povýšit na %s: ověření nebylo platné" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the distro name (e.g. "Fedora 25") --#: src/gs-shell.c:1692 -+#: src/gs-shell.c:1654 - #, c-format - msgid "Unable to upgrade to %s: you do not have permission to upgrade" - msgstr "Nelze povýšit na %s: nemáte oprávnění k povyšování" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the distro name (e.g. "Fedora 25") --#: src/gs-shell.c:1698 -+#: src/gs-shell.c:1660 - #, c-format - msgid "Unable to upgrade to %s: AC power is required" - msgstr "Nelze povýšit na %s: je vyžadováno připojené napájení" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the distro name (e.g. "Fedora 25") --#: src/gs-shell.c:1704 -+#: src/gs-shell.c:1666 - #, c-format - msgid "Unable to upgrade to %s: The battery level is too low" - msgstr "Nelze povýšit na %s: úroveň nabití baterie je příliš nízká" - - #. TRANSLATORS: failure text for the in-app notification, - #. * where the %s is the distro name (e.g. "Fedora 25") --#: src/gs-shell.c:1713 -+#: src/gs-shell.c:1675 - #, c-format - msgid "Unable to upgrade to %s" - msgstr "Nelze povýšit na %s" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1744 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1706 - #, c-format - msgid "Unable to remove %s: authentication was required" - msgstr "Nelze odstranit balíček %s: je vyžadováno ověření" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1749 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1711 - #, c-format - msgid "Unable to remove %s: authentication was invalid" - msgstr "Nelze odstranit balíček %s: ověření nebylo platné" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1754 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1716 - #, c-format - msgid "Unable to remove %s: you do not have permission to remove software" - msgstr "Nelze odstranit balíček %s: nemáte oprávnění k odstranění softwaru" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1760 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1722 - #, c-format - msgid "Unable to remove %s: AC power is required" - msgstr "Nelze odstranit balíček %s: je vyžadováno připojené napájení" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1766 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1728 - #, c-format - msgid "Unable to remove %s: The battery level is too low" - msgstr "Nelze odstranit balíček %s: úroveň nabití baterie je příliš nízká" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the %s is the application name (e.g. "GIMP") --#: src/gs-shell.c:1778 -+#. * where the %s is the app name (e.g. "GIMP") -+#: src/gs-shell.c:1740 - #, c-format - msgid "Unable to remove %s" - msgstr "Nelze odstranit balíček %s" - - #. TRANSLATORS: failure text for the in-app notification, --#. * where the first %s is the application name (e.g. "GIMP") -+#. * where the first %s is the app name (e.g. "GIMP") - #. * and the second %s is the name of the runtime, e.g. - #. * "GNOME SDK [flatpak.gnome.org]" --#: src/gs-shell.c:1813 -+#: src/gs-shell.c:1775 - #, c-format - msgid "Unable to launch %s: %s is not installed" - msgstr "Nelze spustit aplikaci %s: balíček %s není nainstalovaný" - - #. TRANSLATORS: we failed to get a proper error code --#: src/gs-shell.c:1821 src/gs-shell.c:1837 src/gs-shell.c:1879 --#: src/gs-shell.c:1921 src/gs-shell.c:1978 -+#: src/gs-shell.c:1783 src/gs-shell.c:1799 src/gs-shell.c:1841 -+#: src/gs-shell.c:1883 src/gs-shell.c:1940 - msgid "Sorry, something went wrong" - msgstr "Litujeme, ale něco se stalo špatně" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1826 src/gs-shell.c:1868 src/gs-shell.c:1910 --#: src/gs-shell.c:1957 -+#: src/gs-shell.c:1788 src/gs-shell.c:1830 src/gs-shell.c:1872 -+#: src/gs-shell.c:1919 - msgid "Not enough disk space — free up some space and try again" - msgstr "" - "Nebyl dostatek místa na disku – uvolněte nějaké místo a pak to zkuste znovu" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1862 -+#: src/gs-shell.c:1824 - msgid "Failed to install file: not supported" - msgstr "Selhala instalace souboru: není podporován" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1865 -+#: src/gs-shell.c:1827 - msgid "Failed to install file: authentication failed" - msgstr "Selhala instalace souboru: selhalo ověření" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1904 -+#: src/gs-shell.c:1866 - msgid "Failed to install: not supported" - msgstr "Selhala instalace: není podporováno" - - #. TRANSLATORS: failure text for the in-app notification --#: src/gs-shell.c:1907 -+#: src/gs-shell.c:1869 - msgid "Failed to install: authentication failed" - msgstr "Selhala instalace: selhalo ověření" - - #. TRANSLATORS: failure text for the in-app notification, - #. * the %s is the origin, e.g. "Fedora" or - #. * "Fedora Project [fedoraproject.org]" --#: src/gs-shell.c:1952 -+#: src/gs-shell.c:1914 - #, c-format - msgid "Unable to contact %s" - msgstr "Nelze kontaktovat %s" - --#. TRANSLATORS: failure text for the in-app notification, where the 'Software' means this application, aka 'GNOME Software'. --#: src/gs-shell.c:1962 -+#. TRANSLATORS: failure text for the in-app notification, where the 'Software' means this app, aka 'GNOME Software'. -+#: src/gs-shell.c:1924 - msgid "Software needs to be restarted to use new plugins." - msgstr "" - "Aplikace Software musí být restartována, aby mohla používat nový zásuvný " - "modul." - - #. TRANSLATORS: need to be connected to the AC power --#: src/gs-shell.c:1966 -+#: src/gs-shell.c:1928 - msgid "AC power is required" - msgstr "Je vyžadováno připojené napájení" - - #. TRANSLATORS: not enough juice to do this safely --#: src/gs-shell.c:1969 -+#: src/gs-shell.c:1931 - msgid "The battery level is too low" - msgstr "Úroveň nabití baterie je příliš nízká" - -@@ -4326,48 +4389,65 @@ msgid "_Software Repositories" - msgstr "_Softwarové repozitáře" - - #: src/gs-shell.ui:12 --msgid "_Update Preferences" --msgstr "Předvolby akt_ualizací" -+msgid "_Preferences" -+msgstr "_Předvolby" - - #. button in the info bar --#: src/gs-shell.ui:98 -+#: src/gs-shell.ui:109 - msgid "Examine Disk" - msgstr "Prozkoumat disk" - - #. button in the info bar --#. TRANSLATORS: this is a link to the --#. * control-center network panel --#: src/gs-shell.ui:108 src/gs-updates-page.c:885 -+#: src/gs-shell.ui:119 - msgid "Network Settings" - msgstr "Nastavení sítě" - - #. button in the info bar --#: src/gs-shell.ui:118 --msgid "Restart Now" --msgstr "Restartovat hned" -+#: src/gs-shell.ui:129 -+msgid "_Restart Now…" -+msgstr "_Restartovat hned…" - - #. button in the info bar --#: src/gs-shell.ui:128 -+#: src/gs-shell.ui:140 - msgid "More Information" - msgstr "Další informace" - --#: src/gs-shell.ui:188 src/gs-shell.ui:190 -+#: src/gs-shell.ui:200 src/gs-shell.ui:202 - msgid "Search" - msgstr "Hledat" - --#: src/gs-shell.ui:204 src/gs-shell.ui:206 --msgid "Primary Menu" --msgstr "Hlavní nabídky" -+#: src/gs-shell.ui:216 src/gs-shell.ui:218 -+msgid "Main Menu" -+msgstr "Hlavní nabídka" -+ -+#: src/gs-shell.ui:245 -+msgid "Search apps" -+msgstr "Hledat aplikace" -+ -+#: src/gs-shell.ui:257 -+msgid "Metered network ‒ automatic updates paused" -+msgstr "Měřená síť – automatické aktualizace jsou pozastaveny" - --#: src/gs-shell.ui:276 -+#: src/gs-shell.ui:258 - msgid "Find Out _More" - msgstr "Dozvědět se _více…" - -+#. Translators: A label for a button to show all available software. -+#: src/gs-shell.ui:272 -+msgid "_Explore" -+msgstr "_Procházet" -+ -+#. Translators: A label for a button to show only software which is already installed. -+#: src/gs-shell.ui:286 -+msgctxt "List of installed apps" -+msgid "_Installed" -+msgstr "Na_instalováno" -+ - #. Translators: A label for a button to show only updates which are available to install. --#: src/gs-shell.ui:330 -+#: src/gs-shell.ui:308 - msgctxt "Header bar button for list of apps to be updated" --msgid "Updates" --msgstr "Aktualizace" -+msgid "_Updates" -+msgstr "_Aktualizace" - - #. Translators: This is shown in a bubble to represent a 0 byte - #. * storage size, so its context is “storage size: none”. The -@@ -4378,11 +4458,11 @@ msgid "None" - msgstr "Žádná" - - #: src/gs-storage-context-dialog.c:139 --msgid "Application Data" -+msgid "App Data" - msgstr "Data aplikace" - - #: src/gs-storage-context-dialog.c:140 --msgid "Data needed for the application to run" -+msgid "Data needed for the app to run" - msgstr "Data potřebná ke spuštění aplikace" - - #: src/gs-storage-context-dialog.c:145 -@@ -4390,7 +4470,7 @@ msgid "User Data" - msgstr "Uživatelská data" - - #: src/gs-storage-context-dialog.c:146 --msgid "Data created by you in the application" -+msgid "Data created by you in the app" - msgstr "Vámi vytvořená data v aplikaci" - - #: src/gs-storage-context-dialog.c:153 -@@ -4402,7 +4482,7 @@ msgid "Temporary cached data" - msgstr "Dočasná data v mezipaměti" - - #: src/gs-storage-context-dialog.c:172 --msgid "The application itself" -+msgid "The app itself" - msgstr "Aplikace samotná" - - #: src/gs-storage-context-dialog.c:177 -@@ -4410,7 +4490,7 @@ msgid "Required Dependencies" - msgstr "Vyžadované závislosti" - - #: src/gs-storage-context-dialog.c:178 --msgid "Shared system components required by this application" -+msgid "Shared system components required by this app" - msgstr "Sdílené systémové komponenty vyžadované touto aplikací" - - #: src/gs-storage-context-dialog.c:188 -@@ -4426,23 +4506,22 @@ msgstr "Úložiště" - #. Translators: Please do not translate the markup or link href - #: src/gs-storage-context-dialog.ui:69 - msgid "" --"Cached data can be cleared from the _application settings." -+"Cached data can be cleared from the _app settings." - msgstr "" - "Data uložená v mezipaměti lze vymazat v _nastavení " - "aplikace." - --#: src/gs-summary-tile.c:118 -+#: src/gs-summary-tile.c:139 - #, c-format - msgid "%s (Installed)" - msgstr "%s (nainstalováno)" - --#: src/gs-summary-tile.c:123 -+#: src/gs-summary-tile.c:144 - #, c-format - msgid "%s (Installing)" - msgstr "%s (instaluje se)" - --#: src/gs-summary-tile.c:128 -+#: src/gs-summary-tile.c:149 - #, c-format - msgid "%s (Removing)" - msgstr "%s (odebírá se)" -@@ -4508,8 +4587,8 @@ msgstr "Stáhněte prosím čekající aktualizace softwaru." - #. TRANSLATORS: apps were auto-updated and restart is required - #: src/gs-update-monitor.c:355 - #, c-format --msgid "%u Application Updated — Restart Required" --msgid_plural "%u Applications Updated — Restart Required" -+msgid "%u App Updated — Restart Required" -+msgid_plural "%u Apps Updated — Restart Required" - msgstr[0] "Byla aktualizována %u aplikace — vyžaduje restart" - msgstr[1] "Byly aktualizovány %u aplikace — vyžaduje restart" - msgstr[2] "Bylo aktualizováno %u aplikací — vyžaduje restart" -@@ -4517,13 +4596,13 @@ msgstr[2] "Bylo aktualizováno %u aplikací — vyžaduje restart" - #. TRANSLATORS: apps were auto-updated - #: src/gs-update-monitor.c:361 - #, c-format --msgid "%u Application Updated" --msgid_plural "%u Applications Updated" -+msgid "%u App Updated" -+msgid_plural "%u Apps Updated" - msgstr[0] "Byla aktualizována %u aplikace" - msgstr[1] "Byly aktualizovány %u aplikace" - msgstr[2] "Bylo aktualizováno %u aplikací" - --#. TRANSLATORS: %1 is an application name, e.g. Firefox -+#. TRANSLATORS: %1 is an app name, e.g. Firefox - #: src/gs-update-monitor.c:372 - #, c-format - msgid "%s has been updated." -@@ -4531,81 +4610,81 @@ msgstr "Aplikace %s byla aktualizována." - - #. TRANSLATORS: the app needs restarting - #: src/gs-update-monitor.c:375 --msgid "Please restart the application." -+msgid "Please restart the app." - msgstr "Restartujte ji prosím." - --#. TRANSLATORS: %1 and %2 are both application names, e.g. Firefox -+#. TRANSLATORS: %1 and %2 are both app names, e.g. Firefox - #: src/gs-update-monitor.c:383 - #, c-format - msgid "%s and %s have been updated." - msgstr "Aplikace %s a %s byly aktualizovány." - --#. TRANSLATORS: at least one application needs restarting -+#. TRANSLATORS: at least one app needs restarting - #: src/gs-update-monitor.c:389 src/gs-update-monitor.c:408 - #, c-format --msgid "%u application requires a restart." --msgid_plural "%u applications require a restart." -+msgid "%u app requires a restart." -+msgid_plural "%u apps require a restart." - msgstr[0] "%u aplikace vyžaduje restart." - msgstr[1] "%u aplikace vyžadují restart." - msgstr[2] "%u aplikací vyžaduje restart." - --#. TRANSLATORS: %1, %2 and %3 are all application names, e.g. Firefox -+#. TRANSLATORS: %1, %2 and %3 are all app names, e.g. Firefox - #: src/gs-update-monitor.c:401 - #, c-format - msgid "Includes %s, %s and %s." - msgstr "Včetně %s, %s a %s." - - #. TRANSLATORS: this is when the current operating system version goes end-of-life --#: src/gs-update-monitor.c:671 src/gs-updates-page.ui:20 -+#: src/gs-update-monitor.c:696 - msgid "Operating System Updates Unavailable" - msgstr "Aktualizace operačního systému nejsou dostupné" - - #. TRANSLATORS: this is the message dialog for the distro EOL notice --#: src/gs-update-monitor.c:673 -+#: src/gs-update-monitor.c:698 - msgid "Upgrade to continue receiving security updates." - msgstr "Povýšit, aby byly nadále přijímány bezpečnostní aktualizace." - - #. TRANSLATORS: this is a distro upgrade, the replacement would be the - #. * distro name, e.g. 'Fedora' --#: src/gs-update-monitor.c:728 -+#: src/gs-update-monitor.c:753 - #, c-format - msgid "A new version of %s is available to install" - msgstr "K instalaci je dostupná nová verze distribuce %s" - - #. TRANSLATORS: this is a distro upgrade --#: src/gs-update-monitor.c:732 -+#: src/gs-update-monitor.c:757 - msgid "Software Upgrade Available" - msgstr "Dostupné povýšení softwaru" - - #. TRANSLATORS: title when we offline updates have failed --#: src/gs-update-monitor.c:1137 -+#: src/gs-update-monitor.c:1162 - msgid "Software Updates Failed" - msgstr "Aktualizace softwaru selhaly" - - #. TRANSLATORS: message when we offline updates have failed --#: src/gs-update-monitor.c:1139 -+#: src/gs-update-monitor.c:1164 - msgid "An important operating system update failed to be installed." - msgstr "Selhala instalace důležité aktualizace operačního systému." - --#: src/gs-update-monitor.c:1140 -+#: src/gs-update-monitor.c:1165 - msgid "Show Details" - msgstr "Zobrazit podrobnosti" - - #. TRANSLATORS: Notification title when we've done a distro upgrade --#: src/gs-update-monitor.c:1162 -+#: src/gs-update-monitor.c:1187 - msgid "System Upgrade Complete" - msgstr "Bylo dokončeno povýšení systému" - - #. TRANSLATORS: This is the notification body when we've done a - #. * distro upgrade. First %s is the distro name and the 2nd %s - #. * is the version, e.g. "Welcome to Fedora 28!" --#: src/gs-update-monitor.c:1167 -+#: src/gs-update-monitor.c:1192 - #, c-format - msgid "Welcome to %s %s!" - msgstr "Vítejte ve vydání %s %s!" - - #. TRANSLATORS: title when we've done offline updates --#: src/gs-update-monitor.c:1173 -+#: src/gs-update-monitor.c:1198 - msgid "Software Update Installed" - msgid_plural "Software Updates Installed" - msgstr[0] "Aktualizace softwaru nainstalována" -@@ -4613,7 +4692,7 @@ msgstr[1] "Aktualizace softwaru nainstalovány" - msgstr[2] "Aktualizace softwaru nainstalovány" - - #. TRANSLATORS: message when we've done offline updates --#: src/gs-update-monitor.c:1177 -+#: src/gs-update-monitor.c:1202 - msgid "An important operating system update has been installed." - msgid_plural "Important operating system updates have been installed." - msgstr[0] "Byla nainstalována důležitá aktualizace operačního systému." -@@ -4621,34 +4700,34 @@ msgstr[1] "Byly nainstalovány důležité aktualizace operačního systému." - msgstr[2] "Byly nainstalovány důležité aktualizace operačního systému." - - #. TRANSLATORS: Button to look at the updates that were installed. --#. * Note that it has nothing to do with the application reviews, the -+#. * Note that it has nothing to do with the app reviews, the - #. * users can't express their opinions here. In some languages - #. * "Review (evaluate) something" is a different translation than - #. * "Review (browse) something." --#: src/gs-update-monitor.c:1188 -+#: src/gs-update-monitor.c:1213 - msgctxt "updates" - msgid "Review" - msgstr "Přehled" - - #. TRANSLATORS: this is when the offline update failed --#: src/gs-update-monitor.c:1237 -+#: src/gs-update-monitor.c:1262 - msgid "Failed To Update" - msgstr "Aktualizace selhala" - - #. TRANSLATORS: the user must have updated manually after - #. * the updates were prepared --#: src/gs-update-monitor.c:1242 -+#: src/gs-update-monitor.c:1267 - msgid "The system was already up to date." - msgstr "Systém již byl aktuální." - - #. TRANSLATORS: the user aborted the update manually --#: src/gs-update-monitor.c:1247 -+#: src/gs-update-monitor.c:1272 - msgid "The update was cancelled." - msgstr "Aktualizace byla zrušena." - - #. TRANSLATORS: the package manager needed to download - #. * something with no network available --#: src/gs-update-monitor.c:1252 -+#: src/gs-update-monitor.c:1277 - msgid "" - "Internet access was required but wasn’t available. Please make sure that you " - "have internet access and try again." -@@ -4657,7 +4736,7 @@ msgstr "" - "připojení k Internetu a zkuste to znovu." - - #. TRANSLATORS: if the package is not signed correctly --#: src/gs-update-monitor.c:1257 -+#: src/gs-update-monitor.c:1282 - msgid "" - "There were security issues with the update. Please consult your software " - "provider for more details." -@@ -4666,7 +4745,7 @@ msgstr "" - "svým poskytovatelem softwaru." - - #. TRANSLATORS: we ran out of disk space --#: src/gs-update-monitor.c:1262 -+#: src/gs-update-monitor.c:1287 - msgid "" - "There wasn’t enough disk space. Please free up some space and try again." - msgstr "" -@@ -4674,7 +4753,7 @@ msgstr "" - "znovu." - - #. TRANSLATORS: We didn't handle the error type --#: src/gs-update-monitor.c:1266 -+#: src/gs-update-monitor.c:1291 - msgid "" - "We’re sorry: the update failed to install. Please wait for another update " - "and try again. If the problem persists, contact your software provider." -@@ -4684,49 +4763,39 @@ msgstr "" - "poskytovatele softwaru." - - #. TRANSLATORS: This is the time when we last checked for updates --#: src/gs-updates-page.c:248 -+#: src/gs-updates-page.c:253 - #, c-format - msgid "Last checked: %s" - msgstr "Poslední kontrola: %s" - --#: src/gs-updates-page.c:297 --msgid "Stop Refreshing" --msgstr "" -+#: src/gs-updates-page.c:302 -+msgid "Stop" -+msgstr "Zastavit" - --#: src/gs-updates-page.c:306 src/gs-updates-page.c:318 --msgid "Refresh" --msgstr "" -+#: src/gs-updates-page.c:311 src/gs-updates-page.c:323 -+msgid "Check for Updates" -+msgstr "Zkontrolovat aktualizace" - - #. TRANSLATORS: the first %s is the distro name, e.g. 'Fedora' - #. * and the second %s is the distro version, e.g. '25' --#: src/gs-updates-page.c:563 -+#: src/gs-updates-page.c:568 - #, c-format --msgid "%s %s is no longer supported." --msgstr "Systém %s %s již není podporován." -- --#: src/gs-updates-page.c:567 --msgid "Your operating system is no longer supported." --msgstr "Váš operační systém není nadále podporován." -- --#. TRANSLATORS: EOL distros do not get important updates --#: src/gs-updates-page.c:572 --msgid "This means that it does not receive security updates." --msgstr "" --"Znamená to, že pro něj již nadále nejsou poskytovány bezpečnostní opravy." -+msgid "%s %s has stopped receiving critical software updates" -+msgstr "Distribuce %s %s přestala dostávat kritické aktualizace softwaru" - --#. TRANSLATORS: upgrade refers to a major update, e.g. Fedora 25 to 26 --#: src/gs-updates-page.c:576 --msgid "It is recommended that you upgrade to a more recent version." --msgstr "Doporučuje se povýšit na nejnovější verzi." -+#. TRANSLATORS: This message is meant to tell users that they need to upgrade -+#. * or else their distro will not get important updates. -+#: src/gs-updates-page.c:574 -+msgid "Your operating system has stopped receiving critical software updates" -+msgstr "Váš operační systém přestal dostávat kritické aktualizace softwaru" - - #. TRANSLATORS: this is to explain that downloading updates may cost money --#: src/gs-updates-page.c:853 -+#: src/gs-updates-page.c:843 - msgid "Charges May Apply" - msgstr "Možné zpoplatnění" - --#. TRANSLATORS: we need network --#. * to do the updates check --#: src/gs-updates-page.c:857 -+#. TRANSLATORS: we need network to do the updates check -+#: src/gs-updates-page.c:845 - msgid "" - "Checking for updates while using mobile broadband could cause you to incur " - "charges." -@@ -4734,28 +4803,31 @@ msgstr "" - "Kontrola aktualizací přes mobilní připojení může být zpoplatněna vaším " - "operátorem." - --#. TRANSLATORS: this is a link to the --#. * control-center network panel --#: src/gs-updates-page.c:861 -+#. TRANSLATORS: this is a link to the control-center network panel -+#: src/gs-updates-page.c:849 - msgid "Check _Anyway" - msgstr "_Přesto zkontrolovat" - - #. TRANSLATORS: can't do updates check --#: src/gs-updates-page.c:877 -+#: src/gs-updates-page.c:860 - msgid "No Network" - msgstr "Žádné připojení k síti" - --#. TRANSLATORS: we need network --#. * to do the updates check --#: src/gs-updates-page.c:881 -+#. TRANSLATORS: we need network to do the updates check -+#: src/gs-updates-page.c:862 - msgid "Internet access is required to check for updates." - msgstr "Přístup k internetu je nezbytný pro kontrolu aktualizací." - --#: src/gs-updates-page.c:1254 -+#. TRANSLATORS: this is a link to the control-center network panel -+#: src/gs-updates-page.c:866 -+msgid "Network _Settings" -+msgstr "Nastavení _sítě" -+ -+#: src/gs-updates-page.c:1235 - msgid "Check for updates" - msgstr "Zkontrolovat aktualizace" - --#: src/gs-updates-page.c:1290 -+#: src/gs-updates-page.c:1271 - msgctxt "Apps to be updated" - msgid "Updates" - msgstr "Aktualizace" -@@ -4765,25 +4837,25 @@ msgid "Updates page" - msgstr "Stránka s aktualizacemi" - - #. TRANSLATORS: the updates panel is starting up. --#: src/gs-updates-page.ui:82 -+#: src/gs-updates-page.ui:58 - msgid "Loading Updates…" - msgstr "Načítají se aktualizace…" - - #. TRANSLATORS: the updates panel is starting up. --#: src/gs-updates-page.ui:95 -+#: src/gs-updates-page.ui:71 - msgid "This could take a while." - msgstr "Může to chvilku trvat." - - #. TRANSLATORS: This means all software (plural) installed on this system is up to date. --#: src/gs-updates-page.ui:203 -+#: src/gs-updates-page.ui:179 - msgid "Up to Date" - msgstr "Aktuální" - --#: src/gs-updates-page.ui:242 -+#: src/gs-updates-page.ui:218 - msgid "Use Mobile Data?" - msgstr "Použít mobilní data?" - --#: src/gs-updates-page.ui:243 -+#: src/gs-updates-page.ui:219 - msgid "" - "Checking for updates when using mobile broadband could cause you to incur " - "charges." -@@ -4791,68 +4863,68 @@ msgstr "" - "Kontrola aktualizací při používání mobilního širokopásmového připojení vám " - "může způsobit poplatky." - --#: src/gs-updates-page.ui:246 -+#: src/gs-updates-page.ui:222 - msgid "_Check Anyway" - msgstr "_Přesto zkontrolovat" - --#: src/gs-updates-page.ui:262 -+#: src/gs-updates-page.ui:238 - msgid "No Connection" - msgstr "Žádné připojení" - --#: src/gs-updates-page.ui:263 -+#: src/gs-updates-page.ui:239 - msgid "Go online to check for updates." - msgstr "Kvůli kontrole aktualizací se musíte připojit k síti." - --#: src/gs-updates-page.ui:266 -+#: src/gs-updates-page.ui:242 - msgid "_Network Settings" - msgstr "_Nastavení sítě" - --#: src/gs-updates-page.ui:295 -+#: src/gs-updates-page.ui:275 - msgid "Error" - msgstr "Chyba" - --#: src/gs-updates-page.ui:296 -+#: src/gs-updates-page.ui:276 - msgid "Updates are automatically managed." - msgstr "Aktualizace jsou spravovány automaticky." - - #. TRANSLATORS: This is the button for installing all - #. * offline updates --#: src/gs-updates-section.c:312 --msgid "Restart & Update" --msgstr "Restartovat a aktualizovat" -+#: src/gs-updates-section.c:340 -+msgid "_Restart & Update…" -+msgstr "_Restartovat a aktualizovat…" - - #. TRANSLATORS: This is the button for upgrading all --#. * online-updatable applications --#: src/gs-updates-section.c:318 --msgid "Update All" --msgstr "Aktualizovat vše" -+#. * online-updatable apps -+#: src/gs-updates-section.c:346 -+msgid "U_pdate All" -+msgstr "_Aktualizovat vše" - - #. TRANSLATORS: This is the header for system firmware that - #. * requires a reboot to apply --#: src/gs-updates-section.c:450 -+#: src/gs-updates-section.c:474 - msgid "Integrated Firmware" - msgstr "Integrovaný Firmware" - - #. TRANSLATORS: This is the header for offline OS and offline - #. * app updates that require a reboot to apply --#: src/gs-updates-section.c:455 -+#: src/gs-updates-section.c:479 - msgid "Requires Restart" - msgstr "Vyžaduje restart" - - #. TRANSLATORS: This is the header for online runtime and - #. * app updates, typically flatpaks or snaps --#: src/gs-updates-section.c:460 --msgid "Application Updates" -+#: src/gs-updates-section.c:484 -+msgid "App Updates" - msgstr "Aktualizace aplikací" - - #. TRANSLATORS: This is the header for device firmware that can - #. * be installed online --#: src/gs-updates-section.c:465 -+#: src/gs-updates-section.c:489 - msgid "Device Firmware" - msgstr "Firmware zařízení" - - #: src/gs-updates-section.ui:33 src/gs-upgrade-banner.ui:72 --#: plugins/packagekit/gs-packagekit-task.c:155 -+#: plugins/packagekit/gs-packagekit-task.c:154 - msgid "_Download" - msgstr "S_táhnout" - -@@ -4899,8 +4971,8 @@ msgid "A major upgrade, with new features and added polish." - msgstr "Povýšení na novou verzi s novými funkcemi a vylepšeními." - - #: src/gs-upgrade-banner.ui:187 --msgid "_Restart & Upgrade" --msgstr "_Restartovat a aktualizovat" -+msgid "_Restart & Upgrade…" -+msgstr "_Restartovat a aktualizovat…" - - #: src/gs-upgrade-banner.ui:201 - msgid "Remember to back up data and files before upgrading." -@@ -4910,7 +4982,7 @@ msgstr "Nezapomeňte zazálohovat si před povýšením svá data a soubory." - msgid "Add, remove or update software on this computer" - msgstr "Přidat, odebrat nebo aktualizovat software v tomto počítači" - --#. Translators: Search terms to find this application. Do NOT translate or localize the semicolons! The list MUST also end with a semicolon! -+#. Translators: Search terms to find this app. Do NOT translate or localize the semicolons! The list MUST also end with a semicolon! - #: src/org.gnome.Software.desktop.in:12 - msgid "" - "Updates;Upgrade;Sources;Repositories;Preferences;Install;Uninstall;Program;" -@@ -4922,14 +4994,14 @@ msgstr "" - #. TRANSLATORS: this is a group of updates that are not - #. * packages and are not shown in the main list - #: plugins/core/gs-plugin-generic-updates.c:67 --#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:2975 -+#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:3049 - msgid "System Updates" - msgstr "Aktualizace systému" - - #. TRANSLATORS: this is a longer description of the - #. * "System Updates" string - #: plugins/core/gs-plugin-generic-updates.c:72 --#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:2980 -+#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:3054 - msgid "" - "General system updates, such as security or bug fixes, and performance " - "improvements." -@@ -4943,21 +5015,19 @@ msgid "Downloading featured images…" - msgstr "Stahují se obrázky k významným aplikacím…" - - #. Translators: The '%s' is replaced with the OS name, like "Endless OS" --#: plugins/eos-updater/gs-plugin-eos-updater.c:637 -+#: plugins/eos-updater/gs-plugin-eos-updater.c:684 - #, c-format - msgid "%s update with new features and fixes." - msgstr "Aktualizace %s s novými funkcemi a opravami." - --#: plugins/eos-updater/gs-plugin-eos-updater.c:970 -+#: plugins/eos-updater/gs-plugin-eos-updater.c:1267 - msgid "EOS update service could not fetch and apply the update." - msgstr "Aktualizační služba EOS nemohla stáhnout a nasadit aktualizaci." - - #: plugins/epiphany/gs-plugin-epiphany.c:499 - #: plugins/epiphany/gs-plugin-epiphany.c:503 --#, fuzzy --#| msgid "Web Applications" - msgid "Web App" --msgstr "Webové aplikace" -+msgstr "Webová aplikace" - - #: plugins/epiphany/org.gnome.Software.Plugin.Epiphany.metainfo.xml.in:6 - msgid "Web Apps Support" -@@ -4985,139 +5055,139 @@ msgid "Flatpak Support" - msgstr "Podpora pro Flatpak" - - #: plugins/flatpak/org.gnome.Software.Plugin.Flatpak.metainfo.xml.in:7 --msgid "Flatpak is a framework for desktop applications on Linux" -+msgid "Flatpak is a framework for desktop apps on Linux" - msgstr "Flatpak je systém pro provozování aplikací na Linuxu" - - #. Reference: https://docs.flatpak.org/en/latest/flatpak-command-reference.html#idm45858571325264 --#: plugins/flatpak/gs-flatpak.c:313 -+#: plugins/flatpak/gs-flatpak.c:318 - #, c-format - msgid "System folder %s" - msgstr "Systémová složka %s" - --#: plugins/flatpak/gs-flatpak.c:314 plugins/flatpak/gs-flatpak.c:315 -+#: plugins/flatpak/gs-flatpak.c:319 plugins/flatpak/gs-flatpak.c:320 - #, c-format - msgid "Home subfolder %s" - msgstr "Podsložka %s v domovské složce" - --#: plugins/flatpak/gs-flatpak.c:316 -+#: plugins/flatpak/gs-flatpak.c:321 - msgid "Host system folders" - msgstr "Složky hostitelského systému" - --#: plugins/flatpak/gs-flatpak.c:317 -+#: plugins/flatpak/gs-flatpak.c:322 - msgid "Host system configuration from /etc" - msgstr "Konfigurace hostitelského systému z /etc" - --#: plugins/flatpak/gs-flatpak.c:318 -+#: plugins/flatpak/gs-flatpak.c:323 - msgid "Desktop folder" - msgstr "Složka plochy" - --#: plugins/flatpak/gs-flatpak.c:318 -+#: plugins/flatpak/gs-flatpak.c:323 - #, c-format - msgid "Desktop subfolder %s" - msgstr "Podsložka %s ve složce plochy" - --#: plugins/flatpak/gs-flatpak.c:319 -+#: plugins/flatpak/gs-flatpak.c:324 - msgid "Documents folder" - msgstr "Složka dokumentů" - --#: plugins/flatpak/gs-flatpak.c:319 -+#: plugins/flatpak/gs-flatpak.c:324 - #, c-format - msgid "Documents subfolder %s" - msgstr "Podsložka %s ve složce dokumentů" - --#: plugins/flatpak/gs-flatpak.c:320 -+#: plugins/flatpak/gs-flatpak.c:325 - msgid "Music folder" - msgstr "Složka hudby" - --#: plugins/flatpak/gs-flatpak.c:320 -+#: plugins/flatpak/gs-flatpak.c:325 - #, c-format - msgid "Music subfolder %s" - msgstr "Podsložka %s ve složce hudby" - --#: plugins/flatpak/gs-flatpak.c:321 -+#: plugins/flatpak/gs-flatpak.c:326 - msgid "Pictures folder" - msgstr "Složka obrázků" - --#: plugins/flatpak/gs-flatpak.c:321 -+#: plugins/flatpak/gs-flatpak.c:326 - #, c-format - msgid "Pictures subfolder %s" - msgstr "Podsložka %s ve složce obrázků" - --#: plugins/flatpak/gs-flatpak.c:322 -+#: plugins/flatpak/gs-flatpak.c:327 - msgid "Public Share folder" - msgstr "Složka veřejně sdílených" - --#: plugins/flatpak/gs-flatpak.c:322 -+#: plugins/flatpak/gs-flatpak.c:327 - #, c-format - msgid "Public Share subfolder %s" - msgstr "Podsložka %s ve složce veřejně sdílených" - --#: plugins/flatpak/gs-flatpak.c:323 -+#: plugins/flatpak/gs-flatpak.c:328 - msgid "Videos folder" - msgstr "Složka videí" - --#: plugins/flatpak/gs-flatpak.c:323 -+#: plugins/flatpak/gs-flatpak.c:328 - #, c-format - msgid "Videos subfolder %s" - msgstr "Podsložka %s ve složce videí" - --#: plugins/flatpak/gs-flatpak.c:324 -+#: plugins/flatpak/gs-flatpak.c:329 - msgid "Templates folder" - msgstr "Složka šablon" - --#: plugins/flatpak/gs-flatpak.c:324 -+#: plugins/flatpak/gs-flatpak.c:329 - #, c-format - msgid "Templates subfolder %s" - msgstr "Podsložka %s ve složce šablon" - --#: plugins/flatpak/gs-flatpak.c:325 -+#: plugins/flatpak/gs-flatpak.c:330 - msgid "User cache folder" - msgstr "Složka uživatelské mezipaměti" - --#: plugins/flatpak/gs-flatpak.c:325 -+#: plugins/flatpak/gs-flatpak.c:330 - #, c-format - msgid "User cache subfolder %s" - msgstr "Podsložka %s ve složce uživatelské mezipaměti" - --#: plugins/flatpak/gs-flatpak.c:326 -+#: plugins/flatpak/gs-flatpak.c:331 - msgid "User configuration folder" - msgstr "Složka uživatelské konfigurace" - --#: plugins/flatpak/gs-flatpak.c:326 -+#: plugins/flatpak/gs-flatpak.c:331 - #, c-format - msgid "User configuration subfolder %s" - msgstr "Podsložka %s ve složce uživatelské konfigurace" - --#: plugins/flatpak/gs-flatpak.c:327 -+#: plugins/flatpak/gs-flatpak.c:332 - msgid "User data folder" - msgstr "Složka uživatelských dat" - --#: plugins/flatpak/gs-flatpak.c:327 -+#: plugins/flatpak/gs-flatpak.c:332 - #, c-format - msgid "User data subfolder %s" - msgstr "Podsložka %s ve složce uživatelských dat" - --#: plugins/flatpak/gs-flatpak.c:328 -+#: plugins/flatpak/gs-flatpak.c:333 - msgid "User runtime folder" - msgstr "Uživatelská složka pro běh aplikací" - --#: plugins/flatpak/gs-flatpak.c:328 -+#: plugins/flatpak/gs-flatpak.c:333 - #, c-format - msgid "User runtime subfolder %s" - msgstr "Podsložka %s v uživatelské složce pro běh aplikací" - --#: plugins/flatpak/gs-flatpak.c:386 -+#: plugins/flatpak/gs-flatpak.c:391 - #, c-format - msgid "Filesystem access to %s" - msgstr "Přístup k souborovému systému v %s" - - #. TRANSLATORS: status text when downloading new metadata --#: plugins/flatpak/gs-flatpak.c:1403 -+#: plugins/flatpak/gs-flatpak.c:1408 - #, c-format - msgid "Getting flatpak metadata for %s…" - msgstr "Získávají se metadata Flatpak pro %s…" - --#: plugins/flatpak/gs-flatpak.c:3580 -+#: plugins/flatpak/gs-flatpak.c:3589 - #, c-format - msgid "Failed to refine addon ‘%s’: %s" - msgstr "Selhalo vylepšení doplňku „%s“: %s" -@@ -5130,17 +5200,17 @@ msgstr "Uživatelská instalace" - msgid "System Installation" - msgstr "Systémová instalace" - --#: plugins/flatpak/gs-plugin-flatpak.c:1038 -+#: plugins/flatpak/gs-plugin-flatpak.c:1320 - #, c-format - msgid "Failed to add to install for addon ‘%s’: %s" - msgstr "Selhalo přídání doplňku „%s“ k nainstalování: %s" - --#: plugins/flatpak/gs-plugin-flatpak.c:1052 -+#: plugins/flatpak/gs-plugin-flatpak.c:1334 - #, c-format - msgid "Failed to add to uninstall for addon ‘%s’: %s" - msgstr "Selhalo přidání doplňku „%s“ k odinstalování: %s" - --#: plugins/flatpak/gs-plugin-flatpak.c:1318 -+#: plugins/flatpak/gs-plugin-flatpak.c:1601 - #, c-format - msgid "" - "Remote “%s” doesn't allow install of “%s”, possibly due to its filter. " -@@ -5152,87 +5222,85 @@ msgstr "" - #. TRANSLATORS: as in laptop battery power - #: plugins/fwupd/gs-fwupd-app.c:66 - msgid "System power is too low to perform the update" --msgstr "" -+msgstr "Systém nemá dostatek energie, aby provedl aktualizaci" - - #. TRANSLATORS: as in laptop battery power - #: plugins/fwupd/gs-fwupd-app.c:70 - #, c-format - msgid "System power is too low to perform the update (%u%%, requires %u%%)" - msgstr "" -+"Systém nemá dostatek energie, aby provedl aktualizaci (%u%%, vyžaduje %u%%)" - - #. TRANSLATORS: for example, a Bluetooth mouse that is in powersave mode - #: plugins/fwupd/gs-fwupd-app.c:76 - msgid "Device is unreachable, or out of wireless range" --msgstr "" -+msgstr "Zařízení je nedostupné nebo mimo dosah bezdrátové sítě" - - #. TRANSLATORS: for example the batteries *inside* the Bluetooth mouse - #: plugins/fwupd/gs-fwupd-app.c:82 --#, fuzzy, c-format --#| msgid "The battery level is too low" -+#, c-format - msgid "Device battery power is too low" --msgstr "Úroveň nabití baterie je příliš nízká" -+msgstr "Úroveň nabití baterie zařízení je příliš nízká" - - #. TRANSLATORS: for example the batteries *inside* the Bluetooth mouse - #: plugins/fwupd/gs-fwupd-app.c:85 - #, c-format - msgid "Device battery power is too low (%u%%, requires %u%%)" --msgstr "" -+msgstr "Úroveň nabití baterie zařízení je příliš nízká (%u%%, vyžaduje %u%%)" - - #. TRANSLATORS: usually this is when we're waiting for a reboot - #: plugins/fwupd/gs-fwupd-app.c:91 - msgid "Device is waiting for the update to be applied" --msgstr "" -+msgstr "Zařízení čeká na aplikování aktualizace" - - #. TRANSLATORS: as in, wired mains power for a laptop - #: plugins/fwupd/gs-fwupd-app.c:95 - msgid "Device requires AC power to be connected" --msgstr "" -+msgstr "Zařízení vyžaduje připojené napájení za sítě" - - #. TRANSLATORS: lid means "laptop top cover" - #: plugins/fwupd/gs-fwupd-app.c:99 --#, fuzzy --#| msgid "Device cannot be used during update." - msgid "Device cannot be used while the lid is closed" --msgstr "Zařízení nelze během aktualizace používat." -+msgstr "Zařízení nelze používat, pokud je víko notebooku zavřené" - - #. TRANSLATORS: a specific part of hardware, - #. * the first %s is the device name, e.g. 'Unifying Receiver` --#: plugins/fwupd/gs-fwupd-app.c:218 -+#: plugins/fwupd/gs-fwupd-app.c:219 - #, c-format - msgid "%s Device Update" - msgstr "Aktualizace zařízení %s" - - #. TRANSLATORS: the entire system, e.g. all internal devices, - #. * the first %s is the device name, e.g. 'ThinkPad P50` --#: plugins/fwupd/gs-fwupd-app.c:223 -+#: plugins/fwupd/gs-fwupd-app.c:224 - #, c-format - msgid "%s System Update" - msgstr "Aktualizace systému pro %s" - - #. TRANSLATORS: the EC is typically the keyboard controller chip, - #. * the first %s is the device name, e.g. 'ThinkPad P50` --#: plugins/fwupd/gs-fwupd-app.c:228 -+#: plugins/fwupd/gs-fwupd-app.c:229 - #, c-format - msgid "%s Embedded Controller Update" - msgstr "Aktualizace vestavěného řadiče pro %s" - - #. TRANSLATORS: ME stands for Management Engine, the Intel AMT thing, - #. * the first %s is the device name, e.g. 'ThinkPad P50` --#: plugins/fwupd/gs-fwupd-app.c:233 -+#: plugins/fwupd/gs-fwupd-app.c:234 - #, c-format - msgid "%s ME Update" - msgstr "Aktualizace ME pro %s" - - #. TRANSLATORS: ME stands for Management Engine (with Intel AMT), - #. * where the first %s is the device name, e.g. 'ThinkPad P50` --#: plugins/fwupd/gs-fwupd-app.c:238 -+#: plugins/fwupd/gs-fwupd-app.c:239 - #, c-format - msgid "%s Corporate ME Update" - msgstr "Aktualizace ME pro firmy pro %s" - - #. TRANSLATORS: ME stands for Management Engine, where - #. * the first %s is the device name, e.g. 'ThinkPad P50` --#: plugins/fwupd/gs-fwupd-app.c:243 -+#: plugins/fwupd/gs-fwupd-app.c:244 - #, c-format - msgid "%s Consumer ME Update" - msgstr "Aktualizace ME pro běžné spotřebitele pro %s" -@@ -5240,7 +5308,7 @@ msgstr "Aktualizace ME pro běžné spotřebitele pro %s" - #. TRANSLATORS: the controller is a device that has other devices - #. * plugged into it, for example ThunderBolt, FireWire or USB, - #. * the first %s is the device name, e.g. 'Intel ThunderBolt` --#: plugins/fwupd/gs-fwupd-app.c:249 -+#: plugins/fwupd/gs-fwupd-app.c:250 - #, c-format - msgid "%s Controller Update" - msgstr "Aktualizace řadiče pro %s" -@@ -5248,97 +5316,137 @@ msgstr "Aktualizace řadiče pro %s" - #. TRANSLATORS: the Thunderbolt controller is a device that - #. * has other high speed Thunderbolt devices plugged into it; - #. * the first %s is the system name, e.g. 'ThinkPad P50` --#: plugins/fwupd/gs-fwupd-app.c:255 -+#: plugins/fwupd/gs-fwupd-app.c:256 - #, c-format - msgid "%s Thunderbolt Controller Update" - msgstr "Aktualizace řadiče Thunderbolt pro %s" - - #. TRANSLATORS: the CPU microcode is firmware loaded onto the CPU - #. * at system bootup --#: plugins/fwupd/gs-fwupd-app.c:260 -+#: plugins/fwupd/gs-fwupd-app.c:261 - #, c-format - msgid "%s CPU Microcode Update" - msgstr "Aktualizace mikrokódu CPU pro %s" - - #. TRANSLATORS: configuration refers to hardware state, - #. * e.g. a security database or a default power value --#: plugins/fwupd/gs-fwupd-app.c:265 -+#: plugins/fwupd/gs-fwupd-app.c:266 - #, c-format - msgid "%s Configuration Update" - msgstr "Aktualizace nastavení pro %s" - - #. TRANSLATORS: battery refers to the system power source --#: plugins/fwupd/gs-fwupd-app.c:269 -+#: plugins/fwupd/gs-fwupd-app.c:270 - #, c-format - msgid "%s Battery Update" - msgstr "Aktualizace baterie pro %s" - - #. TRANSLATORS: camera can refer to the laptop internal - #. * camera in the bezel or external USB webcam --#: plugins/fwupd/gs-fwupd-app.c:274 -+#: plugins/fwupd/gs-fwupd-app.c:275 - #, c-format - msgid "%s Camera Update" - msgstr "Aktualizace kamery pro %s" - - #. TRANSLATORS: TPM refers to a Trusted Platform Module --#: plugins/fwupd/gs-fwupd-app.c:278 -+#: plugins/fwupd/gs-fwupd-app.c:279 - #, c-format - msgid "%s TPM Update" - msgstr "Aktualizace TPM pro %s" - - #. TRANSLATORS: TouchPad refers to a flat input device --#: plugins/fwupd/gs-fwupd-app.c:282 -+#: plugins/fwupd/gs-fwupd-app.c:283 - #, c-format - msgid "%s Touchpad Update" - msgstr "Aktualizace touchpadu pro %s" - - #. TRANSLATORS: Mouse refers to a handheld input device --#: plugins/fwupd/gs-fwupd-app.c:286 -+#: plugins/fwupd/gs-fwupd-app.c:287 - #, c-format - msgid "%s Mouse Update" - msgstr "Aktualizace myši pro %s" - - #. TRANSLATORS: Keyboard refers to an input device for typing --#: plugins/fwupd/gs-fwupd-app.c:290 -+#: plugins/fwupd/gs-fwupd-app.c:291 - #, c-format - msgid "%s Keyboard Update" - msgstr "Aktualizace klávesnice pro %s" - - #. TRANSLATORS: Storage Controller is typically a RAID or SAS adapter --#: plugins/fwupd/gs-fwupd-app.c:294 -+#: plugins/fwupd/gs-fwupd-app.c:295 - #, c-format - msgid "%s Storage Controller Update" - msgstr "Aktualizace řadiče disků pro %s" - - #. TRANSLATORS: Network Interface refers to the physical - #. * PCI card, not the logical wired connection --#: plugins/fwupd/gs-fwupd-app.c:299 -+#: plugins/fwupd/gs-fwupd-app.c:300 - #, c-format - msgid "%s Network Interface Update" - msgstr "Aktualizace síťové karty pro %s" - - #. TRANSLATORS: Video Display refers to the laptop internal display or - #. * external monitor --#: plugins/fwupd/gs-fwupd-app.c:304 -+#: plugins/fwupd/gs-fwupd-app.c:305 - #, c-format - msgid "%s Display Update" - msgstr "Aktualizace displeje pro %s" - - #. TRANSLATORS: BMC refers to baseboard management controller which - #. * is the device that updates all the other firmware on the system --#: plugins/fwupd/gs-fwupd-app.c:309 -+#: plugins/fwupd/gs-fwupd-app.c:310 - #, c-format - msgid "%s BMC Update" - msgstr "Aktualizace BMC pro %s" - - #. TRANSLATORS: Receiver refers to a radio device, e.g. a tiny Bluetooth - #. * device that stays in the USB port so the wireless peripheral works --#: plugins/fwupd/gs-fwupd-app.c:314 -+#: plugins/fwupd/gs-fwupd-app.c:315 - #, c-format - msgid "%s USB Receiver Update" - msgstr "Aktualizace přijímače USB pro %s" - --#: plugins/fwupd/gs-plugin-fwupd.c:1244 -+#. TRANSLATORS: drive refers to a storage device, e.g. SATA disk -+#: plugins/fwupd/gs-fwupd-app.c:319 -+#, c-format -+msgid "%s Drive Update" -+msgstr "Aktualizace disku pro %s" -+ -+#. TRANSLATORS: flash refers to solid state storage, e.g. UFS or eMMC -+#: plugins/fwupd/gs-fwupd-app.c:323 -+#, c-format -+msgid "%s Flash Drive Update" -+msgstr "Aktualizace flash disku pro %s" -+ -+#. TRANSLATORS: SSD refers to a Solid State Drive, e.g. non-rotating -+#. * SATA or NVMe disk -+#: plugins/fwupd/gs-fwupd-app.c:328 -+#, c-format -+msgid "%s SSD Update" -+msgstr "Aktualizace SSD pro %s" -+ -+#. TRANSLATORS: GPU refers to a Graphics Processing Unit, e.g. -+#. * the "video card" -+#: plugins/fwupd/gs-fwupd-app.c:333 -+#, c-format -+msgid "%s GPU Update" -+msgstr "Aktualizace grafické karty pro %s" -+ -+#. TRANSLATORS: Dock refers to the port replicator hardware laptops are -+#. * cradled in, or lowered onto -+#: plugins/fwupd/gs-fwupd-app.c:338 -+#, c-format -+msgid "%s Dock Update" -+msgstr "Aktualizace dokovacího zařízení pro %s" -+ -+#. TRANSLATORS: Dock refers to the port replicator device connected -+#. * by plugging in a USB cable -- which may or may not also provide power -+#: plugins/fwupd/gs-fwupd-app.c:343 -+#, c-format -+msgid "%s USB Dock Update" -+msgstr "Aktualizace USB dokovacího zařízení pro %s" -+ -+#: plugins/fwupd/gs-plugin-fwupd.c:1763 - msgid "Firmware" - msgstr "Firmware" - -@@ -5350,11 +5458,11 @@ msgstr "Podpora aktualizací firmwaru" - msgid "Provides support for firmware upgrades" - msgstr "Poskytuje podporu pro povyšování verzí firmwaru" - --#: plugins/packagekit/gs-packagekit-task.c:148 -+#: plugins/packagekit/gs-packagekit-task.c:147 - msgid "Install Unsigned Software?" - msgstr "Nainstalovat nepodepsaný software?" - --#: plugins/packagekit/gs-packagekit-task.c:149 -+#: plugins/packagekit/gs-packagekit-task.c:148 - msgid "" - "Software that is to be installed is not signed. It will not be possible to " - "verify the origin of updates to this software, or whether updates have been " -@@ -5363,11 +5471,11 @@ msgstr "" - "Software, který se chystáte nainstalovat, není podepsaný. Nebude tak možné " - "ověřit původ jeho aktualizací, nebo zda aktualizace nebyly zmanipulovány." - --#: plugins/packagekit/gs-packagekit-task.c:153 -+#: plugins/packagekit/gs-packagekit-task.c:152 - msgid "Download Unsigned Software?" - msgstr "Stáhnout nepodepsaný software?" - --#: plugins/packagekit/gs-packagekit-task.c:154 -+#: plugins/packagekit/gs-packagekit-task.c:153 - msgid "" - "Unsigned updates are available. Without a signature, it is not possible to " - "verify the origin of the update, or whether it has been tampered with." -@@ -5375,11 +5483,11 @@ msgstr "" - "Jsou k dispozici nepodepsané aktualizace. Bez podpisu není možné ověřit " - "původ aktualizace, nebo zda nebyla zmanipulována." - --#: plugins/packagekit/gs-packagekit-task.c:158 -+#: plugins/packagekit/gs-packagekit-task.c:157 - msgid "Update Unsigned Software?" - msgstr "Aktualizovat nepodepsaný software?" - --#: plugins/packagekit/gs-packagekit-task.c:159 -+#: plugins/packagekit/gs-packagekit-task.c:158 - msgid "" - "Unsigned updates are available. Without a signature, it is not possible to " - "verify the origin of the update, or whether it has been tampered with. " -@@ -5391,11 +5499,11 @@ msgstr "" - "zakázány, dokud nebudou nepodepsané aktualizace buďto odstraněny nebo " - "nahrazeny jinými." - --#: plugins/packagekit/gs-plugin-packagekit.c:367 -+#: plugins/packagekit/gs-plugin-packagekit.c:416 - msgid "Packages" - msgstr "Balíčky" - --#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:2696 -+#: plugins/rpm-ostree/gs-plugin-rpm-ostree.c:2764 - msgid "Operating System (OSTree)" - msgstr "Operační systém (OSTree)" - -@@ -5412,6 +5520,76 @@ msgstr "Podpora pro Snap" - msgid "A snap is a universal Linux package" - msgstr "Snap je univerzální linuxový balíček" - -+#~ msgid "Selected add-ons will be installed with the app." -+#~ msgstr "Vybrané doplňky budou nainstalovány spolu s aplikací." -+ -+#~ msgid "The last timestamp when the system was online and got any updates" -+#~ msgstr "" -+#~ "Datum a čas, kdy byl systém naposledy on-line a dostal nějaké aktualizace" -+ -+#~ msgid "_User" -+#~ msgstr "_Uživatel" -+ -+#~ msgid "" -+#~ "This software is not available in your language and will appear in US " -+#~ "English." -+#~ msgstr "" -+#~ "Tento software není dostupný ve vašem jazyce a zobrazí se v americké " -+#~ "angličtině." -+ -+#~ msgid "Applications" -+#~ msgstr "Aplikace" -+ -+#~ msgid "Web Applications" -+#~ msgstr "Webové aplikace" -+ -+#~ msgid "Post Review" -+#~ msgstr "Příspěvek do recenzí" -+ -+#~ msgid "_Post" -+#~ msgstr "_Odeslat" -+ -+#~ msgid "Rating" -+#~ msgstr "Hodnocení" -+ -+#~ msgid "" -+#~ "Give a short summary of your review, for example: “Great app, would " -+#~ "recommend”." -+#~ msgstr "" -+#~ "Uveďte krátké shrnutí své recenze, například: „Skvělá aplikace, " -+#~ "doporučuji“." -+ -+#~ msgctxt "app review" -+#~ msgid "Review" -+#~ msgstr "Recenze" -+ -+#~ msgid "What do you think of the app? Try to give reasons for your views." -+#~ msgstr "Co si o aplikaci myslíte? Snažte se uvést důvody svého hodnocení." -+ -+#~ msgid "No screenshot provided" -+#~ msgstr "Nemá snímek obrazovky" -+ -+#~ msgid "Primary Menu" -+#~ msgstr "Hlavní nabídky" -+ -+#~ msgctxt "Header bar button for list of apps to be updated" -+#~ msgid "Updates" -+#~ msgstr "Aktualizace" -+ -+#, c-format -+#~ msgid "%s %s is no longer supported." -+#~ msgstr "Systém %s %s již není podporován." -+ -+#~ msgid "This means that it does not receive security updates." -+#~ msgstr "" -+#~ "Znamená to, že pro něj již nadále nejsou poskytovány bezpečnostní opravy." -+ -+#~ msgid "It is recommended that you upgrade to a more recent version." -+#~ msgstr "Doporučuje se povýšit na nejnovější verzi." -+ -+#~ msgid "Application Updates" -+#~ msgstr "Aktualizace aplikací" -+ - #~ msgid "_Continue" - #~ msgstr "_Pokračovat" - diff --git a/gnome-software.spec b/gnome-software.spec index 79fd305..cacfd7e 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -19,8 +19,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 44.0 -Release: 3%{?dist} +Version: 44.1 +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -28,7 +28,6 @@ URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/44/%{name}-%{tarball_version}.tar.xz Patch01: 0001-crash-with-broken-theme.patch -Patch02: 0002-update-czech-translation.patch BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -228,6 +227,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Apr 21 2023 Milan Crha - 44.1-1 +- Update to 44.1 + * Sun Mar 26 2023 Yaakov Selkowitz - 44.0-3 - Fix libsoup runtime dependency diff --git a/sources b/sources index 91637d7..116347a 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-44.0.tar.xz) = 592a88fd3488d7d9cd573eff99e8ec503169b52354d672263d7e514846c666c56f87fcbdb31fb8c497ed048808ec223646c247326af76a7e4a361084fd1b180e +SHA512 (gnome-software-44.1.tar.xz) = 4f6d50d8308b3d2694a67f35db0c716f8631380282c7586243499449dd86d11ebfa08a18ccd083839b93bcf7e1b16075433cb427642c2c7b59033e721bb32c9b From 2ea292e8f33e1169991bb919204a078a771e6785 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 19 May 2023 12:57:20 +0200 Subject: [PATCH 087/163] Rebuild for RPM --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index cacfd7e..16a0b71 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -20,7 +20,7 @@ Name: gnome-software Version: 44.1 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -227,6 +227,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri May 19 2023 Milan Crha - 44.1-2 +- Rebuild for RPM + * Fri Apr 21 2023 Milan Crha - 44.1-1 - Update to 44.1 From d32b18a85c4d999cd1a06b0929a190c6b5410a55 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 26 May 2023 07:55:44 +0200 Subject: [PATCH 088/163] Update to 44.2 --- gnome-software.spec | 7 +++++-- sources | 2 +- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 16a0b71..5d2b837 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -19,8 +19,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 44.1 -Release: 2%{?dist} +Version: 44.2 +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -227,6 +227,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri May 26 2023 Milan Crha - 44.2-1 +- Update to 44.2 + * Fri May 19 2023 Milan Crha - 44.1-2 - Rebuild for RPM diff --git a/sources b/sources index 116347a..d99906e 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-44.1.tar.xz) = 4f6d50d8308b3d2694a67f35db0c716f8631380282c7586243499449dd86d11ebfa08a18ccd083839b93bcf7e1b16075433cb427642c2c7b59033e721bb32c9b +SHA512 (gnome-software-44.2.tar.xz) = 0f053d1d92285239d7edd62a5dcc5c8ce9e991103e3987808ef82406e2dc665a13e0cd14b043d66dfd420459a6aa7c83e7db2fd6a16a8f3b41a6e93498820251 From 6c9157f9066ec9e2c985ff8cfdff9a4297489c00 Mon Sep 17 00:00:00 2001 From: Tomas Popela Date: Thu, 22 Jun 2023 15:39:56 +0200 Subject: [PATCH 089/163] Disable parental control (through malcontent) and rpm-ostree support in RHEL Also move the webapp conditional to a newer syntax to be consistent. --- gnome-software.spec | 39 ++++++++++++++++++++++++++++++++------- 1 file changed, 32 insertions(+), 7 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 5d2b837..63029d7 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -9,7 +9,11 @@ %global packagekit_version 1.1.1 # Disable WebApps for RHEL builds -%{!?with_webapps: %global with_webapps !0%{?rhel}} +%bcond webapps %[!0%{?rhel}] +# Disable parental control for RHEL builds +%bcond malcontent %[!0%{?rhel}] +# Disable rpm-ostree support for RHEL builds +%bcond rpmostree %[!0%{?rhel}] # this is not a library version %define gs_plugin_version 20 @@ -20,7 +24,7 @@ Name: gnome-software Version: 44.2 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -50,18 +54,22 @@ BuildRequires: pkgconfig(json-glib-1.0) >= %{json_glib_version} BuildRequires: pkgconfig(libadwaita-1) >= %{libadwaita_version} BuildRequires: pkgconfig(libdnf) BuildRequires: pkgconfig(libsoup-3.0) +%if %{with malcontent} BuildRequires: pkgconfig(malcontent-0) +%endif BuildRequires: pkgconfig(ostree-1) BuildRequires: pkgconfig(packagekit-glib2) >= %{packagekit_version} BuildRequires: pkgconfig(polkit-gobject-1) BuildRequires: pkgconfig(rpm) +%if %{with rpmostree} BuildRequires: pkgconfig(rpm-ostree-1) +%endif BuildRequires: pkgconfig(sysprof-capture-4) BuildRequires: pkgconfig(xmlb) >= %{libxmlb_version} Requires: appstream-data Requires: appstream%{?_isa} >= %{appstream_version} -%if %{with_webapps} +%if %{with webapps} Requires: epiphany-runtime%{?_isa} %endif Requires: flatpak%{?_isa} >= %{flatpak_version} @@ -94,6 +102,7 @@ Requires: %{name}%{?_isa} = %{version}-%{release} These development files are for building gnome-software plugins outside the source tree. Most users do not need this subpackage installed. +%if %{with rpmostree} %package rpm-ostree Summary: rpm-ostree backend for gnome-software Requires: %{name}%{?_isa} = %{version}-%{release} @@ -105,6 +114,7 @@ gnome-software is an application that makes it easy to add, remove and update software in the GNOME desktop. This package includes the rpm-ostree backend. +%endif %prep %autosetup -p1 -S gendiff -n %{name}-%{tarball_version} @@ -113,13 +123,21 @@ This package includes the rpm-ostree backend. %meson \ -Dsoup2=false \ -Dsnap=false \ +%if %{with malcontent} -Dmalcontent=true \ +%else + -Dmalcontent=false \ +%endif -Dgudev=true \ -Dpackagekit=true \ -Dpackagekit_autoremove=true \ -Dexternal_appstream=false \ +%if %{with rpmostree} -Drpm_ostree=true \ -%if %{with_webapps} +%else + -Drpm_ostree=false \ +%endif +%if %{with webapps} -Dwebapps=true \ -Dhardcoded_foss_webapps=true \ -Dhardcoded_proprietary_webapps=false \ @@ -171,7 +189,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/icons/hicolor/symbolic/apps/org.gnome.Software-symbolic.svg %{_datadir}/icons/hicolor/scalable/actions/app-remove-symbolic.svg %{_datadir}/metainfo/org.gnome.Software.metainfo.xml -%if %{with_webapps} +%if %{with webapps} %{_datadir}/metainfo/org.gnome.Software.Plugin.Epiphany.metainfo.xml %endif %{_datadir}/metainfo/org.gnome.Software.Plugin.Flatpak.metainfo.xml @@ -180,7 +198,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/libgnomesoftware.so.%{gs_plugin_version} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_appstream.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dummy.so -%if %{with_webapps} +%if %{with webapps} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_epiphany.so %endif %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so @@ -190,7 +208,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_generic-updates.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_hardcoded-blocklist.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_icons.so +%if %{with malcontent} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_malcontent.so +%endif %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_modalias.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_os-release.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit.so @@ -201,7 +221,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_sysconfdir}/xdg/autostart/org.gnome.Software.desktop %dir %{_datadir}/swcatalog %dir %{_datadir}/swcatalog/xml -%if %{with_webapps} +%if %{with webapps} %{_datadir}/swcatalog/xml/gnome-pwa-list-foss.xml %endif %{_datadir}/swcatalog/xml/org.gnome.Software.Curated.xml @@ -214,8 +234,10 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libexecdir}/gnome-software-cmd %{_libexecdir}/gnome-software-restarter +%if %{with rpmostree} %files rpm-ostree %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rpm-ostree.so +%endif %files devel %{_libdir}/pkgconfig/gnome-software.pc @@ -227,6 +249,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Jun 22 2023 Tomas Popela - 44.2-2 +- Disable parental control (though malcontent) and rpm-ostree support in RHEL + * Fri May 26 2023 Milan Crha - 44.2-1 - Update to 44.2 From 91d71073bb7e8304db78a891eb9656be17d46c1e Mon Sep 17 00:00:00 2001 From: Tomas Popela Date: Thu, 22 Jun 2023 19:13:10 +0200 Subject: [PATCH 090/163] Fix a changelog typo Spotten by mcrha. --- gnome-software.spec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 63029d7..ffc39b7 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -250,7 +250,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %changelog * Thu Jun 22 2023 Tomas Popela - 44.2-2 -- Disable parental control (though malcontent) and rpm-ostree support in RHEL +- Disable parental control (through malcontent) and rpm-ostree support in RHEL * Fri May 26 2023 Milan Crha - 44.2-1 - Update to 44.2 From 5e095d670f3401790923845e3491083c2e185c3c Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 30 Jun 2023 11:35:00 +0200 Subject: [PATCH 091/163] Update to 45.alpha --- 0001-crash-with-broken-theme.patch | 33 ------------------------------ gnome-software.spec | 11 +++++----- sources | 2 +- 3 files changed, 7 insertions(+), 39 deletions(-) delete mode 100644 0001-crash-with-broken-theme.patch diff --git a/0001-crash-with-broken-theme.patch b/0001-crash-with-broken-theme.patch deleted file mode 100644 index d41a916..0000000 --- a/0001-crash-with-broken-theme.patch +++ /dev/null @@ -1,33 +0,0 @@ -diff -up gnome-software-devel/src/gs-feature-tile.c.1 gnome-software-devel/src/gs-feature-tile.c ---- gnome-software-devel/src/gs-feature-tile.c.1 2023-01-02 17:08:54.157641969 +0100 -+++ gnome-software-devel/src/gs-feature-tile.c 2023-01-02 17:09:36.881632780 +0100 -@@ -397,9 +397,6 @@ gs_feature_tile_refresh (GsAppTile *self - if (key_colors != tile->key_colors_cache) { - g_autoptr(GArray) colors = NULL; - GdkRGBA fg_rgba; --#if !GTK_CHECK_VERSION(4, 9, 2) -- gboolean fg_rgba_valid; --#endif - GsHSBC fg_hsbc; - const GsHSBC *chosen_hsbc; - GsHSBC chosen_hsbc_modified; -@@ -424,8 +421,17 @@ gs_feature_tile_refresh (GsAppTile *self - gtk_widget_get_color (GTK_WIDGET (self), &fg_rgba); - #else - context = gtk_widget_get_style_context (GTK_WIDGET (self)); -- fg_rgba_valid = gtk_style_context_lookup_color (context, "theme_fg_color", &fg_rgba); -- g_assert (fg_rgba_valid); -+ if (!gtk_style_context_lookup_color (context, "theme_fg_color", &fg_rgba)) { -+ static gboolean i_know = FALSE; -+ if (!i_know) { -+ i_know = TRUE; -+ g_warning ("The theme doesn't provide 'theme_fg_color', fallbacking to black"); -+ } -+ fg_rgba.red = 0.0; -+ fg_rgba.green = 0.0; -+ fg_rgba.blue = 0.0; -+ fg_rgba.alpha = 1.0; -+ } - #endif - - gtk_rgb_to_hsv (fg_rgba.red, fg_rgba.green, fg_rgba.blue, diff --git a/gnome-software.spec b/gnome-software.spec index ffc39b7..9c5b953 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -23,15 +23,13 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 44.2 -Release: 2%{?dist} +Version: 45~alpha +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://wiki.gnome.org/Apps/Software -Source0: https://download.gnome.org/sources/gnome-software/44/%{name}-%{tarball_version}.tar.xz - -Patch01: 0001-crash-with-broken-theme.patch +Source0: https://download.gnome.org/sources/gnome-software/45/%{name}-%{tarball_version}.tar.xz BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils @@ -249,6 +247,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Jun 30 2023 Milan Crha - 45~alpha-1 +- Update to 45.alpha + * Thu Jun 22 2023 Tomas Popela - 44.2-2 - Disable parental control (through malcontent) and rpm-ostree support in RHEL diff --git a/sources b/sources index d99906e..1c19108 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-44.2.tar.xz) = 0f053d1d92285239d7edd62a5dcc5c8ce9e991103e3987808ef82406e2dc665a13e0cd14b043d66dfd420459a6aa7c83e7db2fd6a16a8f3b41a6e93498820251 +SHA512 (gnome-software-45.alpha.tar.xz) = 1a2c5e6eec249fdeb726b6cdd58c47ccbdefd6c9bc7278c6d30f1350cc62d3e1231e12b5b2cd9acee8deff269346171d427fd389194f04ca641825bd32ddaa2a From ee6f7c739f170417e24e4b5061d2d5046e35318a Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Wed, 19 Jul 2023 23:48:37 +0000 Subject: [PATCH 092/163] Rebuilt for https://fedoraproject.org/wiki/Fedora_39_Mass_Rebuild Signed-off-by: Fedora Release Engineering --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 9c5b953..32a220f 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -24,7 +24,7 @@ Name: gnome-software Version: 45~alpha -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -247,6 +247,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Wed Jul 19 2023 Fedora Release Engineering - 45~alpha-2 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_39_Mass_Rebuild + * Fri Jun 30 2023 Milan Crha - 45~alpha-1 - Update to 45.alpha From cc29af56c44eb46f76ac4cc84a414f5f836679a8 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 31 Jul 2023 07:21:50 +0200 Subject: [PATCH 093/163] Update to 45.beta --- gnome-software.spec | 19 +++++++++++-------- sources | 2 +- 2 files changed, 12 insertions(+), 9 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 32a220f..125988a 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -1,12 +1,12 @@ %global appstream_version 0.14.0 -%global flatpak_version 1.5.1 -%global fwupd_version 1.3.3 -%global glib2_version 2.61.1 -%global gtk4_version 4.9.2 -%global json_glib_version 1.2.0 +%global flatpak_version 1.9.1 +%global fwupd_version 1.5.6 +%global glib2_version 2.70.0 +%global gtk4_version 4.10.0 +%global json_glib_version 1.6.0 %global libadwaita_version 1.3.alpha %global libxmlb_version 0.1.7 -%global packagekit_version 1.1.1 +%global packagekit_version 1.2.5 # Disable WebApps for RHEL builds %bcond webapps %[!0%{?rhel}] @@ -23,8 +23,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 45~alpha -Release: 2%{?dist} +Version: 45~beta +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -247,6 +247,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Mon Jul 31 2023 Milan Crha - 45~beta-1 +- Update to 45.beta + * Wed Jul 19 2023 Fedora Release Engineering - 45~alpha-2 - Rebuilt for https://fedoraproject.org/wiki/Fedora_39_Mass_Rebuild diff --git a/sources b/sources index 1c19108..68087d0 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-45.alpha.tar.xz) = 1a2c5e6eec249fdeb726b6cdd58c47ccbdefd6c9bc7278c6d30f1350cc62d3e1231e12b5b2cd9acee8deff269346171d427fd389194f04ca641825bd32ddaa2a +SHA512 (gnome-software-45.beta.tar.xz) = d4218b56478c9e7e83adf4fb8daec8d0730f5ce16cca0a0c59962894a0abb2d21c356a55f232d266aaaa4f15b21c21bc5904cc1f7b6db4d94db8889019fea092 From b660d8025771ee3cf51b9c5bd3c36821733361d1 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 31 Jul 2023 09:44:56 +0200 Subject: [PATCH 094/163] Remove reference to a dropped plugin (it's builtin now) --- gnome-software.spec | 1 - 1 file changed, 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 125988a..02e4cd3 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -215,7 +215,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance-license.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_repos.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rewrite-resource.so %{_sysconfdir}/xdg/autostart/org.gnome.Software.desktop %dir %{_datadir}/swcatalog %dir %{_datadir}/swcatalog/xml From 10938fed7958653661cb060ff2305ee0b20f0e0d Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 1 Sep 2023 09:40:08 +0200 Subject: [PATCH 095/163] Update to 45.rc --- gnome-software.spec | 5 ++++- sources | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 02e4cd3..b0df077 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -23,7 +23,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 45~beta +Version: 45~rc Release: 1%{?dist} Summary: A software center for GNOME @@ -246,6 +246,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Sep 01 2023 Milan Crha - 45~rc-1 +- Update to 45.rc + * Mon Jul 31 2023 Milan Crha - 45~beta-1 - Update to 45.beta diff --git a/sources b/sources index 68087d0..b167261 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-45.beta.tar.xz) = d4218b56478c9e7e83adf4fb8daec8d0730f5ce16cca0a0c59962894a0abb2d21c356a55f232d266aaaa4f15b21c21bc5904cc1f7b6db4d94db8889019fea092 +SHA512 (gnome-software-45.rc.tar.xz) = 674c89619419cb7622bed3ce1453c31460d51ba6716db3d8bfc79829ca619e24d1f9c954f2fe72d96156e2e6dbaaf151faa29c97425b0cac132ec3e49871fb79 From aa509767b4eb49df0a86e39f81a3b1434c552a9a Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 15 Sep 2023 09:41:21 +0200 Subject: [PATCH 096/163] Update to 45.0 --- gnome-software.spec | 5 ++++- sources | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index b0df077..4da8d43 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -23,7 +23,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 45~rc +Version: 45.0 Release: 1%{?dist} Summary: A software center for GNOME @@ -246,6 +246,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Sep 15 2023 Milan Crha - 45.0-1 +- Update to 45.0 + * Fri Sep 01 2023 Milan Crha - 45~rc-1 - Update to 45.rc diff --git a/sources b/sources index b167261..acbec40 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-45.rc.tar.xz) = 674c89619419cb7622bed3ce1453c31460d51ba6716db3d8bfc79829ca619e24d1f9c954f2fe72d96156e2e6dbaaf151faa29c97425b0cac132ec3e49871fb79 +SHA512 (gnome-software-45.0.tar.xz) = 3a7fab748c6d826e07e4bf86462cfecd9494bfaca2383222f7053be97830ab603cb0dc83d4d5693c2ddac1cc72897783922a05f5aae2ad07d6b7f5ccd5a4eefb From 1b93572ab692ac08e2f09af7d3aa42f6f6fbb3bf Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 20 Oct 2023 08:48:21 +0200 Subject: [PATCH 097/163] Update to 45.1 --- gnome-software.spec | 5 ++++- sources | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 4da8d43..21730b3 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -23,7 +23,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 45.0 +Version: 45.1 Release: 1%{?dist} Summary: A software center for GNOME @@ -246,6 +246,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Oct 20 2023 Milan Crha - 45.1-1 +- Update to 45.1 + * Fri Sep 15 2023 Milan Crha - 45.0-1 - Update to 45.0 diff --git a/sources b/sources index acbec40..c15ccca 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-45.0.tar.xz) = 3a7fab748c6d826e07e4bf86462cfecd9494bfaca2383222f7053be97830ab603cb0dc83d4d5693c2ddac1cc72897783922a05f5aae2ad07d6b7f5ccd5a4eefb +SHA512 (gnome-software-45.1.tar.xz) = 5fdf5e6a34ab9acf938bc4ade41b916ad38ad3b4a7f604b2cba9dfaa38f17299001bef8fde9165f6a035fcc7fef3ebd451bd29ff126c0b9d5a7104e448729434 From 5ed67eade63e02401506d540c6063c8fc668ee9b Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Tue, 7 Nov 2023 08:25:58 +0100 Subject: [PATCH 098/163] Add patch to build with appstream 1.0 --- 0001-port-to-appstream1.patch | 494 ++++++++++++++++++++++++++++++++++ gnome-software.spec | 8 +- 2 files changed, 501 insertions(+), 1 deletion(-) create mode 100644 0001-port-to-appstream1.patch diff --git a/0001-port-to-appstream1.patch b/0001-port-to-appstream1.patch new file mode 100644 index 0000000..c166088 --- /dev/null +++ b/0001-port-to-appstream1.patch @@ -0,0 +1,494 @@ +From e6f7e28bdd50a63586ba6a82b936d54db19a311b Mon Sep 17 00:00:00 2001 +From: Matthias Klumpp +Date: Sun, 8 Oct 2023 20:22:44 +0200 +Subject: [PATCH] Adjust to build with AppStream 1.0 as well as 0.16.x + +--- + lib/gs-app.c | 4 ++ + lib/gs-appstream.c | 58 ++++++++++++++++++++---- + lib/gs-utils.c | 8 ++-- + meson.build | 22 +-------- + plugins/core/gs-plugin-appstream.c | 8 ---- + plugins/fwupd/gs-fwupd-app.c | 8 ++++ + plugins/fwupd/gs-plugin-fwupd.c | 4 ++ + src/gs-hardware-support-context-dialog.c | 6 +++ + src/gs-repos-dialog.c | 4 ++ + src/gs-screenshot-carousel.c | 4 +- + src/gs-screenshot-image.c | 41 +++++++++++++---- + src/gs-screenshot-image.h | 7 +++ + subprojects/appstream.wrap | 2 +- + 13 files changed, 120 insertions(+), 56 deletions(-) + +diff --git a/lib/gs-app.c b/lib/gs-app.c +index 048a061225..e2694057cd 100644 +--- a/lib/gs-app.c ++++ b/lib/gs-app.c +@@ -609,7 +609,11 @@ gs_app_to_string_append (GsApp *app, GString *str) + AsScreenshot *ss = g_ptr_array_index (priv->screenshots, i); + g_autofree gchar *key = NULL; + tmp = as_screenshot_get_caption (ss); ++#if AS_CHECK_VERSION(1, 0, 0) ++ im = as_screenshot_get_image (ss, 0, 0, 1); ++#else + im = as_screenshot_get_image (ss, 0, 0); ++#endif + if (im == NULL) + continue; + key = g_strdup_printf ("screenshot-%02u", i); +diff --git a/lib/gs-appstream.c b/lib/gs-appstream.c +index deca176dcf..2cc2427a19 100644 +--- a/lib/gs-appstream.c ++++ b/lib/gs-appstream.c +@@ -1011,8 +1011,11 @@ gs_appstream_refine_app_relation (GsApp *app, + as_relation_set_item_kind (relation, AS_RELATION_ITEM_KIND_CONTROL); + as_relation_set_value_control_kind (relation, as_control_kind_from_string (xb_node_get_text (child))); + } else if (g_str_equal (item_kind, "display_length")) { +- AsDisplayLengthKind display_length_kind; + const gchar *compare; ++ const gchar *side; ++#if !AS_CHECK_VERSION(1, 0, 0) ++ AsDisplayLengthKind display_length_kind; ++#endif + + /* https://www.freedesktop.org/software/appstream/docs/chap-Metadata.html#tag-relations-display_length */ + as_relation_set_item_kind (relation, AS_RELATION_ITEM_KIND_DISPLAY_LENGTH); +@@ -1020,15 +1023,21 @@ gs_appstream_refine_app_relation (GsApp *app, + compare = xb_node_get_attr (child, "compare"); + as_relation_set_compare (relation, (compare != NULL) ? as_relation_compare_from_string (compare) : AS_RELATION_COMPARE_GE); + ++#if AS_CHECK_VERSION(1, 0, 0) ++ side = xb_node_get_attr (child, "side"); ++ as_relation_set_display_side_kind (relation, (side != NULL) ? as_display_side_kind_from_string (side) : AS_DISPLAY_SIDE_KIND_SHORTEST); ++ as_relation_set_value_px (relation, xb_node_get_text_as_uint (child)); ++#else + display_length_kind = as_display_length_kind_from_string (xb_node_get_text (child)); + if (display_length_kind != AS_DISPLAY_LENGTH_KIND_UNKNOWN) { + /* Ignore the `side` attribute */ + as_relation_set_value_display_length_kind (relation, display_length_kind); + } else { +- const gchar *side = xb_node_get_attr (child, "side"); ++ side = xb_node_get_attr (child, "side"); + as_relation_set_display_side_kind (relation, (side != NULL) ? as_display_side_kind_from_string (side) : AS_DISPLAY_SIDE_KIND_SHORTEST); + as_relation_set_value_px (relation, xb_node_get_text_as_uint (child)); + } ++#endif + } else { + g_debug ("Relation type ‘%s’ not currently supported for %s; ignoring", + item_kind, gs_app_get_id (app)); +@@ -1472,7 +1481,7 @@ gs_appstream_refine_app (GsPlugin *plugin, + } + + typedef struct { +- AsSearchTokenMatch match_value; ++ guint16 match_value; + XbQuery *query; + } GsAppstreamSearchHelper; + +@@ -1522,7 +1531,7 @@ gs_appstream_silo_search_component (GPtrArray *array, XbNode *component, const g + } + + typedef struct { +- AsSearchTokenMatch match_value; ++ guint16 match_value; + const gchar *xpath; + } Query; + +@@ -1585,7 +1594,11 @@ gs_appstream_do_search (GsPlugin *plugin, + * Drop the ID token from it as it’s the highest + * numeric value but isn’t visible to the user in the + * UI, which leads to confusing results ordering. */ ++#if AS_CHECK_VERSION(1, 0, 0) ++ gs_app_set_match_value (app, match_value & (~as_utils_get_tag_search_weight ("id"))); ++#else + gs_app_set_match_value (app, match_value & (~AS_SEARCH_TOKEN_MATCH_ID)); ++#endif + gs_app_list_add (list, app); + + if (gs_app_get_kind (app) == AS_COMPONENT_KIND_ADDON) { +@@ -1624,18 +1637,32 @@ gs_appstream_search (GsPlugin *plugin, + GCancellable *cancellable, + GError **error) + { ++#if AS_CHECK_VERSION(1, 0, 0) ++ guint16 pkgname_weight = as_utils_get_tag_search_weight ("pkgname"); ++ guint16 name_weight = as_utils_get_tag_search_weight ("name"); ++ guint16 id_weight = as_utils_get_tag_search_weight ("id"); + const Query queries[] = { +- #ifdef HAVE_AS_SEARCH_TOKEN_MATCH_MEDIATYPE +- { AS_SEARCH_TOKEN_MATCH_MEDIATYPE, "mimetypes/mimetype[text()~=stem(?)]" }, +- #else +- { AS_SEARCH_TOKEN_MATCH_MIMETYPE, "mimetypes/mimetype[text()~=stem(?)]" }, +- #endif ++ { as_utils_get_tag_search_weight ("mediatype"), "provides/mediatype[text()~=stem(?)]" }, + /* Search once with a tokenize-and-casefold operator (`~=`) to support casefolded + * full-text search, then again using substring matching (`contains()`), to + * support prefix matching. Only do the prefix matches on a few fields, and at a + * lower priority, otherwise things will get confusing. +- * ++ * + * See https://gitlab.gnome.org/GNOME/gnome-software/-/issues/2277 */ ++ { pkgname_weight, "pkgname[text()~=stem(?)]" }, ++ { pkgname_weight / 2, "pkgname[contains(text(),stem(?))]" }, ++ { as_utils_get_tag_search_weight ("summary"), "summary[text()~=stem(?)]" }, ++ { name_weight, "name[text()~=stem(?)]" }, ++ { name_weight / 2, "name[contains(text(),stem(?))]" }, ++ { as_utils_get_tag_search_weight ("keyword"), "keywords/keyword[text()~=stem(?)]" }, ++ { id_weight, "id[text()~=stem(?)]" }, ++ { id_weight, "launchable[text()~=stem(?)]" }, ++ { as_utils_get_tag_search_weight ("origin"), "../components[@origin~=stem(?)]" }, ++ { 0, NULL } ++ }; ++#else ++ const Query queries[] = { ++ { AS_SEARCH_TOKEN_MATCH_MEDIATYPE, "mimetypes/mimetype[text()~=stem(?)]" }, + { AS_SEARCH_TOKEN_MATCH_PKGNAME, "pkgname[text()~=stem(?)]" }, + { AS_SEARCH_TOKEN_MATCH_PKGNAME / 2, "pkgname[contains(text(),stem(?))]" }, + { AS_SEARCH_TOKEN_MATCH_SUMMARY, "summary[text()~=stem(?)]" }, +@@ -1647,6 +1674,7 @@ gs_appstream_search (GsPlugin *plugin, + { AS_SEARCH_TOKEN_MATCH_ORIGIN, "../components[@origin~=stem(?)]" }, + { AS_SEARCH_TOKEN_MATCH_NONE, NULL } + }; ++#endif + + return gs_appstream_do_search (plugin, silo, values, queries, list, cancellable, error); + } +@@ -1659,11 +1687,21 @@ gs_appstream_search_developer_apps (GsPlugin *plugin, + GCancellable *cancellable, + GError **error) + { ++#if AS_CHECK_VERSION(1, 0, 0) ++ const Query queries[] = { ++ { as_utils_get_tag_search_weight ("pkgname"), "developer/name[text()~=stem(?)]" }, ++ { as_utils_get_tag_search_weight ("summary"), "project_group[text()~=stem(?)]" }, ++ /* for legacy support */ ++ { as_utils_get_tag_search_weight ("pkgname"), "developer_name[text()~=stem(?)]" }, ++ { 0, NULL } ++ }; ++#else + const Query queries[] = { + { AS_SEARCH_TOKEN_MATCH_PKGNAME, "developer_name[text()~=stem(?)]" }, + { AS_SEARCH_TOKEN_MATCH_SUMMARY, "project_group[text()~=stem(?)]" }, + { AS_SEARCH_TOKEN_MATCH_NONE, NULL } + }; ++#endif + + return gs_appstream_do_search (plugin, silo, values, queries, list, cancellable, error); + } +diff --git a/lib/gs-utils.c b/lib/gs-utils.c +index cf9073025f..19e6ebd046 100644 +--- a/lib/gs-utils.c ++++ b/lib/gs-utils.c +@@ -1694,9 +1694,9 @@ gs_utils_gstring_replace (GString *str, + const gchar *find, + const gchar *replace) + { +- #ifdef HAVE_AS_GSTRING_REPLACE_WITH_FOUR_ARGS ++#if AS_CHECK_VERSION(1, 0, 0) + as_gstring_replace (str, find, replace, 0); +- #else +- as_gstring_replace (str, find, replace); +- #endif ++#else ++ as_gstring_replace2 (str, find, replace, 0); ++#endif + } +diff --git a/meson.build b/meson.build +index 09c39df180..ad105869e5 100644 +--- a/meson.build ++++ b/meson.build +@@ -113,7 +113,7 @@ add_project_arguments('-D_GNU_SOURCE', language : 'c') + conf.set('HAVE_LINUX_UNISTD_H', cc.has_header('linux/unistd.h')) + + appstream = dependency('appstream', +- version : '>= 0.14.0', ++ version : '>= 0.16.2', + fallback : ['appstream', 'appstream_dep'], + default_options : [ + 'docs=false', +@@ -121,26 +121,6 @@ appstream = dependency('appstream', + 'install-docs=false' + ] + ) +-if appstream.type_name() == 'internal' +-else +- if meson.get_compiler('c').has_header_symbol('appstream.h', 'AS_SEARCH_TOKEN_MATCH_MEDIATYPE', dependencies: appstream) +- conf.set('HAVE_AS_SEARCH_TOKEN_MATCH_MEDIATYPE', '1') +- endif +- if meson.get_compiler('c').has_header_symbol('appstream.h', 'AS_FORMAT_STYLE_CATALOG', dependencies: appstream) +- conf.set('HAVE_AS_FORMAT_STYLE_CATALOG', '1') +- endif +- if meson.get_compiler('c').has_function('as_metadata_components_to_catalog', prefix: '#include ', dependencies: appstream) +- conf.set('HAVE_AS_METADATA_COMPONENTS_TO_CATALOG', '1') +- endif +- if meson.get_compiler('c').links('''#include +- int main (void) +- { +- as_gstring_replace (NULL, "a", "b", 0); +- return 0; +- }''', name: 'as_gstring_replace() has four arguments', dependencies: appstream) +- conf.set('HAVE_AS_GSTRING_REPLACE_WITH_FOUR_ARGS', '1') +- endif +-endif + + gdk_pixbuf = dependency('gdk-pixbuf-2.0', version : '>= 2.32.0') + libxmlb = dependency('xmlb', version : '>= 0.1.7', fallback : ['libxmlb', 'libxmlb_dep']) +diff --git a/plugins/core/gs-plugin-appstream.c b/plugins/core/gs-plugin-appstream.c +index cf9f3022b1..ef3226a591 100644 +--- a/plugins/core/gs-plugin-appstream.c ++++ b/plugins/core/gs-plugin-appstream.c +@@ -414,11 +414,7 @@ gs_plugin_appstream_load_dep11_cb (XbBuilderSource *self, + if (bytes == NULL) + return NULL; + +- #ifdef HAVE_AS_FORMAT_STYLE_CATALOG + as_metadata_set_format_style (mdata, AS_FORMAT_STYLE_CATALOG); +- #else +- as_metadata_set_format_style (mdata, AS_FORMAT_STYLE_COLLECTION); +- #endif + as_metadata_parse_bytes (mdata, + bytes, + AS_FORMAT_KIND_YAML, +@@ -428,11 +424,7 @@ gs_plugin_appstream_load_dep11_cb (XbBuilderSource *self, + return NULL; + } + +- #ifdef HAVE_AS_METADATA_COMPONENTS_TO_CATALOG + xml = as_metadata_components_to_catalog (mdata, AS_FORMAT_KIND_XML, &tmp_error); +- #else +- xml = as_metadata_components_to_collection (mdata, AS_FORMAT_KIND_XML, &tmp_error); +- #endif + if (xml == NULL) { + // This API currently returns NULL if there is nothing to serialize, so we + // have to test if this is an error or not. +diff --git a/plugins/fwupd/gs-fwupd-app.c b/plugins/fwupd/gs-fwupd-app.c +index 6dcda6ee92..5d3254da59 100644 +--- a/plugins/fwupd/gs-fwupd-app.c ++++ b/plugins/fwupd/gs-fwupd-app.c +@@ -164,7 +164,11 @@ gs_fwupd_app_set_from_device (GsApp *app, + gs_app_set_install_date (app, fwupd_device_get_created (dev)); + if (fwupd_device_get_description (dev) != NULL) { + g_autofree gchar *tmp = NULL; ++#if AS_CHECK_VERSION(1, 0, 0) ++ tmp = as_markup_convert (fwupd_device_get_description (dev), AS_MARKUP_KIND_TEXT, NULL); ++#else + tmp = as_markup_convert_simple (fwupd_device_get_description (dev), NULL); ++#endif + if (tmp != NULL) + gs_app_set_description (app, GS_APP_QUALITY_NORMAL, tmp); + } +@@ -402,7 +406,11 @@ gs_fwupd_app_set_from_release (GsApp *app, FwupdRelease *rel) + } + if (fwupd_release_get_description (rel) != NULL) { + g_autofree gchar *tmp = NULL; ++#if AS_CHECK_VERSION(1, 0, 0) ++ tmp = as_markup_convert (fwupd_release_get_description (rel), AS_MARKUP_KIND_TEXT, NULL); ++#else + tmp = as_markup_convert_simple (fwupd_release_get_description (rel), NULL); ++#endif + if (tmp != NULL) + gs_app_set_update_details_text (app, tmp); + } +diff --git a/plugins/fwupd/gs-plugin-fwupd.c b/plugins/fwupd/gs-plugin-fwupd.c +index e931b2b6db..0747d6e250 100644 +--- a/plugins/fwupd/gs-plugin-fwupd.c ++++ b/plugins/fwupd/gs-plugin-fwupd.c +@@ -726,7 +726,11 @@ gs_plugin_add_updates (GsPlugin *plugin, + g_autofree gchar *desc = NULL; + if (fwupd_release_get_description (rel) == NULL) + continue; ++#if AS_CHECK_VERSION(1, 0, 0) ++ desc = as_markup_convert (fwupd_release_get_description (rel), AS_MARKUP_KIND_TEXT, NULL); ++#else + desc = as_markup_convert_simple (fwupd_release_get_description (rel), NULL); ++#endif + if (desc == NULL) + continue; + g_string_append_printf (update_desc, +diff --git a/src/gs-hardware-support-context-dialog.c b/src/gs-hardware-support-context-dialog.c +index 0e48c8c266..14653401de 100644 +--- a/src/gs-hardware-support-context-dialog.c ++++ b/src/gs-hardware-support-context-dialog.c +@@ -461,6 +461,7 @@ gs_hardware_support_context_dialog_get_display_support (GdkMonitor *monitor, + AsRelationCompare comparator = as_relation_get_compare (relation); + Range current_display_comparand, relation_comparand; + ++#if !AS_CHECK_VERSION(1, 0, 0) + /* From https://www.freedesktop.org/software/appstream/docs/chap-Metadata.html#tag-requires-recommends-display_length */ + Range display_lengths[] = { + [AS_DISPLAY_LENGTH_KIND_XSMALL] = { 0, 360 }, +@@ -469,6 +470,7 @@ gs_hardware_support_context_dialog_get_display_support (GdkMonitor *monitor, + [AS_DISPLAY_LENGTH_KIND_LARGE] = { 1024, 3840 }, + [AS_DISPLAY_LENGTH_KIND_XLARGE] = { 3840, G_MAXUINT }, + }; ++#endif + + any_display_relations_set = TRUE; + +@@ -485,11 +487,14 @@ gs_hardware_support_context_dialog_get_display_support (GdkMonitor *monitor, + case AS_DISPLAY_SIDE_KIND_LAST: + default: + current_display_comparand.min = current_display_comparand.max = MAX (current_screen_size.width, current_screen_size.height); ++#if !AS_CHECK_VERSION(1, 0, 0) + relation_comparand.min = display_lengths[as_relation_get_value_display_length_kind (relation)].min; + relation_comparand.max = display_lengths[as_relation_get_value_display_length_kind (relation)].max; ++#endif + break; + } + ++#if !AS_CHECK_VERSION(1, 0, 0) + if (evaluate_display_comparison (display_lengths[AS_DISPLAY_LENGTH_KIND_SMALL], comparator, relation_comparand)) { + *mobile_relation_kind_out = max_relation_kind (*mobile_relation_kind_out, as_relation_get_kind (relation)); + *mobile_match_out = TRUE; +@@ -499,6 +504,7 @@ gs_hardware_support_context_dialog_get_display_support (GdkMonitor *monitor, + *desktop_relation_kind_out = max_relation_kind (*desktop_relation_kind_out, as_relation_get_kind (relation)); + *desktop_match_out = TRUE; + } ++#endif + + if (evaluate_display_comparison (current_display_comparand, comparator, relation_comparand)) { + *current_relation_kind_out = max_relation_kind (*current_relation_kind_out, as_relation_get_kind (relation)); +diff --git a/src/gs-repos-dialog.c b/src/gs-repos-dialog.c +index c41c4944a1..7dac0416d9 100644 +--- a/src/gs-repos-dialog.c ++++ b/src/gs-repos-dialog.c +@@ -154,7 +154,11 @@ enable_repo (GsReposDialog *dialog, + g_autoptr(GError) error = NULL; + + /* convert from AppStream markup */ ++#if AS_CHECK_VERSION(1, 0, 0) ++ message = as_markup_convert (gs_app_get_agreement (repo), AS_MARKUP_KIND_TEXT, &error); ++#else + message = as_markup_convert_simple (gs_app_get_agreement (repo), &error); ++#endif + if (message == NULL) { + /* failed, so just try and show the original markup */ + message = g_strdup (gs_app_get_agreement (repo)); +diff --git a/src/gs-screenshot-carousel.c b/src/gs-screenshot-carousel.c +index 04bbf86a1e..d269af6605 100644 +--- a/src/gs-screenshot-carousel.c ++++ b/src/gs-screenshot-carousel.c +@@ -141,8 +141,8 @@ gs_screenshot_carousel_load_screenshots (GsScreenshotCarousel *self, GsApp *app, + gtk_widget_set_can_focus (gtk_widget_get_first_child (ssimg), FALSE); + gs_screenshot_image_set_screenshot (GS_SCREENSHOT_IMAGE (ssimg), ss); + gs_screenshot_image_set_size (GS_SCREENSHOT_IMAGE (ssimg), +- AS_IMAGE_NORMAL_WIDTH, +- AS_IMAGE_NORMAL_HEIGHT); ++ GS_IMAGE_NORMAL_WIDTH, ++ GS_IMAGE_NORMAL_HEIGHT); + gtk_widget_add_css_class (ssimg, "screenshot-image-main"); + gs_screenshot_image_load_async (GS_SCREENSHOT_IMAGE (ssimg), cancellable); + +diff --git a/src/gs-screenshot-image.c b/src/gs-screenshot-image.c +index c313a2589f..b24083b387 100644 +--- a/src/gs-screenshot-image.c ++++ b/src/gs-screenshot-image.c +@@ -284,13 +284,13 @@ gs_screenshot_image_save_downloaded_img (GsScreenshotImage *ssimg, + if (images->len > 1) + return TRUE; + +- if (width == AS_IMAGE_THUMBNAIL_WIDTH && +- height == AS_IMAGE_THUMBNAIL_HEIGHT) { +- width = AS_IMAGE_NORMAL_WIDTH; +- height = AS_IMAGE_NORMAL_HEIGHT; ++ if (width == GS_IMAGE_THUMBNAIL_WIDTH && ++ height == GS_IMAGE_THUMBNAIL_HEIGHT) { ++ width = GS_IMAGE_NORMAL_WIDTH; ++ height = GS_IMAGE_NORMAL_HEIGHT; + } else { +- width = AS_IMAGE_THUMBNAIL_WIDTH; +- height = AS_IMAGE_THUMBNAIL_HEIGHT; ++ width = GS_IMAGE_THUMBNAIL_WIDTH; ++ height = GS_IMAGE_THUMBNAIL_HEIGHT; + } + + width *= ssimg->scale; +@@ -582,16 +582,30 @@ gs_screenshot_image_get_url (GsScreenshotImage *ssimg) + } else if (as_screenshot_get_media_kind (ssimg->screenshot) == AS_SCREENSHOT_MEDIA_KIND_IMAGE) { + AsImage *im; + ++#if AS_CHECK_VERSION(1, 0, 0) ++ im = as_screenshot_get_image (ssimg->screenshot, ++ ssimg->width, ++ ssimg->height, ++ ssimg->scale); ++#else + im = as_screenshot_get_image (ssimg->screenshot, + ssimg->width * ssimg->scale, + ssimg->height * ssimg->scale); ++#endif + + /* if we've failed to load a HiDPI image, fallback to LoDPI */ + if (im == NULL && ssimg->scale > 1) { + ssimg->scale = 1; ++#if AS_CHECK_VERSION(1, 0, 0) ++ im = as_screenshot_get_image (ssimg->screenshot, ++ ssimg->width, ++ ssimg->height, ++ 1); ++#else + im = as_screenshot_get_image (ssimg->screenshot, + ssimg->width, + ssimg->height); ++#endif + } + + if (im) +@@ -698,15 +712,22 @@ gs_screenshot_image_load_async (GsScreenshotImage *ssimg, + * smaller version of it straight away */ + if (!ssimg->showing_image && + as_screenshot_get_media_kind (ssimg->screenshot) == AS_SCREENSHOT_MEDIA_KIND_IMAGE && +- ssimg->width > AS_IMAGE_THUMBNAIL_WIDTH && +- ssimg->height > AS_IMAGE_THUMBNAIL_HEIGHT) { ++ ssimg->width > GS_IMAGE_THUMBNAIL_WIDTH && ++ ssimg->height > GS_IMAGE_THUMBNAIL_HEIGHT) { + const gchar *url_thumb; + g_autofree gchar *basename_thumb = NULL; + g_autofree gchar *cache_kind_thumb = NULL; + AsImage *im; ++#if AS_CHECK_VERSION(1, 0, 0) + im = as_screenshot_get_image (ssimg->screenshot, +- AS_IMAGE_THUMBNAIL_WIDTH * ssimg->scale, +- AS_IMAGE_THUMBNAIL_HEIGHT * ssimg->scale); ++ GS_IMAGE_THUMBNAIL_WIDTH, ++ GS_IMAGE_THUMBNAIL_HEIGHT, ++ ssimg->scale); ++#else ++ im = as_screenshot_get_image (ssimg->screenshot, ++ GS_IMAGE_THUMBNAIL_WIDTH * ssimg->scale, ++ GS_IMAGE_THUMBNAIL_HEIGHT * ssimg->scale); ++#endif + url_thumb = as_image_get_url (im); + basename_thumb = gs_screenshot_get_cachefn_for_url (url_thumb); + cache_kind_thumb = g_build_filename ("screenshots", "112x63", NULL); +diff --git a/src/gs-screenshot-image.h b/src/gs-screenshot-image.h +index 1f6cf81ce6..6e45f5d20a 100644 +--- a/src/gs-screenshot-image.h ++++ b/src/gs-screenshot-image.h +@@ -21,6 +21,13 @@ G_BEGIN_DECLS + + G_DECLARE_FINAL_TYPE (GsScreenshotImage, gs_screenshot_image, GS, SCREENSHOT_IMAGE, GtkWidget) + ++#define GS_IMAGE_LARGE_HEIGHT 423 ++#define GS_IMAGE_LARGE_WIDTH 752 ++#define GS_IMAGE_NORMAL_HEIGHT 351 ++#define GS_IMAGE_NORMAL_WIDTH 624 ++#define GS_IMAGE_THUMBNAIL_HEIGHT 63 ++#define GS_IMAGE_THUMBNAIL_WIDTH 112 ++ + GtkWidget *gs_screenshot_image_new (SoupSession *session); + + AsScreenshot *gs_screenshot_image_get_screenshot (GsScreenshotImage *ssimg); +diff --git a/subprojects/appstream.wrap b/subprojects/appstream.wrap +index 6f0beb0cbc..5763a32c64 100644 +--- a/subprojects/appstream.wrap ++++ b/subprojects/appstream.wrap +@@ -1,5 +1,5 @@ + [wrap-git] + directory = appstream + url = https://github.com/ximion/appstream.git +-revision = v0.14.1 ++revision = v0.16.3 + depth = 1 +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index 21730b3..af54a93 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -24,13 +24,16 @@ Name: gnome-software Version: 45.1 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://wiki.gnome.org/Apps/Software Source0: https://download.gnome.org/sources/gnome-software/45/%{name}-%{tarball_version}.tar.xz +# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/1810 +Patch: 0001-port-to-appstream1.patch + BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils BuildRequires: gcc @@ -246,6 +249,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Tue Nov 07 2023 Milan Crha - 45.1-2 +- Add patch to build with appstream 1.0 + * Fri Oct 20 2023 Milan Crha - 45.1-1 - Update to 45.1 From fa61d9aee481d4275775b33d9a0e3e4b0cf428c1 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Tue, 7 Nov 2023 09:10:58 +0100 Subject: [PATCH 099/163] Require appstream version 1.0.0 --- gnome-software.spec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index af54a93..be9cb1b 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -1,4 +1,4 @@ -%global appstream_version 0.14.0 +%global appstream_version 1.0.0 %global flatpak_version 1.9.1 %global fwupd_version 1.5.6 %global glib2_version 2.70.0 From 34ee6fc989eff65e296e1b230ead120069d140fd Mon Sep 17 00:00:00 2001 From: Neal Gompa Date: Tue, 7 Nov 2023 13:06:54 -0500 Subject: [PATCH 100/163] Fix appstream_version macro for prerelease appstream 1.0 package --- gnome-software.spec | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index be9cb1b..7af1f2a 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -1,4 +1,4 @@ -%global appstream_version 1.0.0 +%global appstream_version 1.0.0~ %global flatpak_version 1.9.1 %global fwupd_version 1.5.6 %global glib2_version 2.70.0 @@ -24,7 +24,7 @@ Name: gnome-software Version: 45.1 -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -249,6 +249,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Tue Nov 07 2023 Neal Gompa - 45.1-3 +- Fix appstream_version macro for prerelease appstream 1.0 package + * Tue Nov 07 2023 Milan Crha - 45.1-2 - Add patch to build with appstream 1.0 From a3f0848b35859cbb0305243afb2c68b54d2500aa Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 1 Dec 2023 10:20:36 +0100 Subject: [PATCH 101/163] Update to 45.2 --- 0001-port-to-appstream1.patch | 13 +++++++++++++ gnome-software.spec | 7 +++++-- sources | 2 +- 3 files changed, 19 insertions(+), 3 deletions(-) diff --git a/0001-port-to-appstream1.patch b/0001-port-to-appstream1.patch index c166088..f121d70 100644 --- a/0001-port-to-appstream1.patch +++ b/0001-port-to-appstream1.patch @@ -489,6 +489,19 @@ index 6f0beb0cbc..5763a32c64 100644 -revision = v0.14.1 +revision = v0.16.3 depth = 1 +diff --git a/lib/gs-appstream.c b/lib/gs-appstream.c +index 6504d6f25..4fd7f5334 100644 +--- a/lib/gs-appstream.c ++++ b/lib/gs-appstream.c +@@ -587,8 +587,6 @@ gs_appstream_refine_add_provides (GsApp *app, XbNode *component, GError **error) + kind = AS_PROVIDED_KIND_FIRMWARE_RUNTIME; + else if (g_strcmp0 (fw_type, "flashed") == 0) + kind = AS_PROVIDED_KIND_FIRMWARE_FLASHED; +- } else if (g_strcmp0 (element_name, "python2") == 0) { +- kind = AS_PROVIDED_KIND_PYTHON_2; + } else if (g_strcmp0 (element_name, "python3") == 0) { + kind = AS_PROVIDED_KIND_PYTHON; + } else if (g_strcmp0 (element_name, "dbus") == 0) { -- GitLab diff --git a/gnome-software.spec b/gnome-software.spec index 7af1f2a..9c7b8db 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -23,8 +23,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 45.1 -Release: 3%{?dist} +Version: 45.2 +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -249,6 +249,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Dec 01 2023 Milan Crha - 45.2-1 +- Update to 45.2 + * Tue Nov 07 2023 Neal Gompa - 45.1-3 - Fix appstream_version macro for prerelease appstream 1.0 package diff --git a/sources b/sources index c15ccca..fe4c93b 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-45.1.tar.xz) = 5fdf5e6a34ab9acf938bc4ade41b916ad38ad3b4a7f604b2cba9dfaa38f17299001bef8fde9165f6a035fcc7fef3ebd451bd29ff126c0b9d5a7104e448729434 +SHA512 (gnome-software-45.2.tar.xz) = ea271146683d199b27ffaaab98a13c25f8f794da3c6cc6b0daeb37f3f4c92d8644926dc592d309ea32dcb131d33e6c77d1c6fa36ac10cf6b23cd7adc73e898cb From 3140f37d2d3b64c2889d143bcb9e6bee142981a4 Mon Sep 17 00:00:00 2001 From: Troy Dawson Date: Tue, 19 Dec 2023 09:38:23 -0800 Subject: [PATCH 102/163] ostree and flatpak not on i686 for RHEL 10 Signed-off-by: Troy Dawson --- gnome-software.spec | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/gnome-software.spec b/gnome-software.spec index 9c7b8db..40678e5 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -34,6 +34,12 @@ Source0: https://download.gnome.org/sources/gnome-software/45/%{name}-%{tarbal # https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/1810 Patch: 0001-port-to-appstream1.patch +# ostree and flatpak not on i686 for RHEL 10 +# https://github.com/containers/composefs/pull/229#issuecomment-1838735764 +%if 0%{?rhel} >= 10 +ExcludeArch: %{ix86} +%endif + BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils BuildRequires: gcc From ef76ba99411e0057ac5ccfd88df8307a1beff187 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 5 Jan 2024 10:28:23 +0100 Subject: [PATCH 103/163] Update to 46.alpha --- 0001-port-to-appstream1.patch | 507 ---------------------------------- gnome-software.spec | 10 +- sources | 2 +- 3 files changed, 6 insertions(+), 513 deletions(-) delete mode 100644 0001-port-to-appstream1.patch diff --git a/0001-port-to-appstream1.patch b/0001-port-to-appstream1.patch deleted file mode 100644 index f121d70..0000000 --- a/0001-port-to-appstream1.patch +++ /dev/null @@ -1,507 +0,0 @@ -From e6f7e28bdd50a63586ba6a82b936d54db19a311b Mon Sep 17 00:00:00 2001 -From: Matthias Klumpp -Date: Sun, 8 Oct 2023 20:22:44 +0200 -Subject: [PATCH] Adjust to build with AppStream 1.0 as well as 0.16.x - ---- - lib/gs-app.c | 4 ++ - lib/gs-appstream.c | 58 ++++++++++++++++++++---- - lib/gs-utils.c | 8 ++-- - meson.build | 22 +-------- - plugins/core/gs-plugin-appstream.c | 8 ---- - plugins/fwupd/gs-fwupd-app.c | 8 ++++ - plugins/fwupd/gs-plugin-fwupd.c | 4 ++ - src/gs-hardware-support-context-dialog.c | 6 +++ - src/gs-repos-dialog.c | 4 ++ - src/gs-screenshot-carousel.c | 4 +- - src/gs-screenshot-image.c | 41 +++++++++++++---- - src/gs-screenshot-image.h | 7 +++ - subprojects/appstream.wrap | 2 +- - 13 files changed, 120 insertions(+), 56 deletions(-) - -diff --git a/lib/gs-app.c b/lib/gs-app.c -index 048a061225..e2694057cd 100644 ---- a/lib/gs-app.c -+++ b/lib/gs-app.c -@@ -609,7 +609,11 @@ gs_app_to_string_append (GsApp *app, GString *str) - AsScreenshot *ss = g_ptr_array_index (priv->screenshots, i); - g_autofree gchar *key = NULL; - tmp = as_screenshot_get_caption (ss); -+#if AS_CHECK_VERSION(1, 0, 0) -+ im = as_screenshot_get_image (ss, 0, 0, 1); -+#else - im = as_screenshot_get_image (ss, 0, 0); -+#endif - if (im == NULL) - continue; - key = g_strdup_printf ("screenshot-%02u", i); -diff --git a/lib/gs-appstream.c b/lib/gs-appstream.c -index deca176dcf..2cc2427a19 100644 ---- a/lib/gs-appstream.c -+++ b/lib/gs-appstream.c -@@ -1011,8 +1011,11 @@ gs_appstream_refine_app_relation (GsApp *app, - as_relation_set_item_kind (relation, AS_RELATION_ITEM_KIND_CONTROL); - as_relation_set_value_control_kind (relation, as_control_kind_from_string (xb_node_get_text (child))); - } else if (g_str_equal (item_kind, "display_length")) { -- AsDisplayLengthKind display_length_kind; - const gchar *compare; -+ const gchar *side; -+#if !AS_CHECK_VERSION(1, 0, 0) -+ AsDisplayLengthKind display_length_kind; -+#endif - - /* https://www.freedesktop.org/software/appstream/docs/chap-Metadata.html#tag-relations-display_length */ - as_relation_set_item_kind (relation, AS_RELATION_ITEM_KIND_DISPLAY_LENGTH); -@@ -1020,15 +1023,21 @@ gs_appstream_refine_app_relation (GsApp *app, - compare = xb_node_get_attr (child, "compare"); - as_relation_set_compare (relation, (compare != NULL) ? as_relation_compare_from_string (compare) : AS_RELATION_COMPARE_GE); - -+#if AS_CHECK_VERSION(1, 0, 0) -+ side = xb_node_get_attr (child, "side"); -+ as_relation_set_display_side_kind (relation, (side != NULL) ? as_display_side_kind_from_string (side) : AS_DISPLAY_SIDE_KIND_SHORTEST); -+ as_relation_set_value_px (relation, xb_node_get_text_as_uint (child)); -+#else - display_length_kind = as_display_length_kind_from_string (xb_node_get_text (child)); - if (display_length_kind != AS_DISPLAY_LENGTH_KIND_UNKNOWN) { - /* Ignore the `side` attribute */ - as_relation_set_value_display_length_kind (relation, display_length_kind); - } else { -- const gchar *side = xb_node_get_attr (child, "side"); -+ side = xb_node_get_attr (child, "side"); - as_relation_set_display_side_kind (relation, (side != NULL) ? as_display_side_kind_from_string (side) : AS_DISPLAY_SIDE_KIND_SHORTEST); - as_relation_set_value_px (relation, xb_node_get_text_as_uint (child)); - } -+#endif - } else { - g_debug ("Relation type ‘%s’ not currently supported for %s; ignoring", - item_kind, gs_app_get_id (app)); -@@ -1472,7 +1481,7 @@ gs_appstream_refine_app (GsPlugin *plugin, - } - - typedef struct { -- AsSearchTokenMatch match_value; -+ guint16 match_value; - XbQuery *query; - } GsAppstreamSearchHelper; - -@@ -1522,7 +1531,7 @@ gs_appstream_silo_search_component (GPtrArray *array, XbNode *component, const g - } - - typedef struct { -- AsSearchTokenMatch match_value; -+ guint16 match_value; - const gchar *xpath; - } Query; - -@@ -1585,7 +1594,11 @@ gs_appstream_do_search (GsPlugin *plugin, - * Drop the ID token from it as it’s the highest - * numeric value but isn’t visible to the user in the - * UI, which leads to confusing results ordering. */ -+#if AS_CHECK_VERSION(1, 0, 0) -+ gs_app_set_match_value (app, match_value & (~as_utils_get_tag_search_weight ("id"))); -+#else - gs_app_set_match_value (app, match_value & (~AS_SEARCH_TOKEN_MATCH_ID)); -+#endif - gs_app_list_add (list, app); - - if (gs_app_get_kind (app) == AS_COMPONENT_KIND_ADDON) { -@@ -1624,18 +1637,32 @@ gs_appstream_search (GsPlugin *plugin, - GCancellable *cancellable, - GError **error) - { -+#if AS_CHECK_VERSION(1, 0, 0) -+ guint16 pkgname_weight = as_utils_get_tag_search_weight ("pkgname"); -+ guint16 name_weight = as_utils_get_tag_search_weight ("name"); -+ guint16 id_weight = as_utils_get_tag_search_weight ("id"); - const Query queries[] = { -- #ifdef HAVE_AS_SEARCH_TOKEN_MATCH_MEDIATYPE -- { AS_SEARCH_TOKEN_MATCH_MEDIATYPE, "mimetypes/mimetype[text()~=stem(?)]" }, -- #else -- { AS_SEARCH_TOKEN_MATCH_MIMETYPE, "mimetypes/mimetype[text()~=stem(?)]" }, -- #endif -+ { as_utils_get_tag_search_weight ("mediatype"), "provides/mediatype[text()~=stem(?)]" }, - /* Search once with a tokenize-and-casefold operator (`~=`) to support casefolded - * full-text search, then again using substring matching (`contains()`), to - * support prefix matching. Only do the prefix matches on a few fields, and at a - * lower priority, otherwise things will get confusing. -- * -+ * - * See https://gitlab.gnome.org/GNOME/gnome-software/-/issues/2277 */ -+ { pkgname_weight, "pkgname[text()~=stem(?)]" }, -+ { pkgname_weight / 2, "pkgname[contains(text(),stem(?))]" }, -+ { as_utils_get_tag_search_weight ("summary"), "summary[text()~=stem(?)]" }, -+ { name_weight, "name[text()~=stem(?)]" }, -+ { name_weight / 2, "name[contains(text(),stem(?))]" }, -+ { as_utils_get_tag_search_weight ("keyword"), "keywords/keyword[text()~=stem(?)]" }, -+ { id_weight, "id[text()~=stem(?)]" }, -+ { id_weight, "launchable[text()~=stem(?)]" }, -+ { as_utils_get_tag_search_weight ("origin"), "../components[@origin~=stem(?)]" }, -+ { 0, NULL } -+ }; -+#else -+ const Query queries[] = { -+ { AS_SEARCH_TOKEN_MATCH_MEDIATYPE, "mimetypes/mimetype[text()~=stem(?)]" }, - { AS_SEARCH_TOKEN_MATCH_PKGNAME, "pkgname[text()~=stem(?)]" }, - { AS_SEARCH_TOKEN_MATCH_PKGNAME / 2, "pkgname[contains(text(),stem(?))]" }, - { AS_SEARCH_TOKEN_MATCH_SUMMARY, "summary[text()~=stem(?)]" }, -@@ -1647,6 +1674,7 @@ gs_appstream_search (GsPlugin *plugin, - { AS_SEARCH_TOKEN_MATCH_ORIGIN, "../components[@origin~=stem(?)]" }, - { AS_SEARCH_TOKEN_MATCH_NONE, NULL } - }; -+#endif - - return gs_appstream_do_search (plugin, silo, values, queries, list, cancellable, error); - } -@@ -1659,11 +1687,21 @@ gs_appstream_search_developer_apps (GsPlugin *plugin, - GCancellable *cancellable, - GError **error) - { -+#if AS_CHECK_VERSION(1, 0, 0) -+ const Query queries[] = { -+ { as_utils_get_tag_search_weight ("pkgname"), "developer/name[text()~=stem(?)]" }, -+ { as_utils_get_tag_search_weight ("summary"), "project_group[text()~=stem(?)]" }, -+ /* for legacy support */ -+ { as_utils_get_tag_search_weight ("pkgname"), "developer_name[text()~=stem(?)]" }, -+ { 0, NULL } -+ }; -+#else - const Query queries[] = { - { AS_SEARCH_TOKEN_MATCH_PKGNAME, "developer_name[text()~=stem(?)]" }, - { AS_SEARCH_TOKEN_MATCH_SUMMARY, "project_group[text()~=stem(?)]" }, - { AS_SEARCH_TOKEN_MATCH_NONE, NULL } - }; -+#endif - - return gs_appstream_do_search (plugin, silo, values, queries, list, cancellable, error); - } -diff --git a/lib/gs-utils.c b/lib/gs-utils.c -index cf9073025f..19e6ebd046 100644 ---- a/lib/gs-utils.c -+++ b/lib/gs-utils.c -@@ -1694,9 +1694,9 @@ gs_utils_gstring_replace (GString *str, - const gchar *find, - const gchar *replace) - { -- #ifdef HAVE_AS_GSTRING_REPLACE_WITH_FOUR_ARGS -+#if AS_CHECK_VERSION(1, 0, 0) - as_gstring_replace (str, find, replace, 0); -- #else -- as_gstring_replace (str, find, replace); -- #endif -+#else -+ as_gstring_replace2 (str, find, replace, 0); -+#endif - } -diff --git a/meson.build b/meson.build -index 09c39df180..ad105869e5 100644 ---- a/meson.build -+++ b/meson.build -@@ -113,7 +113,7 @@ add_project_arguments('-D_GNU_SOURCE', language : 'c') - conf.set('HAVE_LINUX_UNISTD_H', cc.has_header('linux/unistd.h')) - - appstream = dependency('appstream', -- version : '>= 0.14.0', -+ version : '>= 0.16.2', - fallback : ['appstream', 'appstream_dep'], - default_options : [ - 'docs=false', -@@ -121,26 +121,6 @@ appstream = dependency('appstream', - 'install-docs=false' - ] - ) --if appstream.type_name() == 'internal' --else -- if meson.get_compiler('c').has_header_symbol('appstream.h', 'AS_SEARCH_TOKEN_MATCH_MEDIATYPE', dependencies: appstream) -- conf.set('HAVE_AS_SEARCH_TOKEN_MATCH_MEDIATYPE', '1') -- endif -- if meson.get_compiler('c').has_header_symbol('appstream.h', 'AS_FORMAT_STYLE_CATALOG', dependencies: appstream) -- conf.set('HAVE_AS_FORMAT_STYLE_CATALOG', '1') -- endif -- if meson.get_compiler('c').has_function('as_metadata_components_to_catalog', prefix: '#include ', dependencies: appstream) -- conf.set('HAVE_AS_METADATA_COMPONENTS_TO_CATALOG', '1') -- endif -- if meson.get_compiler('c').links('''#include -- int main (void) -- { -- as_gstring_replace (NULL, "a", "b", 0); -- return 0; -- }''', name: 'as_gstring_replace() has four arguments', dependencies: appstream) -- conf.set('HAVE_AS_GSTRING_REPLACE_WITH_FOUR_ARGS', '1') -- endif --endif - - gdk_pixbuf = dependency('gdk-pixbuf-2.0', version : '>= 2.32.0') - libxmlb = dependency('xmlb', version : '>= 0.1.7', fallback : ['libxmlb', 'libxmlb_dep']) -diff --git a/plugins/core/gs-plugin-appstream.c b/plugins/core/gs-plugin-appstream.c -index cf9f3022b1..ef3226a591 100644 ---- a/plugins/core/gs-plugin-appstream.c -+++ b/plugins/core/gs-plugin-appstream.c -@@ -414,11 +414,7 @@ gs_plugin_appstream_load_dep11_cb (XbBuilderSource *self, - if (bytes == NULL) - return NULL; - -- #ifdef HAVE_AS_FORMAT_STYLE_CATALOG - as_metadata_set_format_style (mdata, AS_FORMAT_STYLE_CATALOG); -- #else -- as_metadata_set_format_style (mdata, AS_FORMAT_STYLE_COLLECTION); -- #endif - as_metadata_parse_bytes (mdata, - bytes, - AS_FORMAT_KIND_YAML, -@@ -428,11 +424,7 @@ gs_plugin_appstream_load_dep11_cb (XbBuilderSource *self, - return NULL; - } - -- #ifdef HAVE_AS_METADATA_COMPONENTS_TO_CATALOG - xml = as_metadata_components_to_catalog (mdata, AS_FORMAT_KIND_XML, &tmp_error); -- #else -- xml = as_metadata_components_to_collection (mdata, AS_FORMAT_KIND_XML, &tmp_error); -- #endif - if (xml == NULL) { - // This API currently returns NULL if there is nothing to serialize, so we - // have to test if this is an error or not. -diff --git a/plugins/fwupd/gs-fwupd-app.c b/plugins/fwupd/gs-fwupd-app.c -index 6dcda6ee92..5d3254da59 100644 ---- a/plugins/fwupd/gs-fwupd-app.c -+++ b/plugins/fwupd/gs-fwupd-app.c -@@ -164,7 +164,11 @@ gs_fwupd_app_set_from_device (GsApp *app, - gs_app_set_install_date (app, fwupd_device_get_created (dev)); - if (fwupd_device_get_description (dev) != NULL) { - g_autofree gchar *tmp = NULL; -+#if AS_CHECK_VERSION(1, 0, 0) -+ tmp = as_markup_convert (fwupd_device_get_description (dev), AS_MARKUP_KIND_TEXT, NULL); -+#else - tmp = as_markup_convert_simple (fwupd_device_get_description (dev), NULL); -+#endif - if (tmp != NULL) - gs_app_set_description (app, GS_APP_QUALITY_NORMAL, tmp); - } -@@ -402,7 +406,11 @@ gs_fwupd_app_set_from_release (GsApp *app, FwupdRelease *rel) - } - if (fwupd_release_get_description (rel) != NULL) { - g_autofree gchar *tmp = NULL; -+#if AS_CHECK_VERSION(1, 0, 0) -+ tmp = as_markup_convert (fwupd_release_get_description (rel), AS_MARKUP_KIND_TEXT, NULL); -+#else - tmp = as_markup_convert_simple (fwupd_release_get_description (rel), NULL); -+#endif - if (tmp != NULL) - gs_app_set_update_details_text (app, tmp); - } -diff --git a/plugins/fwupd/gs-plugin-fwupd.c b/plugins/fwupd/gs-plugin-fwupd.c -index e931b2b6db..0747d6e250 100644 ---- a/plugins/fwupd/gs-plugin-fwupd.c -+++ b/plugins/fwupd/gs-plugin-fwupd.c -@@ -726,7 +726,11 @@ gs_plugin_add_updates (GsPlugin *plugin, - g_autofree gchar *desc = NULL; - if (fwupd_release_get_description (rel) == NULL) - continue; -+#if AS_CHECK_VERSION(1, 0, 0) -+ desc = as_markup_convert (fwupd_release_get_description (rel), AS_MARKUP_KIND_TEXT, NULL); -+#else - desc = as_markup_convert_simple (fwupd_release_get_description (rel), NULL); -+#endif - if (desc == NULL) - continue; - g_string_append_printf (update_desc, -diff --git a/src/gs-hardware-support-context-dialog.c b/src/gs-hardware-support-context-dialog.c -index 0e48c8c266..14653401de 100644 ---- a/src/gs-hardware-support-context-dialog.c -+++ b/src/gs-hardware-support-context-dialog.c -@@ -461,6 +461,7 @@ gs_hardware_support_context_dialog_get_display_support (GdkMonitor *monitor, - AsRelationCompare comparator = as_relation_get_compare (relation); - Range current_display_comparand, relation_comparand; - -+#if !AS_CHECK_VERSION(1, 0, 0) - /* From https://www.freedesktop.org/software/appstream/docs/chap-Metadata.html#tag-requires-recommends-display_length */ - Range display_lengths[] = { - [AS_DISPLAY_LENGTH_KIND_XSMALL] = { 0, 360 }, -@@ -469,6 +470,7 @@ gs_hardware_support_context_dialog_get_display_support (GdkMonitor *monitor, - [AS_DISPLAY_LENGTH_KIND_LARGE] = { 1024, 3840 }, - [AS_DISPLAY_LENGTH_KIND_XLARGE] = { 3840, G_MAXUINT }, - }; -+#endif - - any_display_relations_set = TRUE; - -@@ -485,11 +487,14 @@ gs_hardware_support_context_dialog_get_display_support (GdkMonitor *monitor, - case AS_DISPLAY_SIDE_KIND_LAST: - default: - current_display_comparand.min = current_display_comparand.max = MAX (current_screen_size.width, current_screen_size.height); -+#if !AS_CHECK_VERSION(1, 0, 0) - relation_comparand.min = display_lengths[as_relation_get_value_display_length_kind (relation)].min; - relation_comparand.max = display_lengths[as_relation_get_value_display_length_kind (relation)].max; -+#endif - break; - } - -+#if !AS_CHECK_VERSION(1, 0, 0) - if (evaluate_display_comparison (display_lengths[AS_DISPLAY_LENGTH_KIND_SMALL], comparator, relation_comparand)) { - *mobile_relation_kind_out = max_relation_kind (*mobile_relation_kind_out, as_relation_get_kind (relation)); - *mobile_match_out = TRUE; -@@ -499,6 +504,7 @@ gs_hardware_support_context_dialog_get_display_support (GdkMonitor *monitor, - *desktop_relation_kind_out = max_relation_kind (*desktop_relation_kind_out, as_relation_get_kind (relation)); - *desktop_match_out = TRUE; - } -+#endif - - if (evaluate_display_comparison (current_display_comparand, comparator, relation_comparand)) { - *current_relation_kind_out = max_relation_kind (*current_relation_kind_out, as_relation_get_kind (relation)); -diff --git a/src/gs-repos-dialog.c b/src/gs-repos-dialog.c -index c41c4944a1..7dac0416d9 100644 ---- a/src/gs-repos-dialog.c -+++ b/src/gs-repos-dialog.c -@@ -154,7 +154,11 @@ enable_repo (GsReposDialog *dialog, - g_autoptr(GError) error = NULL; - - /* convert from AppStream markup */ -+#if AS_CHECK_VERSION(1, 0, 0) -+ message = as_markup_convert (gs_app_get_agreement (repo), AS_MARKUP_KIND_TEXT, &error); -+#else - message = as_markup_convert_simple (gs_app_get_agreement (repo), &error); -+#endif - if (message == NULL) { - /* failed, so just try and show the original markup */ - message = g_strdup (gs_app_get_agreement (repo)); -diff --git a/src/gs-screenshot-carousel.c b/src/gs-screenshot-carousel.c -index 04bbf86a1e..d269af6605 100644 ---- a/src/gs-screenshot-carousel.c -+++ b/src/gs-screenshot-carousel.c -@@ -141,8 +141,8 @@ gs_screenshot_carousel_load_screenshots (GsScreenshotCarousel *self, GsApp *app, - gtk_widget_set_can_focus (gtk_widget_get_first_child (ssimg), FALSE); - gs_screenshot_image_set_screenshot (GS_SCREENSHOT_IMAGE (ssimg), ss); - gs_screenshot_image_set_size (GS_SCREENSHOT_IMAGE (ssimg), -- AS_IMAGE_NORMAL_WIDTH, -- AS_IMAGE_NORMAL_HEIGHT); -+ GS_IMAGE_NORMAL_WIDTH, -+ GS_IMAGE_NORMAL_HEIGHT); - gtk_widget_add_css_class (ssimg, "screenshot-image-main"); - gs_screenshot_image_load_async (GS_SCREENSHOT_IMAGE (ssimg), cancellable); - -diff --git a/src/gs-screenshot-image.c b/src/gs-screenshot-image.c -index c313a2589f..b24083b387 100644 ---- a/src/gs-screenshot-image.c -+++ b/src/gs-screenshot-image.c -@@ -284,13 +284,13 @@ gs_screenshot_image_save_downloaded_img (GsScreenshotImage *ssimg, - if (images->len > 1) - return TRUE; - -- if (width == AS_IMAGE_THUMBNAIL_WIDTH && -- height == AS_IMAGE_THUMBNAIL_HEIGHT) { -- width = AS_IMAGE_NORMAL_WIDTH; -- height = AS_IMAGE_NORMAL_HEIGHT; -+ if (width == GS_IMAGE_THUMBNAIL_WIDTH && -+ height == GS_IMAGE_THUMBNAIL_HEIGHT) { -+ width = GS_IMAGE_NORMAL_WIDTH; -+ height = GS_IMAGE_NORMAL_HEIGHT; - } else { -- width = AS_IMAGE_THUMBNAIL_WIDTH; -- height = AS_IMAGE_THUMBNAIL_HEIGHT; -+ width = GS_IMAGE_THUMBNAIL_WIDTH; -+ height = GS_IMAGE_THUMBNAIL_HEIGHT; - } - - width *= ssimg->scale; -@@ -582,16 +582,30 @@ gs_screenshot_image_get_url (GsScreenshotImage *ssimg) - } else if (as_screenshot_get_media_kind (ssimg->screenshot) == AS_SCREENSHOT_MEDIA_KIND_IMAGE) { - AsImage *im; - -+#if AS_CHECK_VERSION(1, 0, 0) -+ im = as_screenshot_get_image (ssimg->screenshot, -+ ssimg->width, -+ ssimg->height, -+ ssimg->scale); -+#else - im = as_screenshot_get_image (ssimg->screenshot, - ssimg->width * ssimg->scale, - ssimg->height * ssimg->scale); -+#endif - - /* if we've failed to load a HiDPI image, fallback to LoDPI */ - if (im == NULL && ssimg->scale > 1) { - ssimg->scale = 1; -+#if AS_CHECK_VERSION(1, 0, 0) -+ im = as_screenshot_get_image (ssimg->screenshot, -+ ssimg->width, -+ ssimg->height, -+ 1); -+#else - im = as_screenshot_get_image (ssimg->screenshot, - ssimg->width, - ssimg->height); -+#endif - } - - if (im) -@@ -698,15 +712,22 @@ gs_screenshot_image_load_async (GsScreenshotImage *ssimg, - * smaller version of it straight away */ - if (!ssimg->showing_image && - as_screenshot_get_media_kind (ssimg->screenshot) == AS_SCREENSHOT_MEDIA_KIND_IMAGE && -- ssimg->width > AS_IMAGE_THUMBNAIL_WIDTH && -- ssimg->height > AS_IMAGE_THUMBNAIL_HEIGHT) { -+ ssimg->width > GS_IMAGE_THUMBNAIL_WIDTH && -+ ssimg->height > GS_IMAGE_THUMBNAIL_HEIGHT) { - const gchar *url_thumb; - g_autofree gchar *basename_thumb = NULL; - g_autofree gchar *cache_kind_thumb = NULL; - AsImage *im; -+#if AS_CHECK_VERSION(1, 0, 0) - im = as_screenshot_get_image (ssimg->screenshot, -- AS_IMAGE_THUMBNAIL_WIDTH * ssimg->scale, -- AS_IMAGE_THUMBNAIL_HEIGHT * ssimg->scale); -+ GS_IMAGE_THUMBNAIL_WIDTH, -+ GS_IMAGE_THUMBNAIL_HEIGHT, -+ ssimg->scale); -+#else -+ im = as_screenshot_get_image (ssimg->screenshot, -+ GS_IMAGE_THUMBNAIL_WIDTH * ssimg->scale, -+ GS_IMAGE_THUMBNAIL_HEIGHT * ssimg->scale); -+#endif - url_thumb = as_image_get_url (im); - basename_thumb = gs_screenshot_get_cachefn_for_url (url_thumb); - cache_kind_thumb = g_build_filename ("screenshots", "112x63", NULL); -diff --git a/src/gs-screenshot-image.h b/src/gs-screenshot-image.h -index 1f6cf81ce6..6e45f5d20a 100644 ---- a/src/gs-screenshot-image.h -+++ b/src/gs-screenshot-image.h -@@ -21,6 +21,13 @@ G_BEGIN_DECLS - - G_DECLARE_FINAL_TYPE (GsScreenshotImage, gs_screenshot_image, GS, SCREENSHOT_IMAGE, GtkWidget) - -+#define GS_IMAGE_LARGE_HEIGHT 423 -+#define GS_IMAGE_LARGE_WIDTH 752 -+#define GS_IMAGE_NORMAL_HEIGHT 351 -+#define GS_IMAGE_NORMAL_WIDTH 624 -+#define GS_IMAGE_THUMBNAIL_HEIGHT 63 -+#define GS_IMAGE_THUMBNAIL_WIDTH 112 -+ - GtkWidget *gs_screenshot_image_new (SoupSession *session); - - AsScreenshot *gs_screenshot_image_get_screenshot (GsScreenshotImage *ssimg); -diff --git a/subprojects/appstream.wrap b/subprojects/appstream.wrap -index 6f0beb0cbc..5763a32c64 100644 ---- a/subprojects/appstream.wrap -+++ b/subprojects/appstream.wrap -@@ -1,5 +1,5 @@ - [wrap-git] - directory = appstream - url = https://github.com/ximion/appstream.git --revision = v0.14.1 -+revision = v0.16.3 - depth = 1 -diff --git a/lib/gs-appstream.c b/lib/gs-appstream.c -index 6504d6f25..4fd7f5334 100644 ---- a/lib/gs-appstream.c -+++ b/lib/gs-appstream.c -@@ -587,8 +587,6 @@ gs_appstream_refine_add_provides (GsApp *app, XbNode *component, GError **error) - kind = AS_PROVIDED_KIND_FIRMWARE_RUNTIME; - else if (g_strcmp0 (fw_type, "flashed") == 0) - kind = AS_PROVIDED_KIND_FIRMWARE_FLASHED; -- } else if (g_strcmp0 (element_name, "python2") == 0) { -- kind = AS_PROVIDED_KIND_PYTHON_2; - } else if (g_strcmp0 (element_name, "python3") == 0) { - kind = AS_PROVIDED_KIND_PYTHON; - } else if (g_strcmp0 (element_name, "dbus") == 0) { --- -GitLab - diff --git a/gnome-software.spec b/gnome-software.spec index 40678e5..3569a72 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -23,16 +23,13 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 45.2 +Version: 46~alpha Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://wiki.gnome.org/Apps/Software -Source0: https://download.gnome.org/sources/gnome-software/45/%{name}-%{tarball_version}.tar.xz - -# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/1810 -Patch: 0001-port-to-appstream1.patch +Source0: https://download.gnome.org/sources/gnome-software/46/%{name}-%{tarball_version}.tar.xz # ostree and flatpak not on i686 for RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 @@ -255,6 +252,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Jan 05 2024 Milan Crha - 46~alpha-1 +- Update to 46.alpha + * Fri Dec 01 2023 Milan Crha - 45.2-1 - Update to 45.2 diff --git a/sources b/sources index fe4c93b..50ca12a 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-45.2.tar.xz) = ea271146683d199b27ffaaab98a13c25f8f794da3c6cc6b0daeb37f3f4c92d8644926dc592d309ea32dcb131d33e6c77d1c6fa36ac10cf6b23cd7adc73e898cb +SHA512 (gnome-software-46.alpha.tar.xz) = 373ef9b103b7963dad1824888261958d60d11f9f55d1fc07634de5df6a0436388334fec1a018d83b4024e61c18a2c95b9dc942c3a592cbb9fe1274f5950b4104 From 2152c30083596475de72116b36d0dc48a5f1e81a Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Fri, 19 Jan 2024 23:07:23 +0000 Subject: [PATCH 104/163] Rebuilt for https://fedoraproject.org/wiki/Fedora_40_Mass_Rebuild --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 3569a72..be4564a 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -24,7 +24,7 @@ Name: gnome-software Version: 46~alpha -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -252,6 +252,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Jan 19 2024 Fedora Release Engineering - 46~alpha-2 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_40_Mass_Rebuild + * Fri Jan 05 2024 Milan Crha - 46~alpha-1 - Update to 46.alpha From 881bbc7f12f9e70d401720c2c072f1efc136a1f6 Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Wed, 24 Jan 2024 15:41:25 +0000 Subject: [PATCH 105/163] Rebuilt for https://fedoraproject.org/wiki/Fedora_40_Mass_Rebuild --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index be4564a..4e4adac 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -24,7 +24,7 @@ Name: gnome-software Version: 46~alpha -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -252,6 +252,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Wed Jan 24 2024 Fedora Release Engineering - 46~alpha-3 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_40_Mass_Rebuild + * Fri Jan 19 2024 Fedora Release Engineering - 46~alpha-2 - Rebuilt for https://fedoraproject.org/wiki/Fedora_40_Mass_Rebuild From 0b4b0060f8e8ce015ecef7d3cd4e1ae2918cf27e Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 26 Jan 2024 11:02:25 +0100 Subject: [PATCH 106/163] Resolves: #2260294 (Split fedora-langpacks plugin into a subpackage) --- gnome-software.spec | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 4e4adac..e6d4798 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -24,7 +24,7 @@ Name: gnome-software Version: 46~alpha -Release: 3%{?dist} +Release: 4%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -90,6 +90,7 @@ Requires: librsvg2%{?_isa} Requires: libxmlb%{?_isa} >= %{libxmlb_version} Recommends: PackageKit%{?_isa} >= %{packagekit_version} +Recommends: %{name}-fedora-langpacks Obsoletes: gnome-software-snap < 3.33.1 Obsoletes: gnome-software-editor < 3.35.1 @@ -106,6 +107,14 @@ Requires: %{name}%{?_isa} = %{version}-%{release} These development files are for building gnome-software plugins outside the source tree. Most users do not need this subpackage installed. +%package fedora-langpacks +Summary: Contains fedora-langpacks plugin +Requires: %{name}%{?_isa} = %{version}-%{release} + +%description fedora-langpacks +The fedora-langpacks plugin ensures langpacks packages are installed +for the current locale. + %if %{with rpmostree} %package rpm-ostree Summary: rpm-ostree backend for gnome-software @@ -205,7 +214,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %if %{with webapps} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_epiphany.so %endif -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-pkgdb-collections.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_flatpak.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fwupd.so @@ -237,6 +245,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libexecdir}/gnome-software-cmd %{_libexecdir}/gnome-software-restarter +%files fedora-langpacks +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so + %if %{with rpmostree} %files rpm-ostree %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rpm-ostree.so @@ -252,6 +263,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Jan 26 2024 Milan Crha - 46~alpha-4 +- Resolves: #2260294 (Split fedora-langpacks plugin into a subpackage) + * Wed Jan 24 2024 Fedora Release Engineering - 46~alpha-3 - Rebuilt for https://fedoraproject.org/wiki/Fedora_40_Mass_Rebuild From e1a74cef52eda1601fdc90c6cd1d8f0b6c130c3a Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 9 Feb 2024 10:05:49 +0100 Subject: [PATCH 107/163] Update to 46.beta --- gnome-software.spec | 8 ++++++-- sources | 2 +- 2 files changed, 7 insertions(+), 3 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index e6d4798..e0755b4 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -23,8 +23,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 46~alpha -Release: 4%{?dist} +Version: 46~beta +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -197,6 +197,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/applications/gnome-software-local-file-fwupd.desktop %{_datadir}/applications/gnome-software-local-file-packagekit.desktop %{_datadir}/applications/org.gnome.Software.desktop +%{_datadir}/bash-completion/completions/gnome-software %{_mandir}/man1/gnome-software.1* %{_datadir}/icons/hicolor/*/apps/org.gnome.Software.svg %{_datadir}/icons/hicolor/symbolic/apps/org.gnome.Software-symbolic.svg @@ -263,6 +264,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Feb 09 2024 Milan Crha - 46~beta-1 +- Update to 46.beta + * Fri Jan 26 2024 Milan Crha - 46~alpha-4 - Resolves: #2260294 (Split fedora-langpacks plugin into a subpackage) diff --git a/sources b/sources index 50ca12a..6816df2 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-46.alpha.tar.xz) = 373ef9b103b7963dad1824888261958d60d11f9f55d1fc07634de5df6a0436388334fec1a018d83b4024e61c18a2c95b9dc942c3a592cbb9fe1274f5950b4104 +SHA512 (gnome-software-46.beta.tar.xz) = 932f6fe10ae9baf233a93abb62ad92a8fced0ce39d77c8ab1ecb3450699fc7491eaa4481968aa585a9dab011e1796a71f5b356eee0e2004ca0f8ace74aae473a From 9452c386433141e066efc9baa00b7b6d1cd9aefe Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 1 Mar 2024 11:27:02 +0100 Subject: [PATCH 108/163] Update to 46.rc --- gnome-software.spec | 5 ++++- sources | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index e0755b4..8761fb8 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -23,7 +23,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 46~beta +Version: 46~rc Release: 1%{?dist} Summary: A software center for GNOME @@ -264,6 +264,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Mar 01 2024 Milan Crha - 46~rc-1 +- Update to 46.rc + * Fri Feb 09 2024 Milan Crha - 46~beta-1 - Update to 46.beta diff --git a/sources b/sources index 6816df2..9471511 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-46.beta.tar.xz) = 932f6fe10ae9baf233a93abb62ad92a8fced0ce39d77c8ab1ecb3450699fc7491eaa4481968aa585a9dab011e1796a71f5b356eee0e2004ca0f8ace74aae473a +SHA512 (gnome-software-46.rc.tar.xz) = dc7122c9675722269977d7e69e3c435306be1059e4dbc7303eaa0bda6916481a8a6ca90bbe6eb01f49269045b5a472bfd56c2774ca8281eae3f38e32329d6fb3 From 9848abdaf8f1fbba33a80a2abaf92397ea66ecce Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 18 Mar 2024 10:03:43 +0100 Subject: [PATCH 109/163] Update to 46.0 --- gnome-software.spec | 5 ++++- sources | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 8761fb8..6cd66e1 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -23,7 +23,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 46~rc +Version: 46.0 Release: 1%{?dist} Summary: A software center for GNOME @@ -264,6 +264,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Mon Mar 18 2024 Milan Crha - 46.0-1 +- Update to 46.0 + * Fri Mar 01 2024 Milan Crha - 46~rc-1 - Update to 46.rc diff --git a/sources b/sources index 9471511..2d68da6 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-46.rc.tar.xz) = dc7122c9675722269977d7e69e3c435306be1059e4dbc7303eaa0bda6916481a8a6ca90bbe6eb01f49269045b5a472bfd56c2774ca8281eae3f38e32329d6fb3 +SHA512 (gnome-software-46.0.tar.xz) = d221db960bb0a04c8976d20626eb1154a80b12f64f5b4af09ca837814078797e265ab978ae5cad03e3b592f0b9fc41c837d741ef288590b4992fbb4a0fab1d55 From ea6727cab2990dc27d0a9b2e950ee1de0dc7e15c Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Wed, 27 Mar 2024 09:39:17 +0100 Subject: [PATCH 110/163] Update URL to point to the new app page --- gnome-software.spec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 6cd66e1..dad1e93 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -28,7 +28,7 @@ Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later -URL: https://wiki.gnome.org/Apps/Software +URL: https://apps.gnome.org/Software Source0: https://download.gnome.org/sources/gnome-software/46/%{name}-%{tarball_version}.tar.xz # ostree and flatpak not on i686 for RHEL 10 From e68edf805818db2994c7be2db6aea96cab7bc8f5 Mon Sep 17 00:00:00 2001 From: Adam Williamson Date: Fri, 12 Apr 2024 10:19:53 -0700 Subject: [PATCH 111/163] Backport MR #1949 to fix upgrading --- ...lections-Incorrect-state-set-on-the-.patch | 62 +++++++++++++++++++ gnome-software.spec | 10 ++- 2 files changed, 71 insertions(+), 1 deletion(-) create mode 100644 0001-fedora-pkgdb-collections-Incorrect-state-set-on-the-.patch diff --git a/0001-fedora-pkgdb-collections-Incorrect-state-set-on-the-.patch b/0001-fedora-pkgdb-collections-Incorrect-state-set-on-the-.patch new file mode 100644 index 0000000..88e0522 --- /dev/null +++ b/0001-fedora-pkgdb-collections-Incorrect-state-set-on-the-.patch @@ -0,0 +1,62 @@ +From cd0743032edccfad47d2253b87daebd01b0ee2e1 Mon Sep 17 00:00:00 2001 +From: Milan Crha +Date: Fri, 12 Apr 2024 07:57:14 +0200 +Subject: [PATCH] fedora-pkgdb-collections: Incorrect state set on the upgrade + app + +The "updatable" state means "downloaded locally, ready to be installed", which +is not the case here. The upgrade is either "available" (to be downloaded), or +"unavailable" (end of life). The other states are determined by the other plugins. + +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/2514 +--- + .../gs-plugin-fedora-pkgdb-collections.c | 23 +++---------------- + 1 file changed, 3 insertions(+), 20 deletions(-) + +diff --git a/plugins/fedora-pkgdb-collections/gs-plugin-fedora-pkgdb-collections.c b/plugins/fedora-pkgdb-collections/gs-plugin-fedora-pkgdb-collections.c +index 2983defaa..15d3c385a 100644 +--- a/plugins/fedora-pkgdb-collections/gs-plugin-fedora-pkgdb-collections.c ++++ b/plugins/fedora-pkgdb-collections/gs-plugin-fedora-pkgdb-collections.c +@@ -393,18 +393,10 @@ _create_upgrade_from_info (GsPluginFedoraPkgdbCollections *self, + + /* create */ + app = gs_app_new (app_id); +- switch (item->status) { +- case PKGDB_ITEM_STATUS_ACTIVE: +- case PKGDB_ITEM_STATUS_DEVEL: +- gs_app_set_state (app, GS_APP_STATE_UPDATABLE); +- break; +- case PKGDB_ITEM_STATUS_EOL: ++ if (item->status == PKGDB_ITEM_STATUS_EOL) + gs_app_set_state (app, GS_APP_STATE_UNAVAILABLE); +- break; +- default: ++ else + gs_app_set_state (app, GS_APP_STATE_AVAILABLE); +- break; +- } + gs_app_set_kind (app, AS_COMPONENT_KIND_OPERATING_SYSTEM); + gs_app_set_bundle_kind (app, AS_BUNDLE_KIND_PACKAGE); + gs_app_set_name (app, GS_APP_QUALITY_LOWEST, item->name); +@@ -729,17 +721,8 @@ refine_app (GsPluginFedoraPkgdbCollections *self, + return TRUE; + + /* fix the state */ +- switch (item->status) { +- case PKGDB_ITEM_STATUS_ACTIVE: +- case PKGDB_ITEM_STATUS_DEVEL: +- gs_app_set_state (app, GS_APP_STATE_UPDATABLE); +- break; +- case PKGDB_ITEM_STATUS_EOL: ++ if (item->status == PKGDB_ITEM_STATUS_EOL) + gs_app_set_state (app, GS_APP_STATE_UNAVAILABLE); +- break; +- default: +- break; +- } + + return TRUE; + } +-- +2.44.0 + diff --git a/gnome-software.spec b/gnome-software.spec index dad1e93..eeb1db9 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -24,13 +24,18 @@ Name: gnome-software Version: 46.0 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://apps.gnome.org/Software Source0: https://download.gnome.org/sources/gnome-software/46/%{name}-%{tarball_version}.tar.xz +# https://gitlab.gnome.org/GNOME/gnome-software/-/issues/2514 +# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/1949 +# Fix incorrect upgrade state (breaks upgrade process) +Patch: 0001-fedora-pkgdb-collections-Incorrect-state-set-on-the-.patch + # ostree and flatpak not on i686 for RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 %if 0%{?rhel} >= 10 @@ -264,6 +269,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Apr 12 2024 Adam Williamson - 46.0-2 +- Backport MR #1949 to fix upgrading + * Mon Mar 18 2024 Milan Crha - 46.0-1 - Update to 46.0 From 869715beb209ecb3b0bd011ee889c8db9939365a Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Thu, 25 Apr 2024 10:28:27 +0200 Subject: [PATCH 112/163] Update to 46.1 --- ...lections-Incorrect-state-set-on-the-.patch | 62 ------------------- gnome-software.spec | 12 ++-- sources | 2 +- 3 files changed, 6 insertions(+), 70 deletions(-) delete mode 100644 0001-fedora-pkgdb-collections-Incorrect-state-set-on-the-.patch diff --git a/0001-fedora-pkgdb-collections-Incorrect-state-set-on-the-.patch b/0001-fedora-pkgdb-collections-Incorrect-state-set-on-the-.patch deleted file mode 100644 index 88e0522..0000000 --- a/0001-fedora-pkgdb-collections-Incorrect-state-set-on-the-.patch +++ /dev/null @@ -1,62 +0,0 @@ -From cd0743032edccfad47d2253b87daebd01b0ee2e1 Mon Sep 17 00:00:00 2001 -From: Milan Crha -Date: Fri, 12 Apr 2024 07:57:14 +0200 -Subject: [PATCH] fedora-pkgdb-collections: Incorrect state set on the upgrade - app - -The "updatable" state means "downloaded locally, ready to be installed", which -is not the case here. The upgrade is either "available" (to be downloaded), or -"unavailable" (end of life). The other states are determined by the other plugins. - -Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/2514 ---- - .../gs-plugin-fedora-pkgdb-collections.c | 23 +++---------------- - 1 file changed, 3 insertions(+), 20 deletions(-) - -diff --git a/plugins/fedora-pkgdb-collections/gs-plugin-fedora-pkgdb-collections.c b/plugins/fedora-pkgdb-collections/gs-plugin-fedora-pkgdb-collections.c -index 2983defaa..15d3c385a 100644 ---- a/plugins/fedora-pkgdb-collections/gs-plugin-fedora-pkgdb-collections.c -+++ b/plugins/fedora-pkgdb-collections/gs-plugin-fedora-pkgdb-collections.c -@@ -393,18 +393,10 @@ _create_upgrade_from_info (GsPluginFedoraPkgdbCollections *self, - - /* create */ - app = gs_app_new (app_id); -- switch (item->status) { -- case PKGDB_ITEM_STATUS_ACTIVE: -- case PKGDB_ITEM_STATUS_DEVEL: -- gs_app_set_state (app, GS_APP_STATE_UPDATABLE); -- break; -- case PKGDB_ITEM_STATUS_EOL: -+ if (item->status == PKGDB_ITEM_STATUS_EOL) - gs_app_set_state (app, GS_APP_STATE_UNAVAILABLE); -- break; -- default: -+ else - gs_app_set_state (app, GS_APP_STATE_AVAILABLE); -- break; -- } - gs_app_set_kind (app, AS_COMPONENT_KIND_OPERATING_SYSTEM); - gs_app_set_bundle_kind (app, AS_BUNDLE_KIND_PACKAGE); - gs_app_set_name (app, GS_APP_QUALITY_LOWEST, item->name); -@@ -729,17 +721,8 @@ refine_app (GsPluginFedoraPkgdbCollections *self, - return TRUE; - - /* fix the state */ -- switch (item->status) { -- case PKGDB_ITEM_STATUS_ACTIVE: -- case PKGDB_ITEM_STATUS_DEVEL: -- gs_app_set_state (app, GS_APP_STATE_UPDATABLE); -- break; -- case PKGDB_ITEM_STATUS_EOL: -+ if (item->status == PKGDB_ITEM_STATUS_EOL) - gs_app_set_state (app, GS_APP_STATE_UNAVAILABLE); -- break; -- default: -- break; -- } - - return TRUE; - } --- -2.44.0 - diff --git a/gnome-software.spec b/gnome-software.spec index eeb1db9..e7b85be 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -23,19 +23,14 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 46.0 -Release: 2%{?dist} +Version: 46.1 +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://apps.gnome.org/Software Source0: https://download.gnome.org/sources/gnome-software/46/%{name}-%{tarball_version}.tar.xz -# https://gitlab.gnome.org/GNOME/gnome-software/-/issues/2514 -# https://gitlab.gnome.org/GNOME/gnome-software/-/merge_requests/1949 -# Fix incorrect upgrade state (breaks upgrade process) -Patch: 0001-fedora-pkgdb-collections-Incorrect-state-set-on-the-.patch - # ostree and flatpak not on i686 for RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 %if 0%{?rhel} >= 10 @@ -269,6 +264,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Apr 25 2024 Milan Crha - 46.1-1 +- Update to 46.1 + * Fri Apr 12 2024 Adam Williamson - 46.0-2 - Backport MR #1949 to fix upgrading diff --git a/sources b/sources index 2d68da6..c841edb 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-46.0.tar.xz) = d221db960bb0a04c8976d20626eb1154a80b12f64f5b4af09ca837814078797e265ab978ae5cad03e3b592f0b9fc41c837d741ef288590b4992fbb4a0fab1d55 +SHA512 (gnome-software-46.1.tar.xz) = 7f851faa706c347a92a10b2a70cef7310cf27fec47bb3d9fc0c832041c9d612ec1fdd029df0a60368eda447047ff9f5afffaacd77669ecefdd4d04827de539ca From 4e0c8cfc83d96fc0eed22104de63ed665ee44b04 Mon Sep 17 00:00:00 2001 From: Hristo Marinov Date: Wed, 8 May 2024 19:01:10 +0300 Subject: [PATCH 113/163] OSTree not on i686 for Fedora --- gnome-software.spec | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index e7b85be..c092a4b 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -31,9 +31,9 @@ License: GPL-2.0-or-later URL: https://apps.gnome.org/Software Source0: https://download.gnome.org/sources/gnome-software/46/%{name}-%{tarball_version}.tar.xz -# ostree and flatpak not on i686 for RHEL 10 +# ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 -%if 0%{?rhel} >= 10 +%if 0%{?fedora} || 0%{?rhel} >= 10 ExcludeArch: %{ix86} %endif From 4f2a027a25187f81fd7d7437673ab7d540235dac Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 24 May 2024 08:30:36 +0200 Subject: [PATCH 114/163] Update to 46.2 --- gnome-software.spec | 5 ++++- sources | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index c092a4b..6b65ab7 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -23,7 +23,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 46.1 +Version: 46.2 Release: 1%{?dist} Summary: A software center for GNOME @@ -264,6 +264,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri May 24 2024 Milan Crha - 46.2-1 +- Update to 46.2 + * Thu Apr 25 2024 Milan Crha - 46.1-1 - Update to 46.1 diff --git a/sources b/sources index c841edb..bc7fdbd 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-46.1.tar.xz) = 7f851faa706c347a92a10b2a70cef7310cf27fec47bb3d9fc0c832041c9d612ec1fdd029df0a60368eda447047ff9f5afffaacd77669ecefdd4d04827de539ca +SHA512 (gnome-software-46.2.tar.xz) = 4e7cccc20001ccee114508bb50e2a25968ee6fea64fb545e1174ff435cd368b2d7c928b6a182874af8e9f0c99f9f506e75c5ac9bf61b35ba0a897368ae0abc3c From 2f2f30d236e3c1906ad2e6430051e978656a6623 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 3 Jun 2024 10:27:39 +0200 Subject: [PATCH 115/163] Build fedora-langpacks subpackage only in Fedora The subpackage contains a plugin, which disables itself when the system is not Fedora, thus is does not need to be distributed elsewhere. --- gnome-software.spec | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/gnome-software.spec b/gnome-software.spec index 6b65ab7..8c9715d 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -14,6 +14,8 @@ %bcond malcontent %[!0%{?rhel}] # Disable rpm-ostree support for RHEL builds %bcond rpmostree %[!0%{?rhel}] +# Disable fedora-langpacks subpackage for RHEL builds +%bcond langpacks %[!0%{?rhel}] # this is not a library version %define gs_plugin_version 20 @@ -90,7 +92,9 @@ Requires: librsvg2%{?_isa} Requires: libxmlb%{?_isa} >= %{libxmlb_version} Recommends: PackageKit%{?_isa} >= %{packagekit_version} +%if %{with langpacks} Recommends: %{name}-fedora-langpacks +%endif Obsoletes: gnome-software-snap < 3.33.1 Obsoletes: gnome-software-editor < 3.35.1 @@ -107,6 +111,7 @@ Requires: %{name}%{?_isa} = %{version}-%{release} These development files are for building gnome-software plugins outside the source tree. Most users do not need this subpackage installed. +%if %{with langpacks} %package fedora-langpacks Summary: Contains fedora-langpacks plugin Requires: %{name}%{?_isa} = %{version}-%{release} @@ -114,6 +119,7 @@ Requires: %{name}%{?_isa} = %{version}-%{release} %description fedora-langpacks The fedora-langpacks plugin ensures langpacks packages are installed for the current locale. +%endif %if %{with rpmostree} %package rpm-ostree @@ -168,6 +174,10 @@ This package includes the rpm-ostree backend. # remove unneeded dpkg plugin rm %{buildroot}%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dpkg.so +%if !%{with langpacks} +rm %{buildroot}%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so +%endif + # make the software center load faster desktop-file-edit %{buildroot}%{_datadir}/applications/org.gnome.Software.desktop \ --set-key=X-AppInstall-Package --set-value=%{name} @@ -246,8 +256,10 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libexecdir}/gnome-software-cmd %{_libexecdir}/gnome-software-restarter +%if %{with langpacks} %files fedora-langpacks %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so +%endif %if %{with rpmostree} %files rpm-ostree From 7cca703b2070afbb3f492753c361dd8d04b5529d Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 28 Jun 2024 12:12:25 +0200 Subject: [PATCH 116/163] Update to 47.alpha --- gnome-software.spec | 26 +++++++++++++++++++------- sources | 2 +- 2 files changed, 20 insertions(+), 8 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 8c9715d..9360808 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -1,10 +1,10 @@ -%global appstream_version 1.0.0~ +%global appstream_version 0.14.0 %global flatpak_version 1.9.1 %global fwupd_version 1.5.6 %global glib2_version 2.70.0 -%global gtk4_version 4.10.0 +%global gtk4_version 4.14.0 %global json_glib_version 1.6.0 -%global libadwaita_version 1.3.alpha +%global libadwaita_version 1.6~alpha %global libxmlb_version 0.1.7 %global packagekit_version 1.2.5 @@ -18,20 +18,20 @@ %bcond langpacks %[!0%{?rhel}] # this is not a library version -%define gs_plugin_version 20 +%define gs_plugin_version 21 %global tarball_version %%(echo %{version} | tr '~' '.') %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 46.2 +Version: 47~alpha Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://apps.gnome.org/Software -Source0: https://download.gnome.org/sources/gnome-software/46/%{name}-%{tarball_version}.tar.xz +Source0: https://download.gnome.org/sources/gnome-software/47/%{name}-%{tarball_version}.tar.xz # ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 @@ -44,6 +44,7 @@ BuildRequires: desktop-file-utils BuildRequires: gcc BuildRequires: gettext BuildRequires: gtk-doc +BuildRequires: itstool BuildRequires: libxslt BuildRequires: meson BuildRequires: pkgconfig(appstream) >= %{appstream_version} @@ -211,7 +212,15 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_mandir}/man1/gnome-software.1* %{_datadir}/icons/hicolor/*/apps/org.gnome.Software.svg %{_datadir}/icons/hicolor/symbolic/apps/org.gnome.Software-symbolic.svg -%{_datadir}/icons/hicolor/scalable/actions/app-remove-symbolic.svg +%{_datadir}/icons/hicolor/scalable/categories/system-component-addon.svg +%{_datadir}/icons/hicolor/scalable/categories/system-component-application.svg +%{_datadir}/icons/hicolor/scalable/categories/system-component-codecs.svg +%{_datadir}/icons/hicolor/scalable/categories/system-component-driver.svg +%{_datadir}/icons/hicolor/scalable/categories/system-component-firmware.svg +%{_datadir}/icons/hicolor/scalable/categories/system-component-input-sources.svg +%{_datadir}/icons/hicolor/scalable/categories/system-component-language.svg +%{_datadir}/icons/hicolor/scalable/categories/system-component-os-updates.svg +%{_datadir}/icons/hicolor/scalable/categories/system-component-runtime.svg %{_datadir}/metainfo/org.gnome.Software.metainfo.xml %if %{with webapps} %{_datadir}/metainfo/org.gnome.Software.Plugin.Epiphany.metainfo.xml @@ -276,6 +285,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Jun 28 2024 Milan Crha - 47~alpha-1 +- Update to 47.alpha + * Fri May 24 2024 Milan Crha - 46.2-1 - Update to 46.2 diff --git a/sources b/sources index bc7fdbd..544051e 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-46.2.tar.xz) = 4e7cccc20001ccee114508bb50e2a25968ee6fea64fb545e1174ff435cd368b2d7c928b6a182874af8e9f0c99f9f506e75c5ac9bf61b35ba0a897368ae0abc3c +SHA512 (gnome-software-47.alpha.tar.xz) = e1ec552a52d93c128918fd397a448ab34e182464543eb1bf694c54950c755a28157466f0f9b1482b1036f65a94bc148e6a0852d3232d5e28bf0eb6e9ae82b1c8 From 9d3ce3773bcb96faa58bffd4d45f08359f0b9948 Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Thu, 18 Jul 2024 03:12:21 +0000 Subject: [PATCH 117/163] Rebuilt for https://fedoraproject.org/wiki/Fedora_41_Mass_Rebuild --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 9360808..3a4d753 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -26,7 +26,7 @@ Name: gnome-software Version: 47~alpha -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -285,6 +285,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Jul 18 2024 Fedora Release Engineering - 47~alpha-2 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_41_Mass_Rebuild + * Fri Jun 28 2024 Milan Crha - 47~alpha-1 - Update to 47.alpha From 5897c8b5747e95ea91b2fa9edbcd118dc3adf562 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 2 Aug 2024 09:34:24 +0200 Subject: [PATCH 118/163] Update to 47.beta --- gnome-software.spec | 19 +++++-------------- sources | 2 +- 2 files changed, 6 insertions(+), 15 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 3a4d753..8389288 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -14,8 +14,6 @@ %bcond malcontent %[!0%{?rhel}] # Disable rpm-ostree support for RHEL builds %bcond rpmostree %[!0%{?rhel}] -# Disable fedora-langpacks subpackage for RHEL builds -%bcond langpacks %[!0%{?rhel}] # this is not a library version %define gs_plugin_version 21 @@ -25,8 +23,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 47~alpha -Release: 2%{?dist} +Version: 47~beta +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -93,9 +91,7 @@ Requires: librsvg2%{?_isa} Requires: libxmlb%{?_isa} >= %{libxmlb_version} Recommends: PackageKit%{?_isa} >= %{packagekit_version} -%if %{with langpacks} Recommends: %{name}-fedora-langpacks -%endif Obsoletes: gnome-software-snap < 3.33.1 Obsoletes: gnome-software-editor < 3.35.1 @@ -112,7 +108,6 @@ Requires: %{name}%{?_isa} = %{version}-%{release} These development files are for building gnome-software plugins outside the source tree. Most users do not need this subpackage installed. -%if %{with langpacks} %package fedora-langpacks Summary: Contains fedora-langpacks plugin Requires: %{name}%{?_isa} = %{version}-%{release} @@ -120,7 +115,6 @@ Requires: %{name}%{?_isa} = %{version}-%{release} %description fedora-langpacks The fedora-langpacks plugin ensures langpacks packages are installed for the current locale. -%endif %if %{with rpmostree} %package rpm-ostree @@ -175,10 +169,6 @@ This package includes the rpm-ostree backend. # remove unneeded dpkg plugin rm %{buildroot}%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dpkg.so -%if !%{with langpacks} -rm %{buildroot}%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so -%endif - # make the software center load faster desktop-file-edit %{buildroot}%{_datadir}/applications/org.gnome.Software.desktop \ --set-key=X-AppInstall-Package --set-value=%{name} @@ -265,10 +255,8 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libexecdir}/gnome-software-cmd %{_libexecdir}/gnome-software-restarter -%if %{with langpacks} %files fedora-langpacks %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so -%endif %if %{with rpmostree} %files rpm-ostree @@ -285,6 +273,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Aug 02 2024 Milan Crha - 47~beta-1 +- Update to 47.beta + * Thu Jul 18 2024 Fedora Release Engineering - 47~alpha-2 - Rebuilt for https://fedoraproject.org/wiki/Fedora_41_Mass_Rebuild diff --git a/sources b/sources index 544051e..becf8db 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-47.alpha.tar.xz) = e1ec552a52d93c128918fd397a448ab34e182464543eb1bf694c54950c755a28157466f0f9b1482b1036f65a94bc148e6a0852d3232d5e28bf0eb6e9ae82b1c8 +SHA512 (gnome-software-47.beta.tar.xz) = e9e0daa489ac302d82901f689c553a67725b18c200d4d5c4b9d9bad648db47c2d51067bf3b2200258a73a8ce5e5dfb9bc05d4c389dd5353735842a0f1c82f964 From 1016f497ea8767f1963a833695fd9705ea4afce9 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 2 Aug 2024 09:40:32 +0200 Subject: [PATCH 119/163] Build with DKMS/akmods plugin in Fedora --- gnome-software.spec | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 8389288..37f4d6c 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -14,6 +14,8 @@ %bcond malcontent %[!0%{?rhel}] # Disable rpm-ostree support for RHEL builds %bcond rpmostree %[!0%{?rhel}] +# Disable DKMS/akmods support for RHEL builds +%bcond dkms %[!0%{?rhel}] # this is not a library version %define gs_plugin_version 21 @@ -159,6 +161,11 @@ This package includes the rpm-ostree backend. -Dwebapps=false \ -Dhardcoded_foss_webapps=false \ -Dhardcoded_proprietary_webapps=false \ +%endif +%if %{with dkms} + -Ddkms=true \ +%else + -Ddkms=false \ %endif -Dtests=false %meson_build @@ -166,8 +173,9 @@ This package includes the rpm-ostree backend. %install %meson_install -# remove unneeded dpkg plugin +# remove unneeded dpkg and dummy plugins rm %{buildroot}%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dpkg.so +rm %{buildroot}%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dummy.so # make the software center load faster desktop-file-edit %{buildroot}%{_datadir}/applications/org.gnome.Software.desktop \ @@ -220,7 +228,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %dir %{_libdir}/gnome-software/plugins-%{gs_plugin_version} %{_libdir}/gnome-software/libgnomesoftware.so.%{gs_plugin_version} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_appstream.so -%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dummy.so %if %{with webapps} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_epiphany.so %endif @@ -255,6 +262,12 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libexecdir}/gnome-software-cmd %{_libexecdir}/gnome-software-restarter +%if %{with dkms} +%{_datadir}/polkit-1/actions/org.gnome.software.dkms-helper.policy +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dkms.so +%{_libexecdir}/gnome-software-dkms-helper +%endif + %files fedora-langpacks %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_fedora-langpacks.so @@ -275,6 +288,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %changelog * Fri Aug 02 2024 Milan Crha - 47~beta-1 - Update to 47.beta +- Build with DKMS/akmods plugin in Fedora * Thu Jul 18 2024 Fedora Release Engineering - 47~alpha-2 - Rebuilt for https://fedoraproject.org/wiki/Fedora_41_Mass_Rebuild From 2c9dde7b621515f832d57866492a3dccbe67dc48 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 30 Aug 2024 11:32:32 +0200 Subject: [PATCH 120/163] Update to 47.rc --- gnome-software.spec | 5 ++++- sources | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 37f4d6c..d9c30f5 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -25,7 +25,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 47~beta +Version: 47~rc Release: 1%{?dist} Summary: A software center for GNOME @@ -286,6 +286,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Aug 30 2024 Milan Crha - 47~rc-1 +- Update to 47.rc + * Fri Aug 02 2024 Milan Crha - 47~beta-1 - Update to 47.beta - Build with DKMS/akmods plugin in Fedora diff --git a/sources b/sources index becf8db..d9246ad 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-47.beta.tar.xz) = e9e0daa489ac302d82901f689c553a67725b18c200d4d5c4b9d9bad648db47c2d51067bf3b2200258a73a8ce5e5dfb9bc05d4c389dd5353735842a0f1c82f964 +SHA512 (gnome-software-47.rc.tar.xz) = 6e86d964ce634e1a19910227fce554ed45652f047977dbcefe5d2f564273b1d6ef00a4c7f4bd84103b176efe13daf4c1f01ab0049e1dc751a22b4ff4fae5110f From 399c9361bb329921a20ca40db893c12d5f16d911 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 13 Sep 2024 09:54:36 +0200 Subject: [PATCH 121/163] Update to 47.0 --- gnome-software.spec | 8 +++++--- sources | 2 +- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index d9c30f5..16e66c7 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -25,7 +25,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 47~rc +Version: 47.0 Release: 1%{?dist} Summary: A software center for GNOME @@ -83,6 +83,7 @@ Requires: flatpak%{?_isa} >= %{flatpak_version} Requires: flatpak-libs%{?_isa} >= %{flatpak_version} Requires: fwupd%{?_isa} >= %{fwupd_version} Requires: glib2%{?_isa} >= %{glib2_version} +Requires: gnome-app-list # gnome-menus is needed for app folder .directory entries Requires: gnome-menus%{?_isa} Requires: gsettings-desktop-schemas%{?_isa} @@ -252,8 +253,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %if %{with webapps} %{_datadir}/swcatalog/xml/gnome-pwa-list-foss.xml %endif -%{_datadir}/swcatalog/xml/org.gnome.Software.Curated.xml -%{_datadir}/swcatalog/xml/org.gnome.Software.Featured.xml %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service %{_datadir}/dbus-1/services/org.gnome.Software.service %{_datadir}/gnome-shell/search-providers/org.gnome.Software-search-provider.ini @@ -286,6 +285,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Sep 13 2024 Milan Crha - 47.0-1 +- Update to 47.0 + * Fri Aug 30 2024 Milan Crha - 47~rc-1 - Update to 47.rc diff --git a/sources b/sources index d9246ad..ed97419 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-47.rc.tar.xz) = 6e86d964ce634e1a19910227fce554ed45652f047977dbcefe5d2f564273b1d6ef00a4c7f4bd84103b176efe13daf4c1f01ab0049e1dc751a22b4ff4fae5110f +SHA512 (gnome-software-47.0.tar.xz) = 0aac8e2f9803fbdef9e07c798d3171eb6267090fc1ffcbe1e4888e2499a50c28ec4a817ec82205f1eeb4e3220f11920ff045b817b692c8b1f8e5edbdbd82b6b9 From c60a0c56916812752505c72b9f11e4ea9629b2de Mon Sep 17 00:00:00 2001 From: Yaakov Selkowitz Date: Mon, 16 Sep 2024 23:06:52 -0400 Subject: [PATCH 122/163] Fix ELN build With gnome-app-list split out from gnome-software, only the webapps-related data is installed into swcatalog, and therefore those directories are not created when webapps are disabled (as in RHEL). While c10s does bundle a list file and therefore creates these directories, it is too early to know what this will look like for RHEL 11. --- gnome-software.spec | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 16e66c7..89b3eb2 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -83,7 +83,9 @@ Requires: flatpak%{?_isa} >= %{flatpak_version} Requires: flatpak-libs%{?_isa} >= %{flatpak_version} Requires: fwupd%{?_isa} >= %{fwupd_version} Requires: glib2%{?_isa} >= %{glib2_version} +%if !0%{?rhel} Requires: gnome-app-list +%endif # gnome-menus is needed for app folder .directory entries Requires: gnome-menus%{?_isa} Requires: gsettings-desktop-schemas%{?_isa} @@ -248,9 +250,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_repos.so %{_sysconfdir}/xdg/autostart/org.gnome.Software.desktop +%if %{with webapps} %dir %{_datadir}/swcatalog %dir %{_datadir}/swcatalog/xml -%if %{with webapps} %{_datadir}/swcatalog/xml/gnome-pwa-list-foss.xml %endif %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service From 287e223c6ea7d1f6a23c930c5728f4492c869e00 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Thu, 19 Sep 2024 13:00:50 +0200 Subject: [PATCH 123/163] Resolves: #2312882 (dkms: Fix callback user data in a reload() function) --- ...lback-user-data-in-a-reload-function.patch | 30 +++++++++++++++++++ gnome-software.spec | 7 ++++- 2 files changed, 36 insertions(+), 1 deletion(-) create mode 100644 0001-dkms-Fix-callback-user-data-in-a-reload-function.patch diff --git a/0001-dkms-Fix-callback-user-data-in-a-reload-function.patch b/0001-dkms-Fix-callback-user-data-in-a-reload-function.patch new file mode 100644 index 0000000..e44003e --- /dev/null +++ b/0001-dkms-Fix-callback-user-data-in-a-reload-function.patch @@ -0,0 +1,30 @@ +From 6b29a361465fb9b70c3a4cd66615e200bef65cd6 Mon Sep 17 00:00:00 2001 +Date: Wed, 18 Sep 2024 07:16:42 +0200 +Subject: [PATCH] dkms: Fix callback user data in a reload() function + +The gs_dkms_got_secureboot_state_cb() expects a GTask as its user data, +but the gs_plugin_dkms_reload() passed a GsPlugin instead. That could +cause a crash. + +Reported downstream at: +https://bugzilla.redhat.com/show_bug.cgi?id=2312882 +--- + plugins/dkms/gs-plugin-dkms.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/plugins/dkms/gs-plugin-dkms.c b/plugins/dkms/gs-plugin-dkms.c +index f7971334f..eb423e08d 100644 +--- a/plugins/dkms/gs-plugin-dkms.c ++++ b/plugins/dkms/gs-plugin-dkms.c +@@ -83,7 +83,7 @@ gs_plugin_dkms_reload (GsPlugin *plugin) + + /* mokutil was not installed probably; the reload can be called when some + app/package had been installed, thus re-try to check Secure Boot state */ +- gs_dkms_get_secureboot_state_async (NULL, gs_dkms_got_secureboot_state_cb, g_object_ref (plugin)); ++ gs_dkms_get_secureboot_state_async (NULL, gs_dkms_got_secureboot_state_cb, g_steal_pointer (&task)); + } + } + +-- +2.45.2 + diff --git a/gnome-software.spec b/gnome-software.spec index 89b3eb2..6493449 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -26,13 +26,15 @@ Name: gnome-software Version: 47.0 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://apps.gnome.org/Software Source0: https://download.gnome.org/sources/gnome-software/47/%{name}-%{tarball_version}.tar.xz +Patch: 0001-dkms-Fix-callback-user-data-in-a-reload-function.patch + # ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 %if 0%{?fedora} || 0%{?rhel} >= 10 @@ -287,6 +289,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Sep 19 2024 Milan Crha - 47.0-2 +- Resolves: #2312882 (dkms: Fix callback user data in a reload() function) + * Fri Sep 13 2024 Milan Crha - 47.0-1 - Update to 47.0 From 8459c63d07257e0d29400db904cb772033d4026b Mon Sep 17 00:00:00 2001 From: Richard Hughes Date: Fri, 4 Oct 2024 16:47:40 +0100 Subject: [PATCH 124/163] Rebuild against libfwupd.so.3 --- ...not-use-API-removed-from-fwupd-2.0.x.patch | 45 +++++++++++++++++++ gnome-software.spec | 6 ++- 2 files changed, 50 insertions(+), 1 deletion(-) create mode 100644 0001-fwupd-Do-not-use-API-removed-from-fwupd-2.0.x.patch diff --git a/0001-fwupd-Do-not-use-API-removed-from-fwupd-2.0.x.patch b/0001-fwupd-Do-not-use-API-removed-from-fwupd-2.0.x.patch new file mode 100644 index 0000000..78bd0b9 --- /dev/null +++ b/0001-fwupd-Do-not-use-API-removed-from-fwupd-2.0.x.patch @@ -0,0 +1,45 @@ +From bdfe5c691a1c3302cf61da0781b290c67f88ba6b Mon Sep 17 00:00:00 2001 +From: Richard Hughes +Date: Tue, 1 Oct 2024 12:24:09 +0100 +Subject: [PATCH 14/14] fwupd: Do not use API removed from fwupd 2.0.x + +All the systemd-offline logic was unused, and so removed. +--- + plugins/fwupd/gs-fwupd-app.c | 5 ----- + plugins/fwupd/gs-plugin-fwupd.c | 4 ---- + 2 files changed, 9 deletions(-) + +diff --git a/plugins/fwupd/gs-fwupd-app.c b/plugins/fwupd/gs-fwupd-app.c +index bad97420a..e4376b265 100644 +--- a/plugins/fwupd/gs-fwupd-app.c ++++ b/plugins/fwupd/gs-fwupd-app.c +@@ -117,11 +117,6 @@ gs_fwupd_app_set_from_device (GsApp *app, + ) + gs_app_set_state (app, GS_APP_STATE_UPDATABLE_LIVE); + +- /* only can be applied in systemd-offline */ +- if (fwupd_device_has_flag (dev, FWUPD_DEVICE_FLAG_ONLY_OFFLINE)) +- gs_app_set_metadata (app, "fwupd::OnlyOffline", ""); +- +- + /* reboot required to apply update */ + if (fwupd_device_has_flag (dev, FWUPD_DEVICE_FLAG_NEEDS_REBOOT)) + gs_app_add_quirk (app, GS_APP_QUIRK_NEEDS_REBOOT); +diff --git a/plugins/fwupd/gs-plugin-fwupd.c b/plugins/fwupd/gs-plugin-fwupd.c +index fd6049055..8e3d8ab2c 100644 +--- a/plugins/fwupd/gs-plugin-fwupd.c ++++ b/plugins/fwupd/gs-plugin-fwupd.c +@@ -1430,10 +1430,6 @@ gs_plugin_fwupd_install_async (GsPluginFwupd *self, + * https://github.com/fwupd/fwupd/issues/5522. */ + g_set_object (&self->app_current, app); + +- /* only offline supported */ +- if (gs_app_get_metadata_item (app, "fwupd::OnlyOffline") != NULL) +- install_flags |= FWUPD_INSTALL_FLAG_OFFLINE; +- + gs_app_set_state (app, GS_APP_STATE_INSTALLING); + + fwupd_client_install_async (self->client, data->device_id, +-- +2.46.2 + diff --git a/gnome-software.spec b/gnome-software.spec index 6493449..06e77c9 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -26,7 +26,7 @@ Name: gnome-software Version: 47.0 -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -34,6 +34,7 @@ URL: https://apps.gnome.org/Software Source0: https://download.gnome.org/sources/gnome-software/47/%{name}-%{tarball_version}.tar.xz Patch: 0001-dkms-Fix-callback-user-data-in-a-reload-function.patch +Patch: 0001-fwupd-Do-not-use-API-removed-from-fwupd-2.0.x.patch # ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 @@ -289,6 +290,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Oct 04 2024 Richard Hughes - 47.0-3 +- Rebuild against fwupd 2.0.0 + * Thu Sep 19 2024 Milan Crha - 47.0-2 - Resolves: #2312882 (dkms: Fix callback user data in a reload() function) From 8bf3c4e72093b33e50e2f733699ae1708675b1a2 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Thu, 10 Oct 2024 14:58:22 +0200 Subject: [PATCH 125/163] Update to 47.1 --- ...lback-user-data-in-a-reload-function.patch | 30 ------------- ...not-use-API-removed-from-fwupd-2.0.x.patch | 45 ------------------- gnome-software.spec | 11 +++-- sources | 2 +- 4 files changed, 6 insertions(+), 82 deletions(-) delete mode 100644 0001-dkms-Fix-callback-user-data-in-a-reload-function.patch delete mode 100644 0001-fwupd-Do-not-use-API-removed-from-fwupd-2.0.x.patch diff --git a/0001-dkms-Fix-callback-user-data-in-a-reload-function.patch b/0001-dkms-Fix-callback-user-data-in-a-reload-function.patch deleted file mode 100644 index e44003e..0000000 --- a/0001-dkms-Fix-callback-user-data-in-a-reload-function.patch +++ /dev/null @@ -1,30 +0,0 @@ -From 6b29a361465fb9b70c3a4cd66615e200bef65cd6 Mon Sep 17 00:00:00 2001 -Date: Wed, 18 Sep 2024 07:16:42 +0200 -Subject: [PATCH] dkms: Fix callback user data in a reload() function - -The gs_dkms_got_secureboot_state_cb() expects a GTask as its user data, -but the gs_plugin_dkms_reload() passed a GsPlugin instead. That could -cause a crash. - -Reported downstream at: -https://bugzilla.redhat.com/show_bug.cgi?id=2312882 ---- - plugins/dkms/gs-plugin-dkms.c | 2 +- - 1 file changed, 1 insertion(+), 1 deletion(-) - -diff --git a/plugins/dkms/gs-plugin-dkms.c b/plugins/dkms/gs-plugin-dkms.c -index f7971334f..eb423e08d 100644 ---- a/plugins/dkms/gs-plugin-dkms.c -+++ b/plugins/dkms/gs-plugin-dkms.c -@@ -83,7 +83,7 @@ gs_plugin_dkms_reload (GsPlugin *plugin) - - /* mokutil was not installed probably; the reload can be called when some - app/package had been installed, thus re-try to check Secure Boot state */ -- gs_dkms_get_secureboot_state_async (NULL, gs_dkms_got_secureboot_state_cb, g_object_ref (plugin)); -+ gs_dkms_get_secureboot_state_async (NULL, gs_dkms_got_secureboot_state_cb, g_steal_pointer (&task)); - } - } - --- -2.45.2 - diff --git a/0001-fwupd-Do-not-use-API-removed-from-fwupd-2.0.x.patch b/0001-fwupd-Do-not-use-API-removed-from-fwupd-2.0.x.patch deleted file mode 100644 index 78bd0b9..0000000 --- a/0001-fwupd-Do-not-use-API-removed-from-fwupd-2.0.x.patch +++ /dev/null @@ -1,45 +0,0 @@ -From bdfe5c691a1c3302cf61da0781b290c67f88ba6b Mon Sep 17 00:00:00 2001 -From: Richard Hughes -Date: Tue, 1 Oct 2024 12:24:09 +0100 -Subject: [PATCH 14/14] fwupd: Do not use API removed from fwupd 2.0.x - -All the systemd-offline logic was unused, and so removed. ---- - plugins/fwupd/gs-fwupd-app.c | 5 ----- - plugins/fwupd/gs-plugin-fwupd.c | 4 ---- - 2 files changed, 9 deletions(-) - -diff --git a/plugins/fwupd/gs-fwupd-app.c b/plugins/fwupd/gs-fwupd-app.c -index bad97420a..e4376b265 100644 ---- a/plugins/fwupd/gs-fwupd-app.c -+++ b/plugins/fwupd/gs-fwupd-app.c -@@ -117,11 +117,6 @@ gs_fwupd_app_set_from_device (GsApp *app, - ) - gs_app_set_state (app, GS_APP_STATE_UPDATABLE_LIVE); - -- /* only can be applied in systemd-offline */ -- if (fwupd_device_has_flag (dev, FWUPD_DEVICE_FLAG_ONLY_OFFLINE)) -- gs_app_set_metadata (app, "fwupd::OnlyOffline", ""); -- -- - /* reboot required to apply update */ - if (fwupd_device_has_flag (dev, FWUPD_DEVICE_FLAG_NEEDS_REBOOT)) - gs_app_add_quirk (app, GS_APP_QUIRK_NEEDS_REBOOT); -diff --git a/plugins/fwupd/gs-plugin-fwupd.c b/plugins/fwupd/gs-plugin-fwupd.c -index fd6049055..8e3d8ab2c 100644 ---- a/plugins/fwupd/gs-plugin-fwupd.c -+++ b/plugins/fwupd/gs-plugin-fwupd.c -@@ -1430,10 +1430,6 @@ gs_plugin_fwupd_install_async (GsPluginFwupd *self, - * https://github.com/fwupd/fwupd/issues/5522. */ - g_set_object (&self->app_current, app); - -- /* only offline supported */ -- if (gs_app_get_metadata_item (app, "fwupd::OnlyOffline") != NULL) -- install_flags |= FWUPD_INSTALL_FLAG_OFFLINE; -- - gs_app_set_state (app, GS_APP_STATE_INSTALLING); - - fwupd_client_install_async (self->client, data->device_id, --- -2.46.2 - diff --git a/gnome-software.spec b/gnome-software.spec index 06e77c9..849bd92 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -25,17 +25,14 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 47.0 -Release: 3%{?dist} +Version: 47.1 +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://apps.gnome.org/Software Source0: https://download.gnome.org/sources/gnome-software/47/%{name}-%{tarball_version}.tar.xz -Patch: 0001-dkms-Fix-callback-user-data-in-a-reload-function.patch -Patch: 0001-fwupd-Do-not-use-API-removed-from-fwupd-2.0.x.patch - # ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 %if 0%{?fedora} || 0%{?rhel} >= 10 @@ -143,7 +140,6 @@ This package includes the rpm-ostree backend. %build %meson \ - -Dsoup2=false \ -Dsnap=false \ %if %{with malcontent} -Dmalcontent=true \ @@ -290,6 +286,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Oct 10 2024 Milan Crha - 47.1-1 +- Update to 47.1 + * Fri Oct 04 2024 Richard Hughes - 47.0-3 - Rebuild against fwupd 2.0.0 diff --git a/sources b/sources index ed97419..ee2d17f 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-47.0.tar.xz) = 0aac8e2f9803fbdef9e07c798d3171eb6267090fc1ffcbe1e4888e2499a50c28ec4a817ec82205f1eeb4e3220f11920ff045b817b692c8b1f8e5edbdbd82b6b9 +SHA512 (gnome-software-47.1.tar.xz) = 18c500ef0487f9303097f939e11d2841df87d609d05484e3d4419ce9a27f6156ec4aabeca61191724d557b5603ff7857095ed09fc065b6064d0b92286bc19748 From 79f3e3a0c8c6cde3880c1f5b6cf39c00e4c758fd Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 25 Nov 2024 14:36:36 +0100 Subject: [PATCH 126/163] Update to 47.2 --- gnome-software.spec | 7 ++++++- sources | 2 +- 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 849bd92..9693dd6 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -25,7 +25,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 47.1 +Version: 47.2 Release: 1%{?dist} Summary: A software center for GNOME @@ -89,8 +89,10 @@ Requires: gnome-app-list # gnome-menus is needed for app folder .directory entries Requires: gnome-menus%{?_isa} Requires: gsettings-desktop-schemas%{?_isa} +Requires: gtk4 >= %{gtk4_version} Requires: json-glib%{?_isa} >= %{json_glib_version} Requires: iso-codes +Requires: libadwaita >= %{libadwaita_version} # librsvg2 is needed for gdk-pixbuf svg loader Requires: librsvg2%{?_isa} Requires: libxmlb%{?_isa} >= %{libxmlb_version} @@ -286,6 +288,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Mon Nov 25 2024 Milan Crha - 47.2-1 +- Update to 47.2 + * Thu Oct 10 2024 Milan Crha - 47.1-1 - Update to 47.1 diff --git a/sources b/sources index ee2d17f..4b9ac1c 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-47.1.tar.xz) = 18c500ef0487f9303097f939e11d2841df87d609d05484e3d4419ce9a27f6156ec4aabeca61191724d557b5603ff7857095ed09fc065b6064d0b92286bc19748 +SHA512 (gnome-software-47.2.tar.xz) = 60de4a3c3237bfdc0dbbefdeccb00c97af7332a36c6beb5610fb6a416508e8b4712fd007e395ad283a3f9cb8d3e0f3a56c134ff28b3f22953a448188a1005cb6 From 0dd97896b5b14544057ab9c8c6629bcb9bde6364 Mon Sep 17 00:00:00 2001 From: Yaakov Selkowitz Date: Thu, 5 Dec 2024 16:04:14 -0500 Subject: [PATCH 127/163] Rebuild for fwupd 2.0 The ELN build of fwupd 2.0, which included an ABI version change, was delayed until now. --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 9693dd6..d744445 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -26,7 +26,7 @@ Name: gnome-software Version: 47.2 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -288,6 +288,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Dec 05 2024 Yaakov Selkowitz - 47.2-2 +- Rebuild for fwupd 2.0 + * Mon Nov 25 2024 Milan Crha - 47.2-1 - Update to 47.2 From 6263c5e777f454dff0a865042bf767484847552e Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 9 Dec 2024 10:57:46 +0100 Subject: [PATCH 128/163] Resolves: #2272232 (Crash under gs_appstream_gather_merge_data()) --- ...under-gs_appstream_gather_merge_data.patch | 1468 +++++++++++++++++ gnome-software.spec | 7 +- 2 files changed, 1474 insertions(+), 1 deletion(-) create mode 100644 0001-crash-under-gs_appstream_gather_merge_data.patch diff --git a/0001-crash-under-gs_appstream_gather_merge_data.patch b/0001-crash-under-gs_appstream_gather_merge_data.patch new file mode 100644 index 0000000..b52cefd --- /dev/null +++ b/0001-crash-under-gs_appstream_gather_merge_data.patch @@ -0,0 +1,1468 @@ +From f1140fd98666fbdb35dfe13a6b3f58fedcb1ad0b Mon Sep 17 00:00:00 2001 +Date: Mon, 29 Apr 2024 17:37:57 +0200 +Subject: [PATCH 1/3] gs-plugin-appstream: Simplify XbSilo locking + +Instead of holding RW lock on the internal silo variable, simply return +a reference to it and work with it like with an immutable object. That +simplifies locking and makes the code cleaner. It can also make the code +quicker, in some cases. +--- + plugins/core/gs-plugin-appstream.c | 194 ++++++++++++++++------------- + 1 file changed, 107 insertions(+), 87 deletions(-) + +diff --git a/plugins/core/gs-plugin-appstream.c b/plugins/core/gs-plugin-appstream.c +index 7ccbac12a5..5749a175f3 100644 +--- a/plugins/core/gs-plugin-appstream.c ++++ b/plugins/core/gs-plugin-appstream.c +@@ -36,7 +36,7 @@ struct _GsPluginAppstream + GsWorkerThread *worker; /* (owned) */ + + XbSilo *silo; +- GRWLock silo_lock; ++ GMutex silo_lock; + gchar *silo_filename; + GHashTable *silo_installed_by_desktopid; + GHashTable *silo_installed_by_id; +@@ -65,7 +65,7 @@ gs_plugin_appstream_dispose (GObject *object) + g_clear_pointer (&self->silo_installed_by_desktopid, g_hash_table_unref); + g_clear_pointer (&self->silo_installed_by_id, g_hash_table_unref); + g_clear_object (&self->settings); +- g_rw_lock_clear (&self->silo_lock); ++ g_mutex_clear (&self->silo_lock); + g_clear_object (&self->worker); + g_clear_pointer (&self->file_monitors, g_ptr_array_unref); + +@@ -77,9 +77,7 @@ gs_plugin_appstream_init (GsPluginAppstream *self) + { + GApplication *application = g_application_get_default (); + +- /* XbSilo needs external locking as we destroy the silo and build a new +- * one when something changes */ +- g_rw_lock_init (&self->silo_lock); ++ g_mutex_init (&self->silo_lock); + + /* require settings */ + self->settings = g_settings_new ("org.gnome.software"); +@@ -530,10 +528,13 @@ gs_add_appstream_metainfo_location (GPtrArray *locations, const gchar *root) + g_build_filename (root, "appdata", NULL)); + } + +-static gboolean +-gs_plugin_appstream_check_silo (GsPluginAppstream *self, +- GCancellable *cancellable, +- GError **error) ++static XbSilo * ++gs_plugin_appstream_ref_silo (GsPluginAppstream *self, ++ gchar **out_silo_filename, ++ GHashTable **out_silo_installed_by_desktopid, ++ GHashTable **out_silo_installed_by_id, ++ GCancellable *cancellable, ++ GError **error) + { + const gchar *test_xml; + g_autofree gchar *blobfn = NULL; +@@ -541,21 +542,25 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, + g_autoptr(XbNode) n = NULL; + g_autoptr(GFile) file = NULL; + g_autoptr(GPtrArray) installed = NULL; +- g_autoptr(GRWLockReaderLocker) reader_locker = NULL; +- g_autoptr(GRWLockWriterLocker) writer_locker = NULL; ++ g_autoptr(GMutexLocker) locker = NULL; + g_autoptr(GPtrArray) parent_appdata = g_ptr_array_new_with_free_func (g_free); + g_autoptr(GPtrArray) parent_appstream = NULL; + g_autoptr(GMainContext) old_thread_default = NULL; + +- reader_locker = g_rw_lock_reader_locker_new (&self->silo_lock); ++ locker = g_mutex_locker_new (&self->silo_lock); + /* everything is okay */ + if (self->silo != NULL && xb_silo_is_valid (self->silo) && +- g_atomic_int_get (&self->file_monitor_stamp_current) == g_atomic_int_get (&self->file_monitor_stamp)) +- return TRUE; +- g_clear_pointer (&reader_locker, g_rw_lock_reader_locker_free); ++ g_atomic_int_get (&self->file_monitor_stamp_current) == g_atomic_int_get (&self->file_monitor_stamp)) { ++ if (out_silo_filename != NULL) ++ *out_silo_filename = g_strdup (self->silo_filename); ++ if (out_silo_installed_by_desktopid != NULL) ++ *out_silo_installed_by_desktopid = self->silo_installed_by_desktopid ? g_hash_table_ref (self->silo_installed_by_desktopid) : NULL; ++ if (out_silo_installed_by_id != NULL) ++ *out_silo_installed_by_id = self->silo_installed_by_id ? g_hash_table_ref (self->silo_installed_by_id) : NULL; ++ return g_object_ref (self->silo); ++ } + + /* drat! silo needs regenerating */ +- writer_locker = g_rw_lock_writer_locker_new (&self->silo_lock); + reload: + g_clear_object (&self->silo); + g_clear_pointer (&self->silo_filename, g_free); +@@ -594,7 +599,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, + if (!xb_builder_source_load_xml (source, test_xml, + XB_BUILDER_SOURCE_FLAG_NONE, + error)) +- return FALSE; ++ return NULL; + fixup1 = xb_builder_fixup_new ("AddOriginKeywords", + gs_plugin_appstream_add_origin_keyword_cb, + self, NULL); +@@ -640,7 +645,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, + if (!gs_plugin_appstream_load_appstream (self, builder, fn, cancellable, error)) { + if (old_thread_default != NULL) + g_main_context_push_thread_default (old_thread_default); +- return FALSE; ++ return NULL; + } + } + for (guint i = 0; i < parent_appdata->len; i++) { +@@ -648,7 +653,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, + if (!gs_plugin_appstream_load_appdata (self, builder, fn, cancellable, error)) { + if (old_thread_default != NULL) + g_main_context_push_thread_default (old_thread_default); +- return FALSE; ++ return NULL; + } + } + for (guint i = 0; i < parent_desktop->len; i++) { +@@ -657,7 +662,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, + if (!gs_appstream_load_desktop_files (builder, dir, NULL, &file_monitor, cancellable, error)) { + if (old_thread_default != NULL) + g_main_context_push_thread_default (old_thread_default); +- return FALSE; ++ return NULL; + } + gs_plugin_appstream_maybe_store_file_monitor (self, file_monitor); + } +@@ -678,7 +683,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, + GS_UTILS_CACHE_FLAG_CREATE_DIRECTORY, + error); + if (blobfn == NULL) +- return FALSE; ++ return NULL; + file = g_file_new_for_path (blobfn); + g_debug ("ensuring %s", blobfn); + +@@ -696,7 +701,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, + if (self->silo == NULL) { + if (old_thread_default != NULL) + g_main_context_push_thread_default (old_thread_default); +- return FALSE; ++ return NULL; + } + + if (old_thread_default != NULL) +@@ -717,7 +722,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, + GS_PLUGIN_ERROR, + GS_PLUGIN_ERROR_NOT_SUPPORTED, + "No AppStream data found"); +- return FALSE; ++ return NULL; + } + + g_clear_object (&n); +@@ -768,7 +773,13 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, + } + + /* success */ +- return TRUE; ++ if (out_silo_filename != NULL) ++ *out_silo_filename = g_strdup (self->silo_filename); ++ if (out_silo_installed_by_desktopid != NULL) ++ *out_silo_installed_by_desktopid = self->silo_installed_by_desktopid ? g_hash_table_ref (self->silo_installed_by_desktopid) : NULL; ++ if (out_silo_installed_by_id != NULL) ++ *out_silo_installed_by_id = self->silo_installed_by_id ? g_hash_table_ref (self->silo_installed_by_id) : NULL; ++ return g_object_ref (self->silo); + } + + static void +@@ -776,7 +787,6 @@ gs_plugin_appstream_reload (GsPlugin *plugin) + { + GsPluginAppstream *self; + g_autoptr(GsAppList) list = NULL; +- g_autoptr(GRWLockWriterLocker) writer_locker = NULL; + guint sz; + + g_return_if_fail (GS_IS_PLUGIN_APPSTREAM (plugin)); +@@ -790,9 +800,8 @@ gs_plugin_appstream_reload (GsPlugin *plugin) + } + + self = GS_PLUGIN_APPSTREAM (plugin); +- writer_locker = g_rw_lock_writer_locker_new (&self->silo_lock); +- if (self->silo != NULL) +- xb_silo_invalidate (self->silo); ++ /* simpler than getting the silo and setting it invalid */ ++ g_atomic_int_inc (&self->file_monitor_stamp); + } + + static gint +@@ -834,11 +843,13 @@ setup_thread_cb (GTask *task, + GCancellable *cancellable) + { + GsPluginAppstream *self = GS_PLUGIN_APPSTREAM (source_object); ++ g_autoptr(XbSilo) silo = NULL; + g_autoptr(GError) local_error = NULL; + + assert_in_worker (self); + +- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) ++ silo = gs_plugin_appstream_ref_silo (self, NULL, NULL, NULL, cancellable, &local_error); ++ if (silo == NULL) + g_task_return_error (task, g_steal_pointer (&local_error)); + else + g_task_return_boolean (task, TRUE); +@@ -910,21 +921,21 @@ url_to_app_thread_cb (GTask *task, + GsPluginAppstream *self = GS_PLUGIN_APPSTREAM (source_object); + GsPluginUrlToAppData *data = task_data; + g_autoptr(GsAppList) list = NULL; +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; + g_autoptr(GError) local_error = NULL; + + assert_in_worker (self); + + /* check silo is valid */ +- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) { ++ silo = gs_plugin_appstream_ref_silo (self, NULL, NULL, NULL, cancellable, &local_error); ++ if (silo == NULL) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + +- locker = g_rw_lock_reader_locker_new (&self->silo_lock); + list = gs_app_list_new (); + +- if (gs_appstream_url_to_app (GS_PLUGIN (self), self->silo, list, data->url, cancellable, &local_error)) ++ if (gs_appstream_url_to_app (GS_PLUGIN (self), silo, list, data->url, cancellable, &local_error)) + g_task_return_pointer (task, g_steal_pointer (&list), g_object_unref); + else + g_task_return_error (task, g_steal_pointer (&local_error)); +@@ -1006,17 +1017,14 @@ gs_plugin_appstream_set_compulsory_quirk (GsApp *app, XbNode *component) + static gboolean + gs_plugin_appstream_refine_state (GsPluginAppstream *self, + GsApp *app, ++ GHashTable *silo_installed_by_id, + GError **error) + { +- g_autoptr(GRWLockReaderLocker) locker = NULL; +- + /* Ignore apps with no ID */ +- if (gs_app_get_id (app) == NULL) ++ if (gs_app_get_id (app) == NULL || silo_installed_by_id == NULL) + return TRUE; + +- locker = g_rw_lock_reader_locker_new (&self->silo_lock); +- +- if (g_hash_table_contains (self->silo_installed_by_id, gs_app_get_id (app))) ++ if (g_hash_table_contains (silo_installed_by_id, gs_app_get_id (app))) + gs_app_set_state (app, GS_APP_STATE_INSTALLED); + return TRUE; + } +@@ -1027,20 +1035,21 @@ gs_plugin_refine_from_id (GsPluginAppstream *self, + GsPluginRefineFlags flags, + GHashTable *apps_by_id, + GHashTable *apps_by_origin_and_id, ++ XbSilo *silo, ++ const gchar *silo_filename, ++ GHashTable *silo_installed_by_desktopid, ++ GHashTable *silo_installed_by_id, + gboolean *found, + GError **error) + { + const gchar *id, *origin; + GPtrArray *components; +- g_autoptr(GRWLockReaderLocker) locker = NULL; + + /* not enough info to find */ + id = gs_app_get_id (app); + if (id == NULL) + return TRUE; + +- locker = g_rw_lock_reader_locker_new (&self->silo_lock); +- + origin = gs_app_get_origin_appstream (app); + + /* look in AppStream then fall back to AppData */ +@@ -1056,15 +1065,15 @@ gs_plugin_refine_from_id (GsPluginAppstream *self, + + for (guint i = 0; i < components->len; i++) { + XbNode *component = g_ptr_array_index (components, i); +- if (!gs_appstream_refine_app (GS_PLUGIN (self), app, self->silo, component, flags, self->silo_installed_by_desktopid, +- self->silo_filename ? self->silo_filename : "", self->default_scope, error)) ++ if (!gs_appstream_refine_app (GS_PLUGIN (self), app, silo, component, flags, silo_installed_by_desktopid, ++ silo_filename ? silo_filename : "", self->default_scope, error)) + return FALSE; + gs_plugin_appstream_set_compulsory_quirk (app, component); + } + + /* if an installed desktop or appdata file exists set to installed */ + if (gs_app_get_state (app) == GS_APP_STATE_UNKNOWN) { +- if (!gs_plugin_appstream_refine_state (self, app, error)) ++ if (!gs_plugin_appstream_refine_state (self, app, silo_installed_by_id, error)) + return FALSE; + } + +@@ -1077,6 +1086,10 @@ static gboolean + gs_plugin_refine_from_pkgname (GsPluginAppstream *self, + GsApp *app, + GsPluginRefineFlags flags, ++ XbSilo *silo, ++ const gchar *silo_filename, ++ GHashTable *silo_installed_by_desktopid, ++ GHashTable *silo_installed_by_id, + GError **error) + { + GPtrArray *sources = gs_app_get_sources (app); +@@ -1089,33 +1102,30 @@ gs_plugin_refine_from_pkgname (GsPluginAppstream *self, + /* find all apps when matching any prefixes */ + for (guint j = 0; j < sources->len; j++) { + const gchar *pkgname = g_ptr_array_index (sources, j); +- g_autoptr(GRWLockReaderLocker) locker = NULL; + g_autoptr(GString) xpath = g_string_new (NULL); + g_autoptr(XbNode) component = NULL; + +- locker = g_rw_lock_reader_locker_new (&self->silo_lock); +- + /* prefer actual apps and then fallback to anything else */ + xb_string_append_union (xpath, "components/component[@type='desktop-application']/pkgname[text()='%s']/..", pkgname); + xb_string_append_union (xpath, "components/component[@type='console-application']/pkgname[text()='%s']/..", pkgname); + xb_string_append_union (xpath, "components/component[@type='web-application']/pkgname[text()='%s']/..", pkgname); + xb_string_append_union (xpath, "components/component/pkgname[text()='%s']/..", pkgname); +- component = xb_silo_query_first (self->silo, xpath->str, &error_local); ++ component = xb_silo_query_first (silo, xpath->str, &error_local); + if (component == NULL) { + if (g_error_matches (error_local, G_IO_ERROR, G_IO_ERROR_NOT_FOUND)) + continue; + g_propagate_error (error, g_steal_pointer (&error_local)); + return FALSE; + } +- if (!gs_appstream_refine_app (GS_PLUGIN (self), app, self->silo, component, flags, self->silo_installed_by_desktopid, +- self->silo_filename ? self->silo_filename : "", self->default_scope, error)) ++ if (!gs_appstream_refine_app (GS_PLUGIN (self), app, silo, component, flags, silo_installed_by_desktopid, ++ silo_filename ? silo_filename : "", self->default_scope, error)) + return FALSE; + gs_plugin_appstream_set_compulsory_quirk (app, component); + } + + /* if an installed desktop or appdata file exists set to installed */ + if (gs_app_get_state (app) == GS_APP_STATE_UNKNOWN) { +- if (!gs_plugin_appstream_refine_state (self, app, error)) ++ if (!gs_plugin_appstream_refine_state (self, app, silo_installed_by_id, error)) + return FALSE; + } + +@@ -1153,6 +1163,10 @@ static gboolean refine_wildcard (GsPluginAppstream *self, + GsAppList *list, + GsPluginRefineFlags refine_flags, + GHashTable *apps_by_id, ++ XbSilo *silo, ++ const gchar *silo_filename, ++ GHashTable *silo_installed_by_desktopid, ++ GHashTable *silo_installed_by_id, + GCancellable *cancellable, + GError **error); + +@@ -1171,13 +1185,17 @@ refine_thread_cb (GTask *task, + g_autoptr(GHashTable) apps_by_id = NULL; + g_autoptr(GHashTable) apps_by_origin_and_id = NULL; + g_autoptr(GPtrArray) components = NULL; +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; ++ g_autofree gchar *silo_filename = NULL; ++ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; ++ g_autoptr(GHashTable) silo_installed_by_id = NULL; + g_autoptr(GError) local_error = NULL; + + assert_in_worker (self); + + /* check silo is valid */ +- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) { ++ silo = gs_plugin_appstream_ref_silo (self, &silo_filename, &silo_installed_by_desktopid, &silo_installed_by_id, cancellable, &local_error); ++ if (silo == NULL) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } +@@ -1185,9 +1203,7 @@ refine_thread_cb (GTask *task, + apps_by_id = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify) g_ptr_array_unref); + apps_by_origin_and_id = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify) g_ptr_array_unref); + +- locker = g_rw_lock_reader_locker_new (&self->silo_lock); +- +- components = xb_silo_query (self->silo, "components/component/id", 0, NULL); ++ components = xb_silo_query (silo, "components/component/id", 0, NULL); + for (guint i = 0; components != NULL && i < components->len; i++) { + XbNode *node = g_ptr_array_index (components, i); + g_autoptr(XbNode) component_node = xb_node_get_parent (node); +@@ -1234,7 +1250,7 @@ refine_thread_cb (GTask *task, + } + + g_clear_pointer (&components, g_ptr_array_unref); +- components = xb_silo_query (self->silo, "component/id", 0, NULL); ++ components = xb_silo_query (silo, "component/id", 0, NULL); + for (guint i = 0; components != NULL && i < components->len; i++) { + XbNode *node = g_ptr_array_index (components, i); + g_autoptr(XbNode) component_node = xb_node_get_parent (node); +@@ -1262,12 +1278,14 @@ refine_thread_cb (GTask *task, + continue; + + /* find by ID then fall back to package name */ +- if (!gs_plugin_refine_from_id (self, app, flags, apps_by_id, apps_by_origin_and_id, &found, &local_error)) { ++ if (!gs_plugin_refine_from_id (self, app, flags, apps_by_id, apps_by_origin_and_id, silo, silo_filename, ++ silo_installed_by_desktopid, silo_installed_by_id, &found, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + if (!found) { +- if (!gs_plugin_refine_from_pkgname (self, app, flags, &local_error)) { ++ if (!gs_plugin_refine_from_pkgname (self, app, flags, silo, silo_filename, ++ silo_installed_by_desktopid, silo_installed_by_id, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } +@@ -1286,7 +1304,8 @@ refine_thread_cb (GTask *task, + GsApp *app = gs_app_list_index (app_list, j); + + if (gs_app_has_quirk (app, GS_APP_QUIRK_IS_WILDCARD) && +- !refine_wildcard (self, app, list, flags, apps_by_id, cancellable, &local_error)) { ++ !refine_wildcard (self, app, list, flags, apps_by_id, silo, silo_filename, ++ silo_installed_by_desktopid, silo_installed_by_id,cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } +@@ -1311,20 +1330,21 @@ refine_wildcard (GsPluginAppstream *self, + GsAppList *list, + GsPluginRefineFlags refine_flags, + GHashTable *apps_by_id, ++ XbSilo *silo, ++ const gchar *silo_filename, ++ GHashTable *silo_installed_by_desktopid, ++ GHashTable *silo_installed_by_id, + GCancellable *cancellable, + GError **error) + { + const gchar *id; + GPtrArray *components; +- g_autoptr(GRWLockReaderLocker) locker = NULL; + + /* not enough info to find */ + id = gs_app_get_id (app); + if (id == NULL) + return TRUE; + +- locker = g_rw_lock_reader_locker_new (&self->silo_lock); +- + components = g_hash_table_lookup (apps_by_id, id); + if (components == NULL) + return TRUE; +@@ -1333,20 +1353,20 @@ refine_wildcard (GsPluginAppstream *self, + g_autoptr(GsApp) new = NULL; + + /* new app */ +- new = gs_appstream_create_app (GS_PLUGIN (self), self->silo, component, self->silo_filename ? self->silo_filename : "", ++ new = gs_appstream_create_app (GS_PLUGIN (self), silo, component, silo_filename ? silo_filename : "", + self->default_scope, error); + if (new == NULL) + return FALSE; + gs_app_set_scope (new, AS_COMPONENT_SCOPE_SYSTEM); + gs_app_subsume_metadata (new, app); +- if (!gs_appstream_refine_app (GS_PLUGIN (self), new, self->silo, component, refine_flags, self->silo_installed_by_desktopid, +- self->silo_filename ? self->silo_filename : "", self->default_scope, error)) ++ if (!gs_appstream_refine_app (GS_PLUGIN (self), new, silo, component, refine_flags, silo_installed_by_desktopid, ++ silo_filename ? silo_filename : "", self->default_scope, error)) + return FALSE; + gs_plugin_appstream_set_compulsory_quirk (new, component); + + /* if an installed desktop or appdata file exists set to installed */ + if (gs_app_get_state (new) == GS_APP_STATE_UNKNOWN) { +- if (!gs_plugin_appstream_refine_state (self, new, error)) ++ if (!gs_plugin_appstream_refine_state (self, new, silo_installed_by_id, error)) + return FALSE; + } + +@@ -1398,21 +1418,20 @@ refine_categories_thread_cb (GTask *task, + GCancellable *cancellable) + { + GsPluginAppstream *self = GS_PLUGIN_APPSTREAM (source_object); +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; + GsPluginRefineCategoriesData *data = task_data; + g_autoptr(GError) local_error = NULL; + + assert_in_worker (self); + + /* check silo is valid */ +- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) { ++ silo = gs_plugin_appstream_ref_silo (self, NULL, NULL, NULL, cancellable, &local_error); ++ if (silo == NULL) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + +- locker = g_rw_lock_reader_locker_new (&self->silo_lock); +- +- if (!gs_appstream_refine_category_sizes (self->silo, data->list, cancellable, &local_error)) { ++ if (!gs_appstream_refine_category_sizes (silo, data->list, cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } +@@ -1462,7 +1481,7 @@ list_apps_thread_cb (GTask *task, + GCancellable *cancellable) + { + GsPluginAppstream *self = GS_PLUGIN_APPSTREAM (source_object); +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; + g_autoptr(GsAppList) list = gs_app_list_new (); + GsPluginListAppsData *data = task_data; + GDateTime *released_since = NULL; +@@ -1516,65 +1535,64 @@ list_apps_thread_cb (GTask *task, + } + + /* check silo is valid */ +- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) { ++ silo = gs_plugin_appstream_ref_silo (self, NULL, NULL, NULL, cancellable, &local_error); ++ if (silo == NULL) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + +- locker = g_rw_lock_reader_locker_new (&self->silo_lock); +- + if (released_since != NULL && +- !gs_appstream_add_recent (GS_PLUGIN (self), self->silo, list, age_secs, ++ !gs_appstream_add_recent (GS_PLUGIN (self), silo, list, age_secs, + cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + + if (is_curated != GS_APP_QUERY_TRISTATE_UNSET && +- !gs_appstream_add_popular (self->silo, list, cancellable, &local_error)) { ++ !gs_appstream_add_popular (silo, list, cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + + if (is_featured != GS_APP_QUERY_TRISTATE_UNSET && +- !gs_appstream_add_featured (self->silo, list, cancellable, &local_error)) { ++ !gs_appstream_add_featured (silo, list, cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + + if (category != NULL && +- !gs_appstream_add_category_apps (GS_PLUGIN (self), self->silo, category, list, cancellable, &local_error)) { ++ !gs_appstream_add_category_apps (GS_PLUGIN (self), silo, category, list, cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + + if (is_installed == GS_APP_QUERY_TRISTATE_TRUE && +- !gs_appstream_add_installed (GS_PLUGIN (self), self->silo, list, cancellable, &local_error)) { ++ !gs_appstream_add_installed (GS_PLUGIN (self), silo, list, cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + + if (deployment_featured != NULL && +- !gs_appstream_add_deployment_featured (self->silo, deployment_featured, list, ++ !gs_appstream_add_deployment_featured (silo, deployment_featured, list, + cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + + if (developers != NULL && +- !gs_appstream_search_developer_apps (GS_PLUGIN (self), self->silo, developers, list, cancellable, &local_error)) { ++ !gs_appstream_search_developer_apps (GS_PLUGIN (self), silo, developers, list, cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + + if (keywords != NULL && +- !gs_appstream_search (GS_PLUGIN (self), self->silo, keywords, list, cancellable, &local_error)) { ++ !gs_appstream_search (GS_PLUGIN (self), silo, keywords, list, cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } + + if (alternate_of != NULL && +- !gs_appstream_add_alternates (self->silo, alternate_of, list, cancellable, &local_error)) { ++ !gs_appstream_add_alternates (silo, alternate_of, list, cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } +@@ -1623,12 +1641,14 @@ refresh_metadata_thread_cb (GTask *task, + GCancellable *cancellable) + { + GsPluginAppstream *self = GS_PLUGIN_APPSTREAM (source_object); ++ g_autoptr(XbSilo) silo = NULL; + g_autoptr(GError) local_error = NULL; + + assert_in_worker (self); + + /* Checking the silo will refresh it if needed. */ +- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) ++ silo = gs_plugin_appstream_ref_silo (self, NULL, NULL, NULL, cancellable, &local_error); ++ if (silo == NULL) + g_task_return_error (task, g_steal_pointer (&local_error)); + else + g_task_return_boolean (task, TRUE); +-- +GitLab + + +From cf04c32b5fb1fd267096fad8dd11a22429ad788a Mon Sep 17 00:00:00 2001 +Date: Mon, 29 Apr 2024 17:45:08 +0200 +Subject: [PATCH 2/3] gs-plugin-appstream: Rename file_monitor_stamp to + silo_change_stamp + +Since it's used also in the gs_plugin_appstream_reload() and works +like a change indicator, name it appropriately to avoid confusion. +--- + plugins/core/gs-plugin-appstream.c | 16 ++++++++-------- + 1 file changed, 8 insertions(+), 8 deletions(-) + +diff --git a/plugins/core/gs-plugin-appstream.c b/plugins/core/gs-plugin-appstream.c +index 5749a175f3..99fe5a1432 100644 +--- a/plugins/core/gs-plugin-appstream.c ++++ b/plugins/core/gs-plugin-appstream.c +@@ -46,8 +46,8 @@ struct _GsPluginAppstream + GPtrArray *file_monitors; /* (owned) (element-type GFileMonitor) */ + /* The stamps help to avoid locking the silo lock in the main thread + and also to detect changes while loading other appstream data. */ +- gint file_monitor_stamp; /* the file monitor stamp, increased on every file monitor change */ +- gint file_monitor_stamp_current; /* the currently known file monitor stamp, checked for changes */ ++ gint silo_change_stamp; /* the silo change stamp, increased on every silo change */ ++ gint silo_change_stamp_current; /* the currently known silo change stamp, checked for changes */ + }; + + G_DEFINE_TYPE (GsPluginAppstream, gs_plugin_appstream, GS_TYPE_PLUGIN) +@@ -224,7 +224,7 @@ gs_plugin_appstream_file_monitor_changed_cb (GFileMonitor *monitor, + gpointer user_data) + { + GsPluginAppstream *self = user_data; +- g_atomic_int_inc (&self->file_monitor_stamp); ++ g_atomic_int_inc (&self->silo_change_stamp); + } + + static void +@@ -550,7 +550,7 @@ gs_plugin_appstream_ref_silo (GsPluginAppstream *self, + locker = g_mutex_locker_new (&self->silo_lock); + /* everything is okay */ + if (self->silo != NULL && xb_silo_is_valid (self->silo) && +- g_atomic_int_get (&self->file_monitor_stamp_current) == g_atomic_int_get (&self->file_monitor_stamp)) { ++ g_atomic_int_get (&self->silo_change_stamp_current) == g_atomic_int_get (&self->silo_change_stamp)) { + if (out_silo_filename != NULL) + *out_silo_filename = g_strdup (self->silo_filename); + if (out_silo_installed_by_desktopid != NULL) +@@ -568,7 +568,7 @@ gs_plugin_appstream_ref_silo (GsPluginAppstream *self, + g_clear_pointer (&blobfn, g_free); + self->default_scope = AS_COMPONENT_SCOPE_UNKNOWN; + g_ptr_array_set_size (self->file_monitors, 0); +- g_atomic_int_set (&self->file_monitor_stamp_current, g_atomic_int_get (&self->file_monitor_stamp)); ++ g_atomic_int_set (&self->silo_change_stamp_current, g_atomic_int_get (&self->silo_change_stamp)); + + /* FIXME: https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1422 */ + old_thread_default = g_main_context_ref_thread_default (); +@@ -707,7 +707,7 @@ gs_plugin_appstream_ref_silo (GsPluginAppstream *self, + if (old_thread_default != NULL) + g_main_context_push_thread_default (old_thread_default); + +- if (g_atomic_int_get (&self->file_monitor_stamp_current) != g_atomic_int_get (&self->file_monitor_stamp)) { ++ if (g_atomic_int_get (&self->silo_change_stamp_current) != g_atomic_int_get (&self->silo_change_stamp)) { + g_ptr_array_set_size (parent_appdata, 0); + g_ptr_array_set_size (parent_appstream, 0); + g_debug ("appstream: File monitors reported change while loading appstream data, reloading..."); +@@ -800,8 +800,8 @@ gs_plugin_appstream_reload (GsPlugin *plugin) + } + + self = GS_PLUGIN_APPSTREAM (plugin); +- /* simpler than getting the silo and setting it invalid */ +- g_atomic_int_inc (&self->file_monitor_stamp); ++ /* Invalidate the reference to the current silo */ ++ g_atomic_int_inc (&self->silo_change_stamp); + } + + static gint +-- +GitLab + + +From 59b301b8a878f3e81359909a8d4107715eb60a35 Mon Sep 17 00:00:00 2001 +Date: Tue, 30 Apr 2024 13:13:36 +0200 +Subject: [PATCH 3/3] flatpak: Simplify XbSilo locking + +Instead of holding RW lock on the internal silo variable, simply return +a reference to it and work with it like with an immutable object. That +simplifies locking and makes the code cleaner. It can also make the code +quicker, in some cases. +--- + plugins/flatpak/gs-flatpak.c | 307 +++++++++++++++++++---------------- + 1 file changed, 163 insertions(+), 144 deletions(-) + +diff --git a/plugins/flatpak/gs-flatpak.c b/plugins/flatpak/gs-flatpak.c +index 2e175fd08e..9893cf88b7 100644 +--- a/plugins/flatpak/gs-flatpak.c ++++ b/plugins/flatpak/gs-flatpak.c +@@ -54,9 +54,11 @@ struct _GsFlatpak { + AsComponentScope scope; + GsPlugin *plugin; + XbSilo *silo; +- GRWLock silo_lock; ++ GMutex silo_lock; + gchar *silo_filename; + GHashTable *silo_installed_by_desktopid; ++ gint silo_change_stamp; ++ gint silo_change_stamp_current; + gchar *id; + guint changed_id; + GHashTable *app_silos; +@@ -654,10 +656,7 @@ gs_flatpak_create_source (GsFlatpak *self, FlatpakRemote *xremote) + static void + gs_flatpak_invalidate_silo (GsFlatpak *self) + { +- g_rw_lock_writer_lock (&self->silo_lock); +- if (self->silo != NULL) +- xb_silo_invalidate (self->silo); +- g_rw_lock_writer_unlock (&self->silo_lock); ++ g_atomic_int_inc (&self->silo_change_stamp); + } + + static void +@@ -1085,32 +1084,39 @@ gs_flatpak_rescan_installed (GsFlatpak *self, + g_debug ("Failed to read flatpak .desktop files in %s: %s", path, error_local->message); + } + +-static gboolean +-gs_flatpak_rescan_appstream_store (GsFlatpak *self, +- gboolean interactive, +- GCancellable *cancellable, +- GError **error) ++static XbSilo * ++gs_flatpak_ref_silo (GsFlatpak *self, ++ gboolean interactive, ++ gchar **out_silo_filename, ++ GHashTable **out_silo_installed_by_desktopid, ++ GCancellable *cancellable, ++ GError **error) + { + g_autofree gchar *blobfn = NULL; + g_autoptr(GFile) file = NULL; + g_autoptr(GPtrArray) xremotes = NULL; + g_autoptr(GPtrArray) desktop_paths = NULL; +- g_autoptr(GRWLockReaderLocker) reader_locker = NULL; +- g_autoptr(GRWLockWriterLocker) writer_locker = NULL; ++ g_autoptr(GMutexLocker) locker = NULL; + g_autoptr(XbBuilder) builder = NULL; + g_autoptr(GMainContext) old_thread_default = NULL; + +- reader_locker = g_rw_lock_reader_locker_new (&self->silo_lock); ++ locker = g_mutex_locker_new (&self->silo_lock); + /* everything is okay */ +- if (self->silo != NULL && xb_silo_is_valid (self->silo)) +- return TRUE; +- g_clear_pointer (&reader_locker, g_rw_lock_reader_locker_free); ++ if (self->silo != NULL && xb_silo_is_valid (self->silo) && ++ g_atomic_int_get (&self->silo_change_stamp_current) == g_atomic_int_get (&self->silo_change_stamp)) { ++ if (out_silo_filename != NULL) ++ *out_silo_filename = g_strdup (self->silo_filename); ++ if (out_silo_installed_by_desktopid != NULL && self->silo_installed_by_desktopid) ++ *out_silo_installed_by_desktopid = g_hash_table_ref (self->silo_installed_by_desktopid); ++ return g_object_ref (self->silo); ++ } + + /* drat! silo needs regenerating */ +- writer_locker = g_rw_lock_writer_locker_new (&self->silo_lock); ++ reload: + g_clear_object (&self->silo); + g_clear_pointer (&self->silo_filename, g_free); + g_clear_pointer (&self->silo_installed_by_desktopid, g_hash_table_unref); ++ g_atomic_int_set (&self->silo_change_stamp_current, g_atomic_int_get (&self->silo_change_stamp)); + + /* FIXME: https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1422 */ + old_thread_default = g_main_context_ref_thread_default (); +@@ -1138,7 +1144,7 @@ gs_flatpak_rescan_appstream_store (GsFlatpak *self, + error); + if (xremotes == NULL) { + gs_flatpak_error_convert (error); +- return FALSE; ++ return NULL; + } + for (guint i = 0; i < xremotes->len; i++) { + g_autoptr(GError) error_local = NULL; +@@ -1152,7 +1158,7 @@ gs_flatpak_rescan_appstream_store (GsFlatpak *self, + flatpak_remote_get_name (xremote), error_local->message); + if (g_cancellable_set_error_if_cancelled (cancellable, error)) { + gs_flatpak_error_convert (error); +- return FALSE; ++ return NULL; + } + } + } +@@ -1176,7 +1182,7 @@ gs_flatpak_rescan_appstream_store (GsFlatpak *self, + GS_UTILS_CACHE_FLAG_CREATE_DIRECTORY, + error); + if (blobfn == NULL) +- return FALSE; ++ return NULL; + file = g_file_new_for_path (blobfn); + g_debug ("ensuring %s", blobfn); + +@@ -1195,6 +1201,17 @@ gs_flatpak_rescan_appstream_store (GsFlatpak *self, + if (old_thread_default != NULL) + g_main_context_push_thread_default (old_thread_default); + ++ if (g_atomic_int_get (&self->silo_change_stamp_current) != g_atomic_int_get (&self->silo_change_stamp)) { ++ g_clear_pointer (&blobfn, g_free); ++ g_clear_pointer (&xremotes, g_ptr_array_unref); ++ g_clear_pointer (&desktop_paths, g_ptr_array_unref); ++ g_clear_pointer (&old_thread_default, g_main_context_unref); ++ g_clear_object (&file); ++ g_clear_object (&builder); ++ g_debug ("flatpak: Reported change while loading appstream data, reloading..."); ++ goto reload; ++ } ++ + if (self->silo != NULL) { + g_autoptr(GPtrArray) installed = NULL; + g_autoptr(XbNode) info_filename = NULL; +@@ -1218,66 +1235,46 @@ gs_flatpak_rescan_appstream_store (GsFlatpak *self, + info_filename = xb_silo_query_first (self->silo, "/info/filename", NULL); + if (info_filename != NULL) + self->silo_filename = g_strdup (xb_node_get_text (info_filename)); ++ ++ if (out_silo_filename != NULL) ++ *out_silo_filename = g_strdup (self->silo_filename); ++ if (out_silo_installed_by_desktopid != NULL && self->silo_installed_by_desktopid) ++ *out_silo_installed_by_desktopid = g_hash_table_ref (self->silo_installed_by_desktopid); ++ return g_object_ref (self->silo); + } + +- /* success */ +- return self->silo != NULL; ++ return NULL; + } + + static gboolean + gs_flatpak_rescan_app_data (GsFlatpak *self, + gboolean interactive, ++ XbSilo **out_silo, ++ gchar **out_silo_filename, ++ GHashTable **out_silo_installed_by_desktopid, + GCancellable *cancellable, + GError **error) + { ++ g_autoptr(XbSilo) silo = NULL; ++ + if (self->requires_full_rescan) { + gboolean res = gs_flatpak_refresh (self, 60, interactive, cancellable, error); +- if (res) ++ if (res) { + self->requires_full_rescan = FALSE; +- else ++ } else { + gs_flatpak_internal_data_changed (self); +- return res; ++ return res; ++ } + } + +- if (!gs_flatpak_rescan_appstream_store (self, interactive, cancellable, error)) { ++ silo = gs_flatpak_ref_silo (self, interactive, out_silo_filename, out_silo_installed_by_desktopid, cancellable, error); ++ if (silo == NULL) { + gs_flatpak_internal_data_changed (self); + return FALSE; + } + +- return TRUE; +-} +- +-/* Returns with a read lock held on @self->silo_lock on success. +- The *locker should be NULL when being called. */ +-static gboolean +-ensure_flatpak_silo_with_locker (GsFlatpak *self, +- GRWLockReaderLocker **locker, +- gboolean interactive, +- GCancellable *cancellable, +- GError **error) +-{ +- /* should not hold the lock when called */ +- g_return_val_if_fail (*locker == NULL, FALSE); +- +- /* ensure valid */ +- if (!gs_flatpak_rescan_app_data (self, interactive, cancellable, error)) +- return FALSE; +- +- *locker = g_rw_lock_reader_locker_new (&self->silo_lock); +- +- while (self->silo == NULL) { +- g_clear_pointer (locker, g_rw_lock_reader_locker_free); +- +- if (!gs_flatpak_rescan_appstream_store (self, interactive, cancellable, error)) { +- gs_flatpak_internal_data_changed (self); +- return FALSE; +- } +- +- /* At this point either rescan_appstream_store() returned an error or it successfully +- * initialised self->silo. There is the possibility that another thread will invalidate +- * the silo before we regain the lock. If so, we’ll have to rescan again. */ +- *locker = g_rw_lock_reader_locker_new (&self->silo_lock); +- } ++ if (out_silo != NULL) ++ *out_silo = g_steal_pointer (&silo); + + return TRUE; + } +@@ -1412,6 +1409,7 @@ gs_flatpak_refresh_appstream (GsFlatpak *self, + { + gboolean ret; + g_autoptr(GPtrArray) xremotes = NULL; ++ g_autoptr(XbSilo) silo = NULL; + + /* get remotes */ + xremotes = flatpak_installation_list_remotes (gs_flatpak_get_installation (self, interactive), +@@ -1498,7 +1496,8 @@ gs_flatpak_refresh_appstream (GsFlatpak *self, + } + + /* ensure the AppStream silo is up to date */ +- if (!gs_flatpak_rescan_appstream_store (self, interactive, cancellable, error)) { ++ silo = gs_flatpak_ref_silo (self, interactive, NULL, NULL, cancellable, error); ++ if (silo == NULL) { + gs_flatpak_internal_data_changed (self); + return FALSE; + } +@@ -1646,7 +1645,7 @@ gs_flatpak_add_sources (GsFlatpak *self, + FlatpakInstallation *installation = gs_flatpak_get_installation (self, interactive); + + /* refresh */ +- if (!gs_flatpak_rescan_app_data (self, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, NULL, NULL, NULL, cancellable, error)) + return FALSE; + + /* get installed apps and runtimes */ +@@ -2080,7 +2079,7 @@ gs_flatpak_add_updates (GsFlatpak *self, + FlatpakInstallation *installation = gs_flatpak_get_installation (self, interactive); + + /* ensure valid */ +- if (!gs_flatpak_rescan_app_data (self, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, NULL, NULL, NULL, cancellable, error)) + return FALSE; + + /* get all the updatable apps and runtimes */ +@@ -2390,10 +2389,8 @@ gs_flatpak_create_fake_ref (GsApp *app, GError **error) + return xref; + } + +-/* the _unlocked() version doesn't call gs_flatpak_rescan_app_data, +- * in order to avoid taking the writer lock on self->silo_lock */ + static gboolean +-gs_flatpak_refine_app_state_unlocked (GsFlatpak *self, ++gs_flatpak_refine_app_state_internal (GsFlatpak *self, + GsApp *app, + gboolean interactive, + gboolean force_state_update, +@@ -2505,10 +2502,10 @@ gs_flatpak_refine_app_state (GsFlatpak *self, + GError **error) + { + /* ensure valid */ +- if (!gs_flatpak_rescan_app_data (self, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, NULL, NULL, NULL, cancellable, error)) + return FALSE; + +- return gs_flatpak_refine_app_state_unlocked (self, app, interactive, force_state_update, cancellable, error); ++ return gs_flatpak_refine_app_state_internal (self, app, interactive, force_state_update, cancellable, error); + } + + static GsApp * +@@ -2594,7 +2591,7 @@ gs_flatpak_create_runtime (GsFlatpak *self, + gs_flatpak_app_set_ref_name (app, split[0]); + gs_flatpak_app_set_ref_arch (app, split[1]); + +- if (!gs_flatpak_refine_app_state_unlocked (self, app, interactive, FALSE, NULL, &local_error)) ++ if (!gs_flatpak_refine_app_state_internal (self, app, interactive, FALSE, NULL, &local_error)) + g_debug ("Failed to refine state for runtime '%s': %s", gs_app_get_unique_id (app), local_error->message); + + /* save in the cache */ +@@ -2984,7 +2981,7 @@ gs_plugin_refine_item_size (GsFlatpak *self, + + /* is the app_runtime already installed? */ + app_runtime = gs_app_get_runtime (app); +- if (!gs_flatpak_refine_app_state_unlocked (self, ++ if (!gs_flatpak_refine_app_state_internal (self, + app_runtime, + interactive, + FALSE, +@@ -3096,6 +3093,8 @@ gs_flatpak_refine_appstream_from_bytes (GsFlatpak *self, + GBytes *appstream_gz, + GsPluginRefineFlags flags, + gboolean interactive, ++ const gchar *silo_filename, ++ GHashTable *silo_installed_by_desktopid, + GCancellable *cancellable, + GError **error) + { +@@ -3229,8 +3228,8 @@ gs_flatpak_refine_appstream_from_bytes (GsFlatpak *self, + } + + /* copy details from AppStream to app */ +- if (!gs_appstream_refine_app (self->plugin, app, silo, component_node, flags, self->silo_installed_by_desktopid, +- self->silo_filename ? self->silo_filename : "", self->scope, error)) ++ if (!gs_appstream_refine_app (self->plugin, app, silo, component_node, flags, silo_installed_by_desktopid, ++ silo_filename ? silo_filename : "", self->scope, error)) + return FALSE; + + if (gs_app_get_origin (app)) +@@ -3324,6 +3323,8 @@ static gboolean + gs_flatpak_refine_appstream (GsFlatpak *self, + GsApp *app, + XbSilo *silo, ++ const gchar *silo_filename, ++ GHashTable *silo_installed_by_desktopid, + GsPluginRefineFlags flags, + GHashTable *components_by_bundle, + gboolean interactive, +@@ -3410,11 +3411,12 @@ gs_flatpak_refine_appstream (GsFlatpak *self, + appstream_gz, + flags, + interactive, ++ silo_filename, silo_installed_by_desktopid, + cancellable, error); + } + +- if (!gs_appstream_refine_app (self->plugin, app, silo, component, flags, self->silo_installed_by_desktopid, +- self->silo_filename ? self->silo_filename : "", self->scope, error)) ++ if (!gs_appstream_refine_app (self->plugin, app, silo, component, flags, silo_installed_by_desktopid, ++ silo_filename ? silo_filename : "", self->scope, error)) + return FALSE; + + /* use the default release as the version number */ +@@ -3423,13 +3425,15 @@ gs_flatpak_refine_appstream (GsFlatpak *self, + } + + static gboolean +-gs_flatpak_refine_app_unlocked (GsFlatpak *self, ++gs_flatpak_refine_app_internal (GsFlatpak *self, + GsApp *app, + GsPluginRefineFlags flags, + gboolean interactive, + gboolean force_state_update, + GHashTable *components_by_bundle, +- GRWLockReaderLocker **locker, ++ XbSilo *silo, ++ const gchar *silo_filename, ++ GHashTable *silo_installed_by_desktopid, + GCancellable *cancellable, + GError **error) + { +@@ -3440,13 +3444,9 @@ gs_flatpak_refine_app_unlocked (GsFlatpak *self, + if (gs_app_get_bundle_kind (app) != AS_BUNDLE_KIND_FLATPAK) + return TRUE; + +- g_clear_pointer (locker, g_rw_lock_reader_locker_free); +- +- if (!ensure_flatpak_silo_with_locker (self, locker, interactive, cancellable, error)) +- return FALSE; +- + /* always do AppStream properties */ +- if (!gs_flatpak_refine_appstream (self, app, self->silo, flags, components_by_bundle, interactive, cancellable, error)) ++ if (!gs_flatpak_refine_appstream (self, app, silo, silo_filename, silo_installed_by_desktopid, ++ flags, components_by_bundle, interactive, cancellable, error)) + return FALSE; + + /* AppStream sets the source to appname/arch/branch */ +@@ -3456,7 +3456,7 @@ gs_flatpak_refine_app_unlocked (GsFlatpak *self, + } + + /* check the installed state */ +- if (!gs_flatpak_refine_app_state_unlocked (self, app, interactive, force_state_update, cancellable, error)) { ++ if (!gs_flatpak_refine_app_state_internal (self, app, interactive, force_state_update, cancellable, error)) { + g_prefix_error (error, "failed to get state: "); + return FALSE; + } +@@ -3473,7 +3473,8 @@ gs_flatpak_refine_app_unlocked (GsFlatpak *self, + + /* if the state was changed, perhaps set the version from the release */ + if (old_state != gs_app_get_state (app)) { +- if (!gs_flatpak_refine_appstream (self, app, self->silo, flags, components_by_bundle, interactive, cancellable, error)) ++ if (!gs_flatpak_refine_appstream (self, app, silo, silo_filename, silo_installed_by_desktopid, ++ flags, components_by_bundle, interactive, cancellable, error)) + return FALSE; + } + +@@ -3567,11 +3568,16 @@ gs_flatpak_refine_addons (GsFlatpak *self, + gboolean interactive, + GCancellable *cancellable) + { +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; ++ g_autofree gchar *silo_filename = NULL; ++ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; + g_autoptr(GsAppList) addons = NULL; + g_autoptr(GString) errors = NULL; + guint ii, sz; + ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, &silo_filename, &silo_installed_by_desktopid, cancellable, NULL)) ++ return; ++ + addons = gs_app_dup_addons (parent_app); + sz = addons ? gs_app_list_length (addons) : 0; + +@@ -3582,7 +3588,8 @@ gs_flatpak_refine_addons (GsFlatpak *self, + if (state != gs_app_get_state (addon)) + continue; + +- if (!gs_flatpak_refine_app_unlocked (self, addon, flags, interactive, TRUE, NULL, &locker, cancellable, &local_error)) { ++ if (!gs_flatpak_refine_app_internal (self, addon, flags, interactive, TRUE, NULL, silo, silo_filename, ++ silo_installed_by_desktopid, cancellable, &local_error)) { + if (errors) + g_string_append_c (errors, '\n'); + else +@@ -3614,13 +3621,16 @@ gs_flatpak_refine_app (GsFlatpak *self, + GCancellable *cancellable, + GError **error) + { +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; ++ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; ++ g_autofree gchar *silo_filename = NULL; + + /* ensure valid */ +- if (!gs_flatpak_rescan_app_data (self, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, &silo_filename, &silo_installed_by_desktopid, cancellable, error)) + return FALSE; + +- return gs_flatpak_refine_app_unlocked (self, app, flags, interactive, force_state_update, NULL, &locker, cancellable, error); ++ return gs_flatpak_refine_app_internal (self, app, flags, interactive, force_state_update, NULL, ++ silo, silo_filename, silo_installed_by_desktopid, cancellable, error); + } + + gboolean +@@ -3634,7 +3644,9 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, + const gchar *id; + GPtrArray* components = NULL; + g_autoptr(GError) error_local = NULL; +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; ++ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; ++ g_autofree gchar *silo_filename = NULL; + + GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcard, "Flatpak (refine wildcard)", NULL); + +@@ -3643,7 +3655,8 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, + if (id == NULL) + return TRUE; + +- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) ++ silo = gs_flatpak_ref_silo (self, interactive, &silo_filename, &silo_installed_by_desktopid, cancellable, error); ++ if (silo == NULL) + return FALSE; + + GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardQuerySilo, "Flatpak (query silo)", NULL); +@@ -3653,7 +3666,7 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, + } else { + g_autoptr(GPtrArray) components_with_id = NULL; + *inout_components_by_id = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify) g_ptr_array_unref); +- components_with_id = xb_silo_query (self->silo, "components/component/id", 0, &error_local); ++ components_with_id = xb_silo_query (silo, "components/component/id", 0, &error_local); + if (components_with_id == NULL) { + if (g_error_matches (error_local, G_IO_ERROR, G_IO_ERROR_NOT_FOUND)) + return TRUE; +@@ -3686,7 +3699,7 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, + g_autoptr(GPtrArray) bundles = NULL; + + *inout_components_by_bundle = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_object_unref); +- bundles = xb_silo_query (self->silo, "/components/component/bundle[@type='flatpak']", 0, NULL); ++ bundles = xb_silo_query (silo, "/components/component/bundle[@type='flatpak']", 0, NULL); + for (guint b = 0; bundles != NULL && b < bundles->len; b++) { + XbNode *bundle_node = g_ptr_array_index (bundles, b); + g_autoptr(XbNode) component_node = xb_node_get_parent (bundle_node); +@@ -3709,7 +3722,7 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, + g_autoptr(GsApp) new = NULL; + + GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardCreateAppstreamApp, "Flatpak (create Appstream app)", NULL); +- new = gs_appstream_create_app (self->plugin, self->silo, component, self->silo_filename ? self->silo_filename : "", ++ new = gs_appstream_create_app (self->plugin, silo, component, silo_filename ? silo_filename : "", + self->scope, error); + GS_PROFILER_END_SCOPED (FlatpakRefineWildcardCreateAppstreamApp); + +@@ -3761,7 +3774,8 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, + g_debug ("Failed to get ref info for '%s' from wildcard '%s', skipping it...", gs_app_get_id (new), id); + } else { + GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardRefineNewApp, "Flatpak (refine new app)", NULL); +- if (!gs_flatpak_refine_app_unlocked (self, new, refine_flags, interactive, FALSE, *inout_components_by_bundle, &locker, cancellable, error)) ++ if (!gs_flatpak_refine_app_internal (self, new, refine_flags, interactive, FALSE, *inout_components_by_bundle, ++ silo, silo_filename, silo_installed_by_desktopid, cancellable, error)) + return FALSE; + GS_PROFILER_END_SCOPED (FlatpakRefineWildcardRefineNewApp); + +@@ -3894,10 +3908,18 @@ gs_flatpak_file_to_app_bundle (GsFlatpak *self, + /* load AppStream */ + appstream_gz = flatpak_bundle_ref_get_appstream (xref_bundle); + if (appstream_gz != NULL) { ++ g_autofree gchar *silo_filename = NULL; ++ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; ++ g_autoptr(XbSilo) tmp_silo = NULL; ++ ++ tmp_silo = gs_flatpak_ref_silo (self, interactive, &silo_filename, &silo_installed_by_desktopid, cancellable, error); ++ if (tmp_silo == NULL) ++ return NULL; + if (!gs_flatpak_refine_appstream_from_bytes (self, app, NULL, NULL, + appstream_gz, + GS_PLUGIN_REFINE_FLAGS_REQUIRE_ID, + interactive, ++ silo_filename, silo_installed_by_desktopid, + cancellable, error)) + return NULL; + } else { +@@ -3995,6 +4017,9 @@ gs_flatpak_file_to_app_ref (GsFlatpak *self, + g_autoptr(GsApp) app = NULL; + g_autoptr(XbBuilder) builder = xb_builder_new (); + g_autoptr(XbSilo) silo = NULL; ++ g_autoptr(XbSilo) tmp_silo = NULL; ++ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; ++ g_autofree gchar *silo_filename = NULL; + g_autofree gchar *origin_url = NULL; + g_autofree gchar *ref_comment = NULL; + g_autofree gchar *ref_description = NULL; +@@ -4274,8 +4299,12 @@ gs_flatpak_file_to_app_ref (GsFlatpak *self, + g_debug ("showing AppStream data: %s", xml); + } + ++ tmp_silo = gs_flatpak_ref_silo (self, interactive, &silo_filename, &silo_installed_by_desktopid, cancellable, error); ++ if (tmp_silo == NULL) ++ return NULL; ++ + /* get extra AppStream data if available */ +- if (!gs_flatpak_refine_appstream (self, app, silo, ++ if (!gs_flatpak_refine_appstream (self, app, silo, silo_filename, silo_installed_by_desktopid, + GS_PLUGIN_REFINE_FLAGS_MASK, + NULL, + interactive, +@@ -4296,17 +4325,16 @@ gs_flatpak_search (GsFlatpak *self, + GError **error) + { + g_autoptr(GsAppList) list_tmp = gs_app_list_new (); +- g_autoptr(GRWLockReaderLocker) locker = NULL; + g_autoptr(GMutexLocker) app_silo_locker = NULL; + g_autoptr(GPtrArray) silos_to_remove = g_ptr_array_new (); ++ g_autoptr(XbSilo) silo = NULL; + GHashTableIter iter; + gpointer key, value; + +- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) + return FALSE; + +- if (!gs_appstream_search (self->plugin, self->silo, values, list_tmp, +- cancellable, error)) ++ if (!gs_appstream_search (self->plugin, silo, values, list_tmp, cancellable, error)) + return FALSE; + + gs_flatpak_ensure_remote_title (self, interactive, cancellable); +@@ -4353,8 +4381,8 @@ gs_flatpak_search (GsFlatpak *self, + } + + for (guint i = 0; i < silos_to_remove->len; i++) { +- const char *silo = g_ptr_array_index (silos_to_remove, i); +- g_hash_table_remove (self->app_silos, silo); ++ const char *app_ref = g_ptr_array_index (silos_to_remove, i); ++ g_hash_table_remove (self->app_silos, app_ref); + } + + return TRUE; +@@ -4369,17 +4397,16 @@ gs_flatpak_search_developer_apps (GsFlatpak *self, + GError **error) + { + g_autoptr(GsAppList) list_tmp = gs_app_list_new (); +- g_autoptr(GRWLockReaderLocker) locker = NULL; + g_autoptr(GMutexLocker) app_silo_locker = NULL; + g_autoptr(GPtrArray) silos_to_remove = g_ptr_array_new (); ++ g_autoptr(XbSilo) silo = NULL; + GHashTableIter iter; + gpointer key, value; + +- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) + return FALSE; + +- if (!gs_appstream_search_developer_apps (self->plugin, self->silo, values, list_tmp, +- cancellable, error)) ++ if (!gs_appstream_search_developer_apps (self->plugin, silo, values, list_tmp, cancellable, error)) + return FALSE; + + gs_flatpak_ensure_remote_title (self, interactive, cancellable); +@@ -4426,8 +4453,8 @@ gs_flatpak_search_developer_apps (GsFlatpak *self, + } + + for (guint i = 0; i < silos_to_remove->len; i++) { +- const char *silo = g_ptr_array_index (silos_to_remove, i); +- g_hash_table_remove (self->app_silos, silo); ++ const char *app_ref = g_ptr_array_index (silos_to_remove, i); ++ g_hash_table_remove (self->app_silos, app_ref); + } + + return TRUE; +@@ -4441,14 +4468,12 @@ gs_flatpak_add_category_apps (GsFlatpak *self, + GCancellable *cancellable, + GError **error) + { +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; + +- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) + return FALSE; + +- return gs_appstream_add_category_apps (self->plugin, self->silo, +- category, list, +- cancellable, error); ++ return gs_appstream_add_category_apps (self->plugin, silo, category, list, cancellable, error); + } + + gboolean +@@ -4458,12 +4483,12 @@ gs_flatpak_refine_category_sizes (GsFlatpak *self, + GCancellable *cancellable, + GError **error) + { +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; + +- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) + return FALSE; + +- return gs_appstream_refine_category_sizes (self->silo, list, cancellable, error); ++ return gs_appstream_refine_category_sizes (silo, list, cancellable, error); + } + + gboolean +@@ -4474,13 +4499,12 @@ gs_flatpak_add_popular (GsFlatpak *self, + GError **error) + { + g_autoptr(GsAppList) list_tmp = gs_app_list_new (); +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; + +- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) + return FALSE; + +- if (!gs_appstream_add_popular (self->silo, list_tmp, +- cancellable, error)) ++ if (!gs_appstream_add_popular (silo, list_tmp, cancellable, error)) + return FALSE; + + gs_app_list_add_list (list, list_tmp); +@@ -4496,13 +4520,12 @@ gs_flatpak_add_featured (GsFlatpak *self, + GError **error) + { + g_autoptr(GsAppList) list_tmp = gs_app_list_new (); +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; + +- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) + return FALSE; + +- if (!gs_appstream_add_featured (self->silo, list_tmp, +- cancellable, error)) ++ if (!gs_appstream_add_featured (silo, list_tmp, cancellable, error)) + return FALSE; + + gs_app_list_add_list (list, list_tmp); +@@ -4518,12 +4541,12 @@ gs_flatpak_add_deployment_featured (GsFlatpak *self, + GCancellable *cancellable, + GError **error) + { +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; + +- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) + return FALSE; + +- return gs_appstream_add_deployment_featured (self->silo, deployments, list, cancellable, error); ++ return gs_appstream_add_deployment_featured (silo, deployments, list, cancellable, error); + } + + gboolean +@@ -4535,13 +4558,12 @@ gs_flatpak_add_alternates (GsFlatpak *self, + GError **error) + { + g_autoptr(GsAppList) list_tmp = gs_app_list_new (); +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; + +- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) + return FALSE; + +- if (!gs_appstream_add_alternates (self->silo, app, list_tmp, +- cancellable, error)) ++ if (!gs_appstream_add_alternates (silo, app, list_tmp, cancellable, error)) + return FALSE; + + gs_app_list_add_list (list, list_tmp); +@@ -4558,13 +4580,12 @@ gs_flatpak_add_recent (GsFlatpak *self, + GError **error) + { + g_autoptr(GsAppList) list_tmp = gs_app_list_new (); +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; + +- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) + return FALSE; + +- if (!gs_appstream_add_recent (self->plugin, self->silo, list_tmp, age, +- cancellable, error)) ++ if (!gs_appstream_add_recent (self->plugin, silo, list_tmp, age, cancellable, error)) + return FALSE; + + gs_flatpak_claim_app_list (self, list_tmp, interactive); +@@ -4582,12 +4603,12 @@ gs_flatpak_url_to_app (GsFlatpak *self, + GError **error) + { + g_autoptr(GsAppList) list_tmp = gs_app_list_new (); +- g_autoptr(GRWLockReaderLocker) locker = NULL; ++ g_autoptr(XbSilo) silo = NULL; + +- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) ++ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) + return FALSE; + +- if (!gs_appstream_url_to_app (self->plugin, self->silo, list_tmp, url, cancellable, error)) ++ if (!gs_appstream_url_to_app (self->plugin, silo, list_tmp, url, cancellable, error)) + return FALSE; + + gs_flatpak_claim_app_list (self, list_tmp, interactive); +@@ -4638,10 +4659,8 @@ gs_flatpak_finalize (GObject *object) + g_signal_handler_disconnect (self->monitor, self->changed_id); + self->changed_id = 0; + } +- if (self->silo != NULL) +- g_object_unref (self->silo); +- if (self->monitor != NULL) +- g_object_unref (self->monitor); ++ g_clear_object (&self->silo); ++ g_clear_object (&self->monitor); + g_clear_pointer (&self->silo_filename, g_free); + g_clear_pointer (&self->silo_installed_by_desktopid, g_hash_table_unref); + +@@ -4654,7 +4673,7 @@ gs_flatpak_finalize (GObject *object) + g_object_unref (self->plugin); + g_hash_table_unref (self->broken_remotes); + g_mutex_clear (&self->broken_remotes_mutex); +- g_rw_lock_clear (&self->silo_lock); ++ g_mutex_clear (&self->silo_lock); + g_hash_table_unref (self->app_silos); + g_mutex_clear (&self->app_silos_mutex); + g_clear_pointer (&self->remote_title, g_hash_table_unref); +@@ -4675,7 +4694,7 @@ gs_flatpak_init (GsFlatpak *self) + { + /* XbSilo needs external locking as we destroy the silo and build a new + * one when something changes */ +- g_rw_lock_init (&self->silo_lock); ++ g_mutex_init (&self->silo_lock); + + g_mutex_init (&self->installed_refs_mutex); + self->installed_refs = NULL; +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index d744445..5b8b2b4 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -26,13 +26,15 @@ Name: gnome-software Version: 47.2 -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://apps.gnome.org/Software Source0: https://download.gnome.org/sources/gnome-software/47/%{name}-%{tarball_version}.tar.xz +Patch01: 0001-crash-under-gs_appstream_gather_merge_data.patch + # ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 %if 0%{?fedora} || 0%{?rhel} >= 10 @@ -288,6 +290,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Mon Dec 09 2024 Milan Crha - 47.2-3 +- Resolves: #2272232 (Crash under gs_appstream_gather_merge_data()) + * Thu Dec 05 2024 Yaakov Selkowitz - 47.2-2 - Rebuild for fwupd 2.0 From 27805dcecbe0166032de3430d33fcca2ecec26af Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Tue, 7 Jan 2025 08:57:23 +0100 Subject: [PATCH 129/163] Update to 48.alpha2 --- ...under-gs_appstream_gather_merge_data.patch | 1468 ----------------- gnome-software.spec | 13 +- sources | 2 +- 3 files changed, 8 insertions(+), 1475 deletions(-) delete mode 100644 0001-crash-under-gs_appstream_gather_merge_data.patch diff --git a/0001-crash-under-gs_appstream_gather_merge_data.patch b/0001-crash-under-gs_appstream_gather_merge_data.patch deleted file mode 100644 index b52cefd..0000000 --- a/0001-crash-under-gs_appstream_gather_merge_data.patch +++ /dev/null @@ -1,1468 +0,0 @@ -From f1140fd98666fbdb35dfe13a6b3f58fedcb1ad0b Mon Sep 17 00:00:00 2001 -Date: Mon, 29 Apr 2024 17:37:57 +0200 -Subject: [PATCH 1/3] gs-plugin-appstream: Simplify XbSilo locking - -Instead of holding RW lock on the internal silo variable, simply return -a reference to it and work with it like with an immutable object. That -simplifies locking and makes the code cleaner. It can also make the code -quicker, in some cases. ---- - plugins/core/gs-plugin-appstream.c | 194 ++++++++++++++++------------- - 1 file changed, 107 insertions(+), 87 deletions(-) - -diff --git a/plugins/core/gs-plugin-appstream.c b/plugins/core/gs-plugin-appstream.c -index 7ccbac12a5..5749a175f3 100644 ---- a/plugins/core/gs-plugin-appstream.c -+++ b/plugins/core/gs-plugin-appstream.c -@@ -36,7 +36,7 @@ struct _GsPluginAppstream - GsWorkerThread *worker; /* (owned) */ - - XbSilo *silo; -- GRWLock silo_lock; -+ GMutex silo_lock; - gchar *silo_filename; - GHashTable *silo_installed_by_desktopid; - GHashTable *silo_installed_by_id; -@@ -65,7 +65,7 @@ gs_plugin_appstream_dispose (GObject *object) - g_clear_pointer (&self->silo_installed_by_desktopid, g_hash_table_unref); - g_clear_pointer (&self->silo_installed_by_id, g_hash_table_unref); - g_clear_object (&self->settings); -- g_rw_lock_clear (&self->silo_lock); -+ g_mutex_clear (&self->silo_lock); - g_clear_object (&self->worker); - g_clear_pointer (&self->file_monitors, g_ptr_array_unref); - -@@ -77,9 +77,7 @@ gs_plugin_appstream_init (GsPluginAppstream *self) - { - GApplication *application = g_application_get_default (); - -- /* XbSilo needs external locking as we destroy the silo and build a new -- * one when something changes */ -- g_rw_lock_init (&self->silo_lock); -+ g_mutex_init (&self->silo_lock); - - /* require settings */ - self->settings = g_settings_new ("org.gnome.software"); -@@ -530,10 +528,13 @@ gs_add_appstream_metainfo_location (GPtrArray *locations, const gchar *root) - g_build_filename (root, "appdata", NULL)); - } - --static gboolean --gs_plugin_appstream_check_silo (GsPluginAppstream *self, -- GCancellable *cancellable, -- GError **error) -+static XbSilo * -+gs_plugin_appstream_ref_silo (GsPluginAppstream *self, -+ gchar **out_silo_filename, -+ GHashTable **out_silo_installed_by_desktopid, -+ GHashTable **out_silo_installed_by_id, -+ GCancellable *cancellable, -+ GError **error) - { - const gchar *test_xml; - g_autofree gchar *blobfn = NULL; -@@ -541,21 +542,25 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, - g_autoptr(XbNode) n = NULL; - g_autoptr(GFile) file = NULL; - g_autoptr(GPtrArray) installed = NULL; -- g_autoptr(GRWLockReaderLocker) reader_locker = NULL; -- g_autoptr(GRWLockWriterLocker) writer_locker = NULL; -+ g_autoptr(GMutexLocker) locker = NULL; - g_autoptr(GPtrArray) parent_appdata = g_ptr_array_new_with_free_func (g_free); - g_autoptr(GPtrArray) parent_appstream = NULL; - g_autoptr(GMainContext) old_thread_default = NULL; - -- reader_locker = g_rw_lock_reader_locker_new (&self->silo_lock); -+ locker = g_mutex_locker_new (&self->silo_lock); - /* everything is okay */ - if (self->silo != NULL && xb_silo_is_valid (self->silo) && -- g_atomic_int_get (&self->file_monitor_stamp_current) == g_atomic_int_get (&self->file_monitor_stamp)) -- return TRUE; -- g_clear_pointer (&reader_locker, g_rw_lock_reader_locker_free); -+ g_atomic_int_get (&self->file_monitor_stamp_current) == g_atomic_int_get (&self->file_monitor_stamp)) { -+ if (out_silo_filename != NULL) -+ *out_silo_filename = g_strdup (self->silo_filename); -+ if (out_silo_installed_by_desktopid != NULL) -+ *out_silo_installed_by_desktopid = self->silo_installed_by_desktopid ? g_hash_table_ref (self->silo_installed_by_desktopid) : NULL; -+ if (out_silo_installed_by_id != NULL) -+ *out_silo_installed_by_id = self->silo_installed_by_id ? g_hash_table_ref (self->silo_installed_by_id) : NULL; -+ return g_object_ref (self->silo); -+ } - - /* drat! silo needs regenerating */ -- writer_locker = g_rw_lock_writer_locker_new (&self->silo_lock); - reload: - g_clear_object (&self->silo); - g_clear_pointer (&self->silo_filename, g_free); -@@ -594,7 +599,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, - if (!xb_builder_source_load_xml (source, test_xml, - XB_BUILDER_SOURCE_FLAG_NONE, - error)) -- return FALSE; -+ return NULL; - fixup1 = xb_builder_fixup_new ("AddOriginKeywords", - gs_plugin_appstream_add_origin_keyword_cb, - self, NULL); -@@ -640,7 +645,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, - if (!gs_plugin_appstream_load_appstream (self, builder, fn, cancellable, error)) { - if (old_thread_default != NULL) - g_main_context_push_thread_default (old_thread_default); -- return FALSE; -+ return NULL; - } - } - for (guint i = 0; i < parent_appdata->len; i++) { -@@ -648,7 +653,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, - if (!gs_plugin_appstream_load_appdata (self, builder, fn, cancellable, error)) { - if (old_thread_default != NULL) - g_main_context_push_thread_default (old_thread_default); -- return FALSE; -+ return NULL; - } - } - for (guint i = 0; i < parent_desktop->len; i++) { -@@ -657,7 +662,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, - if (!gs_appstream_load_desktop_files (builder, dir, NULL, &file_monitor, cancellable, error)) { - if (old_thread_default != NULL) - g_main_context_push_thread_default (old_thread_default); -- return FALSE; -+ return NULL; - } - gs_plugin_appstream_maybe_store_file_monitor (self, file_monitor); - } -@@ -678,7 +683,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, - GS_UTILS_CACHE_FLAG_CREATE_DIRECTORY, - error); - if (blobfn == NULL) -- return FALSE; -+ return NULL; - file = g_file_new_for_path (blobfn); - g_debug ("ensuring %s", blobfn); - -@@ -696,7 +701,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, - if (self->silo == NULL) { - if (old_thread_default != NULL) - g_main_context_push_thread_default (old_thread_default); -- return FALSE; -+ return NULL; - } - - if (old_thread_default != NULL) -@@ -717,7 +722,7 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, - GS_PLUGIN_ERROR, - GS_PLUGIN_ERROR_NOT_SUPPORTED, - "No AppStream data found"); -- return FALSE; -+ return NULL; - } - - g_clear_object (&n); -@@ -768,7 +773,13 @@ gs_plugin_appstream_check_silo (GsPluginAppstream *self, - } - - /* success */ -- return TRUE; -+ if (out_silo_filename != NULL) -+ *out_silo_filename = g_strdup (self->silo_filename); -+ if (out_silo_installed_by_desktopid != NULL) -+ *out_silo_installed_by_desktopid = self->silo_installed_by_desktopid ? g_hash_table_ref (self->silo_installed_by_desktopid) : NULL; -+ if (out_silo_installed_by_id != NULL) -+ *out_silo_installed_by_id = self->silo_installed_by_id ? g_hash_table_ref (self->silo_installed_by_id) : NULL; -+ return g_object_ref (self->silo); - } - - static void -@@ -776,7 +787,6 @@ gs_plugin_appstream_reload (GsPlugin *plugin) - { - GsPluginAppstream *self; - g_autoptr(GsAppList) list = NULL; -- g_autoptr(GRWLockWriterLocker) writer_locker = NULL; - guint sz; - - g_return_if_fail (GS_IS_PLUGIN_APPSTREAM (plugin)); -@@ -790,9 +800,8 @@ gs_plugin_appstream_reload (GsPlugin *plugin) - } - - self = GS_PLUGIN_APPSTREAM (plugin); -- writer_locker = g_rw_lock_writer_locker_new (&self->silo_lock); -- if (self->silo != NULL) -- xb_silo_invalidate (self->silo); -+ /* simpler than getting the silo and setting it invalid */ -+ g_atomic_int_inc (&self->file_monitor_stamp); - } - - static gint -@@ -834,11 +843,13 @@ setup_thread_cb (GTask *task, - GCancellable *cancellable) - { - GsPluginAppstream *self = GS_PLUGIN_APPSTREAM (source_object); -+ g_autoptr(XbSilo) silo = NULL; - g_autoptr(GError) local_error = NULL; - - assert_in_worker (self); - -- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) -+ silo = gs_plugin_appstream_ref_silo (self, NULL, NULL, NULL, cancellable, &local_error); -+ if (silo == NULL) - g_task_return_error (task, g_steal_pointer (&local_error)); - else - g_task_return_boolean (task, TRUE); -@@ -910,21 +921,21 @@ url_to_app_thread_cb (GTask *task, - GsPluginAppstream *self = GS_PLUGIN_APPSTREAM (source_object); - GsPluginUrlToAppData *data = task_data; - g_autoptr(GsAppList) list = NULL; -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; - g_autoptr(GError) local_error = NULL; - - assert_in_worker (self); - - /* check silo is valid */ -- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) { -+ silo = gs_plugin_appstream_ref_silo (self, NULL, NULL, NULL, cancellable, &local_error); -+ if (silo == NULL) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - -- locker = g_rw_lock_reader_locker_new (&self->silo_lock); - list = gs_app_list_new (); - -- if (gs_appstream_url_to_app (GS_PLUGIN (self), self->silo, list, data->url, cancellable, &local_error)) -+ if (gs_appstream_url_to_app (GS_PLUGIN (self), silo, list, data->url, cancellable, &local_error)) - g_task_return_pointer (task, g_steal_pointer (&list), g_object_unref); - else - g_task_return_error (task, g_steal_pointer (&local_error)); -@@ -1006,17 +1017,14 @@ gs_plugin_appstream_set_compulsory_quirk (GsApp *app, XbNode *component) - static gboolean - gs_plugin_appstream_refine_state (GsPluginAppstream *self, - GsApp *app, -+ GHashTable *silo_installed_by_id, - GError **error) - { -- g_autoptr(GRWLockReaderLocker) locker = NULL; -- - /* Ignore apps with no ID */ -- if (gs_app_get_id (app) == NULL) -+ if (gs_app_get_id (app) == NULL || silo_installed_by_id == NULL) - return TRUE; - -- locker = g_rw_lock_reader_locker_new (&self->silo_lock); -- -- if (g_hash_table_contains (self->silo_installed_by_id, gs_app_get_id (app))) -+ if (g_hash_table_contains (silo_installed_by_id, gs_app_get_id (app))) - gs_app_set_state (app, GS_APP_STATE_INSTALLED); - return TRUE; - } -@@ -1027,20 +1035,21 @@ gs_plugin_refine_from_id (GsPluginAppstream *self, - GsPluginRefineFlags flags, - GHashTable *apps_by_id, - GHashTable *apps_by_origin_and_id, -+ XbSilo *silo, -+ const gchar *silo_filename, -+ GHashTable *silo_installed_by_desktopid, -+ GHashTable *silo_installed_by_id, - gboolean *found, - GError **error) - { - const gchar *id, *origin; - GPtrArray *components; -- g_autoptr(GRWLockReaderLocker) locker = NULL; - - /* not enough info to find */ - id = gs_app_get_id (app); - if (id == NULL) - return TRUE; - -- locker = g_rw_lock_reader_locker_new (&self->silo_lock); -- - origin = gs_app_get_origin_appstream (app); - - /* look in AppStream then fall back to AppData */ -@@ -1056,15 +1065,15 @@ gs_plugin_refine_from_id (GsPluginAppstream *self, - - for (guint i = 0; i < components->len; i++) { - XbNode *component = g_ptr_array_index (components, i); -- if (!gs_appstream_refine_app (GS_PLUGIN (self), app, self->silo, component, flags, self->silo_installed_by_desktopid, -- self->silo_filename ? self->silo_filename : "", self->default_scope, error)) -+ if (!gs_appstream_refine_app (GS_PLUGIN (self), app, silo, component, flags, silo_installed_by_desktopid, -+ silo_filename ? silo_filename : "", self->default_scope, error)) - return FALSE; - gs_plugin_appstream_set_compulsory_quirk (app, component); - } - - /* if an installed desktop or appdata file exists set to installed */ - if (gs_app_get_state (app) == GS_APP_STATE_UNKNOWN) { -- if (!gs_plugin_appstream_refine_state (self, app, error)) -+ if (!gs_plugin_appstream_refine_state (self, app, silo_installed_by_id, error)) - return FALSE; - } - -@@ -1077,6 +1086,10 @@ static gboolean - gs_plugin_refine_from_pkgname (GsPluginAppstream *self, - GsApp *app, - GsPluginRefineFlags flags, -+ XbSilo *silo, -+ const gchar *silo_filename, -+ GHashTable *silo_installed_by_desktopid, -+ GHashTable *silo_installed_by_id, - GError **error) - { - GPtrArray *sources = gs_app_get_sources (app); -@@ -1089,33 +1102,30 @@ gs_plugin_refine_from_pkgname (GsPluginAppstream *self, - /* find all apps when matching any prefixes */ - for (guint j = 0; j < sources->len; j++) { - const gchar *pkgname = g_ptr_array_index (sources, j); -- g_autoptr(GRWLockReaderLocker) locker = NULL; - g_autoptr(GString) xpath = g_string_new (NULL); - g_autoptr(XbNode) component = NULL; - -- locker = g_rw_lock_reader_locker_new (&self->silo_lock); -- - /* prefer actual apps and then fallback to anything else */ - xb_string_append_union (xpath, "components/component[@type='desktop-application']/pkgname[text()='%s']/..", pkgname); - xb_string_append_union (xpath, "components/component[@type='console-application']/pkgname[text()='%s']/..", pkgname); - xb_string_append_union (xpath, "components/component[@type='web-application']/pkgname[text()='%s']/..", pkgname); - xb_string_append_union (xpath, "components/component/pkgname[text()='%s']/..", pkgname); -- component = xb_silo_query_first (self->silo, xpath->str, &error_local); -+ component = xb_silo_query_first (silo, xpath->str, &error_local); - if (component == NULL) { - if (g_error_matches (error_local, G_IO_ERROR, G_IO_ERROR_NOT_FOUND)) - continue; - g_propagate_error (error, g_steal_pointer (&error_local)); - return FALSE; - } -- if (!gs_appstream_refine_app (GS_PLUGIN (self), app, self->silo, component, flags, self->silo_installed_by_desktopid, -- self->silo_filename ? self->silo_filename : "", self->default_scope, error)) -+ if (!gs_appstream_refine_app (GS_PLUGIN (self), app, silo, component, flags, silo_installed_by_desktopid, -+ silo_filename ? silo_filename : "", self->default_scope, error)) - return FALSE; - gs_plugin_appstream_set_compulsory_quirk (app, component); - } - - /* if an installed desktop or appdata file exists set to installed */ - if (gs_app_get_state (app) == GS_APP_STATE_UNKNOWN) { -- if (!gs_plugin_appstream_refine_state (self, app, error)) -+ if (!gs_plugin_appstream_refine_state (self, app, silo_installed_by_id, error)) - return FALSE; - } - -@@ -1153,6 +1163,10 @@ static gboolean refine_wildcard (GsPluginAppstream *self, - GsAppList *list, - GsPluginRefineFlags refine_flags, - GHashTable *apps_by_id, -+ XbSilo *silo, -+ const gchar *silo_filename, -+ GHashTable *silo_installed_by_desktopid, -+ GHashTable *silo_installed_by_id, - GCancellable *cancellable, - GError **error); - -@@ -1171,13 +1185,17 @@ refine_thread_cb (GTask *task, - g_autoptr(GHashTable) apps_by_id = NULL; - g_autoptr(GHashTable) apps_by_origin_and_id = NULL; - g_autoptr(GPtrArray) components = NULL; -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; -+ g_autofree gchar *silo_filename = NULL; -+ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; -+ g_autoptr(GHashTable) silo_installed_by_id = NULL; - g_autoptr(GError) local_error = NULL; - - assert_in_worker (self); - - /* check silo is valid */ -- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) { -+ silo = gs_plugin_appstream_ref_silo (self, &silo_filename, &silo_installed_by_desktopid, &silo_installed_by_id, cancellable, &local_error); -+ if (silo == NULL) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } -@@ -1185,9 +1203,7 @@ refine_thread_cb (GTask *task, - apps_by_id = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify) g_ptr_array_unref); - apps_by_origin_and_id = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify) g_ptr_array_unref); - -- locker = g_rw_lock_reader_locker_new (&self->silo_lock); -- -- components = xb_silo_query (self->silo, "components/component/id", 0, NULL); -+ components = xb_silo_query (silo, "components/component/id", 0, NULL); - for (guint i = 0; components != NULL && i < components->len; i++) { - XbNode *node = g_ptr_array_index (components, i); - g_autoptr(XbNode) component_node = xb_node_get_parent (node); -@@ -1234,7 +1250,7 @@ refine_thread_cb (GTask *task, - } - - g_clear_pointer (&components, g_ptr_array_unref); -- components = xb_silo_query (self->silo, "component/id", 0, NULL); -+ components = xb_silo_query (silo, "component/id", 0, NULL); - for (guint i = 0; components != NULL && i < components->len; i++) { - XbNode *node = g_ptr_array_index (components, i); - g_autoptr(XbNode) component_node = xb_node_get_parent (node); -@@ -1262,12 +1278,14 @@ refine_thread_cb (GTask *task, - continue; - - /* find by ID then fall back to package name */ -- if (!gs_plugin_refine_from_id (self, app, flags, apps_by_id, apps_by_origin_and_id, &found, &local_error)) { -+ if (!gs_plugin_refine_from_id (self, app, flags, apps_by_id, apps_by_origin_and_id, silo, silo_filename, -+ silo_installed_by_desktopid, silo_installed_by_id, &found, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - if (!found) { -- if (!gs_plugin_refine_from_pkgname (self, app, flags, &local_error)) { -+ if (!gs_plugin_refine_from_pkgname (self, app, flags, silo, silo_filename, -+ silo_installed_by_desktopid, silo_installed_by_id, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } -@@ -1286,7 +1304,8 @@ refine_thread_cb (GTask *task, - GsApp *app = gs_app_list_index (app_list, j); - - if (gs_app_has_quirk (app, GS_APP_QUIRK_IS_WILDCARD) && -- !refine_wildcard (self, app, list, flags, apps_by_id, cancellable, &local_error)) { -+ !refine_wildcard (self, app, list, flags, apps_by_id, silo, silo_filename, -+ silo_installed_by_desktopid, silo_installed_by_id,cancellable, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } -@@ -1311,20 +1330,21 @@ refine_wildcard (GsPluginAppstream *self, - GsAppList *list, - GsPluginRefineFlags refine_flags, - GHashTable *apps_by_id, -+ XbSilo *silo, -+ const gchar *silo_filename, -+ GHashTable *silo_installed_by_desktopid, -+ GHashTable *silo_installed_by_id, - GCancellable *cancellable, - GError **error) - { - const gchar *id; - GPtrArray *components; -- g_autoptr(GRWLockReaderLocker) locker = NULL; - - /* not enough info to find */ - id = gs_app_get_id (app); - if (id == NULL) - return TRUE; - -- locker = g_rw_lock_reader_locker_new (&self->silo_lock); -- - components = g_hash_table_lookup (apps_by_id, id); - if (components == NULL) - return TRUE; -@@ -1333,20 +1353,20 @@ refine_wildcard (GsPluginAppstream *self, - g_autoptr(GsApp) new = NULL; - - /* new app */ -- new = gs_appstream_create_app (GS_PLUGIN (self), self->silo, component, self->silo_filename ? self->silo_filename : "", -+ new = gs_appstream_create_app (GS_PLUGIN (self), silo, component, silo_filename ? silo_filename : "", - self->default_scope, error); - if (new == NULL) - return FALSE; - gs_app_set_scope (new, AS_COMPONENT_SCOPE_SYSTEM); - gs_app_subsume_metadata (new, app); -- if (!gs_appstream_refine_app (GS_PLUGIN (self), new, self->silo, component, refine_flags, self->silo_installed_by_desktopid, -- self->silo_filename ? self->silo_filename : "", self->default_scope, error)) -+ if (!gs_appstream_refine_app (GS_PLUGIN (self), new, silo, component, refine_flags, silo_installed_by_desktopid, -+ silo_filename ? silo_filename : "", self->default_scope, error)) - return FALSE; - gs_plugin_appstream_set_compulsory_quirk (new, component); - - /* if an installed desktop or appdata file exists set to installed */ - if (gs_app_get_state (new) == GS_APP_STATE_UNKNOWN) { -- if (!gs_plugin_appstream_refine_state (self, new, error)) -+ if (!gs_plugin_appstream_refine_state (self, new, silo_installed_by_id, error)) - return FALSE; - } - -@@ -1398,21 +1418,20 @@ refine_categories_thread_cb (GTask *task, - GCancellable *cancellable) - { - GsPluginAppstream *self = GS_PLUGIN_APPSTREAM (source_object); -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; - GsPluginRefineCategoriesData *data = task_data; - g_autoptr(GError) local_error = NULL; - - assert_in_worker (self); - - /* check silo is valid */ -- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) { -+ silo = gs_plugin_appstream_ref_silo (self, NULL, NULL, NULL, cancellable, &local_error); -+ if (silo == NULL) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - -- locker = g_rw_lock_reader_locker_new (&self->silo_lock); -- -- if (!gs_appstream_refine_category_sizes (self->silo, data->list, cancellable, &local_error)) { -+ if (!gs_appstream_refine_category_sizes (silo, data->list, cancellable, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } -@@ -1462,7 +1481,7 @@ list_apps_thread_cb (GTask *task, - GCancellable *cancellable) - { - GsPluginAppstream *self = GS_PLUGIN_APPSTREAM (source_object); -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; - g_autoptr(GsAppList) list = gs_app_list_new (); - GsPluginListAppsData *data = task_data; - GDateTime *released_since = NULL; -@@ -1516,65 +1535,64 @@ list_apps_thread_cb (GTask *task, - } - - /* check silo is valid */ -- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) { -+ silo = gs_plugin_appstream_ref_silo (self, NULL, NULL, NULL, cancellable, &local_error); -+ if (silo == NULL) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - -- locker = g_rw_lock_reader_locker_new (&self->silo_lock); -- - if (released_since != NULL && -- !gs_appstream_add_recent (GS_PLUGIN (self), self->silo, list, age_secs, -+ !gs_appstream_add_recent (GS_PLUGIN (self), silo, list, age_secs, - cancellable, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - - if (is_curated != GS_APP_QUERY_TRISTATE_UNSET && -- !gs_appstream_add_popular (self->silo, list, cancellable, &local_error)) { -+ !gs_appstream_add_popular (silo, list, cancellable, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - - if (is_featured != GS_APP_QUERY_TRISTATE_UNSET && -- !gs_appstream_add_featured (self->silo, list, cancellable, &local_error)) { -+ !gs_appstream_add_featured (silo, list, cancellable, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - - if (category != NULL && -- !gs_appstream_add_category_apps (GS_PLUGIN (self), self->silo, category, list, cancellable, &local_error)) { -+ !gs_appstream_add_category_apps (GS_PLUGIN (self), silo, category, list, cancellable, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - - if (is_installed == GS_APP_QUERY_TRISTATE_TRUE && -- !gs_appstream_add_installed (GS_PLUGIN (self), self->silo, list, cancellable, &local_error)) { -+ !gs_appstream_add_installed (GS_PLUGIN (self), silo, list, cancellable, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - - if (deployment_featured != NULL && -- !gs_appstream_add_deployment_featured (self->silo, deployment_featured, list, -+ !gs_appstream_add_deployment_featured (silo, deployment_featured, list, - cancellable, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - - if (developers != NULL && -- !gs_appstream_search_developer_apps (GS_PLUGIN (self), self->silo, developers, list, cancellable, &local_error)) { -+ !gs_appstream_search_developer_apps (GS_PLUGIN (self), silo, developers, list, cancellable, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - - if (keywords != NULL && -- !gs_appstream_search (GS_PLUGIN (self), self->silo, keywords, list, cancellable, &local_error)) { -+ !gs_appstream_search (GS_PLUGIN (self), silo, keywords, list, cancellable, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } - - if (alternate_of != NULL && -- !gs_appstream_add_alternates (self->silo, alternate_of, list, cancellable, &local_error)) { -+ !gs_appstream_add_alternates (silo, alternate_of, list, cancellable, &local_error)) { - g_task_return_error (task, g_steal_pointer (&local_error)); - return; - } -@@ -1623,12 +1641,14 @@ refresh_metadata_thread_cb (GTask *task, - GCancellable *cancellable) - { - GsPluginAppstream *self = GS_PLUGIN_APPSTREAM (source_object); -+ g_autoptr(XbSilo) silo = NULL; - g_autoptr(GError) local_error = NULL; - - assert_in_worker (self); - - /* Checking the silo will refresh it if needed. */ -- if (!gs_plugin_appstream_check_silo (self, cancellable, &local_error)) -+ silo = gs_plugin_appstream_ref_silo (self, NULL, NULL, NULL, cancellable, &local_error); -+ if (silo == NULL) - g_task_return_error (task, g_steal_pointer (&local_error)); - else - g_task_return_boolean (task, TRUE); --- -GitLab - - -From cf04c32b5fb1fd267096fad8dd11a22429ad788a Mon Sep 17 00:00:00 2001 -Date: Mon, 29 Apr 2024 17:45:08 +0200 -Subject: [PATCH 2/3] gs-plugin-appstream: Rename file_monitor_stamp to - silo_change_stamp - -Since it's used also in the gs_plugin_appstream_reload() and works -like a change indicator, name it appropriately to avoid confusion. ---- - plugins/core/gs-plugin-appstream.c | 16 ++++++++-------- - 1 file changed, 8 insertions(+), 8 deletions(-) - -diff --git a/plugins/core/gs-plugin-appstream.c b/plugins/core/gs-plugin-appstream.c -index 5749a175f3..99fe5a1432 100644 ---- a/plugins/core/gs-plugin-appstream.c -+++ b/plugins/core/gs-plugin-appstream.c -@@ -46,8 +46,8 @@ struct _GsPluginAppstream - GPtrArray *file_monitors; /* (owned) (element-type GFileMonitor) */ - /* The stamps help to avoid locking the silo lock in the main thread - and also to detect changes while loading other appstream data. */ -- gint file_monitor_stamp; /* the file monitor stamp, increased on every file monitor change */ -- gint file_monitor_stamp_current; /* the currently known file monitor stamp, checked for changes */ -+ gint silo_change_stamp; /* the silo change stamp, increased on every silo change */ -+ gint silo_change_stamp_current; /* the currently known silo change stamp, checked for changes */ - }; - - G_DEFINE_TYPE (GsPluginAppstream, gs_plugin_appstream, GS_TYPE_PLUGIN) -@@ -224,7 +224,7 @@ gs_plugin_appstream_file_monitor_changed_cb (GFileMonitor *monitor, - gpointer user_data) - { - GsPluginAppstream *self = user_data; -- g_atomic_int_inc (&self->file_monitor_stamp); -+ g_atomic_int_inc (&self->silo_change_stamp); - } - - static void -@@ -550,7 +550,7 @@ gs_plugin_appstream_ref_silo (GsPluginAppstream *self, - locker = g_mutex_locker_new (&self->silo_lock); - /* everything is okay */ - if (self->silo != NULL && xb_silo_is_valid (self->silo) && -- g_atomic_int_get (&self->file_monitor_stamp_current) == g_atomic_int_get (&self->file_monitor_stamp)) { -+ g_atomic_int_get (&self->silo_change_stamp_current) == g_atomic_int_get (&self->silo_change_stamp)) { - if (out_silo_filename != NULL) - *out_silo_filename = g_strdup (self->silo_filename); - if (out_silo_installed_by_desktopid != NULL) -@@ -568,7 +568,7 @@ gs_plugin_appstream_ref_silo (GsPluginAppstream *self, - g_clear_pointer (&blobfn, g_free); - self->default_scope = AS_COMPONENT_SCOPE_UNKNOWN; - g_ptr_array_set_size (self->file_monitors, 0); -- g_atomic_int_set (&self->file_monitor_stamp_current, g_atomic_int_get (&self->file_monitor_stamp)); -+ g_atomic_int_set (&self->silo_change_stamp_current, g_atomic_int_get (&self->silo_change_stamp)); - - /* FIXME: https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1422 */ - old_thread_default = g_main_context_ref_thread_default (); -@@ -707,7 +707,7 @@ gs_plugin_appstream_ref_silo (GsPluginAppstream *self, - if (old_thread_default != NULL) - g_main_context_push_thread_default (old_thread_default); - -- if (g_atomic_int_get (&self->file_monitor_stamp_current) != g_atomic_int_get (&self->file_monitor_stamp)) { -+ if (g_atomic_int_get (&self->silo_change_stamp_current) != g_atomic_int_get (&self->silo_change_stamp)) { - g_ptr_array_set_size (parent_appdata, 0); - g_ptr_array_set_size (parent_appstream, 0); - g_debug ("appstream: File monitors reported change while loading appstream data, reloading..."); -@@ -800,8 +800,8 @@ gs_plugin_appstream_reload (GsPlugin *plugin) - } - - self = GS_PLUGIN_APPSTREAM (plugin); -- /* simpler than getting the silo and setting it invalid */ -- g_atomic_int_inc (&self->file_monitor_stamp); -+ /* Invalidate the reference to the current silo */ -+ g_atomic_int_inc (&self->silo_change_stamp); - } - - static gint --- -GitLab - - -From 59b301b8a878f3e81359909a8d4107715eb60a35 Mon Sep 17 00:00:00 2001 -Date: Tue, 30 Apr 2024 13:13:36 +0200 -Subject: [PATCH 3/3] flatpak: Simplify XbSilo locking - -Instead of holding RW lock on the internal silo variable, simply return -a reference to it and work with it like with an immutable object. That -simplifies locking and makes the code cleaner. It can also make the code -quicker, in some cases. ---- - plugins/flatpak/gs-flatpak.c | 307 +++++++++++++++++++---------------- - 1 file changed, 163 insertions(+), 144 deletions(-) - -diff --git a/plugins/flatpak/gs-flatpak.c b/plugins/flatpak/gs-flatpak.c -index 2e175fd08e..9893cf88b7 100644 ---- a/plugins/flatpak/gs-flatpak.c -+++ b/plugins/flatpak/gs-flatpak.c -@@ -54,9 +54,11 @@ struct _GsFlatpak { - AsComponentScope scope; - GsPlugin *plugin; - XbSilo *silo; -- GRWLock silo_lock; -+ GMutex silo_lock; - gchar *silo_filename; - GHashTable *silo_installed_by_desktopid; -+ gint silo_change_stamp; -+ gint silo_change_stamp_current; - gchar *id; - guint changed_id; - GHashTable *app_silos; -@@ -654,10 +656,7 @@ gs_flatpak_create_source (GsFlatpak *self, FlatpakRemote *xremote) - static void - gs_flatpak_invalidate_silo (GsFlatpak *self) - { -- g_rw_lock_writer_lock (&self->silo_lock); -- if (self->silo != NULL) -- xb_silo_invalidate (self->silo); -- g_rw_lock_writer_unlock (&self->silo_lock); -+ g_atomic_int_inc (&self->silo_change_stamp); - } - - static void -@@ -1085,32 +1084,39 @@ gs_flatpak_rescan_installed (GsFlatpak *self, - g_debug ("Failed to read flatpak .desktop files in %s: %s", path, error_local->message); - } - --static gboolean --gs_flatpak_rescan_appstream_store (GsFlatpak *self, -- gboolean interactive, -- GCancellable *cancellable, -- GError **error) -+static XbSilo * -+gs_flatpak_ref_silo (GsFlatpak *self, -+ gboolean interactive, -+ gchar **out_silo_filename, -+ GHashTable **out_silo_installed_by_desktopid, -+ GCancellable *cancellable, -+ GError **error) - { - g_autofree gchar *blobfn = NULL; - g_autoptr(GFile) file = NULL; - g_autoptr(GPtrArray) xremotes = NULL; - g_autoptr(GPtrArray) desktop_paths = NULL; -- g_autoptr(GRWLockReaderLocker) reader_locker = NULL; -- g_autoptr(GRWLockWriterLocker) writer_locker = NULL; -+ g_autoptr(GMutexLocker) locker = NULL; - g_autoptr(XbBuilder) builder = NULL; - g_autoptr(GMainContext) old_thread_default = NULL; - -- reader_locker = g_rw_lock_reader_locker_new (&self->silo_lock); -+ locker = g_mutex_locker_new (&self->silo_lock); - /* everything is okay */ -- if (self->silo != NULL && xb_silo_is_valid (self->silo)) -- return TRUE; -- g_clear_pointer (&reader_locker, g_rw_lock_reader_locker_free); -+ if (self->silo != NULL && xb_silo_is_valid (self->silo) && -+ g_atomic_int_get (&self->silo_change_stamp_current) == g_atomic_int_get (&self->silo_change_stamp)) { -+ if (out_silo_filename != NULL) -+ *out_silo_filename = g_strdup (self->silo_filename); -+ if (out_silo_installed_by_desktopid != NULL && self->silo_installed_by_desktopid) -+ *out_silo_installed_by_desktopid = g_hash_table_ref (self->silo_installed_by_desktopid); -+ return g_object_ref (self->silo); -+ } - - /* drat! silo needs regenerating */ -- writer_locker = g_rw_lock_writer_locker_new (&self->silo_lock); -+ reload: - g_clear_object (&self->silo); - g_clear_pointer (&self->silo_filename, g_free); - g_clear_pointer (&self->silo_installed_by_desktopid, g_hash_table_unref); -+ g_atomic_int_set (&self->silo_change_stamp_current, g_atomic_int_get (&self->silo_change_stamp)); - - /* FIXME: https://gitlab.gnome.org/GNOME/gnome-software/-/issues/1422 */ - old_thread_default = g_main_context_ref_thread_default (); -@@ -1138,7 +1144,7 @@ gs_flatpak_rescan_appstream_store (GsFlatpak *self, - error); - if (xremotes == NULL) { - gs_flatpak_error_convert (error); -- return FALSE; -+ return NULL; - } - for (guint i = 0; i < xremotes->len; i++) { - g_autoptr(GError) error_local = NULL; -@@ -1152,7 +1158,7 @@ gs_flatpak_rescan_appstream_store (GsFlatpak *self, - flatpak_remote_get_name (xremote), error_local->message); - if (g_cancellable_set_error_if_cancelled (cancellable, error)) { - gs_flatpak_error_convert (error); -- return FALSE; -+ return NULL; - } - } - } -@@ -1176,7 +1182,7 @@ gs_flatpak_rescan_appstream_store (GsFlatpak *self, - GS_UTILS_CACHE_FLAG_CREATE_DIRECTORY, - error); - if (blobfn == NULL) -- return FALSE; -+ return NULL; - file = g_file_new_for_path (blobfn); - g_debug ("ensuring %s", blobfn); - -@@ -1195,6 +1201,17 @@ gs_flatpak_rescan_appstream_store (GsFlatpak *self, - if (old_thread_default != NULL) - g_main_context_push_thread_default (old_thread_default); - -+ if (g_atomic_int_get (&self->silo_change_stamp_current) != g_atomic_int_get (&self->silo_change_stamp)) { -+ g_clear_pointer (&blobfn, g_free); -+ g_clear_pointer (&xremotes, g_ptr_array_unref); -+ g_clear_pointer (&desktop_paths, g_ptr_array_unref); -+ g_clear_pointer (&old_thread_default, g_main_context_unref); -+ g_clear_object (&file); -+ g_clear_object (&builder); -+ g_debug ("flatpak: Reported change while loading appstream data, reloading..."); -+ goto reload; -+ } -+ - if (self->silo != NULL) { - g_autoptr(GPtrArray) installed = NULL; - g_autoptr(XbNode) info_filename = NULL; -@@ -1218,66 +1235,46 @@ gs_flatpak_rescan_appstream_store (GsFlatpak *self, - info_filename = xb_silo_query_first (self->silo, "/info/filename", NULL); - if (info_filename != NULL) - self->silo_filename = g_strdup (xb_node_get_text (info_filename)); -+ -+ if (out_silo_filename != NULL) -+ *out_silo_filename = g_strdup (self->silo_filename); -+ if (out_silo_installed_by_desktopid != NULL && self->silo_installed_by_desktopid) -+ *out_silo_installed_by_desktopid = g_hash_table_ref (self->silo_installed_by_desktopid); -+ return g_object_ref (self->silo); - } - -- /* success */ -- return self->silo != NULL; -+ return NULL; - } - - static gboolean - gs_flatpak_rescan_app_data (GsFlatpak *self, - gboolean interactive, -+ XbSilo **out_silo, -+ gchar **out_silo_filename, -+ GHashTable **out_silo_installed_by_desktopid, - GCancellable *cancellable, - GError **error) - { -+ g_autoptr(XbSilo) silo = NULL; -+ - if (self->requires_full_rescan) { - gboolean res = gs_flatpak_refresh (self, 60, interactive, cancellable, error); -- if (res) -+ if (res) { - self->requires_full_rescan = FALSE; -- else -+ } else { - gs_flatpak_internal_data_changed (self); -- return res; -+ return res; -+ } - } - -- if (!gs_flatpak_rescan_appstream_store (self, interactive, cancellable, error)) { -+ silo = gs_flatpak_ref_silo (self, interactive, out_silo_filename, out_silo_installed_by_desktopid, cancellable, error); -+ if (silo == NULL) { - gs_flatpak_internal_data_changed (self); - return FALSE; - } - -- return TRUE; --} -- --/* Returns with a read lock held on @self->silo_lock on success. -- The *locker should be NULL when being called. */ --static gboolean --ensure_flatpak_silo_with_locker (GsFlatpak *self, -- GRWLockReaderLocker **locker, -- gboolean interactive, -- GCancellable *cancellable, -- GError **error) --{ -- /* should not hold the lock when called */ -- g_return_val_if_fail (*locker == NULL, FALSE); -- -- /* ensure valid */ -- if (!gs_flatpak_rescan_app_data (self, interactive, cancellable, error)) -- return FALSE; -- -- *locker = g_rw_lock_reader_locker_new (&self->silo_lock); -- -- while (self->silo == NULL) { -- g_clear_pointer (locker, g_rw_lock_reader_locker_free); -- -- if (!gs_flatpak_rescan_appstream_store (self, interactive, cancellable, error)) { -- gs_flatpak_internal_data_changed (self); -- return FALSE; -- } -- -- /* At this point either rescan_appstream_store() returned an error or it successfully -- * initialised self->silo. There is the possibility that another thread will invalidate -- * the silo before we regain the lock. If so, we’ll have to rescan again. */ -- *locker = g_rw_lock_reader_locker_new (&self->silo_lock); -- } -+ if (out_silo != NULL) -+ *out_silo = g_steal_pointer (&silo); - - return TRUE; - } -@@ -1412,6 +1409,7 @@ gs_flatpak_refresh_appstream (GsFlatpak *self, - { - gboolean ret; - g_autoptr(GPtrArray) xremotes = NULL; -+ g_autoptr(XbSilo) silo = NULL; - - /* get remotes */ - xremotes = flatpak_installation_list_remotes (gs_flatpak_get_installation (self, interactive), -@@ -1498,7 +1496,8 @@ gs_flatpak_refresh_appstream (GsFlatpak *self, - } - - /* ensure the AppStream silo is up to date */ -- if (!gs_flatpak_rescan_appstream_store (self, interactive, cancellable, error)) { -+ silo = gs_flatpak_ref_silo (self, interactive, NULL, NULL, cancellable, error); -+ if (silo == NULL) { - gs_flatpak_internal_data_changed (self); - return FALSE; - } -@@ -1646,7 +1645,7 @@ gs_flatpak_add_sources (GsFlatpak *self, - FlatpakInstallation *installation = gs_flatpak_get_installation (self, interactive); - - /* refresh */ -- if (!gs_flatpak_rescan_app_data (self, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, NULL, NULL, NULL, cancellable, error)) - return FALSE; - - /* get installed apps and runtimes */ -@@ -2080,7 +2079,7 @@ gs_flatpak_add_updates (GsFlatpak *self, - FlatpakInstallation *installation = gs_flatpak_get_installation (self, interactive); - - /* ensure valid */ -- if (!gs_flatpak_rescan_app_data (self, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, NULL, NULL, NULL, cancellable, error)) - return FALSE; - - /* get all the updatable apps and runtimes */ -@@ -2390,10 +2389,8 @@ gs_flatpak_create_fake_ref (GsApp *app, GError **error) - return xref; - } - --/* the _unlocked() version doesn't call gs_flatpak_rescan_app_data, -- * in order to avoid taking the writer lock on self->silo_lock */ - static gboolean --gs_flatpak_refine_app_state_unlocked (GsFlatpak *self, -+gs_flatpak_refine_app_state_internal (GsFlatpak *self, - GsApp *app, - gboolean interactive, - gboolean force_state_update, -@@ -2505,10 +2502,10 @@ gs_flatpak_refine_app_state (GsFlatpak *self, - GError **error) - { - /* ensure valid */ -- if (!gs_flatpak_rescan_app_data (self, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, NULL, NULL, NULL, cancellable, error)) - return FALSE; - -- return gs_flatpak_refine_app_state_unlocked (self, app, interactive, force_state_update, cancellable, error); -+ return gs_flatpak_refine_app_state_internal (self, app, interactive, force_state_update, cancellable, error); - } - - static GsApp * -@@ -2594,7 +2591,7 @@ gs_flatpak_create_runtime (GsFlatpak *self, - gs_flatpak_app_set_ref_name (app, split[0]); - gs_flatpak_app_set_ref_arch (app, split[1]); - -- if (!gs_flatpak_refine_app_state_unlocked (self, app, interactive, FALSE, NULL, &local_error)) -+ if (!gs_flatpak_refine_app_state_internal (self, app, interactive, FALSE, NULL, &local_error)) - g_debug ("Failed to refine state for runtime '%s': %s", gs_app_get_unique_id (app), local_error->message); - - /* save in the cache */ -@@ -2984,7 +2981,7 @@ gs_plugin_refine_item_size (GsFlatpak *self, - - /* is the app_runtime already installed? */ - app_runtime = gs_app_get_runtime (app); -- if (!gs_flatpak_refine_app_state_unlocked (self, -+ if (!gs_flatpak_refine_app_state_internal (self, - app_runtime, - interactive, - FALSE, -@@ -3096,6 +3093,8 @@ gs_flatpak_refine_appstream_from_bytes (GsFlatpak *self, - GBytes *appstream_gz, - GsPluginRefineFlags flags, - gboolean interactive, -+ const gchar *silo_filename, -+ GHashTable *silo_installed_by_desktopid, - GCancellable *cancellable, - GError **error) - { -@@ -3229,8 +3228,8 @@ gs_flatpak_refine_appstream_from_bytes (GsFlatpak *self, - } - - /* copy details from AppStream to app */ -- if (!gs_appstream_refine_app (self->plugin, app, silo, component_node, flags, self->silo_installed_by_desktopid, -- self->silo_filename ? self->silo_filename : "", self->scope, error)) -+ if (!gs_appstream_refine_app (self->plugin, app, silo, component_node, flags, silo_installed_by_desktopid, -+ silo_filename ? silo_filename : "", self->scope, error)) - return FALSE; - - if (gs_app_get_origin (app)) -@@ -3324,6 +3323,8 @@ static gboolean - gs_flatpak_refine_appstream (GsFlatpak *self, - GsApp *app, - XbSilo *silo, -+ const gchar *silo_filename, -+ GHashTable *silo_installed_by_desktopid, - GsPluginRefineFlags flags, - GHashTable *components_by_bundle, - gboolean interactive, -@@ -3410,11 +3411,12 @@ gs_flatpak_refine_appstream (GsFlatpak *self, - appstream_gz, - flags, - interactive, -+ silo_filename, silo_installed_by_desktopid, - cancellable, error); - } - -- if (!gs_appstream_refine_app (self->plugin, app, silo, component, flags, self->silo_installed_by_desktopid, -- self->silo_filename ? self->silo_filename : "", self->scope, error)) -+ if (!gs_appstream_refine_app (self->plugin, app, silo, component, flags, silo_installed_by_desktopid, -+ silo_filename ? silo_filename : "", self->scope, error)) - return FALSE; - - /* use the default release as the version number */ -@@ -3423,13 +3425,15 @@ gs_flatpak_refine_appstream (GsFlatpak *self, - } - - static gboolean --gs_flatpak_refine_app_unlocked (GsFlatpak *self, -+gs_flatpak_refine_app_internal (GsFlatpak *self, - GsApp *app, - GsPluginRefineFlags flags, - gboolean interactive, - gboolean force_state_update, - GHashTable *components_by_bundle, -- GRWLockReaderLocker **locker, -+ XbSilo *silo, -+ const gchar *silo_filename, -+ GHashTable *silo_installed_by_desktopid, - GCancellable *cancellable, - GError **error) - { -@@ -3440,13 +3444,9 @@ gs_flatpak_refine_app_unlocked (GsFlatpak *self, - if (gs_app_get_bundle_kind (app) != AS_BUNDLE_KIND_FLATPAK) - return TRUE; - -- g_clear_pointer (locker, g_rw_lock_reader_locker_free); -- -- if (!ensure_flatpak_silo_with_locker (self, locker, interactive, cancellable, error)) -- return FALSE; -- - /* always do AppStream properties */ -- if (!gs_flatpak_refine_appstream (self, app, self->silo, flags, components_by_bundle, interactive, cancellable, error)) -+ if (!gs_flatpak_refine_appstream (self, app, silo, silo_filename, silo_installed_by_desktopid, -+ flags, components_by_bundle, interactive, cancellable, error)) - return FALSE; - - /* AppStream sets the source to appname/arch/branch */ -@@ -3456,7 +3456,7 @@ gs_flatpak_refine_app_unlocked (GsFlatpak *self, - } - - /* check the installed state */ -- if (!gs_flatpak_refine_app_state_unlocked (self, app, interactive, force_state_update, cancellable, error)) { -+ if (!gs_flatpak_refine_app_state_internal (self, app, interactive, force_state_update, cancellable, error)) { - g_prefix_error (error, "failed to get state: "); - return FALSE; - } -@@ -3473,7 +3473,8 @@ gs_flatpak_refine_app_unlocked (GsFlatpak *self, - - /* if the state was changed, perhaps set the version from the release */ - if (old_state != gs_app_get_state (app)) { -- if (!gs_flatpak_refine_appstream (self, app, self->silo, flags, components_by_bundle, interactive, cancellable, error)) -+ if (!gs_flatpak_refine_appstream (self, app, silo, silo_filename, silo_installed_by_desktopid, -+ flags, components_by_bundle, interactive, cancellable, error)) - return FALSE; - } - -@@ -3567,11 +3568,16 @@ gs_flatpak_refine_addons (GsFlatpak *self, - gboolean interactive, - GCancellable *cancellable) - { -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; -+ g_autofree gchar *silo_filename = NULL; -+ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; - g_autoptr(GsAppList) addons = NULL; - g_autoptr(GString) errors = NULL; - guint ii, sz; - -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, &silo_filename, &silo_installed_by_desktopid, cancellable, NULL)) -+ return; -+ - addons = gs_app_dup_addons (parent_app); - sz = addons ? gs_app_list_length (addons) : 0; - -@@ -3582,7 +3588,8 @@ gs_flatpak_refine_addons (GsFlatpak *self, - if (state != gs_app_get_state (addon)) - continue; - -- if (!gs_flatpak_refine_app_unlocked (self, addon, flags, interactive, TRUE, NULL, &locker, cancellable, &local_error)) { -+ if (!gs_flatpak_refine_app_internal (self, addon, flags, interactive, TRUE, NULL, silo, silo_filename, -+ silo_installed_by_desktopid, cancellable, &local_error)) { - if (errors) - g_string_append_c (errors, '\n'); - else -@@ -3614,13 +3621,16 @@ gs_flatpak_refine_app (GsFlatpak *self, - GCancellable *cancellable, - GError **error) - { -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; -+ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; -+ g_autofree gchar *silo_filename = NULL; - - /* ensure valid */ -- if (!gs_flatpak_rescan_app_data (self, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, &silo_filename, &silo_installed_by_desktopid, cancellable, error)) - return FALSE; - -- return gs_flatpak_refine_app_unlocked (self, app, flags, interactive, force_state_update, NULL, &locker, cancellable, error); -+ return gs_flatpak_refine_app_internal (self, app, flags, interactive, force_state_update, NULL, -+ silo, silo_filename, silo_installed_by_desktopid, cancellable, error); - } - - gboolean -@@ -3634,7 +3644,9 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, - const gchar *id; - GPtrArray* components = NULL; - g_autoptr(GError) error_local = NULL; -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; -+ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; -+ g_autofree gchar *silo_filename = NULL; - - GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcard, "Flatpak (refine wildcard)", NULL); - -@@ -3643,7 +3655,8 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, - if (id == NULL) - return TRUE; - -- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) -+ silo = gs_flatpak_ref_silo (self, interactive, &silo_filename, &silo_installed_by_desktopid, cancellable, error); -+ if (silo == NULL) - return FALSE; - - GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardQuerySilo, "Flatpak (query silo)", NULL); -@@ -3653,7 +3666,7 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, - } else { - g_autoptr(GPtrArray) components_with_id = NULL; - *inout_components_by_id = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify) g_ptr_array_unref); -- components_with_id = xb_silo_query (self->silo, "components/component/id", 0, &error_local); -+ components_with_id = xb_silo_query (silo, "components/component/id", 0, &error_local); - if (components_with_id == NULL) { - if (g_error_matches (error_local, G_IO_ERROR, G_IO_ERROR_NOT_FOUND)) - return TRUE; -@@ -3686,7 +3699,7 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, - g_autoptr(GPtrArray) bundles = NULL; - - *inout_components_by_bundle = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_object_unref); -- bundles = xb_silo_query (self->silo, "/components/component/bundle[@type='flatpak']", 0, NULL); -+ bundles = xb_silo_query (silo, "/components/component/bundle[@type='flatpak']", 0, NULL); - for (guint b = 0; bundles != NULL && b < bundles->len; b++) { - XbNode *bundle_node = g_ptr_array_index (bundles, b); - g_autoptr(XbNode) component_node = xb_node_get_parent (bundle_node); -@@ -3709,7 +3722,7 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, - g_autoptr(GsApp) new = NULL; - - GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardCreateAppstreamApp, "Flatpak (create Appstream app)", NULL); -- new = gs_appstream_create_app (self->plugin, self->silo, component, self->silo_filename ? self->silo_filename : "", -+ new = gs_appstream_create_app (self->plugin, silo, component, silo_filename ? silo_filename : "", - self->scope, error); - GS_PROFILER_END_SCOPED (FlatpakRefineWildcardCreateAppstreamApp); - -@@ -3761,7 +3774,8 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, - g_debug ("Failed to get ref info for '%s' from wildcard '%s', skipping it...", gs_app_get_id (new), id); - } else { - GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardRefineNewApp, "Flatpak (refine new app)", NULL); -- if (!gs_flatpak_refine_app_unlocked (self, new, refine_flags, interactive, FALSE, *inout_components_by_bundle, &locker, cancellable, error)) -+ if (!gs_flatpak_refine_app_internal (self, new, refine_flags, interactive, FALSE, *inout_components_by_bundle, -+ silo, silo_filename, silo_installed_by_desktopid, cancellable, error)) - return FALSE; - GS_PROFILER_END_SCOPED (FlatpakRefineWildcardRefineNewApp); - -@@ -3894,10 +3908,18 @@ gs_flatpak_file_to_app_bundle (GsFlatpak *self, - /* load AppStream */ - appstream_gz = flatpak_bundle_ref_get_appstream (xref_bundle); - if (appstream_gz != NULL) { -+ g_autofree gchar *silo_filename = NULL; -+ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; -+ g_autoptr(XbSilo) tmp_silo = NULL; -+ -+ tmp_silo = gs_flatpak_ref_silo (self, interactive, &silo_filename, &silo_installed_by_desktopid, cancellable, error); -+ if (tmp_silo == NULL) -+ return NULL; - if (!gs_flatpak_refine_appstream_from_bytes (self, app, NULL, NULL, - appstream_gz, - GS_PLUGIN_REFINE_FLAGS_REQUIRE_ID, - interactive, -+ silo_filename, silo_installed_by_desktopid, - cancellable, error)) - return NULL; - } else { -@@ -3995,6 +4017,9 @@ gs_flatpak_file_to_app_ref (GsFlatpak *self, - g_autoptr(GsApp) app = NULL; - g_autoptr(XbBuilder) builder = xb_builder_new (); - g_autoptr(XbSilo) silo = NULL; -+ g_autoptr(XbSilo) tmp_silo = NULL; -+ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; -+ g_autofree gchar *silo_filename = NULL; - g_autofree gchar *origin_url = NULL; - g_autofree gchar *ref_comment = NULL; - g_autofree gchar *ref_description = NULL; -@@ -4274,8 +4299,12 @@ gs_flatpak_file_to_app_ref (GsFlatpak *self, - g_debug ("showing AppStream data: %s", xml); - } - -+ tmp_silo = gs_flatpak_ref_silo (self, interactive, &silo_filename, &silo_installed_by_desktopid, cancellable, error); -+ if (tmp_silo == NULL) -+ return NULL; -+ - /* get extra AppStream data if available */ -- if (!gs_flatpak_refine_appstream (self, app, silo, -+ if (!gs_flatpak_refine_appstream (self, app, silo, silo_filename, silo_installed_by_desktopid, - GS_PLUGIN_REFINE_FLAGS_MASK, - NULL, - interactive, -@@ -4296,17 +4325,16 @@ gs_flatpak_search (GsFlatpak *self, - GError **error) - { - g_autoptr(GsAppList) list_tmp = gs_app_list_new (); -- g_autoptr(GRWLockReaderLocker) locker = NULL; - g_autoptr(GMutexLocker) app_silo_locker = NULL; - g_autoptr(GPtrArray) silos_to_remove = g_ptr_array_new (); -+ g_autoptr(XbSilo) silo = NULL; - GHashTableIter iter; - gpointer key, value; - -- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) - return FALSE; - -- if (!gs_appstream_search (self->plugin, self->silo, values, list_tmp, -- cancellable, error)) -+ if (!gs_appstream_search (self->plugin, silo, values, list_tmp, cancellable, error)) - return FALSE; - - gs_flatpak_ensure_remote_title (self, interactive, cancellable); -@@ -4353,8 +4381,8 @@ gs_flatpak_search (GsFlatpak *self, - } - - for (guint i = 0; i < silos_to_remove->len; i++) { -- const char *silo = g_ptr_array_index (silos_to_remove, i); -- g_hash_table_remove (self->app_silos, silo); -+ const char *app_ref = g_ptr_array_index (silos_to_remove, i); -+ g_hash_table_remove (self->app_silos, app_ref); - } - - return TRUE; -@@ -4369,17 +4397,16 @@ gs_flatpak_search_developer_apps (GsFlatpak *self, - GError **error) - { - g_autoptr(GsAppList) list_tmp = gs_app_list_new (); -- g_autoptr(GRWLockReaderLocker) locker = NULL; - g_autoptr(GMutexLocker) app_silo_locker = NULL; - g_autoptr(GPtrArray) silos_to_remove = g_ptr_array_new (); -+ g_autoptr(XbSilo) silo = NULL; - GHashTableIter iter; - gpointer key, value; - -- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) - return FALSE; - -- if (!gs_appstream_search_developer_apps (self->plugin, self->silo, values, list_tmp, -- cancellable, error)) -+ if (!gs_appstream_search_developer_apps (self->plugin, silo, values, list_tmp, cancellable, error)) - return FALSE; - - gs_flatpak_ensure_remote_title (self, interactive, cancellable); -@@ -4426,8 +4453,8 @@ gs_flatpak_search_developer_apps (GsFlatpak *self, - } - - for (guint i = 0; i < silos_to_remove->len; i++) { -- const char *silo = g_ptr_array_index (silos_to_remove, i); -- g_hash_table_remove (self->app_silos, silo); -+ const char *app_ref = g_ptr_array_index (silos_to_remove, i); -+ g_hash_table_remove (self->app_silos, app_ref); - } - - return TRUE; -@@ -4441,14 +4468,12 @@ gs_flatpak_add_category_apps (GsFlatpak *self, - GCancellable *cancellable, - GError **error) - { -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; - -- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) - return FALSE; - -- return gs_appstream_add_category_apps (self->plugin, self->silo, -- category, list, -- cancellable, error); -+ return gs_appstream_add_category_apps (self->plugin, silo, category, list, cancellable, error); - } - - gboolean -@@ -4458,12 +4483,12 @@ gs_flatpak_refine_category_sizes (GsFlatpak *self, - GCancellable *cancellable, - GError **error) - { -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; - -- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) - return FALSE; - -- return gs_appstream_refine_category_sizes (self->silo, list, cancellable, error); -+ return gs_appstream_refine_category_sizes (silo, list, cancellable, error); - } - - gboolean -@@ -4474,13 +4499,12 @@ gs_flatpak_add_popular (GsFlatpak *self, - GError **error) - { - g_autoptr(GsAppList) list_tmp = gs_app_list_new (); -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; - -- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) - return FALSE; - -- if (!gs_appstream_add_popular (self->silo, list_tmp, -- cancellable, error)) -+ if (!gs_appstream_add_popular (silo, list_tmp, cancellable, error)) - return FALSE; - - gs_app_list_add_list (list, list_tmp); -@@ -4496,13 +4520,12 @@ gs_flatpak_add_featured (GsFlatpak *self, - GError **error) - { - g_autoptr(GsAppList) list_tmp = gs_app_list_new (); -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; - -- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) - return FALSE; - -- if (!gs_appstream_add_featured (self->silo, list_tmp, -- cancellable, error)) -+ if (!gs_appstream_add_featured (silo, list_tmp, cancellable, error)) - return FALSE; - - gs_app_list_add_list (list, list_tmp); -@@ -4518,12 +4541,12 @@ gs_flatpak_add_deployment_featured (GsFlatpak *self, - GCancellable *cancellable, - GError **error) - { -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; - -- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) - return FALSE; - -- return gs_appstream_add_deployment_featured (self->silo, deployments, list, cancellable, error); -+ return gs_appstream_add_deployment_featured (silo, deployments, list, cancellable, error); - } - - gboolean -@@ -4535,13 +4558,12 @@ gs_flatpak_add_alternates (GsFlatpak *self, - GError **error) - { - g_autoptr(GsAppList) list_tmp = gs_app_list_new (); -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; - -- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) - return FALSE; - -- if (!gs_appstream_add_alternates (self->silo, app, list_tmp, -- cancellable, error)) -+ if (!gs_appstream_add_alternates (silo, app, list_tmp, cancellable, error)) - return FALSE; - - gs_app_list_add_list (list, list_tmp); -@@ -4558,13 +4580,12 @@ gs_flatpak_add_recent (GsFlatpak *self, - GError **error) - { - g_autoptr(GsAppList) list_tmp = gs_app_list_new (); -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; - -- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) - return FALSE; - -- if (!gs_appstream_add_recent (self->plugin, self->silo, list_tmp, age, -- cancellable, error)) -+ if (!gs_appstream_add_recent (self->plugin, silo, list_tmp, age, cancellable, error)) - return FALSE; - - gs_flatpak_claim_app_list (self, list_tmp, interactive); -@@ -4582,12 +4603,12 @@ gs_flatpak_url_to_app (GsFlatpak *self, - GError **error) - { - g_autoptr(GsAppList) list_tmp = gs_app_list_new (); -- g_autoptr(GRWLockReaderLocker) locker = NULL; -+ g_autoptr(XbSilo) silo = NULL; - -- if (!ensure_flatpak_silo_with_locker (self, &locker, interactive, cancellable, error)) -+ if (!gs_flatpak_rescan_app_data (self, interactive, &silo, NULL, NULL, cancellable, error)) - return FALSE; - -- if (!gs_appstream_url_to_app (self->plugin, self->silo, list_tmp, url, cancellable, error)) -+ if (!gs_appstream_url_to_app (self->plugin, silo, list_tmp, url, cancellable, error)) - return FALSE; - - gs_flatpak_claim_app_list (self, list_tmp, interactive); -@@ -4638,10 +4659,8 @@ gs_flatpak_finalize (GObject *object) - g_signal_handler_disconnect (self->monitor, self->changed_id); - self->changed_id = 0; - } -- if (self->silo != NULL) -- g_object_unref (self->silo); -- if (self->monitor != NULL) -- g_object_unref (self->monitor); -+ g_clear_object (&self->silo); -+ g_clear_object (&self->monitor); - g_clear_pointer (&self->silo_filename, g_free); - g_clear_pointer (&self->silo_installed_by_desktopid, g_hash_table_unref); - -@@ -4654,7 +4673,7 @@ gs_flatpak_finalize (GObject *object) - g_object_unref (self->plugin); - g_hash_table_unref (self->broken_remotes); - g_mutex_clear (&self->broken_remotes_mutex); -- g_rw_lock_clear (&self->silo_lock); -+ g_mutex_clear (&self->silo_lock); - g_hash_table_unref (self->app_silos); - g_mutex_clear (&self->app_silos_mutex); - g_clear_pointer (&self->remote_title, g_hash_table_unref); -@@ -4675,7 +4694,7 @@ gs_flatpak_init (GsFlatpak *self) - { - /* XbSilo needs external locking as we destroy the silo and build a new - * one when something changes */ -- g_rw_lock_init (&self->silo_lock); -+ g_mutex_init (&self->silo_lock); - - g_mutex_init (&self->installed_refs_mutex); - self->installed_refs = NULL; --- -GitLab - diff --git a/gnome-software.spec b/gnome-software.spec index 5b8b2b4..708b3f5 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -18,22 +18,20 @@ %bcond dkms %[!0%{?rhel}] # this is not a library version -%define gs_plugin_version 21 +%define gs_plugin_version 22 %global tarball_version %%(echo %{version} | tr '~' '.') %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 47.2 -Release: 3%{?dist} +Version: 48~alpha2 +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://apps.gnome.org/Software -Source0: https://download.gnome.org/sources/gnome-software/47/%{name}-%{tarball_version}.tar.xz - -Patch01: 0001-crash-under-gs_appstream_gather_merge_data.patch +Source0: https://download.gnome.org/sources/gnome-software/48/%{name}-%{tarball_version}.tar.xz # ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 @@ -290,6 +288,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Tue Jan 07 2025 Milan Crha - 48~alpha2-1 +- Update to 48.alpha2 + * Mon Dec 09 2024 Milan Crha - 47.2-3 - Resolves: #2272232 (Crash under gs_appstream_gather_merge_data()) diff --git a/sources b/sources index 4b9ac1c..c1aa6d8 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-47.2.tar.xz) = 60de4a3c3237bfdc0dbbefdeccb00c97af7332a36c6beb5610fb6a416508e8b4712fd007e395ad283a3f9cb8d3e0f3a56c134ff28b3f22953a448188a1005cb6 +SHA512 (gnome-software-48.alpha2.tar.xz) = 89471657b9fe10b621b15916ced35e24aff133cdb003b57535393a47eac99bef392442cce466a6a8519997cc845f0aa4a4416b79cc3bb8e10b72da17bbfdb0b6 From 0589468f3c6d5d31a4ca5fba6a0c8e5c4c8956bd Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Tue, 14 Jan 2025 18:05:07 +0100 Subject: [PATCH 130/163] Update to 48.alpha3 --- gnome-software.spec | 5 ++++- sources | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 708b3f5..a45bc57 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -25,7 +25,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 48~alpha2 +Version: 48~alpha3 Release: 1%{?dist} Summary: A software center for GNOME @@ -288,6 +288,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Tue Jan 14 2025 Milan Crha - 48~alpha3-1 +- Update to 48.alpha3 + * Tue Jan 07 2025 Milan Crha - 48~alpha2-1 - Update to 48.alpha2 diff --git a/sources b/sources index c1aa6d8..4aa7442 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-48.alpha2.tar.xz) = 89471657b9fe10b621b15916ced35e24aff133cdb003b57535393a47eac99bef392442cce466a6a8519997cc845f0aa4a4416b79cc3bb8e10b72da17bbfdb0b6 +SHA512 (gnome-software-48.alpha3.tar.xz) = 8b05264b77c667687b1f98e9a325b6e8829328387984830bb697f1fa91ef0eef3743bbf30c0440596b655195dcc825a4d1ec56a5d2d9b2d2d87adc3118fc91f2 From 1f728b9f4b847dfbb5a02d36092e4aef0366c999 Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Thu, 16 Jan 2025 22:56:23 +0000 Subject: [PATCH 131/163] Rebuilt for https://fedoraproject.org/wiki/Fedora_42_Mass_Rebuild --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index a45bc57..02e5395 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -26,7 +26,7 @@ Name: gnome-software Version: 48~alpha3 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -288,6 +288,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Thu Jan 16 2025 Fedora Release Engineering - 48~alpha3-2 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_42_Mass_Rebuild + * Tue Jan 14 2025 Milan Crha - 48~alpha3-1 - Update to 48.alpha3 From 539e242884a19daed280a1b30eee235b9f94668a Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 3 Feb 2025 09:00:10 +0100 Subject: [PATCH 132/163] Update to 48.beta --- gnome-software.spec | 7 +++++-- sources | 2 +- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 02e5395..26aca7c 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -25,8 +25,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 48~alpha3 -Release: 2%{?dist} +Version: 48~beta +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -288,6 +288,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Mon Feb 03 2025 Milan Crha - 48~beta-1 +- Update to 48.beta + * Thu Jan 16 2025 Fedora Release Engineering - 48~alpha3-2 - Rebuilt for https://fedoraproject.org/wiki/Fedora_42_Mass_Rebuild diff --git a/sources b/sources index 4aa7442..c07dbaa 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-48.alpha3.tar.xz) = 8b05264b77c667687b1f98e9a325b6e8829328387984830bb697f1fa91ef0eef3743bbf30c0440596b655195dcc825a4d1ec56a5d2d9b2d2d87adc3118fc91f2 +SHA512 (gnome-software-48.beta.tar.xz) = 7f6744bea6e1adb136f9bccd619c9753fa94d5f00a19a3a9e8ef2806b1ea572345abe7462b20ba66e86c9a77a25a0c6cd94ffafd6607f8712e15ed66ebe3dec4 From f46e9e0cb86e66161e17be26e8bda2fbcbc05286 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 3 Mar 2025 09:38:54 +0100 Subject: [PATCH 133/163] Update to 48.rc --- gnome-software.spec | 19 +++++++++++-------- sources | 2 +- 2 files changed, 12 insertions(+), 9 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 26aca7c..3f2562c 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -1,11 +1,11 @@ -%global appstream_version 0.14.0 -%global flatpak_version 1.9.1 -%global fwupd_version 1.5.6 -%global glib2_version 2.70.0 -%global gtk4_version 4.14.0 +%global appstream_version 0.16.4 +%global flatpak_version 1.14.1 +%global fwupd_version 1.6.2 +%global glib2_version 2.76.0 +%global gtk4_version 4.16.0 %global json_glib_version 1.6.0 -%global libadwaita_version 1.6~alpha -%global libxmlb_version 0.1.7 +%global libadwaita_version 1.6.0 +%global libxmlb_version 0.3.4 %global packagekit_version 1.2.5 # Disable WebApps for RHEL builds @@ -25,7 +25,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 48~beta +Version: 48~rc Release: 1%{?dist} Summary: A software center for GNOME @@ -288,6 +288,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Mon Mar 03 2025 Milan Crha - 48~rc-1 +- Update to 48.rc + * Mon Feb 03 2025 Milan Crha - 48~beta-1 - Update to 48.beta diff --git a/sources b/sources index c07dbaa..029e225 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-48.beta.tar.xz) = 7f6744bea6e1adb136f9bccd619c9753fa94d5f00a19a3a9e8ef2806b1ea572345abe7462b20ba66e86c9a77a25a0c6cd94ffafd6607f8712e15ed66ebe3dec4 +SHA512 (gnome-software-48.rc.tar.xz) = 830e70fc6af22e6f70047ef13f2307548f939c8191370de10cdfba9a9fc907297aa06831eebc859bf442889e3782e5168d559ad115a32c3623f5179b16489703 From 909247b0df67611394949fc4cbc492ade7d68393 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 14 Mar 2025 09:47:52 +0100 Subject: [PATCH 134/163] Update to 48.0 --- gnome-software.spec | 5 ++++- sources | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 3f2562c..cf92bf5 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -25,7 +25,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 48~rc +Version: 48.0 Release: 1%{?dist} Summary: A software center for GNOME @@ -288,6 +288,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Mar 14 2025 Milan Crha - 48.0-1 +- Update to 48.0 + * Mon Mar 03 2025 Milan Crha - 48~rc-1 - Update to 48.rc diff --git a/sources b/sources index 029e225..08e726a 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-48.rc.tar.xz) = 830e70fc6af22e6f70047ef13f2307548f939c8191370de10cdfba9a9fc907297aa06831eebc859bf442889e3782e5168d559ad115a32c3623f5179b16489703 +SHA512 (gnome-software-48.0.tar.xz) = ec61395a4376dfbe281337c29822f3854ab240c32172011b5bb589ef4d9c5ee7f1e4dc559e6cdaf5d24c728eb3e01dc7cd6069813c23e280dbb5aaf8f6336742 From 807d38c4d22e6b29f599ab09bf29993421a8ed33 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 11 Apr 2025 08:37:11 +0200 Subject: [PATCH 135/163] Update to 48.1 --- gnome-software.spec | 5 ++++- sources | 2 +- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index cf92bf5..763ed62 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -25,7 +25,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 48.0 +Version: 48.1 Release: 1%{?dist} Summary: A software center for GNOME @@ -288,6 +288,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Fri Apr 11 2025 Milan Crha - 48.1-1 +- Update to 48.1 + * Fri Mar 14 2025 Milan Crha - 48.0-1 - Update to 48.0 diff --git a/sources b/sources index 08e726a..31b7ac3 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-48.0.tar.xz) = ec61395a4376dfbe281337c29822f3854ab240c32172011b5bb589ef4d9c5ee7f1e4dc559e6cdaf5d24c728eb3e01dc7cd6069813c23e280dbb5aaf8f6336742 +SHA512 (gnome-software-48.1.tar.xz) = 7cb1e7a7527e65e6283916cecee55fa4e65d71e538ced65af488d28e94801755d2ab961d2f4603cec0f781893e298fee109df4a839ee99fc3de2cefb82f25a97 From c3fcc6a85e3cac28893a05bb162a01efc02eba08 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Tue, 29 Apr 2025 11:05:44 +0200 Subject: [PATCH 136/163] Switch from PackageKit to DNF5 plugin --- 0001-dnf5-plugin.patch | 5565 ++++++++++++++++++++++++++++++++++++++++ gnome-software.spec | 35 +- 2 files changed, 5599 insertions(+), 1 deletion(-) create mode 100644 0001-dnf5-plugin.patch diff --git a/0001-dnf5-plugin.patch b/0001-dnf5-plugin.patch new file mode 100644 index 0000000..f7b5b67 --- /dev/null +++ b/0001-dnf5-plugin.patch @@ -0,0 +1,5565 @@ +at commit 31a1ad73cc4fa28b0d352a7ac392bec76e9c10a4 +Date: Wed Apr 2 14:21:03 2025 +0200 + +diff --git a/meson_options.txt b/meson_options.txt +index bc32ba561..523f572cd 100644 +--- a/meson_options.txt ++++ b/meson_options.txt +@@ -2,6 +2,7 @@ option('tests', type : 'boolean', value : true, description : 'enable tests') + option('man', type : 'boolean', value : true, description : 'enable man pages') + option('packagekit', type : 'boolean', value : true, description : 'enable PackageKit support') + option('packagekit_autoremove', type : 'boolean', value : false, description : 'autoremove packages in PackageKit') ++option('dnf5', type : 'boolean', value : true, description : 'enable dnf5 support') + option('polkit', type : 'boolean', value : true, description : 'enable PolKit support') + option('eos_updater', type : 'boolean', value : false, description : 'enable eos-updater support') + option('fwupd', type : 'boolean', value : true, description : 'enable fwupd support') +diff --git a/plugins/dnf5/gs-dnf5-progress-helper.c b/plugins/dnf5/gs-dnf5-progress-helper.c +new file mode 100644 +index 000000000..d720adc87 +--- /dev/null ++++ b/plugins/dnf5/gs-dnf5-progress-helper.c +@@ -0,0 +1,532 @@ ++/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- ++ * vi:set noexpandtab tabstop=8 shiftwidth=8: ++ * ++ * Copyright (C) 2024 Red Hat ++ * ++ * SPDX-License-Identifier: GPL-2.0+ ++ */ ++ ++#include ++ ++#include ++ ++#include "gs-dnf5-generated.h" ++ ++#include "gs-dnf5-progress-helper.h" ++ ++struct _GsDnf5ProgressHelper ++{ ++ GObject parent; ++ ++ GsDnf5RpmRpm *rpm_proxy; /* (owned) */ ++ GsDnf5Base *base_proxy; /* (owned) */ ++ GsApp *app; /* (owned) */ ++ gchar *session_object_path; /* (owned) */ ++ GHashTable *ongoing_downloads; /* (owned); gchar * (download_id) ~> DownloadInfo * */ ++ GsAppState recover_download_state; ++ guint64 to_download_total; ++ guint64 downloaded_total; ++ ++ gulong download_add_new_id; ++ gulong download_progress_id; ++ gulong download_mirror_failure_id; ++ gulong download_end_id; ++ gulong transaction_before_begin_id; ++ gulong transaction_after_complete_id; ++ gulong transaction_elem_progress_id; ++ gulong transaction_action_progress_id; ++ gulong transaction_action_start_id; ++ gulong transaction_action_stop_id; ++ gulong transaction_script_error_id; ++ gulong transaction_script_start_id; ++ gulong transaction_script_stop_id; ++ gulong transaction_transaction_progress_id; ++ gulong transaction_transaction_start_id; ++ gulong transaction_transaction_stop_id; ++ gulong transaction_unpack_error_id; ++ gulong transaction_verify_progress_id; ++ gulong transaction_verify_start_id; ++ gulong transaction_verify_stop_id; ++}; ++ ++G_DEFINE_TYPE (GsDnf5ProgressHelper, gs_dnf5_progress_helper, G_TYPE_OBJECT) ++ ++static void ++gs_dnf5_update_download_progress (GsDnf5ProgressHelper *self) ++{ ++ if (self->to_download_total > 0) ++ gs_app_set_progress (self->app, 100 * self->downloaded_total / self->to_download_total); ++} ++ ++typedef struct { ++ guint64 downloaded; ++ guint64 total; ++} DownloadInfo; ++ ++static void ++gs_dnf5_download_add_new_cb (GsDnf5Base *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_download_id, ++ const gchar *arg_description, ++ gint64 arg_total_to_download, ++ GsDnf5ProgressHelper *self) ++{ ++ DownloadInfo *download_info; ++ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: download_id:'%s' description:'%s' total_to_download:%" G_GINT64_FORMAT, ++ G_STRFUNC, arg_download_id, arg_description, arg_total_to_download); ++ g_return_if_fail (arg_download_id != NULL); ++ ++ if (arg_total_to_download <= 0) ++ return; ++ ++ if (g_hash_table_size (self->ongoing_downloads) == 0) { ++ self->recover_download_state = gs_app_get_state (self->app); ++ self->to_download_total = 0; ++ self->downloaded_total = 0; ++ gs_app_set_state (self->app, GS_APP_STATE_DOWNLOADING); ++ } ++ ++ download_info = g_new0 (DownloadInfo, 1); ++ download_info->total = arg_total_to_download; ++ ++ g_hash_table_insert (self->ongoing_downloads, g_strdup (arg_download_id), download_info); ++ self->to_download_total += arg_total_to_download; ++ ++ gs_app_set_size_download (self->app, GS_SIZE_TYPE_VALID, self->to_download_total); ++ gs_dnf5_update_download_progress (self); ++} ++ ++static void ++gs_dnf5_download_end_cb (GsDnf5Base *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_download_id, ++ guint arg_transfer_status, ++ const gchar *arg_message, ++ GsDnf5ProgressHelper *self) ++{ ++ DownloadInfo *download_info; ++ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: download_id:'%s' transfer_status:%u message:'%s'", ++ G_STRFUNC, arg_download_id, arg_transfer_status, arg_message); ++ g_return_if_fail (arg_download_id != NULL); ++ ++ download_info = g_hash_table_lookup (self->ongoing_downloads, arg_download_id); ++ if (download_info != NULL) { ++ self->downloaded_total -= download_info->downloaded; ++ self->downloaded_total += download_info->total; ++ ++ /* remove after being done with the `download_info`, because it frees it */ ++ g_hash_table_remove (self->ongoing_downloads, arg_download_id); ++ download_info = NULL; ++ ++ /* it's the last package to be downloaded */ ++ if (g_hash_table_size (self->ongoing_downloads) == 0) { ++ gs_app_set_state (self->app, self->recover_download_state); ++ gs_app_set_progress (self->app, GS_APP_PROGRESS_UNKNOWN); ++ gs_app_set_size_download (self->app, GS_SIZE_TYPE_UNKNOWN, 0); ++ } else { ++ gs_dnf5_update_download_progress (self); ++ } ++ } ++} ++ ++static void ++gs_dnf5_download_mirror_failure_cb (GsDnf5Base *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_download_id, ++ const gchar *arg_message, ++ const gchar *arg_url, ++ const gchar *arg_metadata, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: download_id:'%s' message:'%s' url:'%s' metadata:'%s'", ++ G_STRFUNC, arg_download_id, arg_message, arg_url, arg_metadata); ++} ++ ++static void ++gs_dnf5_download_progress_cb (GsDnf5Base *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_download_id, ++ gint64 arg_total_to_download, ++ gint64 arg_downloaded, ++ GsDnf5ProgressHelper *self) ++{ ++ DownloadInfo *download_info; ++ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: download_id:'%s' total_to_download:%" G_GINT64_FORMAT " downloaded:%" G_GINT64_FORMAT, ++ G_STRFUNC, arg_download_id, arg_total_to_download, arg_downloaded); ++ ++ download_info = g_hash_table_lookup (self->ongoing_downloads, arg_download_id); ++ if (download_info != NULL) { ++ self->downloaded_total += arg_downloaded - download_info->downloaded; ++ download_info->downloaded = arg_downloaded; ++ if (download_info->downloaded != (guint64) arg_total_to_download) { ++ self->to_download_total -= download_info->total; ++ download_info->total = arg_total_to_download; ++ self->to_download_total += download_info->total; ++ gs_app_set_size_download (self->app, GS_SIZE_TYPE_VALID, self->to_download_total); ++ } ++ gs_dnf5_update_download_progress (self); ++ } ++} ++ ++static void ++gs_dnf5_transaction_before_begin_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ guint64 arg_total, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ gs_app_set_progress (self->app, 0); ++ g_debug ("%s: total:%" G_GUINT64_FORMAT, G_STRFUNC, arg_total); ++} ++ ++static void ++gs_dnf5_transaction_after_complete_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ gboolean arg_success, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: success:%d", G_STRFUNC, arg_success); ++ gs_app_set_progress (self->app, 100); ++} ++ ++static void ++gs_dnf5_transaction_elem_progress_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_nevra, ++ guint64 arg_processed, ++ guint64 arg_total, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: nevra:'%s' progress:%" G_GUINT64_FORMAT "/%" G_GUINT64_FORMAT, G_STRFUNC, arg_nevra, arg_processed, arg_total); ++ if (arg_total != 0) ++ gs_app_set_progress (self->app, arg_processed * 100 / arg_total); ++} ++ ++static void ++gs_dnf5_transaction_action_progress_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_nevra, ++ guint64 arg_processed, ++ guint64 arg_total, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: nevra:'%s' progress:%" G_GUINT64_FORMAT "/%" G_GUINT64_FORMAT, G_STRFUNC, arg_nevra, arg_processed, arg_total); ++} ++ ++static void ++gs_dnf5_transaction_action_start_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_nevra, ++ guint arg_action, ++ guint64 arg_total, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: nevra:'%s' action:%u total:%" G_GUINT64_FORMAT, G_STRFUNC, arg_nevra, arg_action, arg_total); ++} ++ ++static void ++gs_dnf5_transaction_action_stop_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_nevra, ++ guint64 arg_total, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: nevra:'%s' total:%" G_GUINT64_FORMAT, G_STRFUNC, arg_nevra, arg_total); ++} ++ ++static void ++gs_dnf5_transaction_script_error_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_nevra, ++ guint arg_scriptlet_type, ++ guint64 arg_return_code, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: nevra:'%s' scriptlet-type:%u return-code:%" G_GUINT64_FORMAT, G_STRFUNC, arg_nevra, arg_scriptlet_type, arg_return_code); ++} ++ ++static void ++gs_dnf5_transaction_script_start_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_nevra, ++ guint arg_scriptlet_type, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: nevra:'%s' scriptlet-type:%u", G_STRFUNC, arg_nevra, arg_scriptlet_type); ++} ++ ++static void ++gs_dnf5_transaction_script_stop_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_nevra, ++ guint arg_scriptlet_type, ++ guint64 arg_return_code, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: nevra:'%s' scriptlet-type:%u return-code:%" G_GUINT64_FORMAT, G_STRFUNC, arg_nevra, arg_scriptlet_type, arg_return_code); ++} ++ ++static void ++gs_dnf5_transaction_transaction_progress_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ guint64 arg_processed, ++ guint64 arg_total, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: progress:%" G_GUINT64_FORMAT "/%" G_GUINT64_FORMAT, G_STRFUNC, arg_processed, arg_total); ++} ++ ++static void ++gs_dnf5_transaction_transaction_start_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ guint64 arg_total, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: total:%" G_GUINT64_FORMAT, G_STRFUNC, arg_total); ++} ++ ++static void ++gs_dnf5_transaction_transaction_stop_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ guint64 arg_total, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: total:%" G_GUINT64_FORMAT, G_STRFUNC, arg_total); ++} ++ ++static void ++gs_dnf5_transaction_unpack_error_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_nevra, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: nevra:'%s'", G_STRFUNC, arg_nevra); ++} ++ ++static void ++gs_dnf5_transaction_verify_progress_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ guint64 arg_processed, ++ guint64 arg_total, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: progress:%" G_GUINT64_FORMAT "/%" G_GUINT64_FORMAT, G_STRFUNC, arg_processed, arg_total); ++} ++ ++static void ++gs_dnf5_transaction_verify_start_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ guint64 arg_total, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: total:%" G_GUINT64_FORMAT, G_STRFUNC, arg_total); ++} ++ ++static void ++gs_dnf5_transaction_verify_stop_cb (GsDnf5RpmRpm *object, ++ const gchar *arg_session_object_path, ++ guint64 arg_total, ++ GsDnf5ProgressHelper *self) ++{ ++ if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) ++ return; ++ g_debug ("%s: total:%" G_GUINT64_FORMAT, G_STRFUNC, arg_total); ++} ++ ++static void ++gs_dnf5_progress_helper_dispose (GObject *object) ++{ ++ GsDnf5ProgressHelper *self = GS_DNF5_PROGRESS_HELPER (object); ++ GObject *base_proxy = G_OBJECT (self->base_proxy); ++ GObject *rpm_proxy = G_OBJECT (self->rpm_proxy); ++ ++ #define clear_signal_handler(_proxy, _id) G_STMT_START { \ ++ if (_id) { \ ++ g_signal_handler_disconnect (_proxy, _id); \ ++ _id = 0; \ ++ } \ ++ } G_STMT_END ++ ++ clear_signal_handler (base_proxy, self->download_add_new_id); ++ clear_signal_handler (base_proxy, self->download_progress_id); ++ clear_signal_handler (base_proxy, self->download_mirror_failure_id); ++ clear_signal_handler (base_proxy, self->download_end_id); ++ ++ clear_signal_handler (rpm_proxy, self->transaction_before_begin_id); ++ clear_signal_handler (rpm_proxy, self->transaction_after_complete_id); ++ clear_signal_handler (rpm_proxy, self->transaction_elem_progress_id); ++ clear_signal_handler (rpm_proxy, self->transaction_action_progress_id); ++ clear_signal_handler (rpm_proxy, self->transaction_action_start_id); ++ clear_signal_handler (rpm_proxy, self->transaction_action_stop_id); ++ clear_signal_handler (rpm_proxy, self->transaction_script_error_id); ++ clear_signal_handler (rpm_proxy, self->transaction_script_start_id); ++ clear_signal_handler (rpm_proxy, self->transaction_script_stop_id); ++ clear_signal_handler (rpm_proxy, self->transaction_transaction_progress_id); ++ clear_signal_handler (rpm_proxy, self->transaction_transaction_start_id); ++ clear_signal_handler (rpm_proxy, self->transaction_transaction_stop_id); ++ clear_signal_handler (rpm_proxy, self->transaction_unpack_error_id); ++ clear_signal_handler (rpm_proxy, self->transaction_verify_progress_id); ++ clear_signal_handler (rpm_proxy, self->transaction_verify_start_id); ++ clear_signal_handler (rpm_proxy, self->transaction_verify_stop_id); ++ ++ #undef clear_signal_handler ++ ++ gs_app_set_progress (self->app, GS_APP_PROGRESS_UNKNOWN); ++ ++ G_OBJECT_CLASS (gs_dnf5_progress_helper_parent_class)->dispose (object); ++} ++ ++static void ++gs_dnf5_progress_helper_finalize (GObject *object) ++{ ++ GsDnf5ProgressHelper *self = GS_DNF5_PROGRESS_HELPER (object); ++ ++ g_clear_object (&self->base_proxy); ++ g_clear_object (&self->rpm_proxy); ++ g_clear_object (&self->app); ++ g_clear_pointer (&self->session_object_path, g_free); ++ g_clear_pointer (&self->ongoing_downloads, g_hash_table_destroy); ++ ++ G_OBJECT_CLASS (gs_dnf5_progress_helper_parent_class)->finalize (object); ++} ++ ++static void ++gs_dnf5_progress_helper_class_init (GsDnf5ProgressHelperClass *klass) ++{ ++ GObjectClass *object_class = G_OBJECT_CLASS (klass); ++ ++ object_class->dispose = gs_dnf5_progress_helper_dispose; ++ object_class->finalize = gs_dnf5_progress_helper_finalize; ++} ++ ++static void ++gs_dnf5_progress_helper_init (GsDnf5ProgressHelper *self) ++{ ++ self->ongoing_downloads = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_free); ++} ++ ++GsDnf5ProgressHelper * ++gs_dnf5_progress_helper_new (GsDnf5Base *base_proxy, ++ GsDnf5RpmRpm *rpm_proxy, ++ GsApp *progress_app, ++ const gchar *session_object_path) ++{ ++ GsDnf5ProgressHelper *self; ++ ++ g_return_val_if_fail (GS_DNF5_IS_BASE (base_proxy), NULL); ++ g_return_val_if_fail (GS_DNF5_IS_RPM_RPM (rpm_proxy), NULL); ++ g_return_val_if_fail (GS_IS_APP (progress_app), NULL); ++ g_return_val_if_fail (session_object_path != NULL, NULL); ++ ++ self = g_object_new (GS_TYPE_DNF5_PROGRESS_HELPER, NULL); ++ self->base_proxy = g_object_ref (base_proxy); ++ self->rpm_proxy = g_object_ref (rpm_proxy); ++ self->app = g_object_ref (progress_app); ++ self->session_object_path = g_strdup (session_object_path); ++ ++ gs_app_set_progress (self->app, GS_APP_PROGRESS_UNKNOWN); ++ ++ self->download_add_new_id = ++ g_signal_connect_object (base_proxy, "download_add_new", ++ G_CALLBACK (gs_dnf5_download_add_new_cb), self, 0); ++ self->download_progress_id = ++ g_signal_connect_object (base_proxy, "download_progress", ++ G_CALLBACK (gs_dnf5_download_progress_cb), self, 0); ++ self->download_mirror_failure_id = ++ g_signal_connect_object (base_proxy, "download_mirror_failure", ++ G_CALLBACK (gs_dnf5_download_mirror_failure_cb), self, 0); ++ self->download_end_id = ++ g_signal_connect_object (base_proxy, "download_end", ++ G_CALLBACK (gs_dnf5_download_end_cb), self, 0); ++ ++ self->transaction_before_begin_id = ++ g_signal_connect_object (rpm_proxy, "transaction_before_begin", ++ G_CALLBACK (gs_dnf5_transaction_before_begin_cb), self, 0); ++ self->transaction_after_complete_id = ++ g_signal_connect_object (rpm_proxy, "transaction_after_complete", ++ G_CALLBACK (gs_dnf5_transaction_after_complete_cb), self, 0); ++ self->transaction_elem_progress_id = ++ g_signal_connect_object (rpm_proxy, "transaction_elem_progress", ++ G_CALLBACK (gs_dnf5_transaction_elem_progress_cb), self, 0); ++ self->transaction_action_progress_id = ++ g_signal_connect_object (rpm_proxy, "transaction_action_progress", ++ G_CALLBACK (gs_dnf5_transaction_action_progress_cb), self, 0); ++ self->transaction_action_start_id = ++ g_signal_connect_object (rpm_proxy, "transaction_action_start", ++ G_CALLBACK (gs_dnf5_transaction_action_start_cb), self, 0); ++ self->transaction_action_stop_id = ++ g_signal_connect_object (rpm_proxy, "transaction_action_stop", ++ G_CALLBACK (gs_dnf5_transaction_action_stop_cb), self, 0); ++ self->transaction_script_error_id = ++ g_signal_connect_object (rpm_proxy, "transaction_script_error", ++ G_CALLBACK (gs_dnf5_transaction_script_error_cb), self, 0); ++ self->transaction_script_start_id = ++ g_signal_connect_object (rpm_proxy, "transaction_script_start", ++ G_CALLBACK (gs_dnf5_transaction_script_start_cb), self, 0); ++ self->transaction_script_stop_id = ++ g_signal_connect_object (rpm_proxy, "transaction_script_stop", ++ G_CALLBACK (gs_dnf5_transaction_script_stop_cb), self, 0); ++ self->transaction_transaction_progress_id = ++ g_signal_connect_object (rpm_proxy, "transaction_transaction_progress", ++ G_CALLBACK (gs_dnf5_transaction_transaction_progress_cb), self, 0); ++ self->transaction_transaction_start_id = ++ g_signal_connect_object (rpm_proxy, "transaction_transaction_start", ++ G_CALLBACK (gs_dnf5_transaction_transaction_start_cb), self, 0); ++ self->transaction_transaction_stop_id = ++ g_signal_connect_object (rpm_proxy, "transaction_transaction_stop", ++ G_CALLBACK (gs_dnf5_transaction_transaction_stop_cb), self, 0); ++ self->transaction_unpack_error_id = ++ g_signal_connect_object (rpm_proxy, "transaction_unpack_error", ++ G_CALLBACK (gs_dnf5_transaction_unpack_error_cb), self, 0); ++ self->transaction_verify_progress_id = ++ g_signal_connect_object (rpm_proxy, "transaction_verify_progress", ++ G_CALLBACK (gs_dnf5_transaction_verify_progress_cb), self, 0); ++ self->transaction_verify_start_id = ++ g_signal_connect_object (rpm_proxy, "transaction_verify_start", ++ G_CALLBACK (gs_dnf5_transaction_verify_start_cb), self, 0); ++ self->transaction_verify_stop_id = ++ g_signal_connect_object (rpm_proxy, "transaction_verify_stop", ++ G_CALLBACK (gs_dnf5_transaction_verify_stop_cb), self, 0); ++ ++ return self; ++} +diff --git a/plugins/dnf5/gs-dnf5-progress-helper.h b/plugins/dnf5/gs-dnf5-progress-helper.h +new file mode 100644 +index 000000000..73d528d54 +--- /dev/null ++++ b/plugins/dnf5/gs-dnf5-progress-helper.h +@@ -0,0 +1,30 @@ ++/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- ++ * vi:set noexpandtab tabstop=8 shiftwidth=8: ++ * ++ * Copyright (C) 2024 Red Hat ++ * ++ * SPDX-License-Identifier: GPL-2.0+ ++ */ ++ ++#pragma once ++ ++#include ++#include ++ ++#include ++ ++#include "gs-dnf5-generated.h" ++ ++G_BEGIN_DECLS ++ ++#define GS_TYPE_DNF5_PROGRESS_HELPER (gs_dnf5_progress_helper_get_type ()) ++ ++G_DECLARE_FINAL_TYPE (GsDnf5ProgressHelper, gs_dnf5_progress_helper, GS, DNF5_PROGRESS_HELPER, GObject) ++ ++GsDnf5ProgressHelper * ++ gs_dnf5_progress_helper_new (GsDnf5Base *base_proxy, ++ GsDnf5RpmRpm *rpm_proxy, ++ GsApp *progress_app, ++ const gchar *session_object_path); ++ ++G_END_DECLS +diff --git a/plugins/dnf5/gs-plugin-dnf5.c b/plugins/dnf5/gs-plugin-dnf5.c +new file mode 100644 +index 000000000..93f22dc4f +--- /dev/null ++++ b/plugins/dnf5/gs-plugin-dnf5.c +@@ -0,0 +1,3738 @@ ++/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- ++ * vi:set noexpandtab tabstop=8 shiftwidth=8: ++ * ++ * Copyright (C) 2024 Red Hat ++ * ++ * SPDX-License-Identifier: GPL-2.0+ ++ */ ++ ++/* ++ * SECTION: dnf5 plugin. ++ * ++ * Talks to dnf5 to manage packages through dnf. ++ */ ++ ++#include ++ ++#include ++#include ++ ++#include "gs-app-private.h" ++ ++#include "gs-worker-thread.h" ++#include "gs-dnf5-generated.h" ++#include "gs-dnf5-rpm-generated.h" ++#include "gs-dnf5-progress-helper.h" ++ ++#include "gs-plugin-dnf5.h" ++ ++#define GS_DNF5_RELEASEVER_DEFAULT NULL ++#define GS_DNF5_INTERFACE_RPM_DNF "org.rpm.dnf.v0" ++#define GS_DNF5_OBJECT_PATH_RPM_DNF "/org/rpm/dnf/v0" ++ ++/* for how long a session can be left opened until it's auto-closed */ ++#define GS_SESSION_LIFETIME_SECS (5 * 60) ++ ++struct _GsPluginDnf5 ++{ ++ GsPlugin parent; ++ ++ GsWorkerThread *worker; /* (owned) */ ++ GDBusConnection *connection; ++ GsDnf5RpmTransaction *rpm_transaction_proxy; ++ guint rpm_transaction_watch_id; ++ gint calling_rpm; ++ ++ struct _SessionData { ++ GMutex mutex; ++ GCond cond; ++ guint autoclose_timer; ++ GsDnf5SessionManager *proxy; ++ gchar *object_path; ++ guint n_used; ++ gint needs_reset; ++ } session_data; ++ ++ struct _DependencySizesData { ++ GMutex mutex; ++ GPtrArray *apps; /* (element-type GsApp) */ ++ GCancellable *cancellable; /* non-NULL, when an op is running */ ++ } dependency_sizes_data; ++}; ++ ++G_DEFINE_TYPE (GsPluginDnf5, gs_plugin_dnf5, GS_TYPE_PLUGIN) ++ ++#define assert_in_worker(self) \ ++ g_assert (gs_worker_thread_is_in_worker_context (self->worker)) ++ ++static gint ++gs_dnf5_get_priority_for_interactivity (gboolean interactive) ++{ ++ return interactive ? G_PRIORITY_DEFAULT : G_PRIORITY_LOW; ++} ++ ++static void ++gs_dnf5_convert_error (GError **error) ++{ ++ gboolean not_authorized; ++ if (error == NULL || *error == NULL) ++ return; ++ ++ /* The message is not localized in the dnf5, thus this should work */ ++ not_authorized = strstr ((*error)->message, "GDBus.Error:org.rpm.dnf.v0.Error: Not authorized") != NULL; ++ ++ g_dbus_error_strip_remote_error (*error); ++ gs_utils_error_convert_gdbus (error); ++ if (not_authorized && g_error_matches (*error, G_IO_ERROR, G_IO_ERROR_DBUS_ERROR)) { ++ (*error)->domain = GS_PLUGIN_ERROR; ++ (*error)->code = GS_PLUGIN_ERROR_AUTH_REQUIRED; ++ } else if (g_error_matches (*error, G_IO_ERROR, G_IO_ERROR_DBUS_ERROR) || ( ++ !gs_utils_error_convert_gdbus (error) && ++ !gs_utils_error_convert_gio (error))) { ++ (*error)->domain = GS_PLUGIN_ERROR; ++ (*error)->code = GS_PLUGIN_ERROR_FAILED; ++ } ++} ++ ++static void ++gs_dnf5_report_error (GsPluginDnf5 *self, ++ const GError *error, ++ gboolean interactive) ++{ ++ g_autoptr(GsPluginEvent) event = NULL; ++ ++ event = gs_plugin_event_new ("error", error, ++ NULL); ++ if (interactive) ++ gs_plugin_event_add_flag (event, GS_PLUGIN_EVENT_FLAG_INTERACTIVE); ++ gs_plugin_event_add_flag (event, GS_PLUGIN_EVENT_FLAG_WARNING); ++ gs_plugin_report_event (GS_PLUGIN (self), event); ++} ++ ++/* The session reset is used to refresh information about the packages, ++ like after a package install/uninstall, it might not be noticed by ++ the daemon internal structures that the package is installed/uninstalled. */ ++static void ++gs_dnf5_mark_session_needs_reset (GsPluginDnf5 *self) ++{ ++ g_atomic_int_set (&self->session_data.needs_reset, 1); ++} ++ ++static void ++gs_dnf5_rpm_start_transaction_cb (GsDnf5RpmTransaction *proxy, ++ const gchar *dbcookie, ++ guint transaction_id, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = user_data; ++ ++ g_debug ("%s: %p: dbcookie:'%s' transaction_id:%u", G_STRFUNC, self, dbcookie, transaction_id); ++} ++ ++static void ++gs_dnf5_rpm_end_transaction_cb (GsDnf5RpmTransaction *proxy, ++ const gchar *dbcookie, ++ guint transaction_id, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = user_data; ++ ++ g_debug ("%s: %p: dbcookie:'%s' transaction_id:%u", G_STRFUNC, self, dbcookie, transaction_id); ++ ++ /* the transactions are for install/uninstall, thus ++ mark the connection to require a reset() */ ++ gs_dnf5_mark_session_needs_reset (self); ++ ++ /* also do not know what precisely changed, thus a heavy hammer */ ++ gs_plugin_reload (GS_PLUGIN (self)); ++} ++ ++static void ++gs_dnf5_got_rpm_transaction_proxy_cb (GObject *source_object, ++ GAsyncResult *result, ++ gpointer user_data) ++{ ++ g_autoptr(GsPluginDnf5) self = user_data; ++ g_autoptr(GError) local_error = NULL; ++ ++ self->rpm_transaction_proxy = gs_dnf5_rpm_transaction_proxy_new_finish (result, &local_error); ++ ++ if (self->rpm_transaction_proxy != NULL) { ++ g_debug ("Opened RPM Transaction D-Bus proxy"); ++ ++ g_signal_connect_object (self->rpm_transaction_proxy, "start-transaction", ++ G_CALLBACK (gs_dnf5_rpm_start_transaction_cb), self, 0); ++ g_signal_connect_object (self->rpm_transaction_proxy, "end-transaction", ++ G_CALLBACK (gs_dnf5_rpm_end_transaction_cb), self, 0); ++ } else { ++ g_debug ("Failed to open RPM Transaction proxy: %s", local_error ? local_error->message : "Unknown error"); ++ } ++} ++ ++static void ++gs_dnf5_rpm_transaction_appeared_cb (GDBusConnection *connection, ++ const gchar *name, ++ const gchar *name_owner, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = user_data; ++ ++ g_debug ("%s: name:'%s' owner:'%s' existing-proxy:%p calling_rpm:%d", ++ G_STRFUNC, name, name_owner, self->rpm_transaction_proxy, ++ g_atomic_int_get (&self->calling_rpm)); ++ ++ if (name_owner != NULL && *name_owner != '\0' && !g_atomic_int_get (&self->calling_rpm)) { ++ g_clear_object (&self->rpm_transaction_proxy); ++ gs_dnf5_rpm_transaction_proxy_new (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ "org.rpm.announce", ++ "/org/rpm/Transaction", ++ NULL, ++ gs_dnf5_got_rpm_transaction_proxy_cb, ++ g_object_ref (self)); ++ } ++} ++ ++static void ++gs_dnf5_rpm_transaction_vanished_cb (GDBusConnection *connection, ++ const gchar *name, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = user_data; ++ ++ g_debug ("%s: name:'%s' existing-proxy:%p", G_STRFUNC, name, self->rpm_transaction_proxy); ++ ++ g_clear_object (&self->rpm_transaction_proxy); ++} ++ ++static void ++gs_dnf5_bus_get_cb (GObject *source_object, ++ GAsyncResult *result, ++ gpointer user_data) ++{ ++ g_autoptr(GTask) task = user_data; ++ g_autoptr(GError) local_error = NULL; ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (g_task_get_source_object (task)); ++ ++ self->connection = g_bus_get_finish (result, &local_error); ++ gs_dnf5_convert_error (&local_error); ++ ++ if (self->connection != NULL) { ++ self->rpm_transaction_watch_id = g_bus_watch_name_on_connection (self->connection, ++ "org.rpm.announce", ++ G_BUS_NAME_WATCHER_FLAGS_NONE, ++ gs_dnf5_rpm_transaction_appeared_cb, ++ gs_dnf5_rpm_transaction_vanished_cb, ++ self, ++ NULL); ++ } ++ ++ if (self->connection != NULL) ++ g_task_return_boolean (task, TRUE); ++ else ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++} ++ ++static void ++gs_plugin_dnf5_setup_async (GsPlugin *plugin, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ g_autoptr(GTask) task = NULL; ++ ++ g_debug ("dnf5 setup"); ++ ++ /* Start up a worker thread to process all the plugin’s function calls. */ ++ self->worker = gs_worker_thread_new ("gs-plugin-dnf5"); ++ ++ task = g_task_new (plugin, cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_setup_async); ++ ++ g_bus_get (G_BUS_TYPE_SYSTEM, cancellable, gs_dnf5_bus_get_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_setup_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ ++static void ++gs_dnf5_shutdown_cb (GObject *source_object, ++ GAsyncResult *result, ++ gpointer user_data) ++{ ++ g_autoptr(GTask) task = user_data; ++ GsPluginDnf5 *self = g_task_get_source_object (task); ++ g_autoptr(GsWorkerThread) worker = NULL; ++ g_autoptr(GError) local_error = NULL; ++ ++ worker = g_steal_pointer (&self->worker); ++ ++ if (!gs_worker_thread_shutdown_finish (worker, result, &local_error)) ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ else ++ g_task_return_boolean (task, TRUE); ++} ++ ++static void ++gs_plugin_dnf5_shutdown_async (GsPlugin *plugin, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ g_autoptr(GTask) task = NULL; ++ g_autoptr(GCancellable) dependency_sizes_cancellable = NULL; ++ ++ task = g_task_new (plugin, cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_shutdown_async); ++ ++ /* stop any dependency sizes ongoing operation */ ++ g_mutex_lock (&self->dependency_sizes_data.mutex); ++ if (self->dependency_sizes_data.cancellable) ++ dependency_sizes_cancellable = g_object_ref (self->dependency_sizes_data.cancellable); ++ g_mutex_unlock (&self->dependency_sizes_data.mutex); ++ if (dependency_sizes_cancellable != NULL) ++ g_cancellable_cancel (dependency_sizes_cancellable); ++ ++ /* Stop the worker thread. */ ++ gs_worker_thread_shutdown_async (self->worker, cancellable, gs_dnf5_shutdown_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_shutdown_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ ++static void ++gs_dnf5_close_session_real (GsDnf5SessionManager *proxy, ++ const gchar *session_path) ++{ ++ g_autoptr(GError) local_error = NULL; ++ gboolean result = FALSE; ++ ++ /* Not passing operation's cancellable, because it can be cancelled by the user, ++ but the session needs to be closed. */ ++ if (gs_dnf5_session_manager_call_close_session_sync (proxy, session_path, &result, NULL, &local_error)) ++ g_warn_if_fail (result); ++ else ++ g_debug ("Failed to close session: %s", local_error->message); ++} ++ ++static gboolean ++gs_dnf5_autoclose_session_cb (gpointer user_data) ++{ ++ GsPluginDnf5 *self = user_data; ++ g_autoptr(GMutexLocker) locker = g_mutex_locker_new (&self->session_data.mutex); ++ ++ self->session_data.autoclose_timer = 0; ++ if (self->session_data.n_used == 0 && self->session_data.proxy != NULL) { ++ gs_dnf5_close_session_real (self->session_data.proxy, self->session_data.object_path); ++ ++ g_clear_object (&self->session_data.proxy); ++ g_clear_pointer (&self->session_data.object_path, g_free); ++ } ++ ++ return G_SOURCE_REMOVE; ++} ++ ++static gboolean ++gs_dnf5_reset_session_sync (GsPluginDnf5 *self, ++ const gchar *session_path, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ g_autoptr(GsDnf5Base) base_proxy = NULL; ++ g_autofree gchar *error_msg = NULL; ++ gboolean success = FALSE; ++ ++ base_proxy = gs_dnf5_base_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ error); ++ if (base_proxy == NULL) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to create Base proxy: "); ++ return FALSE; ++ } ++ ++ if (!gs_dnf5_base_call_reset_sync (base_proxy, &success, &error_msg, cancellable, error)) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to call Base::reset(): "); ++ return FALSE; ++ } ++ ++ if (!success) { ++ g_set_error (error, G_IO_ERROR, G_IO_ERROR_FAILED, "Failed to execute Base::reset(): %s", error_msg ? error_msg : "Unknown error"); ++ return FALSE; ++ } ++ ++ return TRUE; ++} ++ ++static gchar * /* (transfer full) */ ++gs_dnf5_open_session (GsPluginDnf5 *self, ++ const gchar *releasever, ++ GsDnf5SessionManager **out_proxy, /* (transfer full) */ ++ GCancellable *cancellable, ++ GError **error) ++{ ++ g_autoptr(GMutexLocker) locker = g_mutex_locker_new (&self->session_data.mutex); ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autofree gchar *session_path = NULL; ++ ++ if (releasever == GS_DNF5_RELEASEVER_DEFAULT) { ++ if (self->session_data.autoclose_timer) { ++ g_source_remove (self->session_data.autoclose_timer); ++ self->session_data.autoclose_timer = 0; ++ } ++ ++ if (self->session_data.proxy != NULL) { ++ GsDnf5SessionManager *proxy = self->session_data.proxy; ++ ++ while (g_atomic_int_get (&self->session_data.needs_reset) && ++ !g_cancellable_is_cancelled (cancellable)) { ++ g_autoptr(GError) local_error = NULL; ++ if (self->session_data.n_used > 0) { ++ g_debug ("Existing session needs reset, waiting for opened operations to finish"); ++ while (self->session_data.n_used && g_atomic_int_get (&self->session_data.needs_reset)) { ++ g_cond_wait_until (&self->session_data.cond, &self->session_data.mutex, ++ /* check whether was cancelled up to three times per second */ ++ g_get_monotonic_time () + (G_TIME_SPAN_SECOND / 3)); ++ ++ if (g_cancellable_set_error_if_cancelled (cancellable, error)) ++ return NULL; ++ } ++ } ++ ++ if (g_cancellable_set_error_if_cancelled (cancellable, error)) ++ return NULL; ++ ++ if (g_atomic_int_get (&self->session_data.needs_reset)) { ++ gboolean success; ++ ++ success = gs_dnf5_reset_session_sync (self, self->session_data.object_path, cancellable, &local_error); ++ g_atomic_int_set (&self->session_data.needs_reset, 0); ++ ++ /* let any waiter for session reset know the conditions changed */ ++ g_cond_broadcast (&self->session_data.cond); ++ ++ if (success) { ++ g_debug ("Successfully reset existing session"); ++ } else { ++ g_debug ("Failed to reset existing session: %s", local_error ? local_error->message : "Unknown error"); ++ break; ++ } ++ } else { ++ g_debug ("Wanted to reset the session, but someone else did that already, thus skipping the reset"); ++ break; ++ } ++ } ++ ++ if (g_cancellable_set_error_if_cancelled (cancellable, error)) ++ return NULL; ++ ++ if (proxy == self->session_data.proxy) { ++ self->session_data.n_used++; ++ g_debug ("Using existing session"); ++ *out_proxy = g_object_ref (self->session_data.proxy); ++ return g_strdup (self->session_data.object_path); ++ } ++ } ++ } ++ ++ g_debug ("Creating new session"); ++ *out_proxy = gs_dnf5_session_manager_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_NONE, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ GS_DNF5_OBJECT_PATH_RPM_DNF, ++ cancellable, ++ error); ++ ++ if (*out_proxy == NULL) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to get Session Manager: "); ++ return NULL; ++ } ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ ++ if (releasever != GS_DNF5_RELEASEVER_DEFAULT) { ++ g_variant_builder_add (options_builder, "{sv}", "releasever", ++ g_variant_new_string (releasever)); ++ } else { ++ g_autoptr(GVariantBuilder) config = NULL; ++ ++ config = g_variant_builder_new (G_VARIANT_TYPE ("a{ss}")); ++ g_variant_builder_add (config, "{ss}", "optional_metadata_types", ++ "appstream"); ++ ++ g_variant_builder_add (options_builder, "{sv}", "config", ++ g_variant_builder_end (config)); ++ } ++ ++ if (!gs_dnf5_session_manager_call_open_session_sync (*out_proxy, ++ g_variant_builder_end (options_builder), ++ &session_path, ++ cancellable, ++ error)) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to open session: "); ++ return NULL; ++ } ++ ++ if (releasever == GS_DNF5_RELEASEVER_DEFAULT) { ++ g_assert (self->session_data.proxy == NULL); ++ self->session_data.proxy = g_object_ref (*out_proxy); ++ self->session_data.object_path = g_strdup (session_path); ++ self->session_data.n_used = 1; ++ } ++ ++ return g_steal_pointer (&session_path); ++} ++ ++static void ++gs_dnf5_close_session (GsPluginDnf5 *self, ++ GsDnf5SessionManager *proxy, ++ const gchar *session_path) ++{ ++ g_autoptr(GMutexLocker) locker = g_mutex_locker_new (&self->session_data.mutex); ++ ++ if (self->session_data.proxy == proxy) { ++ g_assert (self->session_data.n_used > 0); ++ self->session_data.n_used--; ++ ++ /* let any waiter for session reset know the n_used changed */ ++ g_cond_broadcast (&self->session_data.cond); ++ ++ if (self->session_data.n_used == 0) { ++ g_assert (self->session_data.autoclose_timer == 0); ++ self->session_data.autoclose_timer = g_timeout_add_seconds (GS_SESSION_LIFETIME_SECS, gs_dnf5_autoclose_session_cb, self); ++ } ++ } else { ++ gs_dnf5_close_session_real (proxy, session_path); ++ } ++} ++ ++/* Returns whether to continue */ ++typedef gboolean (* GsDnf5ForeachFunc) (GsPluginDnf5 *self, ++ GVariant *value, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error); ++ ++static gboolean ++gs_dnf5_foreach_item (GsPluginDnf5 *self, ++ GVariant *array, ++ GsDnf5ForeachFunc func, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ GVariantIter iter; ++ GVariant *child; ++ ++ g_variant_iter_init (&iter, array); ++ while (child = g_variant_iter_next_value (&iter), child != NULL) { ++ g_autoptr(GError) local_error = NULL; ++ gboolean done; ++ ++ done = !func (self, child, user_data, cancellable, &local_error); ++ g_variant_unref (child); ++ ++ if (local_error) { ++ g_propagate_error (error, g_steal_pointer (&local_error)); ++ return FALSE; ++ } ++ ++ if (g_cancellable_set_error_if_cancelled (cancellable, error)) ++ return FALSE; ++ ++ if (done) ++ break; ++ } ++ ++ return TRUE; ++} ++ ++static void ++gs_dnf5_app_set_str (GVariantDict *dict, ++ const gchar *key, ++ GsApp *app, ++ void (*set_func) (GsApp *app, ++ const gchar *value)) ++{ ++ g_autoptr(GVariant) value = NULL; ++ ++ value = g_variant_dict_lookup_value (dict, key, G_VARIANT_TYPE_STRING); ++ if (value != NULL) ++ set_func (app, g_variant_get_string (value, NULL)); ++} ++ ++static void ++gs_dnf5_app_set_str2 (GVariantDict *dict, ++ const gchar *key, ++ GsApp *app, ++ void (*set_func) (GsApp *app, ++ GsAppQuality quality, ++ const gchar *value)) ++{ ++ g_autoptr(GVariant) value = NULL; ++ ++ value = g_variant_dict_lookup_value (dict, key, G_VARIANT_TYPE_STRING); ++ if (value != NULL) ++ set_func (app, GS_APP_QUALITY_NORMAL, g_variant_get_string (value, NULL)); ++} ++ ++static void ++gs_dnf5_app_set_size (GVariantDict *dict, ++ const gchar *key, ++ GsApp *app, ++ void (*set_func) (GsApp *app, ++ GsSizeType size_type, ++ guint64 size_bytes)) ++{ ++ g_autoptr(GVariant) value = NULL; ++ ++ value = g_variant_dict_lookup_value (dict, key, G_VARIANT_TYPE_UINT64); ++ if (value != NULL) ++ set_func (app, GS_SIZE_TYPE_VALID, g_variant_get_uint64 (value)); ++} ++ ++static gchar * ++gs_dnf5_dup_version_from_dict (GVariantDict *dict) ++{ ++ g_autoptr(GVariant) version = NULL; ++ ++ version = g_variant_dict_lookup_value (dict, "version", G_VARIANT_TYPE_STRING); ++ if (version != NULL) { ++ const gchar *version_str = g_variant_get_string (version, NULL); ++ if (version_str != NULL && *version_str != '\0') { ++ g_autoptr(GVariant) release = NULL; ++ const gchar *release_str = NULL; ++ release = g_variant_dict_lookup_value (dict, "release", G_VARIANT_TYPE_STRING); ++ if (release != NULL) ++ release_str = g_variant_get_string (release, NULL); ++ if (release_str != NULL && *release_str != '\0') { ++ g_autofree gchar *version_release_str = g_strconcat (version_str, "-", release_str, NULL); ++ return g_steal_pointer (&version_release_str); ++ } else { ++ return g_strdup (version_str); ++ } ++ } ++ } ++ ++ return NULL; ++} ++ ++static void ++gs_dnf5_app_set_version (GVariantDict *dict, ++ GsApp *app, ++ void (*set_func) (GsApp *app, ++ const gchar *value)) ++{ ++ g_autofree gchar *ver_str = gs_dnf5_dup_version_from_dict (dict); ++ if (ver_str != NULL) ++ set_func (app, ver_str); ++} ++ ++static void ++gs_plugin_dnf5_set_packaging_format (GsApp *app) ++{ ++ gs_app_set_metadata (app, "GnomeSoftware::PackagingFormat", "RPM"); ++ gs_app_set_metadata (app, "GnomeSoftware::PackagingBaseCssColor", "error_color"); ++} ++ ++static void ++gs_dnf5_update_app_state (GsApp *app, ++ GsAppState state, ++ GVariantDict *dict) ++{ ++ if (state == GS_APP_STATE_UNKNOWN) { ++ g_autoptr(GVariant) value = NULL; ++ value = g_variant_dict_lookup_value (dict, "is_installed", G_VARIANT_TYPE_BOOLEAN); ++ if (value == NULL) ++ return; ++ if (g_variant_get_boolean (value)) ++ state = GS_APP_STATE_INSTALLED; ++ else ++ state = GS_APP_STATE_AVAILABLE; ++ } ++ /* The state can be only installed, available or updatable */ ++ if (gs_app_get_state (app) == state || ++ gs_app_get_state (app) == GS_APP_STATE_UPDATABLE) ++ return; ++ if (gs_app_get_state (app) == GS_APP_STATE_UNKNOWN) ++ gs_app_set_state (app, state); ++ else if (gs_app_get_state (app) != GS_APP_STATE_INSTALLED || ++ state == GS_APP_STATE_UPDATABLE) ++ gs_app_set_state (app, state); ++} ++ ++static void ++gs_dnf5_update_app_changelogs (GsApp *app, ++ GVariantDict *dict) ++{ ++ GVariantIter iter; ++ GVariant *child; ++ g_autoptr(GString) changes = NULL; ++ g_autoptr(GVariant) changelogs = NULL; ++ ++ changelogs = g_variant_dict_lookup_value (dict, "changelogs", NULL); ++ if (changelogs == NULL) ++ return; ++ ++ g_variant_iter_init (&iter, changelogs); ++ while (child = g_variant_iter_next_value (&iter), child != NULL) { ++ gint64 when = 0; ++ const gchar *whom = NULL; ++ const gchar *what = NULL; ++ ++ g_variant_get (child, "(x&s&s)", &when, &whom, &what); ++ ++ if (whom != NULL && what != NULL) { ++ g_autofree gchar *tmp = NULL; ++ const gchar *eml_start, *eml_end; ++ ++ /* Hide the email address in the changes */ ++ eml_start = strchr (whom, '<'); ++ eml_end = strrchr (whom, '>'); ++ if (eml_start != NULL && eml_start < eml_end) { ++ if (g_ascii_isspace (eml_end[1])) ++ eml_end++; ++ tmp = g_malloc0 (strlen (whom) + 1); ++ strncpy (tmp, whom, eml_start - whom); ++ strcat (tmp, eml_end + 1); ++ whom = tmp; ++ } ++ ++ if (changes == NULL) ++ changes = g_string_new (""); ++ else ++ g_string_append (changes, "\n\n"); ++ g_string_append (changes, whom); ++ g_string_append_c (changes, '\n'); ++ g_string_append (changes, what); ++ } ++ ++ g_variant_unref (child); ++ } ++ ++ if (changes != NULL) ++ gs_app_set_update_details_text (app, changes->str); ++} ++ ++typedef struct { ++ GsAppList *list; ++ GsAppState set_state; ++ GHashTable *nevra_to_app; /* (nullable): gchar *nevra ~> GsApp * */ ++ GHashTable *replaces; /* (nullable): GINT_TO_POINTER(pkg-id) ~> gchar *old_version */ ++} ReadPackageData; ++ ++static gboolean ++gs_dnf5_read_package_cb (GsPluginDnf5 *self, ++ GVariant *package_array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ ReadPackageData *rpd = user_data; ++ GsAppList *list = rpd->list; ++ GHashTable *nevra_to_app = rpd->nevra_to_app; ++ g_autofree gchar *name = NULL; ++ g_autoptr(GsApp) app = NULL; ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) value = NULL; ++ ++ dict = g_variant_dict_new (package_array); ++ ++ value = g_variant_dict_lookup_value (dict, "name", G_VARIANT_TYPE_STRING); ++ if (value != NULL) { ++ const gchar *name_const = g_variant_get_string (value, NULL); ++ app = gs_plugin_cache_lookup (GS_PLUGIN (self), name_const); ++ if (app == NULL) ++ name = g_strdup (name_const); ++ g_clear_pointer (&value, g_variant_unref); ++ } ++ ++ if (app == NULL) { ++ app = gs_app_new (NULL); ++ gs_app_set_management_plugin (app, GS_PLUGIN (self)); ++ gs_app_set_metadata (app, "GnomeSoftware::Creator", gs_plugin_get_name (GS_PLUGIN (self))); ++ gs_plugin_dnf5_set_packaging_format (app); ++ gs_app_set_kind (app, AS_COMPONENT_KIND_GENERIC); ++ gs_app_set_bundle_kind (app, AS_BUNDLE_KIND_PACKAGE); ++ gs_app_set_scope (app, AS_COMPONENT_SCOPE_SYSTEM); ++ ++ gs_dnf5_app_set_str (dict, "name", app, gs_app_add_source); ++ gs_dnf5_app_set_str (dict, "nevra", app, gs_app_add_source_id); ++ gs_dnf5_app_set_str2 (dict, "name", app, gs_app_set_name); ++ gs_dnf5_app_set_str2 (dict, "summary", app, gs_app_set_summary); ++ gs_dnf5_app_set_str2 (dict, "description", app, gs_app_set_description); ++ gs_dnf5_app_set_str2 (dict, "license", app, gs_app_set_license); ++ gs_dnf5_app_set_size (dict, "install_size", app, gs_app_set_size_installed); ++ gs_dnf5_app_set_size (dict, "download_size", app, gs_app_set_size_download); ++ ++ value = g_variant_dict_lookup_value (dict, "url", G_VARIANT_TYPE_STRING); ++ if (value != NULL) { ++ gs_app_set_url (app, AS_URL_KIND_HOMEPAGE, g_variant_get_string (value, NULL)); ++ g_clear_pointer (&value, g_variant_unref); ++ } ++ ++ gs_plugin_cache_add (GS_PLUGIN (self), name, app); ++ } ++ ++ gs_dnf5_update_app_changelogs (app, dict); ++ gs_dnf5_update_app_state (app, rpd->set_state, dict); ++ ++ if (rpd->set_state == GS_APP_STATE_UPDATABLE) { ++ gs_dnf5_app_set_version (dict, app, gs_app_set_update_version); ++ gs_app_add_quirk (app, GS_APP_QUIRK_NEEDS_REBOOT); ++ } else { ++ gs_dnf5_app_set_version (dict, app, gs_app_set_version); ++ } ++ ++ if (nevra_to_app != NULL) { ++ g_clear_pointer (&value, g_variant_unref); ++ value = g_variant_dict_lookup_value (dict, "nevra", G_VARIANT_TYPE_STRING); ++ if (value != NULL) { ++ const gchar *nevra_const = g_variant_get_string (value, NULL); ++ if (nevra_const != NULL && *nevra_const != '\0') ++ g_hash_table_insert (nevra_to_app, g_strdup (nevra_const), g_object_ref (app)); ++ } ++ } ++ ++ gs_app_list_add (list, app); ++ ++ return TRUE; ++} ++ ++static gboolean ++gs_dnf5_read_repo_cb (GsPluginDnf5 *self, ++ GVariant *package_array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ GsAppList *list = user_data; ++ g_autoptr(GsApp) app = NULL; ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) value = NULL; ++ const gchar *id; ++ ++ dict = g_variant_dict_new (package_array); ++ ++ value = g_variant_dict_lookup_value (dict, "id", G_VARIANT_TYPE_STRING); ++ if (value == NULL) ++ return TRUE; ++ ++ id = g_variant_get_string (value, NULL); ++ if (id == NULL || *id == '\0') ++ return TRUE; ++ ++ /* Skip sub-repos */ ++ if (g_str_has_suffix (id, "-source") || ++ g_str_has_suffix (id, "-debuginfo") || ++ g_str_has_suffix (id, "-testing")) ++ return TRUE; ++ ++ g_clear_pointer (&value, g_variant_unref); ++ id = NULL; ++ ++ app = gs_app_new (NULL); ++ gs_app_set_management_plugin (app, GS_PLUGIN (self)); ++ gs_app_set_kind (app, AS_COMPONENT_KIND_REPOSITORY); ++ gs_app_set_bundle_kind (app, AS_BUNDLE_KIND_PACKAGE); ++ gs_app_set_scope (app, AS_COMPONENT_SCOPE_SYSTEM); ++ gs_app_add_quirk (app, GS_APP_QUIRK_NOT_LAUNCHABLE); ++ gs_app_set_metadata (app, "GnomeSoftware::Creator", gs_plugin_get_name (GS_PLUGIN (self))); ++ gs_plugin_dnf5_set_packaging_format (app); ++ gs_app_set_metadata (app, "GnomeSoftware::SortKey", "300"); ++ gs_app_set_origin_ui (app, _("Packages")); ++ ++ gs_dnf5_app_set_str (dict, "id", app, gs_app_set_id); ++ gs_dnf5_app_set_str2 (dict, "name", app, gs_app_set_name); ++ gs_dnf5_app_set_str2 (dict, "name", app, gs_app_set_description); ++ ++ value = g_variant_dict_lookup_value (dict, "enabled", G_VARIANT_TYPE_BOOLEAN); ++ if (value != NULL) { ++ gs_app_set_state (app, g_variant_get_boolean (value) ? ++ GS_APP_STATE_INSTALLED : GS_APP_STATE_AVAILABLE); ++ g_clear_pointer (&value, g_variant_unref); ++ } else { ++ gs_app_set_state (app, GS_APP_STATE_INSTALLED); ++ } ++ ++ gs_app_list_add (list, app); ++ ++ return TRUE; ++} ++ ++static gboolean ++gs_dnf5_refine_from_advisory_packages_cb (GsPluginDnf5 *self, ++ GVariant *array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ GHashTable *nevra_to_app = user_data; ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) var_nevra = NULL; ++ ++ dict = g_variant_dict_new (array); ++ ++ var_nevra = g_variant_dict_lookup_value (dict, "nevra", G_VARIANT_TYPE_STRING); ++ if (var_nevra != NULL) { ++ const gchar *nevra = g_variant_get_string (var_nevra, NULL); ++ if (nevra != NULL) { ++ GsApp *app; ++ ++ app = g_hash_table_lookup (nevra_to_app, nevra); ++ if (app != NULL) ++ gs_app_set_update_urgency (app, AS_URGENCY_KIND_CRITICAL); ++ } ++ } ++ ++ return TRUE; ++} ++ ++static gboolean ++gs_dnf5_refine_from_advisory_collections_cb (GsPluginDnf5 *self, ++ GVariant *array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ GHashTable *nevra_to_app = user_data; ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) packages = NULL; ++ gboolean res = TRUE; ++ ++ dict = g_variant_dict_new (array); ++ ++ packages = g_variant_dict_lookup_value (dict, "packages", G_VARIANT_TYPE_ARRAY); ++ if (packages != NULL) ++ res = gs_dnf5_foreach_item (self, packages, gs_dnf5_refine_from_advisory_packages_cb, nevra_to_app, cancellable, error); ++ ++ return res; ++} ++ ++static gboolean ++gs_dnf5_refine_from_advisory_cb (GsPluginDnf5 *self, ++ GVariant *array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ GHashTable *nevra_to_app = user_data; ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) collections = NULL; ++ g_autoptr(GVariant) severity = NULL; ++ gboolean res = TRUE; ++ ++ dict = g_variant_dict_new (array); ++ ++ /* ensure only advisories with severity 'critical' are traversed */ ++ severity = g_variant_dict_lookup_value (dict, "severity", G_VARIANT_TYPE_STRING); ++ if (severity == NULL || g_variant_get_string (severity, NULL) == NULL || ++ g_ascii_strcasecmp (g_variant_get_string (severity, NULL), "critical") != 0) ++ return TRUE; ++ ++ collections = g_variant_dict_lookup_value (dict, "collections", G_VARIANT_TYPE_ARRAY); ++ if (collections != NULL) ++ res = gs_dnf5_foreach_item (self, collections, gs_dnf5_refine_from_advisory_collections_cb, nevra_to_app, cancellable, error); ++ ++ return res; ++} ++ ++static GVariant * ++gs_dnf5_dup_package_attrs (void) ++{ ++ g_autoptr(GVariantBuilder) attrs_builder = NULL; ++ ++ attrs_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_variant_builder_add (attrs_builder, "s", "nevra"); ++ g_variant_builder_add (attrs_builder, "s", "name"); ++ g_variant_builder_add (attrs_builder, "s", "epoch"); ++ g_variant_builder_add (attrs_builder, "s", "version"); ++ g_variant_builder_add (attrs_builder, "s", "release"); ++ g_variant_builder_add (attrs_builder, "s", "arch"); ++ g_variant_builder_add (attrs_builder, "s", "repo_id"); ++ g_variant_builder_add (attrs_builder, "s", "install_size"); ++ g_variant_builder_add (attrs_builder, "s", "download_size"); ++ g_variant_builder_add (attrs_builder, "s", "is_installed"); ++ g_variant_builder_add (attrs_builder, "s", "summary"); ++ g_variant_builder_add (attrs_builder, "s", "url"); ++ g_variant_builder_add (attrs_builder, "s", "license"); ++ g_variant_builder_add (attrs_builder, "s", "description"); ++ g_variant_builder_add (attrs_builder, "s", "changelogs"); ++ ++ return g_variant_builder_end (attrs_builder); ++} ++ ++static void ++gs_dnf5_gather_async_result_cb (GObject *source_object, ++ GAsyncResult *result, ++ gpointer user_data) ++{ ++ GAsyncResult **out_result = user_data; ++ *out_result = g_object_ref (result); ++} ++ ++static void ++gs_dnf5_confirm_key_response_cb (GObject *source_object, ++ GAsyncResult *result, ++ gpointer user_data) ++{ ++ g_autoptr(GError) local_error = NULL; ++ ++ if (!gs_dnf5_rpm_repo_call_confirm_key_finish (GS_DNF5_RPM_REPO (source_object), result, &local_error)) ++ g_debug ("Failed to confirm key: %s", local_error->message); ++} ++ ++typedef struct { ++ gchar *title; ++ gchar *msg; ++ gchar *details; ++ gchar *accept_label; ++ gchar *key_id; ++ GsPluginDnf5 *self; /* (owned) */ ++ GWeakRef repo_proxy_weakref; /* GsDnf5RpmRepo */ ++} QuestionData; ++ ++static void ++question_data_free (QuestionData *data) ++{ ++ if (data != NULL) { ++ g_free (data->title); ++ g_free (data->msg); ++ g_free (data->details); ++ g_free (data->accept_label); ++ g_free (data->key_id); ++ g_clear_object (&data->self); ++ g_weak_ref_clear (&data->repo_proxy_weakref); ++ g_free (data); ++ } ++} ++ ++static gboolean ++gs_dnf5_ask_question_idle_cb (gpointer user_data) ++{ ++ QuestionData *data = user_data; ++ g_autoptr(GsDnf5RpmRepo) repo_proxy = NULL; ++ ++ repo_proxy = g_weak_ref_get (&data->repo_proxy_weakref); ++ if (repo_proxy != NULL) { ++ gboolean confirmed; ++ ++ confirmed = gs_plugin_ask_untrusted (GS_PLUGIN (data->self), data->title, data->msg, data->details, data->accept_label); ++ ++ gs_dnf5_rpm_repo_call_confirm_key (repo_proxy, data->key_id, confirmed, NULL, gs_dnf5_confirm_key_response_cb, NULL); ++ } ++ ++ return G_SOURCE_REMOVE; ++} ++ ++typedef struct { ++ GsPluginDnf5 *self; /* (not owned) */ ++ const gchar *session_path; /* (not owned) */ ++ GsDnf5RpmRepo *repo_proxy; /* (not owned) */ ++} RepoKeyImportData; ++ ++static void ++gs_dnf5_repo_key_import_request_cb (GsDnf5Base *object, ++ const gchar *arg_session_object_path, ++ const gchar *arg_key_id, ++ const gchar *const *arg_user_ids, ++ const gchar *arg_key_fingerprint, ++ const gchar *arg_key_url, ++ gint64 arg_timestamp, ++ RepoKeyImportData *repo_key_import_data) ++{ ++ QuestionData *data; ++ g_autoptr(GString) user_ids = NULL; ++ g_autofree gchar *key_filename = NULL; ++ g_autoptr(GString) str_fingerprint = NULL; ++ GString *details = NULL; ++ const gchar *fingerprint; ++ const gchar *from; ++ ++ if (g_strcmp0 (repo_key_import_data->session_path, arg_session_object_path) != 0) ++ return; ++ ++ user_ids = g_string_new (NULL); ++ for (guint i = 0; arg_user_ids != NULL && arg_user_ids[i] != NULL; i++) { ++ if (i > 0) ++ g_string_append (user_ids, ", "); ++ g_string_append_c (user_ids, '"'); ++ g_string_append (user_ids, arg_user_ids[i]); ++ g_string_append_c (user_ids, '"'); ++ } ++ ++ g_debug ("%s: key_id:'%s' user_ids:[%s] key_fingerprint:'%s' key_url:'%s' timestamp:%" G_GINT64_FORMAT, ++ G_STRFUNC, arg_key_id, user_ids->str, arg_key_fingerprint, arg_key_url, arg_timestamp); ++ ++ if (g_ascii_strncasecmp (arg_key_url, "file:", 5) == 0) ++ key_filename = g_filename_from_uri (arg_key_url, NULL, NULL); ++ ++ if ((strlen (arg_key_fingerprint) % 4) == 0) { ++ str_fingerprint = g_string_new (arg_key_fingerprint); ++ for (gint i = str_fingerprint->len - 4; i > 0; i -= 4) { ++ g_string_insert_c (str_fingerprint, i, ' '); ++ } ++ } ++ ++ details = g_string_new (""); ++ ++ from = key_filename != NULL ? key_filename : arg_key_url; ++ fingerprint = str_fingerprint != NULL ? str_fingerprint->str : arg_key_fingerprint; ++ ++ #define add_nonempty_line(_format, _value) G_STMT_START { \ ++ if ((_value) != NULL && *(_value) != '\0') { \ ++ g_string_append_printf (details, _format, _value); \ ++ g_string_append_c (details, '\n'); \ ++ } \ ++ } G_STMT_END ++ ++ /* Translators: the '%s' is replaced with the key user name */ ++ add_nonempty_line (_("Key user: %s"), user_ids->str); ++ /* Translators: the '%s' is replaced with the key fingerprint, a few hex digits */ ++ add_nonempty_line (_("Fingerprint: %s"), fingerprint); ++ /* Translators: the '%s' is replaced with the local path or a URI to the key */ ++ add_nonempty_line (_("From: %s"), from); ++ ++ #undef add_nonempty_line ++ ++ data = g_new0 (QuestionData, 1); ++ data->title = g_strdup (_("Import Key")); ++ /* Translators: the '%s' is replaced with the key ID, usually a few hex digits */ ++ data->msg = g_strdup_printf (_("Do you want to import key %s?"), arg_key_id); ++ data->details = g_string_free (details, FALSE); ++ data->accept_label = g_strdup (_("_Import Key")); ++ data->key_id = g_strdup (arg_key_id); ++ data->self = g_object_ref (repo_key_import_data->self); ++ g_weak_ref_init (&data->repo_proxy_weakref, repo_key_import_data->repo_proxy); ++ ++ g_idle_add_full (G_PRIORITY_HIGH_IDLE, gs_dnf5_ask_question_idle_cb, data, (GDestroyNotify) question_data_free); ++} ++ ++static void ++gs_dnf5_goal_cancelled_cb (GObject *source_object, ++ GAsyncResult *result, ++ gpointer user_data) ++{ ++ g_autoptr(GCancellable) run_cancellable = user_data; ++ g_autoptr(GError) local_error = NULL; ++ g_autofree gchar *error_message = NULL; ++ gboolean succeeded = FALSE; ++ ++ if (gs_dnf5_goal_call_cancel_finish (GS_DNF5_GOAL (source_object), &succeeded, &error_message, result, &local_error)) { ++ if (succeeded) { ++ g_debug ("%s: Transaction cancelled by the user", G_STRFUNC); ++ g_cancellable_cancel (run_cancellable); ++ } else { ++ g_debug ("%s: Cannot cancel transaction: %s", G_STRFUNC, error_message); ++ } ++ } else if (!g_error_matches (local_error, G_IO_ERROR, G_IO_ERROR_CANCELLED)) { ++ g_debug ("%s: Failed to cancel transaction: %s", G_STRFUNC, local_error->message); ++ } ++} ++ ++static gboolean ++gs_dnf5_reset_transaction_sync (GsPluginDnf5 *self, ++ const gchar *session_path, ++ GsDnf5RpmRpm *rpm_proxy, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ g_autoptr(GsDnf5Goal) goal_proxy = NULL; ++ ++ goal_proxy = gs_dnf5_goal_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ error); ++ if (goal_proxy == NULL) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to create Goal proxy: "); ++ return FALSE; ++ } ++ ++ return gs_dnf5_goal_call_reset_sync (goal_proxy, cancellable, error); ++} ++ ++/* this is needed to receive D-Bus signals about progress in the worker thread */ ++static gboolean ++gs_dnf5_goal_call_do_transaction_sync_wrapper (GsDnf5Goal *proxy, ++ GVariant *arg_options, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ g_autoptr(GMainContext) main_context = g_main_context_ref_thread_default (); ++ g_autoptr(GAsyncResult) async_result = NULL; ++ gs_dnf5_goal_call_do_transaction (proxy, arg_options, cancellable, gs_dnf5_gather_async_result_cb, &async_result); ++ while (!async_result) ++ g_main_context_iteration (main_context, TRUE); ++ return gs_dnf5_goal_call_do_transaction_finish (proxy, async_result, error); ++} ++ ++typedef struct { ++ GsDnf5Goal *goal_proxy; ++ GCancellable *run_cancellable; ++} TransactionData; ++ ++static void ++gs_dnf5_transaction_cancelled_cb (GCancellable *parent_cancellable, ++ TransactionData *transaction_data) ++{ ++ gs_dnf5_goal_call_cancel (transaction_data->goal_proxy, transaction_data->run_cancellable, ++ gs_dnf5_goal_cancelled_cb, g_object_ref (transaction_data->run_cancellable)); ++} ++ ++typedef enum { ++ GS_DNF5_TRANSACTION_FLAG_NONE = 0, ++ GS_DNF5_TRANSACTION_FLAG_OFFLINE = 1 << 0, ++ GS_DNF5_TRANSACTION_FLAG_RESOLVE_ONLY = 1 << 1 ++} GsDnf5TransactionFlags; ++ ++static gboolean ++gs_dnf5_run_transaction (GsPluginDnf5 *self, ++ const gchar *session_path, ++ GsDnf5RpmRpm *rpm_proxy, ++ GsApp *progress_app, ++ GsDnf5TransactionFlags flags, ++ GVariant **out_transaction, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ g_autoptr(GsDnf5Base) base_proxy = NULL; ++ g_autoptr(GsDnf5Goal) goal_proxy = NULL; ++ g_autoptr(GsDnf5RpmRepo) repo_proxy = NULL; ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariant) transaction = NULL; ++ g_autoptr(GsDnf5ProgressHelper) helper = NULL; ++ g_autoptr(GCancellable) run_cancellable = NULL; ++ RepoKeyImportData repo_key_import_data; ++ TransactionData transaction_data; ++ gulong repo_key_import_id; ++ gulong cancellable_id = 0; ++ guint result = 0; ++ gboolean success; ++ ++ base_proxy = gs_dnf5_base_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ error); ++ if (base_proxy == NULL) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to create Base proxy: "); ++ return FALSE; ++ } ++ ++ repo_proxy = gs_dnf5_rpm_repo_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ error); ++ if (repo_proxy == NULL) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to create Repo proxy: "); ++ return FALSE; ++ } ++ ++ goal_proxy = gs_dnf5_goal_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ error); ++ if (goal_proxy == NULL) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to create Goal proxy: "); ++ return FALSE; ++ } ++ ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (goal_proxy), G_MAXINT); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ ++ if (progress_app != NULL) ++ helper = gs_dnf5_progress_helper_new (base_proxy, rpm_proxy, progress_app, session_path); ++ ++ repo_key_import_data.self = self; ++ repo_key_import_data.session_path = session_path; ++ repo_key_import_data.repo_proxy = repo_proxy; ++ repo_key_import_id = g_signal_connect (base_proxy, "repo_key_import_request", ++ G_CALLBACK (gs_dnf5_repo_key_import_request_cb), &repo_key_import_data); ++ ++ if (!gs_dnf5_goal_call_resolve_sync (goal_proxy, ++ g_variant_builder_end (options_builder), ++ &transaction, ++ &result, ++ cancellable, ++ error)) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to resolve transaction: "); ++ g_signal_handler_disconnect (base_proxy, repo_key_import_id); ++ return FALSE; ++ } ++ ++ if (out_transaction != NULL && transaction != NULL) ++ *out_transaction = g_variant_ref_sink (transaction); ++ ++ /* 0 ... all fine, 1 ... there are warnings, 2 ... failed */ ++ if (result == 2) { ++ g_auto(GStrv) problems = NULL; ++ ++ if (gs_dnf5_goal_call_get_transaction_problems_string_sync (goal_proxy, &problems, cancellable, error) && ++ problems != NULL) { ++ /* extra space at the end, but no harm, it reuses translated string */ ++ GString *msg = g_string_new ("Failed to resolve transaction: "); ++ for (guint i = 0; problems[i] != NULL; i++) { ++ g_string_append_c (msg, '\n'); ++ g_string_append (msg, problems[i]); ++ } ++ g_set_error_literal (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_FAILED, msg->str); ++ } else { ++ g_set_error_literal (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_FAILED, ++ _("Unknown error")); ++ g_prefix_error (error, "Failed to resolve transaction: "); ++ } ++ g_signal_handler_disconnect (base_proxy, repo_key_import_id); ++ return FALSE; ++ } ++ ++ g_clear_pointer (&options_builder, g_variant_builder_unref); ++ ++ if ((flags & GS_DNF5_TRANSACTION_FLAG_RESOLVE_ONLY) != 0) { ++ g_signal_handler_disconnect (base_proxy, repo_key_import_id); ++ return TRUE; ++ } ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ if ((flags & GS_DNF5_TRANSACTION_FLAG_OFFLINE) != 0) { ++ g_variant_builder_add (options_builder, "{sv}", "offline", ++ g_variant_new_boolean (TRUE)); ++ } ++ ++ run_cancellable = g_cancellable_new (); ++ if (cancellable != NULL) { ++ transaction_data.goal_proxy = goal_proxy; ++ transaction_data.run_cancellable = run_cancellable; ++ ++ cancellable_id = g_cancellable_connect (cancellable, G_CALLBACK (gs_dnf5_transaction_cancelled_cb), ++ &transaction_data, NULL); ++ } ++ ++ success = gs_dnf5_goal_call_do_transaction_sync_wrapper (goal_proxy, ++ g_variant_builder_end (options_builder), ++ run_cancellable, ++ error); ++ ++ g_cancellable_disconnect (cancellable, cancellable_id); ++ g_signal_handler_disconnect (base_proxy, repo_key_import_id); ++ ++ /* in case there is a pending async call result for the cancel() invocation */ ++ g_cancellable_cancel (run_cancellable); ++ ++ if (!success) { ++ g_auto(GStrv) problems = NULL; ++ ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to run transaction: "); ++ ++ if (error != NULL && *error != NULL && ++ gs_dnf5_goal_call_get_transaction_problems_string_sync (goal_proxy, &problems, cancellable, NULL) && ++ problems != NULL) { ++ GString *msg = g_string_new ((*error)->message); ++ for (guint i = 0; problems[i] != NULL; i++) { ++ g_string_append_c (msg, '\n'); ++ g_string_append (msg, problems[i]); ++ } ++ g_clear_error (error); ++ g_set_error_literal (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_FAILED, msg->str); ++ } ++ } ++ ++ return success; ++} ++ ++enum OpKindType { OP_KIND_UNKNOWN, OP_KIND_INSTALL, OP_KIND_UPGRADE, OP_KIND_DOWNGRADE, OP_KIND_REINSTALL, OP_KIND_REMOVE, OP_KIND_REPLACED }; ++ ++static enum OpKindType ++gs_dnf5_get_package_op_kind (GVariant *item_array) ++{ ++ struct _op_kinds { ++ const gchar *name; ++ enum OpKindType kind; ++ } op_kinds[] = { ++ { "Install", OP_KIND_INSTALL }, ++ { "Upgrade", OP_KIND_UPGRADE }, ++ { "Downgrade", OP_KIND_DOWNGRADE }, ++ { "Reinstall", OP_KIND_REINSTALL }, ++ { "Remove", OP_KIND_REMOVE }, ++ { "Replaced", OP_KIND_REPLACED } ++ }; ++ const gchar *str = NULL; ++ ++ g_variant_get_child (item_array, 0, "&s", &str); ++ if (str == NULL || g_ascii_strcasecmp (str, "package") != 0) ++ return OP_KIND_UNKNOWN; ++ ++ g_variant_get_child (item_array, 1, "&s", &str); ++ if (str == NULL) ++ return OP_KIND_UNKNOWN; ++ ++ for (guint i = 0; i < G_N_ELEMENTS (op_kinds); i++) { ++ if (g_ascii_strcasecmp (str, op_kinds[i].name) == 0) { ++ return op_kinds[i].kind; ++ } ++ } ++ ++ return OP_KIND_UNKNOWN; ++} ++ ++static gboolean ++gs_dnf5_gather_update_replaces_cb (GsPluginDnf5 *self, ++ GVariant *item_array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ ReadPackageData *rpd = user_data; ++ enum OpKindType op_kind = gs_dnf5_get_package_op_kind (item_array); ++ ++ if (op_kind == OP_KIND_REPLACED && rpd->replaces) { ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) value = NULL; ++ ++ value = g_variant_get_child_value (item_array, 4); ++ dict = g_variant_dict_new (value); ++ g_clear_pointer (&value, g_variant_unref); ++ ++ value = g_variant_dict_lookup_value (dict, "id", G_VARIANT_TYPE_INT32); ++ if (value != NULL) { ++ gint32 id = g_variant_get_int32 (value); ++ gchar *version = gs_dnf5_dup_version_from_dict (dict); ++ if (version != NULL) ++ g_hash_table_insert (rpd->replaces, GINT_TO_POINTER (id), version); ++ } ++ } ++ ++ return TRUE; ++} ++ ++typedef struct _UpdateReplacesData { ++ GsApp *app; ++ GHashTable *replaces; ++} UpdateReplacesData; ++ ++static gboolean ++gs_dnf5_gather_update_replaced_pkgs_cb (GsPluginDnf5 *self, ++ GVariant *item_array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ UpdateReplacesData *upd = user_data; ++ gint32 replaces_id = g_variant_get_int32 (item_array); ++ const gchar *old_version = g_hash_table_lookup (upd->replaces, GINT_TO_POINTER (replaces_id)); ++ if (old_version != NULL) ++ gs_app_set_version (upd->app, old_version); ++ ++ return TRUE; ++} ++ ++static gboolean ++gs_dnf5_gather_updates_from_transaction_cb (GsPluginDnf5 *self, ++ GVariant *item_array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ ReadPackageData *rpd = user_data; ++ enum OpKindType op_kind = gs_dnf5_get_package_op_kind (item_array); ++ const gchar *str; ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) value = NULL; ++ g_autoptr(GsApp) upd_app = NULL; ++ g_autoptr(GString) nevra = NULL; ++ GsApp *known_app; ++ ++ if (op_kind == OP_KIND_UNKNOWN || op_kind == OP_KIND_REPLACED) ++ return TRUE; ++ ++ value = g_variant_get_child_value (item_array, 4); ++ dict = g_variant_dict_new (value); ++ g_clear_pointer (&value, g_variant_unref); ++ ++ value = g_variant_dict_lookup_value (dict, "name", G_VARIANT_TYPE_STRING); ++ if (value == NULL) ++ return TRUE; ++ str = g_variant_get_string (value, NULL); ++ if (str == NULL) ++ return TRUE; ++ ++ nevra = g_string_new (str); ++ ++ g_clear_pointer (&value, g_variant_unref); ++ value = g_variant_dict_lookup_value (dict, "evr", G_VARIANT_TYPE_STRING); ++ if (value == NULL) ++ return TRUE; ++ str = g_variant_get_string (value, NULL); ++ if (str == NULL) ++ return TRUE; ++ ++ g_string_append_c (nevra, '-'); ++ g_string_append (nevra, str); ++ ++ g_clear_pointer (&value, g_variant_unref); ++ value = g_variant_dict_lookup_value (dict, "arch", G_VARIANT_TYPE_STRING); ++ if (value == NULL) ++ return TRUE; ++ str = g_variant_get_string (value, NULL); ++ if (str == NULL) ++ return TRUE; ++ ++ g_string_append_c (nevra, '.'); ++ g_string_append (nevra, str); ++ ++ known_app = g_hash_table_lookup (rpd->nevra_to_app, nevra->str); ++ if (known_app != NULL) { ++ upd_app = g_object_ref (known_app); ++ if (gs_app_get_version (upd_app) == NULL) ++ gs_dnf5_app_set_version (dict, upd_app, gs_app_set_version); ++ else ++ gs_dnf5_app_set_version (dict, upd_app, gs_app_set_update_version); ++ ++ if (rpd->replaces != NULL) { ++ g_autoptr(GVariantDict) dict2 = NULL; ++ ++ g_clear_pointer (&value, g_variant_unref); ++ value = g_variant_get_child_value (item_array, 3); ++ dict2 = g_variant_dict_new (value); ++ g_clear_pointer (&value, g_variant_unref); ++ value = g_variant_dict_lookup_value (dict2, "replaces", G_VARIANT_TYPE_ARRAY); ++ if (value != NULL) { ++ UpdateReplacesData upd = { 0, }; ++ ++ upd.app = upd_app; ++ upd.replaces = rpd->replaces; ++ ++ if (!gs_dnf5_foreach_item (self, value, gs_dnf5_gather_update_replaced_pkgs_cb, &upd, cancellable, error)) ++ return FALSE; ++ } ++ } ++ } else { ++ upd_app = gs_app_new (NULL); ++ gs_app_set_management_plugin (upd_app, GS_PLUGIN (self)); ++ gs_app_set_metadata (upd_app, "GnomeSoftware::Creator", gs_plugin_get_name (GS_PLUGIN (self))); ++ gs_plugin_dnf5_set_packaging_format (upd_app); ++ gs_app_set_kind (upd_app, AS_COMPONENT_KIND_GENERIC); ++ gs_app_set_bundle_kind (upd_app, AS_BUNDLE_KIND_PACKAGE); ++ gs_app_set_scope (upd_app, AS_COMPONENT_SCOPE_SYSTEM); ++ gs_app_add_quirk (upd_app, GS_APP_QUIRK_HIDE_EVERYWHERE); ++ gs_app_add_quirk (upd_app, GS_APP_QUIRK_NEEDS_REBOOT); ++ ++ gs_dnf5_app_set_str (dict, "name", upd_app, gs_app_add_source); ++ gs_dnf5_app_set_str2 (dict, "name", upd_app, gs_app_set_name); ++ gs_dnf5_app_set_version (dict, upd_app, gs_app_set_version); ++ gs_app_add_source_id (upd_app, nevra->str); ++ ++ gs_app_list_add (rpd->list, upd_app); ++ g_hash_table_insert (rpd->nevra_to_app, g_string_free (g_steal_pointer (&nevra), FALSE), g_object_ref (upd_app)); ++ } ++ ++ gs_dnf5_app_set_size (dict, "install_size", upd_app, gs_app_set_size_installed); ++ gs_dnf5_app_set_size (dict, "download_size", upd_app, gs_app_set_size_download); ++ ++ switch (op_kind) { ++ case OP_KIND_INSTALL: ++ gs_app_set_state (upd_app, GS_APP_STATE_AVAILABLE); ++ break; ++ case OP_KIND_UPGRADE: ++ case OP_KIND_DOWNGRADE: ++ case OP_KIND_REINSTALL: ++ gs_app_set_state (upd_app, GS_APP_STATE_UPDATABLE); ++ break; ++ case OP_KIND_REMOVE: ++ gs_app_set_state (upd_app, GS_APP_STATE_UNAVAILABLE); ++ break; ++ case OP_KIND_REPLACED: ++ case OP_KIND_UNKNOWN: ++ default: ++ g_warn_if_reached (); ++ break; ++ } ++ ++ return TRUE; ++} ++ ++/* Run in @worker. */ ++static void ++gs_dnf5_list_apps_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsAppQueryTristate is_for_update = GS_APP_QUERY_TRISTATE_UNSET; ++ GsAppQueryTristate is_source = GS_APP_QUERY_TRISTATE_UNSET; ++ GsPluginListAppsData *data = task_data; ++ const gchar * const *provides_files = NULL; ++ const gchar *provides_tag = NULL; ++ GsAppQueryProvidesType provides_type = GS_APP_QUERY_PROVIDES_UNKNOWN; ++ g_autofree gchar *session_path = NULL; ++ g_autoptr(GsAppList) list = NULL; ++ g_autoptr(GsDnf5SessionManager) session_manager = NULL; ++ g_autoptr(GsDnf5RpmRpm) rpm_proxy = NULL; ++ g_autoptr(GError) local_error = NULL; ++ gboolean success = TRUE; ++ ++ assert_in_worker (self); ++ ++ if (data->query != NULL) { ++ is_for_update = gs_app_query_get_is_for_update (data->query); ++ is_source = gs_app_query_get_is_source (data->query); ++ provides_files = gs_app_query_get_provides_files (data->query); ++ provides_type = gs_app_query_get_provides (data->query, &provides_tag); ++ } ++ ++ if ((is_for_update == GS_APP_QUERY_TRISTATE_UNSET && ++ is_source == GS_APP_QUERY_TRISTATE_UNSET && ++ provides_tag == NULL && ++ provides_files == NULL) || ++ is_for_update == GS_APP_QUERY_TRISTATE_FALSE || ++ is_source == GS_APP_QUERY_TRISTATE_FALSE || ++ gs_app_query_get_n_properties_set (data->query) != 1) { ++ g_task_return_new_error (task, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, ++ "Unsupported query"); ++ return; ++ } ++ ++ session_path = gs_dnf5_open_session (self, GS_DNF5_RELEASEVER_DEFAULT, &session_manager, cancellable, &local_error); ++ if (session_path == NULL) { ++ gs_dnf5_convert_error (&local_error); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ return; ++ } ++ ++ rpm_proxy = gs_dnf5_rpm_rpm_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ &local_error); ++ success = rpm_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to create Rpm proxy: "); ++ } ++ ++ if (success) { ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); ++ list = gs_app_list_new (); ++ ++ if (is_for_update == GS_APP_QUERY_TRISTATE_TRUE) { ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariant) result = NULL; ++ ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "package_attrs", ++ gs_dnf5_dup_package_attrs ()); ++ g_variant_builder_add (options_builder, "{sv}", "with_provides", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "with_filenames", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "with_src", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "scope", ++ g_variant_new_string ("upgrades")); ++ ++ success = gs_dnf5_rpm_rpm_call_list_sync (rpm_proxy, ++ g_variant_builder_end (options_builder), ++ &result, ++ cancellable, ++ &local_error); ++ ++ if (success) { ++ g_autoptr(GHashTable) nevra_to_app = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_object_unref); ++ g_autoptr(GHashTable) replaces = g_hash_table_new_full (g_direct_hash, g_direct_equal, NULL, g_free); ++ ReadPackageData rpd = { 0, }; ++ rpd.list = list; ++ rpd.set_state = GS_APP_STATE_UPDATABLE; ++ rpd.nevra_to_app = nevra_to_app; ++ rpd.replaces = replaces; ++ ++ success = gs_dnf5_foreach_item (self, result, gs_dnf5_read_package_cb, &rpd, cancellable, &local_error); ++ ++ if (success && g_hash_table_size (nevra_to_app) > 0) { ++ g_autoptr(GVariantBuilder) options_builder2 = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_autoptr(GVariant) transaction = NULL; ++ const gchar * const packages[2] = { NULL, NULL }; ++ ++ success = gs_dnf5_reset_transaction_sync (self, session_path, rpm_proxy, cancellable, &local_error); ++ ++ success = success && ++ gs_dnf5_rpm_rpm_call_upgrade_sync (rpm_proxy, ++ packages, ++ g_variant_builder_end (options_builder2), ++ cancellable, ++ &local_error); ++ success = success && ++ gs_dnf5_run_transaction (self, session_path, rpm_proxy, NULL, ++ GS_DNF5_TRANSACTION_FLAG_RESOLVE_ONLY, ++ &transaction, cancellable, &local_error); ++ if (success && transaction != NULL) { ++ success = gs_dnf5_foreach_item (self, transaction, ++ gs_dnf5_gather_update_replaces_cb, &rpd, ++ cancellable, &local_error); ++ success = success && ++ gs_dnf5_foreach_item (self, transaction, ++ gs_dnf5_gather_updates_from_transaction_cb, &rpd, ++ cancellable, &local_error); ++ } ++ } ++ ++ if (success && g_hash_table_size (nevra_to_app) > 0) { ++ g_autoptr(GsDnf5Advisory) advisory_proxy = NULL; ++ g_autoptr(GError) local_error2 = NULL; ++ gboolean adv_success; ++ ++ advisory_proxy = gs_dnf5_advisory_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ &local_error2); ++ adv_success = advisory_proxy != NULL; ++ ++ if (adv_success) { ++ g_autoptr(GVariantBuilder) adv_options_builder = NULL; ++ g_autoptr(GVariantBuilder) attrs_builder = NULL; ++ g_autoptr(GVariantBuilder) severities_builder = NULL; ++ g_autoptr(GVariant) adv_result = NULL; ++ ++ attrs_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_variant_builder_add (attrs_builder, "s", "severity"); ++ g_variant_builder_add (attrs_builder, "s", "collections"); ++ ++ severities_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_variant_builder_add (severities_builder, "s", "critical"); ++ ++ adv_options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (adv_options_builder, "{sv}", "advisory_attrs", ++ g_variant_builder_end (attrs_builder)); ++ g_variant_builder_add (adv_options_builder, "{sv}", "availability", ++ g_variant_new_string ("updates")); ++ g_variant_builder_add (adv_options_builder, "{sv}", "severities", ++ g_variant_builder_end (severities_builder)); ++ ++ adv_success = gs_dnf5_advisory_call_list_sync (advisory_proxy, ++ g_variant_builder_end (adv_options_builder), ++ &adv_result, ++ cancellable, ++ &local_error2); ++ if (adv_success) { ++ adv_success = gs_dnf5_foreach_item (self, adv_result, ++ gs_dnf5_refine_from_advisory_cb, nevra_to_app, ++ cancellable, &local_error2); ++ } else { ++ g_debug ("Failed to call Advisory::list: %s", local_error2->message); ++ } ++ } else { ++ g_debug ("Failed to create Advisory proxy: %s", local_error2->message); ++ } ++ } ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to call Rpm::list: "); ++ } ++ } else if (is_source == GS_APP_QUERY_TRISTATE_TRUE) { ++ g_autoptr(GsDnf5RpmRepo) repo_proxy = NULL; ++ ++ repo_proxy = gs_dnf5_rpm_repo_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ &local_error); ++ success = repo_proxy != NULL; ++ if (success) { ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariantBuilder) attrs_builder = NULL; ++ g_autoptr(GVariant) result = NULL; ++ ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (repo_proxy), G_MAXINT); ++ ++ attrs_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_variant_builder_add (attrs_builder, "s", "id"); ++ g_variant_builder_add (attrs_builder, "s", "name"); ++ g_variant_builder_add (attrs_builder, "s", "enabled"); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "repo_attrs", ++ g_variant_builder_end (attrs_builder)); ++ g_variant_builder_add (options_builder, "{sv}", "enable_disable", ++ g_variant_new_string ("all")); ++ ++ success = gs_dnf5_rpm_repo_call_list_sync (repo_proxy, ++ g_variant_builder_end (options_builder), ++ &result, ++ cancellable, ++ &local_error); ++ ++ if (success) { ++ success = gs_dnf5_foreach_item (self, result, gs_dnf5_read_repo_cb, list, cancellable, &local_error); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to call list: "); ++ } ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to create Rpm repo proxy: "); ++ } ++ } else if (provides_files != NULL) { ++ g_autoptr(GVariantBuilder) patterns_builder = NULL; ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariant) result = NULL; ++ ++ patterns_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ for (guint i = 0; provides_files[i] != NULL; i++) { ++ g_variant_builder_add (patterns_builder, "s", provides_files[i]); ++ } ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "scope", ++ g_variant_new_string ("all")); ++ g_variant_builder_add (options_builder, "{sv}", "with_nevra", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "with_provides", ++ g_variant_new_boolean (TRUE)); ++ g_variant_builder_add (options_builder, "{sv}", "with_filenames", ++ g_variant_new_boolean (TRUE)); ++ g_variant_builder_add (options_builder, "{sv}", "with_src", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "package_attrs", ++ gs_dnf5_dup_package_attrs ()); ++ g_variant_builder_add (options_builder, "{sv}", "patterns", ++ g_variant_builder_end (patterns_builder)); ++ ++ success = gs_dnf5_rpm_rpm_call_list_sync (rpm_proxy, ++ g_variant_builder_end (options_builder), ++ &result, ++ cancellable, ++ &local_error); ++ ++ if (success) { ++ ReadPackageData rpd = { 0, }; ++ rpd.list = list; ++ rpd.set_state = GS_APP_STATE_UNKNOWN; ++ rpd.nevra_to_app = NULL; ++ success = gs_dnf5_foreach_item (self, result, gs_dnf5_read_package_cb, &rpd, cancellable, &local_error); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to call list: "); ++ } ++ } else if (provides_tag != NULL) { ++ g_autoptr(GVariantBuilder) patterns_builder = NULL; ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariant) result = NULL; ++ g_autofree gchar *pattern1 = NULL, *pattern2 = NULL; ++ ++ patterns_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ ++ switch (provides_type) { ++ case GS_APP_QUERY_PROVIDES_PACKAGE_NAME: ++ g_variant_builder_add (patterns_builder, "s", provides_tag); ++ break; ++ case GS_APP_QUERY_PROVIDES_GSTREAMER: ++ pattern1 = g_strdup_printf ("gstreamer0.10(%s)", provides_tag); ++ pattern2 = g_strdup_printf ("gstreamer1(%s)", provides_tag); ++ break; ++ case GS_APP_QUERY_PROVIDES_FONT: ++ pattern1 = g_strdup_printf ("font(%s)", provides_tag); ++ break; ++ case GS_APP_QUERY_PROVIDES_MIME_HANDLER: ++ pattern1 = g_strdup_printf ("mimehandler(%s)", provides_tag); ++ break; ++ case GS_APP_QUERY_PROVIDES_PS_DRIVER: ++ pattern1 = g_strdup_printf ("postscriptdriver(%s)", provides_tag); ++ break; ++ case GS_APP_QUERY_PROVIDES_PLASMA: ++ pattern1 = g_strdup_printf ("plasma4(%s)", provides_tag); ++ pattern2 = g_strdup_printf ("plasma5(%s)", provides_tag); ++ break; ++ case GS_APP_QUERY_PROVIDES_UNKNOWN: ++ default: ++ g_assert_not_reached (); ++ } ++ if (pattern1 != NULL) ++ g_variant_builder_add (patterns_builder, "s", pattern1); ++ if (pattern2 != NULL) ++ g_variant_builder_add (patterns_builder, "s", pattern2); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "scope", ++ g_variant_new_string ("all")); ++ g_variant_builder_add (options_builder, "{sv}", "with_nevra", ++ g_variant_new_boolean (provides_type == GS_APP_QUERY_PROVIDES_PACKAGE_NAME)); ++ g_variant_builder_add (options_builder, "{sv}", "with_provides", ++ g_variant_new_boolean (provides_type != GS_APP_QUERY_PROVIDES_PACKAGE_NAME)); ++ g_variant_builder_add (options_builder, "{sv}", "with_filenames", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "with_src", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "package_attrs", ++ gs_dnf5_dup_package_attrs ()); ++ g_variant_builder_add (options_builder, "{sv}", "patterns", ++ g_variant_builder_end (patterns_builder)); ++ ++ success = gs_dnf5_rpm_rpm_call_list_sync (rpm_proxy, ++ g_variant_builder_end (options_builder), ++ &result, ++ cancellable, ++ &local_error); ++ ++ if (success) { ++ ReadPackageData rpd = { 0, }; ++ rpd.list = list; ++ rpd.set_state = GS_APP_STATE_UNKNOWN; ++ rpd.nevra_to_app = NULL; ++ success = gs_dnf5_foreach_item (self, result, gs_dnf5_read_package_cb, &rpd, cancellable, &local_error); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to call list: "); ++ } ++ } else { ++ g_assert_not_reached (); ++ } ++ } ++ ++ gs_dnf5_close_session (self, session_manager, session_path); ++ ++ if (success) { ++ g_task_return_pointer (task, g_steal_pointer (&list), g_object_unref); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ } ++} ++ ++static void ++gs_plugin_dnf5_list_apps_async (GsPlugin *plugin, ++ GsAppQuery *query, ++ GsPluginListAppsFlags flags, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ gboolean interactive = (flags & GS_PLUGIN_LIST_APPS_FLAGS_INTERACTIVE) != 0; ++ g_autoptr(GTask) task = NULL; ++ ++ task = gs_plugin_list_apps_data_new_task (plugin, query, flags, ++ cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_list_apps_async); ++ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_list_apps_thread_cb, g_steal_pointer (&task)); ++} ++ ++static GsAppList * ++gs_plugin_dnf5_list_apps_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_pointer (G_TASK (result), error); ++} ++ ++static gboolean ++gs_dnf5_gather_dependency_sizes_cb (GsPluginDnf5 *self, ++ GVariant *item_array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ GsApp *main_app = user_data; ++ const gchar *str; ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) value = NULL; ++ g_autoptr(GsApp) dep_app = NULL; ++ ++ g_variant_get_child (item_array, 0, "&s", &str); ++ if (str == NULL || g_ascii_strcasecmp (str, "package") != 0) ++ return TRUE; ++ ++ g_variant_get_child (item_array, 2, "&s", &str); ++ if (str == NULL || g_ascii_strcasecmp (str, "dependency") != 0) ++ return TRUE; ++ ++ value = g_variant_get_child_value (item_array, 4); ++ dict = g_variant_dict_new (value); ++ g_clear_pointer (&value, g_variant_unref); ++ ++ value = g_variant_dict_lookup_value (dict, "name", G_VARIANT_TYPE_STRING); ++ if (value == NULL) ++ return TRUE; ++ str = g_variant_get_string (value, NULL); ++ if (str == NULL) ++ return TRUE; ++ /* the app itself is in the list too */ ++ if (g_strcmp0 (gs_app_get_source_default (main_app), str) == 0) ++ return TRUE; ++ ++ /* always create a new app, no cached can be used here */ ++ dep_app = gs_app_new (NULL); ++ gs_app_set_management_plugin (dep_app, GS_PLUGIN (self)); ++ gs_app_set_metadata (dep_app, "GnomeSoftware::Creator", gs_plugin_get_name (GS_PLUGIN (self))); ++ gs_plugin_dnf5_set_packaging_format (dep_app); ++ gs_app_set_kind (dep_app, AS_COMPONENT_KIND_GENERIC); ++ gs_app_set_bundle_kind (dep_app, AS_BUNDLE_KIND_PACKAGE); ++ gs_app_set_scope (dep_app, AS_COMPONENT_SCOPE_SYSTEM); ++ gs_app_add_quirk (dep_app, GS_APP_QUIRK_HIDE_EVERYWHERE); ++ ++ gs_dnf5_app_set_str (dict, "name", dep_app, gs_app_add_source); ++ gs_dnf5_app_set_str (dict, "nevra", dep_app, gs_app_add_source_id); ++ gs_dnf5_app_set_str2 (dict, "name", dep_app, gs_app_set_name); ++ gs_dnf5_app_set_str2 (dict, "summary", dep_app, gs_app_set_summary); ++ gs_dnf5_app_set_str2 (dict, "description", dep_app, gs_app_set_description); ++ gs_dnf5_app_set_str2 (dict, "license", dep_app, gs_app_set_license); ++ gs_dnf5_app_set_size (dict, "install_size", dep_app, gs_app_set_size_installed); ++ gs_dnf5_app_set_size (dict, "download_size", dep_app, gs_app_set_size_download); ++ ++ gs_dnf5_update_app_state (dep_app, GS_APP_STATE_UNKNOWN, dict); ++ ++ gs_app_add_related (main_app, dep_app); ++ ++ return TRUE; ++} ++ ++static gpointer ++gs_dnf5_dependency_sizes_thread (gpointer thread_data) ++{ ++ g_autofree GWeakRef *weakref = thread_data; ++ g_autoptr(GsPluginDnf5) self = g_weak_ref_get (weakref); ++ g_autoptr(GCancellable) cancellable = NULL; ++ g_autoptr(GError) local_error = NULL; ++ guint index = 0; ++ ++ if (self == NULL) ++ return NULL; ++ ++ g_mutex_lock (&self->dependency_sizes_data.mutex); ++ ++ if (self->dependency_sizes_data.cancellable != NULL) ++ cancellable = g_object_ref (self->dependency_sizes_data.cancellable); ++ ++ while (self->dependency_sizes_data.apps != NULL && index < self->dependency_sizes_data.apps->len && ++ !g_cancellable_is_cancelled (self->dependency_sizes_data.cancellable)) { ++ GsApp *app = g_ptr_array_index (self->dependency_sizes_data.apps, index); ++ g_autofree gchar *session_path = NULL; ++ g_autoptr(GsDnf5SessionManager) session_manager = NULL; ++ g_autoptr(GsDnf5RpmRpm) rpm_proxy = NULL; ++ gboolean success; ++ ++ index++; ++ ++ if (gs_app_is_installed (app) || ++ gs_app_list_length (gs_app_get_related (app)) > 0) ++ continue; ++ ++ g_mutex_unlock (&self->dependency_sizes_data.mutex); ++ ++ /* need to use temporary session, because the goals are piled up and cannot be cancelled yet */ ++ session_path = gs_dnf5_open_session (self, GS_DNF5_RELEASEVER_DEFAULT, &session_manager, cancellable, &local_error); ++ ++ success = session_path != NULL; ++ if (!success) ++ gs_dnf5_convert_error (&local_error); ++ ++ if (success) { ++ rpm_proxy = gs_dnf5_rpm_rpm_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ &local_error); ++ success = rpm_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to create Rpm proxy: "); ++ } ++ } ++ ++ if (success) { ++ g_autoptr(GVariantBuilder) options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_autoptr(GVariant) transaction = NULL; ++ const gchar *package_name = gs_app_get_source_default (app); ++ const gchar *packages[2] = { NULL, NULL }; ++ ++ packages[0] = package_name; ++ ++ success = gs_dnf5_reset_transaction_sync (self, session_path, rpm_proxy, cancellable, &local_error); ++ ++ success = success && ++ gs_dnf5_rpm_rpm_call_install_sync (rpm_proxy, ++ (const gchar * const *) packages, ++ g_variant_builder_end (options_builder), ++ cancellable, ++ &local_error); ++ success = success && ++ gs_dnf5_run_transaction (self, session_path, rpm_proxy, NULL, ++ GS_DNF5_TRANSACTION_FLAG_RESOLVE_ONLY, ++ &transaction, cancellable, &local_error); ++ if (success && transaction != NULL) ++ success = gs_dnf5_foreach_item (self, transaction, gs_dnf5_gather_dependency_sizes_cb, app, cancellable, &local_error); ++ } ++ ++ gs_dnf5_close_session (self, session_manager, session_path); ++ ++ g_mutex_lock (&self->dependency_sizes_data.mutex); ++ ++ if (!success) ++ break; ++ } ++ ++ g_clear_pointer (&self->dependency_sizes_data.apps, g_ptr_array_unref); ++ g_clear_object (&self->dependency_sizes_data.cancellable); ++ g_mutex_unlock (&self->dependency_sizes_data.mutex); ++ ++ if (local_error != NULL) ++ g_debug ("Failed to get app dependency sizes: %s", local_error->message); ++ ++ return NULL; ++} ++ ++static gboolean ++gs_dnf5_get_dependency_sizes_sync (GsPluginDnf5 *self, ++ GHashTable *apps, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ g_autoptr(GMutexLocker) locker = g_mutex_locker_new (&self->session_data.mutex); ++ GHashTableIter iter; ++ gpointer value = NULL; ++ gboolean need_thread = FALSE; ++ ++ g_hash_table_iter_init (&iter, apps); ++ while (g_hash_table_iter_next (&iter, NULL, &value)) { ++ GsApp *app = value; ++ GsAppList *related = gs_app_get_related (app); ++ ++ if (gs_app_has_quirk (app, GS_APP_QUIRK_HIDE_EVERYWHERE) || ++ gs_app_get_state (app) == GS_APP_STATE_AVAILABLE_LOCAL || ++ gs_app_is_installed (app) || ++ gs_app_list_length (related) > 0) ++ continue; ++ ++ /* getting list of the dependencies to be installed can take a long time, thus run it ++ in a new thread, to not block the refine job */ ++ if (self->dependency_sizes_data.apps == NULL) { ++ need_thread = TRUE; ++ self->dependency_sizes_data.apps = g_ptr_array_new_with_free_func (g_object_unref); ++ } ++ ++ if (!g_ptr_array_find (self->dependency_sizes_data.apps, app, NULL)) ++ g_ptr_array_add (self->dependency_sizes_data.apps, g_object_ref (app)); ++ } ++ ++ if (need_thread) { ++ GWeakRef *weakref = g_new0 (GWeakRef, 1); ++ ++ g_assert (self->dependency_sizes_data.cancellable == NULL); ++ self->dependency_sizes_data.cancellable = g_cancellable_new (); ++ ++ g_weak_ref_set (weakref, self); ++ ++ g_thread_unref (g_thread_new ("gs-dnf5-dependency-sizes", gs_dnf5_dependency_sizes_thread, g_steal_pointer (&weakref))); ++ } ++ ++ return TRUE; ++} ++ ++static gboolean ++gs_dnf5_refine_cb (GsPluginDnf5 *self, ++ GVariant *package_array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ GHashTable *apps = user_data; ++ const gchar *name; ++ GsApp *app; ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) value = NULL; ++ ++ dict = g_variant_dict_new (package_array); ++ ++ value = g_variant_dict_lookup_value (dict, "name", G_VARIANT_TYPE_STRING); ++ if (value == NULL) ++ return TRUE; ++ name = g_variant_get_string (value, NULL); ++ if (name == NULL) ++ return TRUE; ++ app = g_hash_table_lookup (apps, name); ++ if (app == NULL) ++ return TRUE; ++ ++ if (gs_app_has_management_plugin (app, NULL) && ++ gs_app_get_bundle_kind (app) == AS_BUNDLE_KIND_PACKAGE && ++ gs_app_get_scope (app) == AS_COMPONENT_SCOPE_SYSTEM) { ++ gs_app_set_management_plugin (app, GS_PLUGIN (self)); ++ gs_plugin_dnf5_set_packaging_format (app); ++ } ++ ++ gs_dnf5_app_set_version (dict, app, gs_app_set_version); ++ gs_dnf5_app_set_size (dict, "install_size", app, gs_app_set_size_installed); ++ gs_dnf5_app_set_size (dict, "download_size", app, gs_app_set_size_download); ++ ++ gs_dnf5_update_app_state (app, GS_APP_STATE_UNKNOWN, dict); ++ ++ return TRUE; ++} ++ ++/* Run in @worker. */ ++static void ++gs_dnf5_refine_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsPlugin *plugin = GS_PLUGIN (self); ++ GsPluginRefineData *data = task_data; ++ g_autofree gchar *session_path = NULL; ++ g_autoptr(GHashTable) apps = NULL; ++ g_autoptr(GsDnf5SessionManager) session_manager = NULL; ++ g_autoptr(GsDnf5RpmRpm) rpm_proxy = NULL; ++ g_autoptr(GError) local_error = NULL; ++ gboolean success = TRUE; ++ ++ assert_in_worker (self); ++ ++ apps = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_object_unref); ++ for (guint i = 0; i < gs_app_list_length (data->list); i++) { ++ GsApp *app = gs_app_list_index (data->list, i); ++ if (!gs_app_has_quirk (app, GS_APP_QUIRK_IS_WILDCARD) && ( ++ gs_app_get_state (app) == GS_APP_STATE_UNKNOWN || ++ ((data->flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_SIZE_DATA) != 0 && ++ gs_app_list_length (gs_app_get_related (app)) == 0))) { ++ if (gs_app_get_source_default (app) != NULL && ++ ((gs_app_has_management_plugin (app, NULL) && ++ gs_app_get_bundle_kind (app) == AS_BUNDLE_KIND_PACKAGE && ++ gs_app_get_scope (app) == AS_COMPONENT_SCOPE_SYSTEM) || ++ gs_app_has_management_plugin (app, plugin))) ++ g_hash_table_insert (apps, g_strdup (gs_app_get_source_default (app)), g_object_ref (app)); ++ } ++ } ++ ++ if (g_hash_table_size (apps) == 0) { ++ g_task_return_boolean (task, TRUE); ++ return; ++ } ++ ++ session_path = gs_dnf5_open_session (self, GS_DNF5_RELEASEVER_DEFAULT, &session_manager, cancellable, &local_error); ++ if (session_path == NULL) { ++ gs_dnf5_convert_error (&local_error); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ return; ++ } ++ ++ rpm_proxy = gs_dnf5_rpm_rpm_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ &local_error); ++ success = rpm_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to create Rpm proxy: "); ++ } ++ ++ if (success) { ++ g_autoptr(GVariantBuilder) attrs_builder = NULL; ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariantBuilder) patterns_builder = NULL; ++ g_autoptr(GVariant) result = NULL; ++ GHashTableIter iter; ++ gpointer key = NULL; ++ ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); ++ ++ patterns_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_hash_table_iter_init (&iter, apps); ++ while (g_hash_table_iter_next (&iter, &key, NULL)) { ++ const gchar *name = key; ++ g_variant_builder_add (patterns_builder, "s", name); ++ } ++ ++ attrs_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_variant_builder_add (attrs_builder, "s", "name"); ++ g_variant_builder_add (attrs_builder, "s", "version"); ++ g_variant_builder_add (attrs_builder, "s", "install_size"); ++ g_variant_builder_add (attrs_builder, "s", "download_size"); ++ g_variant_builder_add (attrs_builder, "s", "is_installed"); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "patterns", ++ g_variant_builder_end (patterns_builder)); ++ g_variant_builder_add (options_builder, "{sv}", "package_attrs", ++ g_variant_builder_end (attrs_builder)); ++ g_variant_builder_add (options_builder, "{sv}", "with_nevra", ++ g_variant_new_boolean (TRUE)); ++ g_variant_builder_add (options_builder, "{sv}", "with_provides", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "with_filenames", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "with_src", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "scope", ++ g_variant_new_string ("all")); ++ g_variant_builder_add (options_builder, "{sv}", "latest_limit", ++ g_variant_new_int32 (1)); ++ ++ success = gs_dnf5_rpm_rpm_call_list_sync (rpm_proxy, ++ g_variant_builder_end (options_builder), ++ &result, ++ cancellable, ++ &local_error); ++ ++ if (success) { ++ success = gs_dnf5_foreach_item (self, result, gs_dnf5_refine_cb, apps, cancellable, &local_error); ++ ++ if (success && ++ (data->flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_SIZE_DATA) != 0) { ++ /* do not panic when cannot get dependency sizes for the apps */ ++ if (!gs_dnf5_get_dependency_sizes_sync (self, apps, cancellable, &local_error)) { ++ g_debug ("Failed to get dependency sizes: %s", local_error->message); ++ g_clear_error (&local_error); ++ } ++ } ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to call list: "); ++ } ++ } ++ ++ gs_dnf5_close_session (self, session_manager, session_path); ++ ++ if (success) { ++ g_task_return_boolean (task, TRUE); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ } ++} ++ ++static void ++gs_plugin_dnf5_refine_async (GsPlugin *plugin, ++ GsAppList *list, ++ GsPluginRefineFlags flags, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ gboolean interactive = gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE); ++ g_autoptr(GTask) task = NULL; ++ ++ task = gs_plugin_refine_data_new_task (plugin, list, flags, ++ cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_refine_async); ++ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_refine_thread_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_refine_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ ++/* Run in @worker. */ ++static void ++gs_dnf5_refresh_metadata_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ g_autofree gchar *session_path = NULL; ++ g_autoptr(GsDnf5SessionManager) session_manager = NULL; ++ g_autoptr(GsDnf5Base) base_proxy = NULL; ++ g_autoptr(GError) local_error = NULL; ++ gboolean success = TRUE; ++ ++ assert_in_worker (self); ++ ++ session_path = gs_dnf5_open_session (self, GS_DNF5_RELEASEVER_DEFAULT, &session_manager, cancellable, &local_error); ++ if (session_path == NULL) { ++ gs_dnf5_convert_error (&local_error); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ return; ++ } ++ ++ base_proxy = gs_dnf5_base_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ &local_error); ++ success = base_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to create Base proxy: "); ++ } ++ ++ if (success && GPOINTER_TO_INT (task_data) == 1) { ++ g_autofree gchar *op_error_msg = NULL; ++ gboolean op_success = FALSE; ++ ++ success = gs_dnf5_base_call_clean_sync (base_proxy, ++ "expire-cache", ++ &op_success, ++ &op_error_msg, ++ cancellable, ++ &local_error); ++ if (!success) ++ g_debug ("Failed to call expire-cache: %s", local_error->message); ++ else if (!op_success) ++ g_debug ("Failed to expire-cache: %s", op_error_msg); ++ ++ /* ignore expire-cache error, only log about it */ ++ g_clear_error (&local_error); ++ ++ /* reset the session, to take the expiration into the effect */ ++ success = gs_dnf5_reset_session_sync (self, session_path, cancellable, &local_error); ++ } ++ ++ if (success) { ++ gboolean result = FALSE; ++ ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (base_proxy), G_MAXINT); ++ ++ success = gs_dnf5_base_call_read_all_repos_sync (base_proxy, &result, cancellable, &local_error); ++ ++ /* 'result' is ignored here, due to no error provided */ ++ if (!success) { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to call read-all-repos: "); ++ } ++ } ++ ++ gs_dnf5_close_session (self, session_manager, session_path); ++ ++ if (success) { ++ g_task_return_boolean (task, TRUE); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ } ++} ++ ++static void ++gs_plugin_dnf5_refresh_metadata_async (GsPlugin *plugin, ++ guint64 cache_age_secs, ++ GsPluginRefreshMetadataFlags flags, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ gboolean interactive = (flags & GS_PLUGIN_REFRESH_METADATA_FLAGS_INTERACTIVE) != 0; ++ g_autoptr(GTask) task = NULL; ++ ++ task = g_task_new (self, cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_refresh_metadata_async); ++ /* no need to save whole structure, the seconds are not used at all, ++ thus make it only a flag whether to invalidate the cache or not first */ ++ g_task_set_task_data (task, GINT_TO_POINTER (cache_age_secs < 60 ? 1 : 0), NULL); ++ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_refresh_metadata_thread_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_refresh_metadata_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ ++void ++gs_plugin_adopt_app (GsPlugin *plugin, ++ GsApp *app) ++{ ++ if (gs_app_get_bundle_kind (app) == AS_BUNDLE_KIND_PACKAGE && ++ gs_app_get_scope (app) == AS_COMPONENT_SCOPE_SYSTEM) { ++ gs_app_set_management_plugin (app, plugin); ++ gs_plugin_dnf5_set_packaging_format (app); ++ return; ++ } else if (gs_app_get_kind (app) == AS_COMPONENT_KIND_OPERATING_SYSTEM) { ++ gs_app_set_management_plugin (app, plugin); ++ } ++} ++ ++static gboolean ++gs_dnf5_install_update (GsPlugin *plugin, ++ GsAppList *list, ++ gboolean is_install, ++ gboolean interactive, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ g_autofree gchar *session_path = NULL; ++ g_autoptr(GPtrArray) packages = NULL; ++ g_autoptr(GsAppList) used_apps = NULL; ++ g_autoptr(GsDnf5SessionManager) session_manager = NULL; ++ g_autoptr(GsDnf5RpmRpm) rpm_proxy = NULL; ++ g_autoptr(GsApp) progress_app = NULL; ++ gboolean success; ++ ++ /* queue for install if installation needs the network */ ++ if (!gs_plugin_get_network_available (plugin)) { ++ if (is_install) { ++ for (guint i = 0; i < gs_app_list_length (list); i++) { ++ GsApp *app = gs_app_list_index (list, i); ++ if (gs_app_has_management_plugin (app, plugin)) { ++ if (gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY) { ++ g_warn_if_reached (); ++ continue; ++ } ++ ++ gs_app_set_state (app, GS_APP_STATE_QUEUED_FOR_INSTALL); ++ } ++ } ++ } ++ return TRUE; ++ } ++ ++ packages = g_ptr_array_new_with_free_func (g_free); ++ used_apps = gs_app_list_new (); ++ ++ for (guint i = 0; i < gs_app_list_length (list); i++) { ++ GsApp *app = gs_app_list_index (list, i); ++ if (gs_app_has_management_plugin (app, plugin)) { ++ const gchar *source = gs_app_get_source_default (app); ++ if (source != NULL) { ++ GFile *local_file = gs_app_get_local_file (app); ++ if (local_file != NULL) ++ g_ptr_array_add (packages, g_file_get_uri (local_file)); ++ else ++ g_ptr_array_add (packages, g_strdup (source)); ++ gs_app_list_add (used_apps, app); ++ if (progress_app == NULL) ++ progress_app = g_object_ref (app); ++ } ++ } else if (gs_app_has_quirk (app, GS_APP_QUIRK_IS_PROXY)) { ++ GsAppList *related = gs_app_get_related (app); ++ for (guint j = 0; j < gs_app_list_length (related); j++) { ++ GsApp *rel_app = gs_app_list_index (related, j); ++ if (gs_app_has_management_plugin (rel_app, plugin)) { ++ const gchar *source = gs_app_get_source_default (rel_app); ++ if (source != NULL) { ++ GFile *local_file = gs_app_get_local_file (rel_app); ++ if (local_file != NULL) ++ g_ptr_array_add (packages, g_file_get_uri (local_file)); ++ else ++ g_ptr_array_add (packages, g_strdup (source)); ++ gs_app_list_add (used_apps, rel_app); ++ } ++ } ++ } ++ if (progress_app == NULL) ++ progress_app = g_object_ref (app); ++ } ++ } ++ ++ if (packages->len == 0) { ++ g_set_error_literal (error, ++ GS_PLUGIN_ERROR, ++ GS_PLUGIN_ERROR_NOT_SUPPORTED, ++ "installing not available"); ++ return FALSE; ++ } ++ ++ session_path = gs_dnf5_open_session (self, GS_DNF5_RELEASEVER_DEFAULT, &session_manager, cancellable, error); ++ if (session_path == NULL) { ++ gs_dnf5_convert_error (error); ++ return FALSE; ++ } ++ ++ for (guint i = 0; i < gs_app_list_length (used_apps); i++) { ++ GsApp *app = gs_app_list_index (used_apps, i); ++ g_autoptr(GsAppList) addons = NULL; ++ ++ if (gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY) { ++ g_warn_if_reached (); ++ continue; ++ } ++ ++ if (is_install) { ++ gs_app_set_state (app, GS_APP_STATE_INSTALLING); ++ addons = gs_app_dup_addons (app); ++ } ++ for (guint j = 0; addons != NULL && j < gs_app_list_length (addons); j++) { ++ GsApp *addon = gs_app_list_index (addons, j); ++ if (gs_app_get_to_be_installed (addon)) { ++ const gchar *addon_source = gs_app_get_source_default (app); ++ if (addon_source != NULL) { ++ g_ptr_array_add (packages, g_strdup (addon_source)); ++ if (is_install) ++ gs_app_set_state (addon, GS_APP_STATE_INSTALLING); ++ } ++ } ++ } ++ } ++ ++ rpm_proxy = gs_dnf5_rpm_rpm_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ error); ++ success = rpm_proxy != NULL; ++ if (success) { ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ ++ /* NULL-terminate the array, to be like strv */ ++ g_ptr_array_add (packages, NULL); ++ ++ success = gs_dnf5_reset_transaction_sync (self, session_path, rpm_proxy, cancellable, error); ++ ++ if (success && is_install) { ++ success = gs_dnf5_rpm_rpm_call_install_sync (rpm_proxy, ++ (const gchar * const *) packages->pdata, ++ g_variant_builder_end (options_builder), ++ cancellable, ++ error); ++ } else if (success) { ++ success = gs_dnf5_rpm_rpm_call_upgrade_sync (rpm_proxy, ++ (const gchar * const *) packages->pdata, ++ g_variant_builder_end (options_builder), ++ cancellable, ++ error); ++ } ++ success = success && gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, ++ is_install ? GS_DNF5_TRANSACTION_FLAG_NONE : GS_DNF5_TRANSACTION_FLAG_OFFLINE, ++ NULL, cancellable, error); ++ if (success && !is_install) { ++ /* ensure the update is finished with the 'reboot' action */ ++ g_autoptr(GsDnf5Offline) offline_proxy = NULL; ++ ++ offline_proxy = gs_dnf5_offline_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ error); ++ success = offline_proxy != NULL; ++ if (success) { ++ g_autofree gchar *op_error_msg = NULL; ++ gboolean op_success = FALSE; ++ ++ success = gs_dnf5_offline_call_set_finish_action_sync (offline_proxy, "reboot", &op_success, &op_error_msg, cancellable, error); ++ if (success && !op_success) { ++ success = FALSE; ++ if (op_error_msg != NULL) { ++ g_set_error_literal (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_FAILED, op_error_msg); ++ g_prefix_error_literal (error, "Failed to set finish action: "); ++ } ++ } else if (!success) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to set finish action: "); ++ } ++ } else { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to create Offline proxy: "); ++ } ++ } ++ } else { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to create Rpm proxy: "); ++ } ++ ++ gs_dnf5_close_session (self, session_manager, session_path); ++ ++ if (success) { ++ gs_dnf5_mark_session_needs_reset (self); ++ } else { ++ gs_dnf5_convert_error (error); ++ ++ if (error != NULL && *error != NULL) ++ gs_dnf5_report_error (self, *error, interactive); ++ } ++ ++ for (guint i = 0; i < gs_app_list_length (used_apps); i++) { ++ GsApp *app = gs_app_list_index (used_apps, i); ++ g_autoptr(GsAppList) addons = NULL; ++ ++ if (gs_app_get_state (app) == GS_APP_STATE_INSTALLING) { ++ if (success) { ++ gs_app_set_state (app, GS_APP_STATE_INSTALLED); ++ gs_app_set_size_download (app, GS_SIZE_TYPE_VALID, 0); ++ } else { ++ gs_app_set_state_recover (app); ++ } ++ } else if (success) { ++ /* apps prepared for offline update are downloaded */ ++ gs_app_set_size_download (app, GS_SIZE_TYPE_VALID, 0); ++ } ++ ++ if (is_install) ++ addons = gs_app_dup_addons (app); ++ for (guint j = 0; addons != NULL && j < gs_app_list_length (addons); j++) { ++ GsApp *addon = gs_app_list_index (addons, j); ++ if (gs_app_get_state (addon) == GS_APP_STATE_INSTALLING) { ++ if (success) { ++ gs_app_set_state (addon, GS_APP_STATE_INSTALLED); ++ gs_app_set_size_download (addon, GS_SIZE_TYPE_VALID, 0); ++ } else { ++ gs_app_set_state_recover (addon); ++ } ++ } else if (success) { ++ /* apps prepared for offline update are downloaded */ ++ gs_app_set_size_download (app, GS_SIZE_TYPE_VALID, 0); ++ } ++ } ++ } ++ ++ return success; ++} ++ ++/* Run in @worker. */ ++static void ++gs_dnf5_install_apps_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsPlugin *plugin = GS_PLUGIN (self); ++ GsPluginInstallAppsData *data = task_data; ++ g_autoptr(GError) local_error = NULL; ++ gboolean success; ++ ++ assert_in_worker (self); ++ ++ g_atomic_int_inc (&self->calling_rpm); ++ ++ success = gs_dnf5_install_update (plugin, data->apps, TRUE, ++ (data->flags & GS_PLUGIN_INSTALL_APPS_FLAGS_INTERACTIVE) != 0, ++ cancellable, &local_error); ++ ++ g_atomic_int_dec_and_test (&self->calling_rpm); ++ ++ if (success) ++ g_task_return_boolean (task, TRUE); ++ else ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++} ++ ++static void ++gs_plugin_dnf5_install_apps_async (GsPlugin *plugin, ++ GsAppList *apps, ++ GsPluginInstallAppsFlags flags, ++ GsPluginProgressCallback progress_callback, ++ gpointer progress_user_data, ++ GsPluginAppNeedsUserActionCallback app_needs_user_action_callback, ++ gpointer app_needs_user_action_data, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ gboolean interactive = (flags & GS_PLUGIN_INSTALL_APPS_FLAGS_INTERACTIVE) != 0; ++ g_autoptr(GTask) task = NULL; ++ ++ task = gs_plugin_install_apps_data_new_task (plugin, apps, flags, progress_callback, progress_user_data, ++ app_needs_user_action_callback, app_needs_user_action_data, ++ cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_install_apps_async); ++ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_install_apps_thread_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_install_apps_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ ++/* Run in @worker. */ ++static void ++gs_dnf5_uninstall_apps_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsPlugin *plugin = GS_PLUGIN (self); ++ GsPluginUninstallAppsData *data = task_data; ++ g_autofree gchar *session_path = NULL; ++ g_autoptr(GPtrArray) touched_apps = NULL; ++ g_autoptr(GPtrArray) packages = NULL; ++ g_autoptr(GsDnf5SessionManager) session_manager = NULL; ++ g_autoptr(GsDnf5RpmRpm) rpm_proxy = NULL; ++ g_autoptr(GsApp) progress_app = NULL; ++ g_autoptr(GError) local_error = NULL; ++ gboolean success; ++ ++ assert_in_worker (self); ++ ++ touched_apps = g_ptr_array_new_with_free_func (g_object_unref); ++ packages = g_ptr_array_new_with_free_func (g_free); ++ ++ for (guint i = 0; i < gs_app_list_length (data->apps); i++) { ++ g_autoptr(GsAppList) addons = NULL; ++ GsApp *app = gs_app_list_index (data->apps, i); ++ const gchar *source; ++ if (!gs_app_has_management_plugin (app, plugin)) ++ continue; ++ if (gs_app_get_kind (app) == AS_COMPONENT_KIND_REPOSITORY) { ++ g_warn_if_reached (); ++ continue; ++ } ++ source = gs_app_get_source_default (app); ++ if (source == NULL) { ++ g_task_return_new_error (task, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_NOT_SUPPORTED, ++ "remove not available"); ++ return; ++ } ++ g_ptr_array_add (packages, g_strdup (source)); ++ g_ptr_array_add (touched_apps, g_object_ref (app)); ++ gs_app_set_state (app, GS_APP_STATE_REMOVING); ++ ++ if (progress_app == NULL) ++ progress_app = g_object_ref (app); ++ ++ addons = gs_app_dup_addons (app); ++ for (guint j = 0; addons != NULL && j < gs_app_list_length (addons); j++) { ++ GsApp *addon = gs_app_list_index (addons, j); ++ if (gs_app_get_state (addon) == GS_APP_STATE_INSTALLED) { ++ const gchar *addon_source = gs_app_get_source_default (addon); ++ if (addon_source != NULL) { ++ g_ptr_array_add (packages, g_strdup (addon_source)); ++ g_ptr_array_add (touched_apps, g_object_ref (addon)); ++ gs_app_set_state (addon, GS_APP_STATE_REMOVING); ++ } ++ } ++ } ++ } ++ ++ if (packages->len == 0) { ++ g_task_return_boolean (task, TRUE); ++ return; ++ } ++ ++ session_path = gs_dnf5_open_session (self, GS_DNF5_RELEASEVER_DEFAULT, &session_manager, cancellable, &local_error); ++ if (session_path == NULL) { ++ gs_dnf5_convert_error (&local_error); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ return; ++ } ++ ++ g_atomic_int_inc (&self->calling_rpm); ++ ++ rpm_proxy = gs_dnf5_rpm_rpm_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ &local_error); ++ success = rpm_proxy != NULL; ++ if (success) { ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "strict", ++ g_variant_new_boolean (FALSE)); ++ ++ /* NULL-terminate the array, to be like strv */ ++ g_ptr_array_add (packages, NULL); ++ ++ success = gs_dnf5_reset_transaction_sync (self, session_path, rpm_proxy, cancellable, &local_error); ++ ++ success = success && ++ gs_dnf5_rpm_rpm_call_remove_sync (rpm_proxy, ++ (const gchar * const *) packages->pdata, ++ g_variant_builder_end (options_builder), ++ cancellable, ++ &local_error); ++ success = success && gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, GS_DNF5_TRANSACTION_FLAG_NONE, NULL, cancellable, &local_error); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to create Rpm proxy: "); ++ } ++ ++ gs_dnf5_close_session (self, session_manager, session_path); ++ g_atomic_int_dec_and_test (&self->calling_rpm); ++ ++ if (success) { ++ gs_dnf5_mark_session_needs_reset (self); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ gs_dnf5_report_error (self, local_error, (data->flags & GS_PLUGIN_UNINSTALL_APPS_FLAGS_INTERACTIVE) != 0); ++ } ++ ++ for (guint i = 0; i < touched_apps->len; i++) { ++ GsApp *app = g_ptr_array_index (touched_apps, i); ++ if (gs_app_get_state (app) == GS_APP_STATE_REMOVING) { ++ if (success) ++ gs_app_set_state (app, GS_APP_STATE_UNKNOWN); ++ else ++ gs_app_set_state_recover (app); ++ } ++ } ++ ++ if (success) ++ g_task_return_boolean (task, TRUE); ++ else ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++} ++ ++static void ++gs_plugin_dnf5_uninstall_apps_async (GsPlugin *plugin, ++ GsAppList *apps, ++ GsPluginUninstallAppsFlags flags, ++ GsPluginProgressCallback progress_callback, ++ gpointer progress_user_data, ++ GsPluginAppNeedsUserActionCallback app_needs_user_action_callback, ++ gpointer app_needs_user_action_data, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ gboolean interactive = (flags & GS_PLUGIN_UNINSTALL_APPS_FLAGS_INTERACTIVE) != 0; ++ g_autoptr(GTask) task = NULL; ++ ++ task = gs_plugin_uninstall_apps_data_new_task (plugin, apps, flags, progress_callback, progress_user_data, ++ app_needs_user_action_callback, app_needs_user_action_data, ++ cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_uninstall_apps_async); ++ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_uninstall_apps_thread_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_uninstall_apps_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ ++/* Run in @worker. */ ++static void ++gs_dnf5_update_apps_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsPlugin *plugin = GS_PLUGIN (self); ++ GsPluginUpdateAppsData *data = task_data; ++ g_autoptr(GError) local_error = NULL; ++ gboolean success; ++ ++ assert_in_worker (self); ++ ++ g_atomic_int_inc (&self->calling_rpm); ++ ++ success = gs_dnf5_install_update (plugin, data->apps, FALSE, ++ (data->flags & GS_PLUGIN_UPDATE_APPS_FLAGS_INTERACTIVE) != 0, ++ cancellable, &local_error); ++ ++ g_atomic_int_dec_and_test (&self->calling_rpm); ++ ++ if (success) ++ g_task_return_boolean (task, TRUE); ++ else ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++} ++ ++static void ++gs_plugin_dnf5_update_apps_async (GsPlugin *plugin, ++ GsAppList *apps, ++ GsPluginUpdateAppsFlags flags, ++ GsPluginProgressCallback progress_callback, ++ gpointer progress_user_data, ++ GsPluginAppNeedsUserActionCallback app_needs_user_action_callback, ++ gpointer app_needs_user_action_data, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ gboolean interactive = (flags & GS_PLUGIN_UPDATE_APPS_FLAGS_INTERACTIVE) != 0; ++ g_autoptr(GTask) task = NULL; ++ ++ task = gs_plugin_update_apps_data_new_task (plugin, apps, flags, progress_callback, progress_user_data, ++ app_needs_user_action_callback, app_needs_user_action_data, ++ cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_update_apps_async); ++ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_update_apps_thread_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_update_apps_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ ++static gboolean ++gs_dnf5_manage_repository_sync (GsPluginDnf5 *self, ++ GsApp *repository, ++ gboolean enable, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ g_autofree gchar *session_path = NULL; ++ g_autoptr(GsDnf5SessionManager) session_manager = NULL; ++ g_autoptr(GsDnf5RpmRepo) repo_proxy = NULL; ++ gboolean success; ++ ++ if (!gs_app_has_management_plugin (repository, GS_PLUGIN (self))) ++ return TRUE; ++ ++ if (gs_app_get_kind (repository) != AS_COMPONENT_KIND_REPOSITORY) { ++ g_set_error (error, ++ GS_PLUGIN_ERROR, ++ GS_PLUGIN_ERROR_NOT_SUPPORTED, ++ "wrong app kind (%s) passed to manage_repository", ++ as_component_kind_to_string (gs_app_get_kind (repository))); ++ return FALSE; ++ } ++ ++ session_path = gs_dnf5_open_session (self, GS_DNF5_RELEASEVER_DEFAULT, &session_manager, cancellable, error); ++ if (session_path == NULL) { ++ gs_dnf5_convert_error (error); ++ return FALSE; ++ } ++ ++ repo_proxy = gs_dnf5_rpm_repo_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ error); ++ success = repo_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to create Rpm proxy: "); ++ } ++ ++ if (success) { ++ const gchar *ids[2] = { NULL, NULL }; ++ ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (repo_proxy), G_MAXINT); ++ ++ ids[0] = gs_app_get_id (repository); ++ ++ if (enable) ++ success = gs_dnf5_rpm_repo_call_enable_sync (repo_proxy, ids, cancellable, error); ++ else ++ success = gs_dnf5_rpm_repo_call_disable_sync (repo_proxy, ids, cancellable, error); ++ ++ if (success) { ++ if (enable) ++ gs_app_set_state (repository, GS_APP_STATE_INSTALLED); ++ else ++ gs_app_set_state (repository, GS_APP_STATE_AVAILABLE); ++ } else { ++ gs_dnf5_convert_error (error); ++ g_prefix_error (error, "Failed to call %s: ", enable ? "enable" : "disable"); ++ } ++ } ++ ++ gs_dnf5_close_session (self, session_manager, session_path); ++ ++ return success; ++} ++ ++/* Run in @worker. */ ++static void ++gs_dnf5_enable_repository_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsPluginManageRepositoryData *data = task_data; ++ g_autoptr(GError) local_error = NULL; ++ ++ assert_in_worker (self); ++ ++ if (gs_dnf5_manage_repository_sync (self, data->repository, TRUE, cancellable, &local_error)) { ++ g_task_return_boolean (task, TRUE); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ } ++} ++ ++static void ++gs_plugin_dnf5_enable_repository_async (GsPlugin *plugin, ++ GsApp *repository, ++ GsPluginManageRepositoryFlags flags, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ gboolean interactive = (flags & GS_PLUGIN_MANAGE_REPOSITORY_FLAGS_INTERACTIVE) != 0; ++ g_autoptr(GTask) task = NULL; ++ ++ task = gs_plugin_manage_repository_data_new_task (plugin, repository, flags, ++ cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_enable_repository_async); ++ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_enable_repository_thread_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_enable_repository_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ ++/* Run in @worker. */ ++static void ++gs_dnf5_disable_repository_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsPluginManageRepositoryData *data = task_data; ++ g_autoptr(GError) local_error = NULL; ++ ++ assert_in_worker (self); ++ ++ if (gs_dnf5_manage_repository_sync (self, data->repository, FALSE, cancellable, &local_error)) { ++ g_task_return_boolean (task, TRUE); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ } ++} ++ ++static void ++gs_plugin_dnf5_disable_repository_async (GsPlugin *plugin, ++ GsApp *repository, ++ GsPluginManageRepositoryFlags flags, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ gboolean interactive = (flags & GS_PLUGIN_MANAGE_REPOSITORY_FLAGS_INTERACTIVE) != 0; ++ g_autoptr(GTask) task = NULL; ++ ++ task = gs_plugin_manage_repository_data_new_task (plugin, repository, flags, ++ cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_disable_repository_async); ++ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_disable_repository_thread_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_disable_repository_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ ++static gboolean ++gs_dnf5_pick_rpm_desktop_file_cb (GsPlugin *plugin, ++ GsApp *app, ++ const gchar *filename, ++ GKeyFile *key_file, ++ gpointer user_data) ++{ ++ return strstr (filename, "/snapd/") == NULL && ++ strstr (filename, "/snap/") == NULL && ++ strstr (filename, "/flatpak/") == NULL && ++ g_key_file_has_group (key_file, "Desktop Entry") && ++ !g_key_file_has_key (key_file, "Desktop Entry", "X-Flatpak", NULL) && ++ !g_key_file_has_key (key_file, "Desktop Entry", "X-SnapInstanceName", NULL); ++} ++ ++static void ++gs_plugin_dnf5_launch_async (GsPlugin *plugin, ++ GsApp *app, ++ GsPluginLaunchFlags flags, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ gs_plugin_app_launch_filtered_async (plugin, app, flags, ++ gs_dnf5_pick_rpm_desktop_file_cb, NULL, ++ cancellable, ++ callback, user_data); ++} ++ ++static gboolean ++gs_plugin_dnf5_launch_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return gs_plugin_app_launch_filtered_finish (plugin, result, error); ++} ++ ++static gboolean ++gs_dnf5_file_to_app_sync (GsPluginDnf5 *self, ++ GsAppList *list, ++ GFile *file, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ g_autofree gchar *content_type = NULL; ++ g_autofree gchar *session_path = NULL; ++ g_autoptr(GsDnf5SessionManager) session_manager = NULL; ++ g_autoptr(GsDnf5RpmRpm) rpm_proxy = NULL; ++ gboolean success = TRUE; ++ const gchar *mimetypes[] = { ++ "application/x-app-package", ++ "application/x-deb", ++ "application/vnd.debian.binary-package", ++ "application/x-redhat-package-manager", ++ "application/x-rpm", ++ NULL }; ++ ++ /* does this match any of the mimetypes we support */ ++ content_type = gs_utils_get_content_type (file, cancellable, error); ++ if (content_type == NULL) ++ return FALSE; ++ if (!g_strv_contains (mimetypes, content_type)) ++ return TRUE; ++ ++ session_path = gs_dnf5_open_session (self, GS_DNF5_RELEASEVER_DEFAULT, &session_manager, cancellable, error); ++ if (session_path == NULL) { ++ gs_dnf5_convert_error (error); ++ return FALSE; ++ } ++ ++ rpm_proxy = gs_dnf5_rpm_rpm_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ error); ++ success = rpm_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to create Rpm proxy: "); ++ } ++ ++ if (success) { ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariantBuilder) patterns_builder = NULL; ++ g_autoptr(GVariant) result = NULL; ++ g_autofree gchar *file_uri = NULL; ++ ++ file_uri = g_file_get_path (file); ++ ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); ++ ++ patterns_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_variant_builder_add (patterns_builder, "s", file_uri); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "patterns", ++ g_variant_builder_end (patterns_builder)); ++ g_variant_builder_add (options_builder, "{sv}", "package_attrs", ++ gs_dnf5_dup_package_attrs ()); ++ g_variant_builder_add (options_builder, "{sv}", "with_provides", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "with_filenames", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "with_src", ++ g_variant_new_boolean (FALSE)); ++ g_variant_builder_add (options_builder, "{sv}", "scope", ++ g_variant_new_string ("all")); ++ ++ success = gs_dnf5_rpm_rpm_call_list_sync (rpm_proxy, ++ g_variant_builder_end (options_builder), ++ &result, ++ cancellable, ++ error); ++ ++ if (success) { ++ g_autofree gchar *basename = g_file_get_basename (file); ++ ReadPackageData rpd = { 0, }; ++ rpd.list = list; ++ rpd.set_state = GS_APP_STATE_AVAILABLE_LOCAL; ++ rpd.nevra_to_app = NULL; ++ success = gs_dnf5_foreach_item (self, result, gs_dnf5_read_package_cb, &rpd, cancellable, error); ++ ++ if (success) { ++ for (guint i = 0; i < gs_app_list_length (list); i++) { ++ GsApp *app = gs_app_list_index (list, i); ++ /* it's already downloaded, because it's a local file */ ++ gs_app_set_size_download (app, GS_SIZE_TYPE_VALID, 0); ++ gs_app_set_bundle_kind (app, AS_BUNDLE_KIND_PACKAGE); ++ gs_app_set_local_file (app, file); ++ gs_app_set_metadata (app, "GnomeSoftware::packagename-value", basename); ++ } ++ } ++ } else { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to call list: "); ++ } ++ } ++ ++ gs_dnf5_close_session (self, session_manager, session_path); ++ ++ return success; ++} ++ ++static void ++gs_dnf5_file_to_app_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ g_autoptr(GsAppList) list = gs_app_list_new (); ++ g_autoptr(GError) local_error = NULL; ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsPluginFileToAppData *data = task_data; ++ ++ if (gs_dnf5_file_to_app_sync (self, list, data->file, cancellable, &local_error)) { ++ g_task_return_pointer (task, g_steal_pointer (&list), g_object_unref); ++ } else if (local_error != NULL) { ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ } else { ++ g_task_return_pointer (task, g_steal_pointer (&list), g_object_unref); ++ } ++} ++ ++static void ++gs_plugin_dnf5_file_to_app_async (GsPlugin *plugin, ++ GFile *file, ++ GsPluginFileToAppFlags flags, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ g_autoptr(GTask) task = NULL; ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ gboolean interactive = (flags & GS_PLUGIN_FILE_TO_APP_FLAGS_INTERACTIVE) != 0; ++ ++ task = gs_plugin_file_to_app_data_new_task (plugin, file, flags, cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_file_to_app_async); ++ ++ /* Queue a job to get the apps. */ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_file_to_app_thread_cb, g_steal_pointer (&task)); ++} ++ ++static GsAppList * ++gs_plugin_dnf5_file_to_app_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_pointer (G_TASK (result), error); ++} ++ ++static gboolean ++gs_dnf5_system_upgrade_sync (GsPluginDnf5 *self, ++ const gchar *releasever, ++ GsApp *progress_app, ++ gboolean download_only, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ g_autofree gchar *session_path = NULL; ++ g_autoptr(GsAppList) list = NULL; ++ g_autoptr(GsDnf5SessionManager) session_manager = NULL; ++ g_autoptr(GsDnf5Offline) offline_proxy = NULL; ++ g_autoptr(GsDnf5RpmRpm) rpm_proxy = NULL; ++ gboolean success; ++ ++ session_path = gs_dnf5_open_session (self, releasever, &session_manager, cancellable, error); ++ if (session_path == NULL) { ++ gs_dnf5_convert_error (error); ++ return FALSE; ++ } ++ ++ rpm_proxy = gs_dnf5_rpm_rpm_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ error); ++ success = rpm_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to create Rpm proxy: "); ++ } ++ ++ if (success) { ++ offline_proxy = gs_dnf5_offline_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ error); ++ success = offline_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to create Offline proxy: "); ++ } ++ } ++ ++ if (success) { ++ gboolean pending = FALSE; ++ g_autoptr(GVariant) transaction_status = NULL; ++ ++ if (gs_dnf5_offline_call_get_status_sync (offline_proxy, &pending, &transaction_status, cancellable, error) && ++ pending && transaction_status != NULL) { ++ const gchar *target_releasever = NULL; ++ gboolean found = g_variant_lookup (transaction_status, "target_releasever", "&s", &target_releasever); ++ if (found && g_strcmp0 (target_releasever, releasever) == 0) { ++ g_debug ("There is prepared an upgrade for version '%s' already, skipping preparation", releasever); ++ gs_dnf5_close_session (self, session_manager, session_path); ++ return TRUE; ++ } else if (found && target_releasever != NULL) { ++ g_debug ("There is prepared an update for version '%s', but needs version '%s', redo preparation", target_releasever, releasever); ++ } ++ } ++ } ++ ++ if (success) { ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariant) result = NULL; ++ ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ ++ success = gs_dnf5_reset_transaction_sync (self, session_path, rpm_proxy, cancellable, error); ++ ++ success = success && ++ gs_dnf5_rpm_rpm_call_system_upgrade_sync (rpm_proxy, ++ g_variant_builder_end (options_builder), ++ cancellable, ++ error); ++ ++ if (success) { ++ success = gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, GS_DNF5_TRANSACTION_FLAG_OFFLINE, NULL, cancellable, error); ++ ++ if (success && !download_only) { ++ g_autofree gchar *op_error_msg = NULL; ++ gboolean op_success = FALSE; ++ ++ /* ensure the upgrade is finished with the 'reboot' action */ ++ success = gs_dnf5_offline_call_set_finish_action_sync (offline_proxy, "reboot", &op_success, &op_error_msg, cancellable, error); ++ if (success && !op_success) { ++ success = FALSE; ++ if (op_error_msg != NULL) { ++ g_set_error_literal (error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_FAILED, op_error_msg); ++ g_prefix_error_literal (error, "Failed to set finish action: "); ++ } ++ } else if (!success) { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to set finish action: "); ++ } ++ } ++ } else { ++ gs_dnf5_convert_error (error); ++ g_prefix_error_literal (error, "Failed to call system_upgrade: "); ++ } ++ } ++ ++ gs_dnf5_close_session (self, session_manager, session_path); ++ ++ return success; ++} ++ ++/* Run in @worker. */ ++static void ++gs_dnf5_download_upgrade_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsPluginDownloadUpgradeData *data = task_data; ++ g_autoptr(GError) local_error = NULL; ++ ++ assert_in_worker (self); ++ ++ gs_app_set_state (data->app, GS_APP_STATE_DOWNLOADING); ++ ++ if (gs_dnf5_system_upgrade_sync (self, gs_app_get_version (data->app), data->app, TRUE, cancellable, &local_error)) { ++ gs_app_set_state (data->app, GS_APP_STATE_UPDATABLE); ++ g_task_return_boolean (task, TRUE); ++ } else { ++ gs_app_set_state (data->app, GS_APP_STATE_AVAILABLE); ++ gs_dnf5_convert_error (&local_error); ++ gs_dnf5_report_error (self, local_error, (data->flags & GS_PLUGIN_DOWNLOAD_UPGRADE_FLAGS_INTERACTIVE) != 0); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ } ++} ++ ++static void ++gs_plugin_dnf5_download_upgrade_async (GsPlugin *plugin, ++ GsApp *app, ++ GsPluginDownloadUpgradeFlags flags, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ g_autoptr(GTask) task = NULL; ++ gboolean interactive = (flags & GS_PLUGIN_DOWNLOAD_UPGRADE_FLAGS_INTERACTIVE) != 0; ++ ++ task = gs_plugin_download_upgrade_data_new_task (plugin, app, flags, cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_download_upgrade_async); ++ ++ /* only process this app if was created by this plugin */ ++ if (!gs_app_has_management_plugin (app, plugin)) { ++ g_task_return_boolean (task, TRUE); ++ return; ++ } ++ ++ /* check is distro-upgrade */ ++ if (gs_app_get_kind (app) != AS_COMPONENT_KIND_OPERATING_SYSTEM) { ++ g_task_return_boolean (task, TRUE); ++ return; ++ } ++ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_download_upgrade_thread_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_download_upgrade_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ ++/* Run in @worker. */ ++static void ++gs_dnf5_trigger_upgrade_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsPluginTriggerUpgradeData *data = task_data; ++ g_autoptr(GError) local_error = NULL; ++ ++ assert_in_worker (self); ++ ++ gs_app_set_state (data->app, GS_APP_STATE_PENDING_INSTALL); ++ ++ if (gs_dnf5_system_upgrade_sync (self, gs_app_get_version (data->app), data->app, FALSE, cancellable, &local_error)) { ++ gs_app_set_state (data->app, GS_APP_STATE_UPDATABLE); ++ g_task_return_boolean (task, TRUE); ++ } else { ++ gs_app_set_state (data->app, GS_APP_STATE_AVAILABLE); ++ gs_dnf5_convert_error (&local_error); ++ gs_dnf5_report_error (self, local_error, (data->flags & GS_PLUGIN_TRIGGER_UPGRADE_FLAGS_INTERACTIVE) != 0); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ } ++} ++ ++static void ++gs_plugin_dnf5_trigger_upgrade_async (GsPlugin *plugin, ++ GsApp *app, ++ GsPluginTriggerUpgradeFlags flags, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ g_autoptr(GTask) task = NULL; ++ gboolean interactive = (flags & GS_PLUGIN_TRIGGER_UPGRADE_FLAGS_INTERACTIVE) != 0; ++ ++ task = gs_plugin_trigger_upgrade_data_new_task (plugin, app, flags, cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_trigger_upgrade_async); ++ ++ /* only process this app if was created by this plugin */ ++ if (!gs_app_has_management_plugin (app, plugin)) { ++ g_task_return_boolean (task, TRUE); ++ return; ++ } ++ ++ /* check is distro-upgrade */ ++ if (gs_app_get_kind (app) != AS_COMPONENT_KIND_OPERATING_SYSTEM) { ++ g_task_return_boolean (task, TRUE); ++ return; ++ } ++ ++ gs_app_set_state (app, GS_APP_STATE_PENDING_INSTALL); ++ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_trigger_upgrade_thread_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_trigger_upgrade_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ ++static void ++gs_plugin_dnf5_dispose (GObject *object) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (object); ++ ++ if (self->rpm_transaction_watch_id != 0) { ++ g_bus_unwatch_name (self->rpm_transaction_watch_id); ++ self->rpm_transaction_watch_id = 0; ++ } ++ ++ g_clear_object (&self->worker); ++ g_clear_object (&self->connection); ++ g_clear_object (&self->rpm_transaction_proxy); ++ ++ g_mutex_lock (&self->session_data.mutex); ++ if (self->session_data.autoclose_timer) { ++ g_source_remove (self->session_data.autoclose_timer); ++ self->session_data.autoclose_timer = 0; ++ } ++ ++ if (self->session_data.proxy != NULL) { ++ gs_dnf5_close_session_real (self->session_data.proxy, self->session_data.object_path); ++ ++ g_clear_object (&self->session_data.proxy); ++ g_clear_pointer (&self->session_data.object_path, g_free); ++ } ++ g_mutex_unlock (&self->session_data.mutex); ++ ++ g_mutex_lock (&self->dependency_sizes_data.mutex); ++ g_clear_pointer (&self->dependency_sizes_data.apps, g_ptr_array_unref); ++ g_clear_object (&self->dependency_sizes_data.cancellable); ++ g_mutex_unlock (&self->dependency_sizes_data.mutex); ++ ++ G_OBJECT_CLASS (gs_plugin_dnf5_parent_class)->dispose (object); ++} ++ ++static void ++gs_plugin_dnf5_finalize (GObject *object) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (object); ++ ++ g_mutex_clear (&self->session_data.mutex); ++ g_cond_clear (&self->session_data.cond); ++ g_mutex_clear (&self->dependency_sizes_data.mutex); ++ ++ G_OBJECT_CLASS (gs_plugin_dnf5_parent_class)->finalize (object); ++} ++ ++static void ++gs_plugin_dnf5_class_init (GsPluginDnf5Class *klass) ++{ ++ GObjectClass *object_class = G_OBJECT_CLASS (klass); ++ GsPluginClass *plugin_class = GS_PLUGIN_CLASS (klass); ++ ++ object_class->dispose = gs_plugin_dnf5_dispose; ++ object_class->finalize = gs_plugin_dnf5_finalize; ++ ++ plugin_class->setup_async = gs_plugin_dnf5_setup_async; ++ plugin_class->setup_finish = gs_plugin_dnf5_setup_finish; ++ plugin_class->shutdown_async = gs_plugin_dnf5_shutdown_async; ++ plugin_class->shutdown_finish = gs_plugin_dnf5_shutdown_finish; ++ plugin_class->list_apps_async = gs_plugin_dnf5_list_apps_async; ++ plugin_class->list_apps_finish = gs_plugin_dnf5_list_apps_finish; ++ plugin_class->refine_async = gs_plugin_dnf5_refine_async; ++ plugin_class->refine_finish = gs_plugin_dnf5_refine_finish; ++ plugin_class->refresh_metadata_async = gs_plugin_dnf5_refresh_metadata_async; ++ plugin_class->refresh_metadata_finish = gs_plugin_dnf5_refresh_metadata_finish; ++ plugin_class->update_apps_async = gs_plugin_dnf5_update_apps_async; ++ plugin_class->update_apps_finish = gs_plugin_dnf5_update_apps_finish; ++ plugin_class->enable_repository_async = gs_plugin_dnf5_enable_repository_async; ++ plugin_class->enable_repository_finish = gs_plugin_dnf5_enable_repository_finish; ++ plugin_class->disable_repository_async = gs_plugin_dnf5_disable_repository_async; ++ plugin_class->disable_repository_finish = gs_plugin_dnf5_disable_repository_finish; ++ plugin_class->install_apps_async = gs_plugin_dnf5_install_apps_async; ++ plugin_class->install_apps_finish = gs_plugin_dnf5_install_apps_finish; ++ plugin_class->uninstall_apps_async = gs_plugin_dnf5_uninstall_apps_async; ++ plugin_class->uninstall_apps_finish = gs_plugin_dnf5_uninstall_apps_finish; ++ plugin_class->launch_async = gs_plugin_dnf5_launch_async; ++ plugin_class->launch_finish = gs_plugin_dnf5_launch_finish; ++ plugin_class->file_to_app_async = gs_plugin_dnf5_file_to_app_async; ++ plugin_class->file_to_app_finish = gs_plugin_dnf5_file_to_app_finish; ++ plugin_class->download_upgrade_async = gs_plugin_dnf5_download_upgrade_async; ++ plugin_class->download_upgrade_finish = gs_plugin_dnf5_download_upgrade_finish; ++ plugin_class->trigger_upgrade_async = gs_plugin_dnf5_trigger_upgrade_async; ++ plugin_class->trigger_upgrade_finish = gs_plugin_dnf5_trigger_upgrade_finish; ++} ++ ++static void ++gs_plugin_dnf5_init (GsPluginDnf5 *self) ++{ ++ GsPlugin *plugin = GS_PLUGIN (self); ++ ++ g_mutex_init (&self->session_data.mutex); ++ g_cond_init (&self->session_data.cond); ++ g_mutex_init (&self->dependency_sizes_data.mutex); ++ ++ /* getting app properties from appstream is quicker */ ++ gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_RUN_AFTER, "appstream"); ++ ++ /* like appstream, we need the icon plugin to load cached icons into pixbufs */ ++ gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_RUN_BEFORE, "icons"); ++ ++ /* prioritize over packagekit */ ++ gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_CONFLICTS, "packagekit"); ++ ++ /* set name of MetaInfo file */ ++ gs_plugin_set_appstream_id (plugin, "org.gnome.Software.Plugin.Dnf5"); ++} ++ ++GType ++gs_plugin_query_type (void) ++{ ++ return GS_TYPE_PLUGIN_DNF5; ++} +diff --git a/plugins/dnf5/gs-plugin-dnf5.h b/plugins/dnf5/gs-plugin-dnf5.h +new file mode 100644 +index 000000000..319d5843c +--- /dev/null ++++ b/plugins/dnf5/gs-plugin-dnf5.h +@@ -0,0 +1,20 @@ ++/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- ++ * vi:set noexpandtab tabstop=8 shiftwidth=8: ++ * ++ * Copyright (C) 2024 Red Hat ++ * ++ * SPDX-License-Identifier: GPL-2.0+ ++ */ ++ ++#pragma once ++ ++#include ++#include ++ ++G_BEGIN_DECLS ++ ++#define GS_TYPE_PLUGIN_DNF5 (gs_plugin_dnf5_get_type ()) ++ ++G_DECLARE_FINAL_TYPE (GsPluginDnf5, gs_plugin_dnf5, GS, PLUGIN_DNF5, GsPlugin) ++ ++G_END_DECLS +diff --git a/plugins/dnf5/meson.build b/plugins/dnf5/meson.build +new file mode 100644 +index 000000000..6059a9da1 +--- /dev/null ++++ b/plugins/dnf5/meson.build +@@ -0,0 +1,39 @@ ++cargs = ['-DG_LOG_DOMAIN="GsDnf5"'] ++ ++dnf5_generated = gnome.gdbus_codegen( ++ 'gs-dnf5-generated', ++ sources: [ 'org.rpm.dnf.v0.Advisory.xml', ++ 'org.rpm.dnf.v0.Base.xml', ++ 'org.rpm.dnf.v0.Goal.xml', ++ 'org.rpm.dnf.v0.Offline.xml', ++ 'org.rpm.dnf.v0.rpm.Repo.xml', ++ 'org.rpm.dnf.v0.rpm.Rpm.xml', ++ 'org.rpm.dnf.v0.SessionManager.xml' ++ ], ++ interface_prefix : 'org.rpm.dnf.v0', ++ namespace : 'GsDnf5' ++) ++ ++dnf5_generated += gnome.gdbus_codegen( ++ 'gs-dnf5-rpm-generated', ++ sources: [ 'org.rpm.Transaction.xml' ], ++ interface_prefix : 'org.rpm', ++ namespace : 'GsDnf5Rpm' ++) ++ ++shared_module( ++ 'gs_plugin_dnf5', ++ dnf5_generated, ++ sources : [ ++ 'gs-dnf5-progress-helper.c', ++ 'gs-plugin-dnf5.c' ++ ], ++ include_directories : [ ++ include_directories('../..'), ++ include_directories('../../lib'), ++ ], ++ install : true, ++ install_dir: plugin_dir, ++ c_args : cargs, ++ dependencies : [ plugin_libs ], ++) +diff --git a/plugins/dnf5/org.rpm.Transaction.xml b/plugins/dnf5/org.rpm.Transaction.xml +new file mode 100644 +index 000000000..7d0cbab48 +--- /dev/null ++++ b/plugins/dnf5/org.rpm.Transaction.xml +@@ -0,0 +1,26 @@ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ +diff --git a/plugins/dnf5/org.rpm.dnf.v0.Advisory.xml b/plugins/dnf5/org.rpm.dnf.v0.Advisory.xml +new file mode 100644 +index 000000000..6aecee9fa +--- /dev/null ++++ b/plugins/dnf5/org.rpm.dnf.v0.Advisory.xml +@@ -0,0 +1,74 @@ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ +diff --git a/plugins/dnf5/org.rpm.dnf.v0.Base.xml b/plugins/dnf5/org.rpm.dnf.v0.Base.xml +new file mode 100644 +index 000000000..dfdc1745a +--- /dev/null ++++ b/plugins/dnf5/org.rpm.dnf.v0.Base.xml +@@ -0,0 +1,153 @@ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ +diff --git a/plugins/dnf5/org.rpm.dnf.v0.Goal.xml b/plugins/dnf5/org.rpm.dnf.v0.Goal.xml +new file mode 100644 +index 000000000..f1ba08953 +--- /dev/null ++++ b/plugins/dnf5/org.rpm.dnf.v0.Goal.xml +@@ -0,0 +1,118 @@ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ +diff --git a/plugins/dnf5/org.rpm.dnf.v0.Offline.xml b/plugins/dnf5/org.rpm.dnf.v0.Offline.xml +new file mode 100644 +index 000000000..083b5b17c +--- /dev/null ++++ b/plugins/dnf5/org.rpm.dnf.v0.Offline.xml +@@ -0,0 +1,82 @@ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ +diff --git a/plugins/dnf5/org.rpm.dnf.v0.SessionManager.xml b/plugins/dnf5/org.rpm.dnf.v0.SessionManager.xml +new file mode 100644 +index 000000000..a0facd692 +--- /dev/null ++++ b/plugins/dnf5/org.rpm.dnf.v0.SessionManager.xml +@@ -0,0 +1,69 @@ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ +diff --git a/plugins/dnf5/org.rpm.dnf.v0.rpm.Repo.xml b/plugins/dnf5/org.rpm.dnf.v0.rpm.Repo.xml +new file mode 100644 +index 000000000..13c4cf1f8 +--- /dev/null ++++ b/plugins/dnf5/org.rpm.dnf.v0.rpm.Repo.xml +@@ -0,0 +1,85 @@ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ +diff --git a/plugins/dnf5/org.rpm.dnf.v0.rpm.Rpm.xml b/plugins/dnf5/org.rpm.dnf.v0.rpm.Rpm.xml +new file mode 100644 +index 000000000..5df68cd91 +--- /dev/null ++++ b/plugins/dnf5/org.rpm.dnf.v0.rpm.Rpm.xml +@@ -0,0 +1,468 @@ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ +diff --git a/plugins/meson.build b/plugins/meson.build +index a108e47e5..a131a5cd3 100644 +--- a/plugins/meson.build ++++ b/plugins/meson.build +@@ -16,6 +16,9 @@ subdir('fedora-pkgdb-collections') + if get_option('dkms') + subdir('dkms') + endif ++if get_option('dnf5') ++ subdir('dnf5') ++endif + if get_option('eos_updater') + subdir('eos-updater') + endif +diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +index 669bd7fdb..d6ae9a268 100644 +--- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c ++++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +@@ -160,6 +160,7 @@ gs_plugin_rpm_ostree_init (GsPluginRpmOstree *self) + * more sense to use a custom plugin instead of using PackageKit. + */ + gs_plugin_add_rule (GS_PLUGIN (self), GS_PLUGIN_RULE_CONFLICTS, "packagekit"); ++ gs_plugin_add_rule (GS_PLUGIN (self), GS_PLUGIN_RULE_CONFLICTS, "dnf5"); + + /* need pkgname */ + gs_plugin_add_rule (GS_PLUGIN (self), GS_PLUGIN_RULE_RUN_AFTER, "appstream"); +diff --git a/po/POTFILES.in b/po/POTFILES.in +index 71aa486e2..d3e909dee 100644 +--- a/po/POTFILES.in ++++ b/po/POTFILES.in +@@ -112,6 +112,7 @@ lib/gs-utils.c + src/org.gnome.Software.desktop.in + plugins/dkms/gs-plugin-dkms.c + plugins/core/gs-plugin-generic-updates.c ++plugins/dnf5/gs-plugin-dnf5.c + plugins/eos-updater/gs-plugin-eos-updater.c + plugins/epiphany/gs-plugin-epiphany.c + plugins/epiphany/org.gnome.Software.Plugin.Epiphany.metainfo.xml.in diff --git a/gnome-software.spec b/gnome-software.spec index 763ed62..0e01617 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -17,6 +17,9 @@ # Disable DKMS/akmods support for RHEL builds %bcond dkms %[!0%{?rhel}] +%bcond packagekit 0 +%bcond dnf5 1 + # this is not a library version %define gs_plugin_version 22 @@ -26,13 +29,15 @@ Name: gnome-software Version: 48.1 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://apps.gnome.org/Software Source0: https://download.gnome.org/sources/gnome-software/48/%{name}-%{tarball_version}.tar.xz +Patch: 0001-dnf5-plugin.patch + # ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 %if 0%{?fedora} || 0%{?rhel} >= 10 @@ -65,7 +70,9 @@ BuildRequires: pkgconfig(libsoup-3.0) BuildRequires: pkgconfig(malcontent-0) %endif BuildRequires: pkgconfig(ostree-1) +%if %{with packagekit} BuildRequires: pkgconfig(packagekit-glib2) >= %{packagekit_version} +%endif BuildRequires: pkgconfig(polkit-gobject-1) BuildRequires: pkgconfig(rpm) %if %{with rpmostree} @@ -79,6 +86,11 @@ Requires: appstream%{?_isa} >= %{appstream_version} %if %{with webapps} Requires: epiphany-runtime%{?_isa} %endif +%if %{with dnf5} +Requires: dnf5daemon-server%{?_isa} +Requires: libdnf5-plugin-appstream%{?_isa} +Requires: rpm-plugin-dbus-announce%{?_isa} +%endif Requires: flatpak%{?_isa} >= %{flatpak_version} Requires: flatpak-libs%{?_isa} >= %{flatpak_version} Requires: fwupd%{?_isa} >= %{fwupd_version} @@ -97,7 +109,9 @@ Requires: libadwaita >= %{libadwaita_version} Requires: librsvg2%{?_isa} Requires: libxmlb%{?_isa} >= %{libxmlb_version} +%if %{with packagekit} Recommends: PackageKit%{?_isa} >= %{packagekit_version} +%endif Recommends: %{name}-fedora-langpacks Obsoletes: gnome-software-snap < 3.33.1 @@ -149,8 +163,17 @@ This package includes the rpm-ostree backend. -Dmalcontent=false \ %endif -Dgudev=true \ +%if %{with packagekit} -Dpackagekit=true \ -Dpackagekit_autoremove=true \ +%else + -Dpackagekit=false \ +%endif +%if %{with dnf5} + -Ddnf5=true \ +%else + -Ddnf5=false \ +%endif -Dexternal_appstream=false \ %if %{with rpmostree} -Drpm_ostree=true \ @@ -232,6 +255,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %dir %{_libdir}/gnome-software/plugins-%{gs_plugin_version} %{_libdir}/gnome-software/libgnomesoftware.so.%{gs_plugin_version} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_appstream.so +%if %{with dnf5} +%{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_dnf5.so +%endif %if %{with webapps} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_epiphany.so %endif @@ -246,7 +272,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %endif %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_modalias.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_os-release.so +%if %{with packagekit} %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_packagekit.so +%endif %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance-license.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_repos.so @@ -256,7 +284,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %dir %{_datadir}/swcatalog/xml %{_datadir}/swcatalog/xml/gnome-pwa-list-foss.xml %endif +%if %{with packagekit} %{_datadir}/dbus-1/services/org.freedesktop.PackageKit.service +%endif %{_datadir}/dbus-1/services/org.gnome.Software.service %{_datadir}/gnome-shell/search-providers/org.gnome.Software-search-provider.ini %{_datadir}/glib-2.0/schemas/org.gnome.software.gschema.xml @@ -288,6 +318,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Tue Apr 29 2025 Milan Crha - 48.1-2 +- Switch from PackageKit to DNF5 plugin + * Fri Apr 11 2025 Milan Crha - 48.1-1 - Update to 48.1 From b57929aa0d37a6d3bd613fb4091556644195ad58 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 2 Jun 2025 13:51:22 +0200 Subject: [PATCH 137/163] Require dnf5daemon-server-polkit for the dnf5 plugin It will be in pair with PackageKit, where the wheel users can install packages without being asked for the credentials. --- gnome-software.spec | 1 + 1 file changed, 1 insertion(+) diff --git a/gnome-software.spec b/gnome-software.spec index 0e01617..e840e8d 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -88,6 +88,7 @@ Requires: epiphany-runtime%{?_isa} %endif %if %{with dnf5} Requires: dnf5daemon-server%{?_isa} +Requires: dnf5daemon-server-polkit Requires: libdnf5-plugin-appstream%{?_isa} Requires: rpm-plugin-dbus-announce%{?_isa} %endif From 315c97814f1b4f0a3bd5e5f1e66709f956ba1b5a Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 2 Jun 2025 13:53:45 +0200 Subject: [PATCH 138/163] Update to 48.2 --- gnome-software.spec | 7 +++++-- sources | 2 +- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index e840e8d..f36f610 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -28,8 +28,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 48.1 -Release: 2%{?dist} +Version: 48.2 +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -319,6 +319,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Mon Jun 02 2025 Milan Crha - 48.2-1 +- Update to 48.2 + * Tue Apr 29 2025 Milan Crha - 48.1-2 - Switch from PackageKit to DNF5 plugin diff --git a/sources b/sources index 31b7ac3..da03639 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-48.1.tar.xz) = 7cb1e7a7527e65e6283916cecee55fa4e65d71e538ced65af488d28e94801755d2ab961d2f4603cec0f781893e298fee109df4a839ee99fc3de2cefb82f25a97 +SHA512 (gnome-software-48.2.tar.xz) = 3a03f475de56cb2ba534a0a7eaaaeb21677cf27a54db03bb84e3953dce796bfc437daf59b41155884260006c18562c50d7e01056aeb190a18449cbcbf2f5120c From bd322e2006e57dca80cc555b5d4acd85e3f0d4d7 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 23 Jun 2025 13:49:59 +0200 Subject: [PATCH 139/163] Switch %autosetup from gendiff to git backups It's easier to build patches on top of the current code when multiple files are involved. --- gnome-software.spec | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index f36f610..1c0a1a1 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -48,6 +48,7 @@ BuildRequires: docbook-style-xsl BuildRequires: desktop-file-utils BuildRequires: gcc BuildRequires: gettext +BuildRequires: git-core BuildRequires: gtk-doc BuildRequires: itstool BuildRequires: libxslt @@ -153,7 +154,7 @@ This package includes the rpm-ostree backend. %endif %prep -%autosetup -p1 -S gendiff -n %{name}-%{tarball_version} +%autosetup -p1 -S git -n %{name}-%{tarball_version} %build %meson \ From 9d8fd61e9a565b9e23073f1e7a0bc79d4c15de35 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 27 Jun 2025 09:10:50 +0200 Subject: [PATCH 140/163] Update to 49.alpha --- 0001-dnf5-plugin.patch | 112 +++-- gnome-software.spec | 1021 +--------------------------------------- sources | 2 +- 3 files changed, 76 insertions(+), 1059 deletions(-) diff --git a/0001-dnf5-plugin.patch b/0001-dnf5-plugin.patch index f7b5b67..b2e8117 100644 --- a/0001-dnf5-plugin.patch +++ b/0001-dnf5-plugin.patch @@ -1,11 +1,11 @@ -at commit 31a1ad73cc4fa28b0d352a7ac392bec76e9c10a4 -Date: Wed Apr 2 14:21:03 2025 +0200 +at commit f3042a5f73fc6b04e26ceca5a1a469879af30fd3 +Date: Fri Jun 20 11:20:33 2025 +0200 diff --git a/meson_options.txt b/meson_options.txt -index bc32ba561..523f572cd 100644 +index cd49cf529..27fa15e8b 100644 --- a/meson_options.txt +++ b/meson_options.txt -@@ -2,6 +2,7 @@ option('tests', type : 'boolean', value : true, description : 'enable tests') +@@ -3,6 +3,7 @@ option('installed_tests', type : 'boolean', value : false, description : 'enable option('man', type : 'boolean', value : true, description : 'enable man pages') option('packagekit', type : 'boolean', value : true, description : 'enable PackageKit support') option('packagekit_autoremove', type : 'boolean', value : false, description : 'autoremove packages in PackageKit') @@ -589,10 +589,10 @@ index 000000000..73d528d54 +G_END_DECLS diff --git a/plugins/dnf5/gs-plugin-dnf5.c b/plugins/dnf5/gs-plugin-dnf5.c new file mode 100644 -index 000000000..93f22dc4f +index 000000000..bae3bde28 --- /dev/null +++ b/plugins/dnf5/gs-plugin-dnf5.c -@@ -0,0 +1,3738 @@ +@@ -0,0 +1,3770 @@ +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- + * vi:set noexpandtab tabstop=8 shiftwidth=8: + * @@ -691,17 +691,22 @@ index 000000000..93f22dc4f + +static void +gs_dnf5_report_error (GsPluginDnf5 *self, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + const GError *error, + gboolean interactive) +{ + g_autoptr(GsPluginEvent) event = NULL; + ++ if (!event_callback) ++ return; ++ + event = gs_plugin_event_new ("error", error, + NULL); + if (interactive) + gs_plugin_event_add_flag (event, GS_PLUGIN_EVENT_FLAG_INTERACTIVE); + gs_plugin_event_add_flag (event, GS_PLUGIN_EVENT_FLAG_WARNING); -+ gs_plugin_report_event (GS_PLUGIN (self), event); ++ event_callback (GS_PLUGIN (self), event, event_user_data); +} + +/* The session reset is used to refresh information about the packages, @@ -2186,7 +2191,7 @@ index 000000000..93f22dc4f +{ + GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); + GsAppQueryTristate is_for_update = GS_APP_QUERY_TRISTATE_UNSET; -+ GsAppQueryTristate is_source = GS_APP_QUERY_TRISTATE_UNSET; ++ const AsComponentKind *component_kinds = NULL; + GsPluginListAppsData *data = task_data; + const gchar * const *provides_files = NULL; + const gchar *provides_tag = NULL; @@ -2202,17 +2207,17 @@ index 000000000..93f22dc4f + + if (data->query != NULL) { + is_for_update = gs_app_query_get_is_for_update (data->query); -+ is_source = gs_app_query_get_is_source (data->query); ++ component_kinds = gs_app_query_get_component_kinds (data->query); + provides_files = gs_app_query_get_provides_files (data->query); + provides_type = gs_app_query_get_provides (data->query, &provides_tag); + } + + if ((is_for_update == GS_APP_QUERY_TRISTATE_UNSET && -+ is_source == GS_APP_QUERY_TRISTATE_UNSET && ++ component_kinds == NULL && + provides_tag == NULL && + provides_files == NULL) || + is_for_update == GS_APP_QUERY_TRISTATE_FALSE || -+ is_source == GS_APP_QUERY_TRISTATE_FALSE || ++ (component_kinds != NULL && !gs_component_kind_array_contains (component_kinds, AS_COMPONENT_KIND_REPOSITORY)) || + gs_app_query_get_n_properties_set (data->query) != 1) { + g_task_return_new_error (task, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, + "Unsupported query"); @@ -2359,7 +2364,7 @@ index 000000000..93f22dc4f + gs_dnf5_convert_error (&local_error); + g_prefix_error_literal (&local_error, "Failed to call Rpm::list: "); + } -+ } else if (is_source == GS_APP_QUERY_TRISTATE_TRUE) { ++ } else if (gs_component_kind_array_contains (component_kinds, AS_COMPONENT_KIND_REPOSITORY)) { + g_autoptr(GsDnf5RpmRepo) repo_proxy = NULL; + + repo_proxy = gs_dnf5_rpm_repo_proxy_new_sync (self->connection, @@ -2534,6 +2539,8 @@ index 000000000..93f22dc4f +gs_plugin_dnf5_list_apps_async (GsPlugin *plugin, + GsAppQuery *query, + GsPluginListAppsFlags flags, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + GCancellable *cancellable, + GAsyncReadyCallback callback, + gpointer user_data) @@ -2542,7 +2549,7 @@ index 000000000..93f22dc4f + gboolean interactive = (flags & GS_PLUGIN_LIST_APPS_FLAGS_INTERACTIVE) != 0; + g_autoptr(GTask) task = NULL; + -+ task = gs_plugin_list_apps_data_new_task (plugin, query, flags, ++ task = gs_plugin_list_apps_data_new_task (plugin, query, flags, event_callback, event_user_data, + cancellable, callback, user_data); + g_task_set_source_tag (task, gs_plugin_dnf5_list_apps_async); + @@ -2590,7 +2597,7 @@ index 000000000..93f22dc4f + if (str == NULL) + return TRUE; + /* the app itself is in the list too */ -+ if (g_strcmp0 (gs_app_get_source_default (main_app), str) == 0) ++ if (g_strcmp0 (gs_app_get_default_source (main_app), str) == 0) + return TRUE; + + /* always create a new app, no cached can be used here */ @@ -2676,7 +2683,7 @@ index 000000000..93f22dc4f + if (success) { + g_autoptr(GVariantBuilder) options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); + g_autoptr(GVariant) transaction = NULL; -+ const gchar *package_name = gs_app_get_source_default (app); ++ const gchar *package_name = gs_app_get_default_source (app); + const gchar *packages[2] = { NULL, NULL }; + + packages[0] = package_name; @@ -2827,14 +2834,14 @@ index 000000000..93f22dc4f + GsApp *app = gs_app_list_index (data->list, i); + if (!gs_app_has_quirk (app, GS_APP_QUIRK_IS_WILDCARD) && ( + gs_app_get_state (app) == GS_APP_STATE_UNKNOWN || -+ ((data->flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_SIZE_DATA) != 0 && ++ ((data->require_flags & GS_PLUGIN_REFINE_REQUIRE_FLAGS_SIZE_DATA) != 0 && + gs_app_list_length (gs_app_get_related (app)) == 0))) { -+ if (gs_app_get_source_default (app) != NULL && ++ if (gs_app_get_default_source (app) != NULL && + ((gs_app_has_management_plugin (app, NULL) && + gs_app_get_bundle_kind (app) == AS_BUNDLE_KIND_PACKAGE && + gs_app_get_scope (app) == AS_COMPONENT_SCOPE_SYSTEM) || + gs_app_has_management_plugin (app, plugin))) -+ g_hash_table_insert (apps, g_strdup (gs_app_get_source_default (app)), g_object_ref (app)); ++ g_hash_table_insert (apps, g_strdup (gs_app_get_default_source (app)), g_object_ref (app)); + } + } + @@ -2914,7 +2921,7 @@ index 000000000..93f22dc4f + success = gs_dnf5_foreach_item (self, result, gs_dnf5_refine_cb, apps, cancellable, &local_error); + + if (success && -+ (data->flags & GS_PLUGIN_REFINE_FLAGS_REQUIRE_SIZE_DATA) != 0) { ++ (data->require_flags & GS_PLUGIN_REFINE_REQUIRE_FLAGS_SIZE_DATA) != 0) { + /* do not panic when cannot get dependency sizes for the apps */ + if (!gs_dnf5_get_dependency_sizes_sync (self, apps, cancellable, &local_error)) { + g_debug ("Failed to get dependency sizes: %s", local_error->message); @@ -2940,16 +2947,20 @@ index 000000000..93f22dc4f +static void +gs_plugin_dnf5_refine_async (GsPlugin *plugin, + GsAppList *list, -+ GsPluginRefineFlags flags, ++ GsPluginRefineFlags job_flags, ++ GsPluginRefineRequireFlags require_flags, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + GCancellable *cancellable, + GAsyncReadyCallback callback, + gpointer user_data) +{ + GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); -+ gboolean interactive = gs_plugin_has_flags (plugin, GS_PLUGIN_FLAGS_INTERACTIVE); ++ gboolean interactive = (job_flags & GS_PLUGIN_REFINE_FLAGS_INTERACTIVE) != 0; + g_autoptr(GTask) task = NULL; + -+ task = gs_plugin_refine_data_new_task (plugin, list, flags, ++ task = gs_plugin_refine_data_new_task (plugin, list, job_flags, require_flags, ++ event_callback, event_user_data, + cancellable, callback, user_data); + g_task_set_source_tag (task, gs_plugin_dnf5_refine_async); + @@ -3050,6 +3061,8 @@ index 000000000..93f22dc4f +gs_plugin_dnf5_refresh_metadata_async (GsPlugin *plugin, + guint64 cache_age_secs, + GsPluginRefreshMetadataFlags flags, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + GCancellable *cancellable, + GAsyncReadyCallback callback, + gpointer user_data) @@ -3095,6 +3108,8 @@ index 000000000..93f22dc4f + GsAppList *list, + gboolean is_install, + gboolean interactive, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + GCancellable *cancellable, + GError **error) +{ @@ -3131,7 +3146,7 @@ index 000000000..93f22dc4f + for (guint i = 0; i < gs_app_list_length (list); i++) { + GsApp *app = gs_app_list_index (list, i); + if (gs_app_has_management_plugin (app, plugin)) { -+ const gchar *source = gs_app_get_source_default (app); ++ const gchar *source = gs_app_get_default_source (app); + if (source != NULL) { + GFile *local_file = gs_app_get_local_file (app); + if (local_file != NULL) @@ -3147,7 +3162,7 @@ index 000000000..93f22dc4f + for (guint j = 0; j < gs_app_list_length (related); j++) { + GsApp *rel_app = gs_app_list_index (related, j); + if (gs_app_has_management_plugin (rel_app, plugin)) { -+ const gchar *source = gs_app_get_source_default (rel_app); ++ const gchar *source = gs_app_get_default_source (rel_app); + if (source != NULL) { + GFile *local_file = gs_app_get_local_file (rel_app); + if (local_file != NULL) @@ -3193,7 +3208,7 @@ index 000000000..93f22dc4f + for (guint j = 0; addons != NULL && j < gs_app_list_length (addons); j++) { + GsApp *addon = gs_app_list_index (addons, j); + if (gs_app_get_to_be_installed (addon)) { -+ const gchar *addon_source = gs_app_get_source_default (app); ++ const gchar *addon_source = gs_app_get_default_source (app); + if (addon_source != NULL) { + g_ptr_array_add (packages, g_strdup (addon_source)); + if (is_install) @@ -3282,7 +3297,7 @@ index 000000000..93f22dc4f + gs_dnf5_convert_error (error); + + if (error != NULL && *error != NULL) -+ gs_dnf5_report_error (self, *error, interactive); ++ gs_dnf5_report_error (self, event_callback, event_user_data, *error, interactive); + } + + for (guint i = 0; i < gs_app_list_length (used_apps); i++) { @@ -3341,6 +3356,7 @@ index 000000000..93f22dc4f + + success = gs_dnf5_install_update (plugin, data->apps, TRUE, + (data->flags & GS_PLUGIN_INSTALL_APPS_FLAGS_INTERACTIVE) != 0, ++ data->event_callback, data->event_user_data, + cancellable, &local_error); + + g_atomic_int_dec_and_test (&self->calling_rpm); @@ -3357,6 +3373,8 @@ index 000000000..93f22dc4f + GsPluginInstallAppsFlags flags, + GsPluginProgressCallback progress_callback, + gpointer progress_user_data, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + GsPluginAppNeedsUserActionCallback app_needs_user_action_callback, + gpointer app_needs_user_action_data, + GCancellable *cancellable, @@ -3368,6 +3386,7 @@ index 000000000..93f22dc4f + g_autoptr(GTask) task = NULL; + + task = gs_plugin_install_apps_data_new_task (plugin, apps, flags, progress_callback, progress_user_data, ++ event_callback, event_user_data, + app_needs_user_action_callback, app_needs_user_action_data, + cancellable, callback, user_data); + g_task_set_source_tag (task, gs_plugin_dnf5_install_apps_async); @@ -3418,7 +3437,7 @@ index 000000000..93f22dc4f + g_warn_if_reached (); + continue; + } -+ source = gs_app_get_source_default (app); ++ source = gs_app_get_default_source (app); + if (source == NULL) { + g_task_return_new_error (task, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_NOT_SUPPORTED, + "remove not available"); @@ -3435,7 +3454,7 @@ index 000000000..93f22dc4f + for (guint j = 0; addons != NULL && j < gs_app_list_length (addons); j++) { + GsApp *addon = gs_app_list_index (addons, j); + if (gs_app_get_state (addon) == GS_APP_STATE_INSTALLED) { -+ const gchar *addon_source = gs_app_get_source_default (addon); ++ const gchar *addon_source = gs_app_get_default_source (addon); + if (addon_source != NULL) { + g_ptr_array_add (packages, g_strdup (addon_source)); + g_ptr_array_add (touched_apps, g_object_ref (addon)); @@ -3499,7 +3518,8 @@ index 000000000..93f22dc4f + gs_dnf5_mark_session_needs_reset (self); + } else { + gs_dnf5_convert_error (&local_error); -+ gs_dnf5_report_error (self, local_error, (data->flags & GS_PLUGIN_UNINSTALL_APPS_FLAGS_INTERACTIVE) != 0); ++ gs_dnf5_report_error (self, data->event_callback, data->event_user_data, ++ local_error, (data->flags & GS_PLUGIN_UNINSTALL_APPS_FLAGS_INTERACTIVE) != 0); + } + + for (guint i = 0; i < touched_apps->len; i++) { @@ -3524,6 +3544,8 @@ index 000000000..93f22dc4f + GsPluginUninstallAppsFlags flags, + GsPluginProgressCallback progress_callback, + gpointer progress_user_data, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + GsPluginAppNeedsUserActionCallback app_needs_user_action_callback, + gpointer app_needs_user_action_data, + GCancellable *cancellable, @@ -3535,6 +3557,7 @@ index 000000000..93f22dc4f + g_autoptr(GTask) task = NULL; + + task = gs_plugin_uninstall_apps_data_new_task (plugin, apps, flags, progress_callback, progress_user_data, ++ event_callback, event_user_data, + app_needs_user_action_callback, app_needs_user_action_data, + cancellable, callback, user_data); + g_task_set_source_tag (task, gs_plugin_dnf5_uninstall_apps_async); @@ -3570,6 +3593,7 @@ index 000000000..93f22dc4f + + success = gs_dnf5_install_update (plugin, data->apps, FALSE, + (data->flags & GS_PLUGIN_UPDATE_APPS_FLAGS_INTERACTIVE) != 0, ++ data->event_callback, data->event_user_data, + cancellable, &local_error); + + g_atomic_int_dec_and_test (&self->calling_rpm); @@ -3586,6 +3610,8 @@ index 000000000..93f22dc4f + GsPluginUpdateAppsFlags flags, + GsPluginProgressCallback progress_callback, + gpointer progress_user_data, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + GsPluginAppNeedsUserActionCallback app_needs_user_action_callback, + gpointer app_needs_user_action_data, + GCancellable *cancellable, @@ -3597,6 +3623,7 @@ index 000000000..93f22dc4f + g_autoptr(GTask) task = NULL; + + task = gs_plugin_update_apps_data_new_task (plugin, apps, flags, progress_callback, progress_user_data, ++ event_callback, event_user_data, + app_needs_user_action_callback, app_needs_user_action_data, + cancellable, callback, user_data); + g_task_set_source_tag (task, gs_plugin_dnf5_update_apps_async); @@ -3708,6 +3735,8 @@ index 000000000..93f22dc4f +gs_plugin_dnf5_enable_repository_async (GsPlugin *plugin, + GsApp *repository, + GsPluginManageRepositoryFlags flags, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + GCancellable *cancellable, + GAsyncReadyCallback callback, + gpointer user_data) @@ -3716,7 +3745,7 @@ index 000000000..93f22dc4f + gboolean interactive = (flags & GS_PLUGIN_MANAGE_REPOSITORY_FLAGS_INTERACTIVE) != 0; + g_autoptr(GTask) task = NULL; + -+ task = gs_plugin_manage_repository_data_new_task (plugin, repository, flags, ++ task = gs_plugin_manage_repository_data_new_task (plugin, repository, flags, event_callback, event_user_data, + cancellable, callback, user_data); + g_task_set_source_tag (task, gs_plugin_dnf5_enable_repository_async); + @@ -3757,6 +3786,8 @@ index 000000000..93f22dc4f +gs_plugin_dnf5_disable_repository_async (GsPlugin *plugin, + GsApp *repository, + GsPluginManageRepositoryFlags flags, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + GCancellable *cancellable, + GAsyncReadyCallback callback, + gpointer user_data) @@ -3765,7 +3796,7 @@ index 000000000..93f22dc4f + gboolean interactive = (flags & GS_PLUGIN_MANAGE_REPOSITORY_FLAGS_INTERACTIVE) != 0; + g_autoptr(GTask) task = NULL; + -+ task = gs_plugin_manage_repository_data_new_task (plugin, repository, flags, ++ task = gs_plugin_manage_repository_data_new_task (plugin, repository, flags, event_callback, event_user_data, + cancellable, callback, user_data); + g_task_set_source_tag (task, gs_plugin_dnf5_disable_repository_async); + @@ -3949,6 +3980,8 @@ index 000000000..93f22dc4f +gs_plugin_dnf5_file_to_app_async (GsPlugin *plugin, + GFile *file, + GsPluginFileToAppFlags flags, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + GCancellable *cancellable, + GAsyncReadyCallback callback, + gpointer user_data) @@ -3957,7 +3990,7 @@ index 000000000..93f22dc4f + GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); + gboolean interactive = (flags & GS_PLUGIN_FILE_TO_APP_FLAGS_INTERACTIVE) != 0; + -+ task = gs_plugin_file_to_app_data_new_task (plugin, file, flags, cancellable, callback, user_data); ++ task = gs_plugin_file_to_app_data_new_task (plugin, file, flags, event_callback, event_user_data, cancellable, callback, user_data); + g_task_set_source_tag (task, gs_plugin_dnf5_file_to_app_async); + + /* Queue a job to get the apps. */ @@ -4106,7 +4139,8 @@ index 000000000..93f22dc4f + } else { + gs_app_set_state (data->app, GS_APP_STATE_AVAILABLE); + gs_dnf5_convert_error (&local_error); -+ gs_dnf5_report_error (self, local_error, (data->flags & GS_PLUGIN_DOWNLOAD_UPGRADE_FLAGS_INTERACTIVE) != 0); ++ gs_dnf5_report_error (self, data->event_callback, data->event_user_data, ++ local_error, (data->flags & GS_PLUGIN_DOWNLOAD_UPGRADE_FLAGS_INTERACTIVE) != 0); + g_task_return_error (task, g_steal_pointer (&local_error)); + } +} @@ -4115,6 +4149,8 @@ index 000000000..93f22dc4f +gs_plugin_dnf5_download_upgrade_async (GsPlugin *plugin, + GsApp *app, + GsPluginDownloadUpgradeFlags flags, ++ GsPluginEventCallback event_callback, ++ void *event_user_data, + GCancellable *cancellable, + GAsyncReadyCallback callback, + gpointer user_data) @@ -4123,7 +4159,7 @@ index 000000000..93f22dc4f + g_autoptr(GTask) task = NULL; + gboolean interactive = (flags & GS_PLUGIN_DOWNLOAD_UPGRADE_FLAGS_INTERACTIVE) != 0; + -+ task = gs_plugin_download_upgrade_data_new_task (plugin, app, flags, cancellable, callback, user_data); ++ task = gs_plugin_download_upgrade_data_new_task (plugin, app, flags, event_callback, event_user_data, cancellable, callback, user_data); + g_task_set_source_tag (task, gs_plugin_dnf5_download_upgrade_async); + + /* only process this app if was created by this plugin */ @@ -4171,7 +4207,6 @@ index 000000000..93f22dc4f + } else { + gs_app_set_state (data->app, GS_APP_STATE_AVAILABLE); + gs_dnf5_convert_error (&local_error); -+ gs_dnf5_report_error (self, local_error, (data->flags & GS_PLUGIN_TRIGGER_UPGRADE_FLAGS_INTERACTIVE) != 0); + g_task_return_error (task, g_steal_pointer (&local_error)); + } +} @@ -4321,9 +4356,6 @@ index 000000000..93f22dc4f + + /* prioritize over packagekit */ + gs_plugin_add_rule (plugin, GS_PLUGIN_RULE_CONFLICTS, "packagekit"); -+ -+ /* set name of MetaInfo file */ -+ gs_plugin_set_appstream_id (plugin, "org.gnome.Software.Plugin.Dnf5"); +} + +GType @@ -5540,10 +5572,10 @@ index a108e47e5..a131a5cd3 100644 subdir('eos-updater') endif diff --git a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -index 669bd7fdb..d6ae9a268 100644 +index 627a5143e..64451bccc 100644 --- a/plugins/rpm-ostree/gs-plugin-rpm-ostree.c +++ b/plugins/rpm-ostree/gs-plugin-rpm-ostree.c -@@ -160,6 +160,7 @@ gs_plugin_rpm_ostree_init (GsPluginRpmOstree *self) +@@ -168,6 +168,7 @@ gs_plugin_rpm_ostree_init (GsPluginRpmOstree *self) * more sense to use a custom plugin instead of using PackageKit. */ gs_plugin_add_rule (GS_PLUGIN (self), GS_PLUGIN_RULE_CONFLICTS, "packagekit"); diff --git a/gnome-software.spec b/gnome-software.spec index 1c0a1a1..5f6b255 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -28,13 +28,13 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 48.2 +Version: 49~alpha Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://apps.gnome.org/Software -Source0: https://download.gnome.org/sources/gnome-software/48/%{name}-%{tarball_version}.tar.xz +Source0: https://download.gnome.org/sources/gnome-software/49/%{name}-%{tarball_version}.tar.xz Patch: 0001-dnf5-plugin.patch @@ -320,1019 +320,4 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog -* Mon Jun 02 2025 Milan Crha - 48.2-1 -- Update to 48.2 - -* Tue Apr 29 2025 Milan Crha - 48.1-2 -- Switch from PackageKit to DNF5 plugin - -* Fri Apr 11 2025 Milan Crha - 48.1-1 -- Update to 48.1 - -* Fri Mar 14 2025 Milan Crha - 48.0-1 -- Update to 48.0 - -* Mon Mar 03 2025 Milan Crha - 48~rc-1 -- Update to 48.rc - -* Mon Feb 03 2025 Milan Crha - 48~beta-1 -- Update to 48.beta - -* Thu Jan 16 2025 Fedora Release Engineering - 48~alpha3-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_42_Mass_Rebuild - -* Tue Jan 14 2025 Milan Crha - 48~alpha3-1 -- Update to 48.alpha3 - -* Tue Jan 07 2025 Milan Crha - 48~alpha2-1 -- Update to 48.alpha2 - -* Mon Dec 09 2024 Milan Crha - 47.2-3 -- Resolves: #2272232 (Crash under gs_appstream_gather_merge_data()) - -* Thu Dec 05 2024 Yaakov Selkowitz - 47.2-2 -- Rebuild for fwupd 2.0 - -* Mon Nov 25 2024 Milan Crha - 47.2-1 -- Update to 47.2 - -* Thu Oct 10 2024 Milan Crha - 47.1-1 -- Update to 47.1 - -* Fri Oct 04 2024 Richard Hughes - 47.0-3 -- Rebuild against fwupd 2.0.0 - -* Thu Sep 19 2024 Milan Crha - 47.0-2 -- Resolves: #2312882 (dkms: Fix callback user data in a reload() function) - -* Fri Sep 13 2024 Milan Crha - 47.0-1 -- Update to 47.0 - -* Fri Aug 30 2024 Milan Crha - 47~rc-1 -- Update to 47.rc - -* Fri Aug 02 2024 Milan Crha - 47~beta-1 -- Update to 47.beta -- Build with DKMS/akmods plugin in Fedora - -* Thu Jul 18 2024 Fedora Release Engineering - 47~alpha-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_41_Mass_Rebuild - -* Fri Jun 28 2024 Milan Crha - 47~alpha-1 -- Update to 47.alpha - -* Fri May 24 2024 Milan Crha - 46.2-1 -- Update to 46.2 - -* Thu Apr 25 2024 Milan Crha - 46.1-1 -- Update to 46.1 - -* Fri Apr 12 2024 Adam Williamson - 46.0-2 -- Backport MR #1949 to fix upgrading - -* Mon Mar 18 2024 Milan Crha - 46.0-1 -- Update to 46.0 - -* Fri Mar 01 2024 Milan Crha - 46~rc-1 -- Update to 46.rc - -* Fri Feb 09 2024 Milan Crha - 46~beta-1 -- Update to 46.beta - -* Fri Jan 26 2024 Milan Crha - 46~alpha-4 -- Resolves: #2260294 (Split fedora-langpacks plugin into a subpackage) - -* Wed Jan 24 2024 Fedora Release Engineering - 46~alpha-3 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_40_Mass_Rebuild - -* Fri Jan 19 2024 Fedora Release Engineering - 46~alpha-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_40_Mass_Rebuild - -* Fri Jan 05 2024 Milan Crha - 46~alpha-1 -- Update to 46.alpha - -* Fri Dec 01 2023 Milan Crha - 45.2-1 -- Update to 45.2 - -* Tue Nov 07 2023 Neal Gompa - 45.1-3 -- Fix appstream_version macro for prerelease appstream 1.0 package - -* Tue Nov 07 2023 Milan Crha - 45.1-2 -- Add patch to build with appstream 1.0 - -* Fri Oct 20 2023 Milan Crha - 45.1-1 -- Update to 45.1 - -* Fri Sep 15 2023 Milan Crha - 45.0-1 -- Update to 45.0 - -* Fri Sep 01 2023 Milan Crha - 45~rc-1 -- Update to 45.rc - -* Mon Jul 31 2023 Milan Crha - 45~beta-1 -- Update to 45.beta - -* Wed Jul 19 2023 Fedora Release Engineering - 45~alpha-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_39_Mass_Rebuild - -* Fri Jun 30 2023 Milan Crha - 45~alpha-1 -- Update to 45.alpha - -* Thu Jun 22 2023 Tomas Popela - 44.2-2 -- Disable parental control (through malcontent) and rpm-ostree support in RHEL - -* Fri May 26 2023 Milan Crha - 44.2-1 -- Update to 44.2 - -* Fri May 19 2023 Milan Crha - 44.1-2 -- Rebuild for RPM - -* Fri Apr 21 2023 Milan Crha - 44.1-1 -- Update to 44.1 - -* Sun Mar 26 2023 Yaakov Selkowitz - 44.0-3 -- Fix libsoup runtime dependency - -* Fri Mar 24 2023 Milan Crha - 44.0-2 -- Resolves: #2181367 (Prefer Fedora Flatpaks before RPM before other sources for apps) - -* Fri Mar 17 2023 Milan Crha - 44.0-1 -- Update to 44.0 - -* Fri Mar 03 2023 Milan Crha - 44~rc-1 -- Update to 44.rc - -* Thu Feb 23 2023 Adam Williamson - 44~beta-2 -- Backport MR #1635 to fix update notifications - -* Tue Feb 14 2023 Milan Crha - 44.beta-1 -- Update to 44.beta - -* Thu Feb 09 2023 Michael Catanzaro - 44~alpha-3 -- Switch to libsoup 3 - -* Thu Jan 19 2023 Fedora Release Engineering - 44~alpha-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_38_Mass_Rebuild - -* Mon Jan 09 2023 Milan Crha - 44.alpha-1 -- Update to 44.alpha - -* Fri Dec 02 2022 Milan Crha - 43.2-1 -- Update to 43.2 - -* Tue Nov 08 2022 Milan Crha - 43.1-3 -- Also skip gnome-pwa-list-foss.xml when building without WebApps - -* Tue Nov 08 2022 Milan Crha - 43.1-2 -- Disable WebApps for RHEL builds - -* Mon Oct 24 2022 Milan Crha - 43.1-1 -- Update to 43.1 - -* Wed Oct 05 2022 Milan Crha - 43.0-3 -- Resolves: #2132292 (rpm-ostree plugin refuses to update) - -* Tue Sep 27 2022 Kalev Lember - 43.0-2 -- Rebuild to fix sysprof-capture symbols leaking into libraries consuming it - -* Fri Sep 16 2022 Milan Crha - 43.0-1 -- Update to 43.0 - -* Tue Sep 13 2022 Milan Crha - 43.rc-2 -- Resolves: #2124869 (Cannot install RPM package file) - -* Fri Sep 02 2022 Milan Crha - 43.rc-1 -- Update to 43.rc - -* Wed Aug 17 2022 Milan Crha - 43.beta-3 -- Resolves: #2119089 (No enough apps to show for the "Editor's Choice" section) - -* Mon Aug 15 2022 Milan Crha - 43.beta-2 -- Add patch for install-queue - -* Fri Aug 05 2022 Milan Crha - 43.beta-1 -- Update to 43.beta - -* Thu Jul 21 2022 Fedora Release Engineering - 43.alpha-3 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_37_Mass_Rebuild - -* Thu Jul 07 2022 Adam Williamson - 43.alpha-2 -- Backport MR #1401 to fix issue #1816 and fedora-workstation #107 - -* Fri Jul 01 2022 Milan Crha - 43.alpha-1 -- Update to 43.alpha - -* Fri Jun 17 2022 Richard Hughes - 42.2-4 -- Add patch to make fwupd user requests work - -* Thu Jun 16 2022 David King - 42.2-3 -- Filter private libraries from Provides -- Use pkgconfig for BuildRequires -- Improve directory onwership - -* Mon Jun 13 2022 Milan Crha - 42.2-2 -- Add patch for crash under gs_flatpak_refine_app_unlocked() - -* Mon May 30 2022 Milan Crha - 42.2-1 -- Update to 42.2 -- Add patch to correct order of the setup of the GsShell - -* Wed Apr 27 2022 Milan Crha - 42.1-1 -- Update to 42.1 - -* Fri Mar 18 2022 Milan Crha - 42.0-1 -- Update to 42.0 - -* Thu Mar 10 2022 Milan Crha - 42.rc-2 -- Add upstream patches for gs-download-utils (i#1677 and i#1679) - -* Mon Mar 07 2022 Milan Crha - 42.rc-1 -- Update to 42.rc - -* Mon Feb 21 2022 Milan Crha - 42.beta-3 -- Resolves: #2056082 (Enable PackageKit autoremove option) - -* Wed Feb 16 2022 Milan Crha - 42.beta-2 -- Resolves: #2054939 (Crash on a PackageKit app install) -- Add a temporary workaround for gtk_widget_measure error flood on GsAppRow - -* Fri Feb 11 2022 Milan Crha - 42.beta-1 -- Update to 42.beta - -* Thu Jan 20 2022 Fedora Release Engineering - 42~alpha-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_36_Mass_Rebuild - -* Fri Jan 07 2022 Milan Crha - 42.alpha-1 -- Update to 42.alpha - -* Fri Dec 03 2021 Milan Crha - 41.2-1 -- Update to 41.2 - -* Fri Oct 29 2021 Milan Crha - 41.1-1 -- Update to 41.1 - -* Tue Oct 19 2021 Milan Crha - 41.0-6 -- Resolves: #2012863 (gs-installed-page: Change section on application state change) - -* Mon Oct 11 2021 Milan Crha - 41.0-5 -- Add patch to mark compulsory only repos, not apps from it - -* Fri Oct 08 2021 Milan Crha - 41.0-4 -- Resolves: #2011176 (flathub repo can't be added through gnome-software) -- Resolves: #2010660 (gs-repos-dialog: Can show also desktop applications) -- Resolves: #2010353 (Optional repos cannot be disabled) - -* Thu Oct 07 2021 Milan Crha - 41.0-3 -- Resolves: #2010740 (Refresh on repository setup change) - -* Mon Oct 04 2021 Milan Crha - 41.0-2 -- Resolves: #2009063 (Correct update notifications) - -* Mon Sep 20 2021 Milan Crha - 41.0-1 -- Update to 41.0 - -* Mon Sep 13 2021 Milan Crha - 41~rc-2 -- Resolves: #2003365 (packagekit: Ensure PkClient::interactive flag being set) - -* Wed Sep 08 2021 Milan Crha - 41~rc-1 -- Update to 41.rc - -* Wed Sep 01 2021 Milan Crha - 41~beta-3 -- Resolves: #1995817 (gs-updates-section: Check also dependencies' download size) - -* Tue Aug 24 2021 Kalev Lember - 41~beta-2 -- Enable parental controls support - -* Fri Aug 13 2021 Milan Crha - 41~beta-1 -- Update to 41.beta - -* Thu Jul 22 2021 Fedora Release Engineering - 41~alpha-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_35_Mass_Rebuild - -* Wed Jul 21 2021 Milan Crha - 41~alpha-1 -- Update to 41.alpha - -* Mon Jul 12 2021 Milan Crha - 40.3-2 -- Add rpm-ostree patch to hide packages from the search results -- Add patch to implement what-provides search in the Flatpak plugin - -* Mon Jul 12 2021 Milan Crha - 40.3-1 -- Update to 40.3 - -* Wed Jun 23 2021 Milan Crha - 40.2-2 -- Add patch to automatically install application updates (i#1248) - -* Fri Jun 04 2021 Milan Crha - 40.2-1 -- Update to 40.2 - -* Mon May 03 2021 Milan Crha - 40.1-2 -- Add patch for crash under gs_details_page_refresh_all() (i#1227) - -* Mon May 03 2021 Milan Crha - 40.1-1 -- Update to 40.1 - -* Fri Mar 26 2021 Kalev Lember - 40.0-2 -- Rebuild to fix sysprof-capture symbols leaking into libraries consuming it - -* Mon Mar 22 2021 Kalev Lember - 40.0-1 -- Update to 40.0 - -* Thu Mar 18 2021 Adam Williamson - 40~rc-2 -- Backport a couple of bug fixes from upstream (icon display, crash bug) - -* Mon Mar 15 2021 Kalev Lember - 40~rc-1 -- Update to 40.rc - -* Wed Mar 10 2021 Adam Williamson - 40~beta-2 -- Backport MR #643 to fix update notifications on first run (#1930401) - -* Tue Feb 16 2021 Kalev Lember - 40~beta-1 -- Update to 40.beta - -* Mon Feb 08 2021 Richard Hughes - 3.38.1-1 -- New upstream version -- Fix package details not found for some packages -- Ignore harmless warnings when using unusual fwupd versions - -* Tue Jan 26 2021 Fedora Release Engineering - 3.38.0-3 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_34_Mass_Rebuild - -* Mon Sep 14 2020 Kalev Lember - 3.38.0-2 -- Revert an optimization that broke packagekit updates - -* Fri Sep 11 2020 Kalev Lember - 3.38.0-1 -- Update to 3.38.0 - -* Tue Sep 01 2020 Kalev Lember - 3.37.92-1 -- Update to 3.37.92 - -* Tue Aug 18 2020 Richard Hughes - 3.36.1-4 -- Rebuild for the libxmlb API bump. - -* Sat Aug 01 2020 Fedora Release Engineering - 3.36.1-3 -- Second attempt - Rebuilt for - https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild - -* Mon Jul 27 2020 Fedora Release Engineering - 3.36.1-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild - -* Fri May 22 2020 Richard Hughes - 3.36.1-1 -- Update to 3.36.1 - -* Tue May 12 2020 Kalev Lember - 3.36.0-2 -- Backport various rpm-ostree backend fixes - -* Wed Mar 11 2020 Kalev Lember - 3.36.0-1 -- Update to 3.36.0 - -* Wed Mar 04 2020 Kalev Lember - 3.35.92-1 -- Update to 3.35.92 - -* Fri Feb 21 2020 Richard Hughes - 3.35.91-2 -- Backport a patch to fix a crash when looking at the application details. - -* Wed Feb 19 2020 Richard Hughes - 3.35.91-1 -- Update to 3.35.91. - -* Tue Jan 28 2020 Fedora Release Engineering - 3.35.2-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_32_Mass_Rebuild - -* Mon Nov 25 2019 Richard Hughes - 3.35.2-1 -- Update to 3.35.2. - -* Fri Oct 18 2019 Kalev Lember - 3.34.1-6 -- Backport patches to fix a crash in gs_flatpak_get_installation (#1762689) - -* Mon Oct 14 2019 Kalev Lember - 3.34.1-5 -- Update renamed appstream ids for GNOME 3.34 - -* Fri Oct 11 2019 Richard Hughes - 3.34.1-4 -- Backport a simpler to correct the installed applications -- Resolves #1759193 - -* Fri Oct 11 2019 Richard Hughes - 3.34.1-3 -- Backport a better patch to correct the installed applications -- Resolves #1759193 - -* Thu Oct 10 2019 Richard Hughes - 3.34.1-2 -- Backport a patch to correct the applications shown in the installed list -- Resolves #1759193 - -* Mon Oct 07 2019 Kalev Lember - 3.34.1-1 -- Update to 3.34.1 - -* Wed Sep 25 2019 Kalev Lember - 3.34.0-2 -- Fix third party repo enabling not working (#1749566) - -* Mon Sep 09 2019 Kalev Lember - 3.34.0-1 -- Update to 3.34.0 - -* Thu Jul 25 2019 Fedora Release Engineering - 3.32.4-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_31_Mass_Rebuild - -* Thu Jul 11 2019 Kalev Lember - 3.32.4-1 -- Update to 3.32.4 - -* Thu Jul 11 2019 Richard Hughes - 3.32.3-5 -- Disable the snap plugin. Canonical upstream are not going to be installing - gnome-software in the next LTS, prefering instead to ship a "Snap Store" - rather than GNOME Software. -- Enabling the snap plugin also enables the Snap Store which violated the same - rules which prevented us installing Flathub by default. -- The existing plugin is barely maintained and I don't want to be the one - responsible when it breaks. - -* Thu Jun 13 2019 Kalev Lember - 3.32.3-4 -- Rebuild for accidental libflatpak ABI break - -* Mon Jun 10 22:13:19 CET 2019 Igor Gnatenko - 3.32.3-3 -- Rebuild for RPM 4.15 - -* Mon Jun 10 15:42:01 CET 2019 Igor Gnatenko - 3.32.3-2 -- Rebuild for RPM 4.15 - -* Fri May 24 2019 Kalev Lember - 3.32.3-1 -- Update to 3.32.3 - -* Tue May 07 2019 Kalev Lember - 3.32.2-1 -- Update to 3.32.2 - -* Fri May 03 2019 Kalev Lember - 3.32.1-4 -- Update a patch to final upstream version - -* Tue Apr 30 2019 Kalev Lember - 3.32.1-3 -- Backport a number of rpm-ostree fixes - -* Tue Apr 16 2019 Adam Williamson - 3.32.1-2 -- Rebuild with Meson fix for #1699099 - -* Mon Apr 15 2019 Kalev Lember - 3.32.1-1 -- Update to 3.32.1 - -* Fri Apr 05 2019 Neal Gompa - 3.32.0-6 -- Require snapd instead of the obsolete snapd-login-service for snap subpackage - -* Wed Apr 03 2019 Kalev Lember - 3.32.0-5 -- Switch to system libdnf - -* Fri Mar 29 2019 Kalev Lember - 3.32.0-4 -- Rebuild for new rpm-ostree - -* Fri Mar 15 2019 Kalev Lember - 3.32.0-3 -- Add nm-connection-editor.desktop to Utilities folder (#1686851) - -* Tue Mar 12 2019 Kalev Lember - 3.32.0-2 -- Backport a patch to add shadows to app icons - -* Mon Mar 11 2019 Kalev Lember - 3.32.0-1 -- Update to 3.32.0 - -* Tue Mar 05 2019 Kalev Lember - 3.31.92-1 -- Update to 3.31.92 - -* Thu Feb 28 2019 Kalev Lember - 3.31.90-4 -- Change PackageKit requires to recommends - -* Wed Feb 27 2019 Kalev Lember - 3.31.90-3 -- Remove unneeded dpkg plugin - -* Mon Feb 25 2019 Kalev Lember - 3.31.90-2 -- Split rpm-ostree backend to its own subpackage - -* Sun Feb 24 2019 Kalev Lember - 3.31.90-1 -- Update to 3.31.90 -- Add "anaconda" repo to official repos list (#1679693) - -* Thu Jan 31 2019 Fedora Release Engineering - 3.31.2-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_30_Mass_Rebuild - -* Wed Jan 16 2019 Kalev Lember - 3.31.2-1 -- Update to 3.31.2 - -* Fri Dec 14 2018 Kalev Lember - 3.31.1-2 -- Fix offline update notifications to show up (#1659231) - -* Tue Oct 09 2018 Kalev Lember - 3.31.1-1 -- Update to 3.31.1 - -* Fri Oct 05 2018 Kalev Lember - 3.30.2-1 -- Update to 3.30.2 - -* Wed Sep 26 2018 Kalev Lember - 3.30.1-2 -- Add modular repos to official repos list - -* Tue Sep 25 2018 Kalev Lember - 3.30.1-1 -- Update to 3.30.1 - -* Thu Sep 06 2018 Kalev Lember - 3.30.0-1 -- Update to 3.30.0 - -* Tue Aug 28 2018 Richard Hughes - 3.29.92-1 -- Update to 3.29.92 - -* Fri Jul 13 2018 Fedora Release Engineering - 3.29.1-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_29_Mass_Rebuild - -* Wed May 09 2018 Kalev Lember - 3.29.1-1 -- Update to 3.29.1 - -* Mon Apr 09 2018 Kalev Lember - 3.28.1-1 -- Update to 3.28.1 - -* Thu Mar 29 2018 Kalev Lember - 3.28.0-5 -- Fix empty OS Updates showing up -- Make rpm-ostree update triggering work - -* Thu Mar 15 2018 Kalev Lember - 3.28.0-4 -- Fix opening results from gnome-shell search provider - -* Wed Mar 14 2018 Kalev Lember - 3.28.0-3 -- Fix crash on initial run with no network (#1554986) - -* Tue Mar 13 2018 Kalev Lember - 3.28.0-2 -- Backport an upstream patch to fix shell extensions app ID - -* Mon Mar 12 2018 Kalev Lember - 3.28.0-1 -- Update to 3.28.0 - -* Sun Mar 11 2018 Kalev Lember - 3.27.92-3 -- Rebuilt for gspell 1.8 - -* Wed Mar 07 2018 Kalev Lember - 3.27.92-2 -- Move org.gnome.Software.Featured.xml from -editor to main package - -* Mon Mar 05 2018 Kalev Lember - 3.27.92-1 -- Update to 3.27.92 - -* Sun Mar 04 2018 Neal Gompa - 3.27.90-4 -- Drop obsolete snapd-login-service requirement for snap plugin subpackage - -* Mon Feb 19 2018 Adam Williamson - 3.27.90-3 -- Backport fix for RHBZ #1546893 from upstream git - -* Mon Feb 19 2018 Kalev Lember - 3.27.90-2 -- Re-enable rpm-ostree plugin - -* Thu Feb 15 2018 Kalev Lember - 3.27.90-1 -- Update to 3.27.90 -- Temporarily disable the rpm-ostree plugin - -* Tue Feb 13 2018 Björn Esser - 3.27.4-4 -- Rebuild against newer gnome-desktop3 package - -* Thu Feb 08 2018 Kalev Lember - 3.27.4-3 -- Add fedora-workstation-repositories to nonfree-sources schema defaults - -* Wed Feb 07 2018 Fedora Release Engineering - 3.27.4-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_28_Mass_Rebuild - -* Mon Jan 08 2018 Kalev Lember - 3.27.4-1 -- Update to 3.27.4 -- Drop unused --without packagekit option - -* Fri Jan 05 2018 Igor Gnatenko - 3.27.3-2 -- Remove obsolete scriptlets - -* Sat Dec 16 2017 Kalev Lember - 3.27.3-1 -- Update to 3.27.3 - -* Mon Nov 13 2017 Kalev Lember - 3.27.2-1 -- Update to 3.27.2 - -* Thu Nov 09 2017 Kalev Lember - 3.26.2-1 -- Update to 3.26.2 -- Re-enable fwupd support - -* Tue Oct 31 2017 Kalev Lember - 3.26.1-5 -- Enable the rpm-ostree plugin - -* Wed Oct 25 2017 Kalev Lember - 3.26.1-4 -- Fix "too many results returned" error after distro upgrades (#1496489) - -* Tue Oct 10 2017 Kalev Lember - 3.26.1-3 -- Backport a flatpakref installation fix - -* Mon Oct 09 2017 Richard Hughes - 3.26.1-2 -- Disable fwupd support until we get a 3.27.1 tarball - -* Sun Oct 08 2017 Kalev Lember - 3.26.1-1 -- Update to 3.26.1 - -* Mon Sep 11 2017 Kalev Lember - 3.26.0-1 -- Update to 3.26.0 - -* Sun Aug 27 2017 Kalev Lember - 3.25.91-1 -- Update to 3.25.91 - -* Tue Aug 15 2017 Kalev Lember - 3.25.90-1 -- Update to 3.25.90 - -* Fri Aug 11 2017 Igor Gnatenko - 3.25.4-6 -- Rebuilt after RPM update (№ 3) - -* Thu Aug 10 2017 Igor Gnatenko - 3.25.4-5 -- Rebuilt for RPM soname bump - -* Thu Aug 10 2017 Igor Gnatenko - 3.25.4-4 -- Rebuilt for RPM soname bump - -* Wed Aug 02 2017 Fedora Release Engineering - 3.25.4-3 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_27_Binutils_Mass_Rebuild - -* Wed Jul 26 2017 Fedora Release Engineering - 3.25.4-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_27_Mass_Rebuild - -* Fri Jul 21 2017 Kalev Lember - 3.25.4-1 -- Update to 3.25.4 - -* Tue Jul 18 2017 Kalev Lember - 3.25.3-6 -- Drop a meson workaround now that meson is fixed - -* Wed Jun 28 2017 Neal Gompa - 3.25.3-5 -- Actually properly enable snap subpackage after removing conditional - -* Wed Jun 28 2017 Neal Gompa - 3.25.3-4 -- Remove unnecessary arch-specific conditional for snap subpackage - -* Tue Jun 27 2017 Neal Gompa - 3.25.3-3 -- Ensure snap subpackage is installed if snapd is installed - -* Fri Jun 23 2017 Richard Hughes - 3.24.3-2 -- Enable the snap subpackage - -* Fri Jun 23 2017 Kalev Lember - 3.25.3-1 -- Update to 3.25.3 -- Switch to the meson build system -- Add an -editor subpackage with new banner editor - -* Mon May 15 2017 Richard Hughes - 3.24.3-1 -- Update to 3.23.3 -- Fix a common crash when installing flatpakrepo files -- Ensure we show the banner when upgrades are available - -* Tue May 09 2017 Kalev Lember - 3.24.2-1 -- Update to 3.24.2 - -* Tue Apr 25 2017 Adam Williamson - 3.24.1-2 -- Backport crasher fix from upstream (RHBZ #1444669 / BGO #781217) - -* Tue Apr 11 2017 Kalev Lember - 3.24.1-1 -- Update to 3.24.1 - -* Tue Mar 21 2017 Kalev Lember - 3.24.0-1 -- Update to 3.24.0 - -* Thu Mar 16 2017 Kalev Lember - 3.23.92-1 -- Update to 3.23.92 - -* Mon Feb 27 2017 Richard Hughes - 3.23.91-1 -- Update to 3.23.91 - -* Mon Feb 13 2017 Richard Hughes - 3.23.90-1 -- Update to 3.23.90 - -* Fri Feb 10 2017 Fedora Release Engineering - 3.23.3-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_26_Mass_Rebuild - -* Thu Dec 15 2016 Richard Hughes - 3.23.3-1 -- Update to 3.23.3 - -* Wed Nov 23 2016 Kalev Lember - 3.23.2-1 -- Update to 3.23.2 - -* Tue Nov 08 2016 Kalev Lember - 3.22.2-1 -- Update to 3.22.2 - -* Wed Oct 12 2016 Kalev Lember - 3.22.1-1 -- Update to 3.22.1 - -* Mon Sep 19 2016 Kalev Lember - 3.22.0-1 -- Update to 3.22.0 - -* Wed Sep 14 2016 Kalev Lember - 3.21.92-1 -- Update to 3.21.92 -- Don't set group tags - -* Thu Sep 01 2016 Kalev Lember - 3.21.91-1 -- Update to 3.21.91 - -* Wed Aug 17 2016 Kalev Lember - 3.21.90-2 -- Rebuilt for fixed libappstream-glib headers - -* Wed Aug 17 2016 Kalev Lember - 3.21.90-1 -- Update to 3.21.90 -- Tighten -devel subpackage dependencies - -* Thu Jul 28 2016 Richard Hughes - 3.21.4-2 -- Allow building without PackageKit for the atomic workstation. - -* Mon Jul 18 2016 Richard Hughes - 3.21.4-1 -- Update to 3.21.4 - -* Thu May 26 2016 Kalev Lember - 3.21.2-2 -- Build with flatpak support - -* Mon May 23 2016 Richard Hughes - 3.21.2-1 -- Update to 3.21.2 - -* Tue May 10 2016 Kalev Lember - 3.21.1-2 -- Require PackageKit 1.1.1 for system upgrade support - -* Mon Apr 25 2016 Richard Hughes - 3.21.1-1 -- Update to 3.21.1 - -* Mon Apr 25 2016 Richard Hughes - 3.20.2-1 -- Update to 3.20.1 -- Allow popular and featured apps to match any plugin -- Do not make the ODRS plugin depend on xdg-app -- Fix many of the os-upgrade issues and implement the latest mockups -- Make all the plugins more threadsafe -- Return all update descriptions newer than the installed version -- Show some non-fatal error messages if installing fails -- Use a background PackageKit transaction when downloading upgrades - -* Wed Apr 13 2016 Kalev Lember - 3.20.1-1 -- Update to 3.20.1 - -* Fri Apr 01 2016 Richard Hughes - 3.20.1-2 -- Set the list of official sources -- Compile with xdg-app support - -* Tue Mar 22 2016 Kalev Lember - 3.20.0-1 -- Update to 3.20.0 - -* Mon Mar 14 2016 Richard Hughes - 3.19.92-1 -- Update to 3.19.92 - -* Thu Mar 03 2016 Kalev Lember - 3.19.91-2 -- Set minimum required json-glib version - -* Mon Feb 29 2016 Richard Hughes - 3.19.91-1 -- Update to 3.19.91 - -* Mon Feb 15 2016 Richard Hughes - 3.19.90-1 -- Update to 3.19.90 - -* Wed Feb 03 2016 Fedora Release Engineering - 3.19.4-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_24_Mass_Rebuild - -* Fri Jan 15 2016 Richard Hughes - 3.19.4-1 -- Update to 3.19.4 - -* Thu Dec 03 2015 Kalev Lember - 3.18.3-2 -- Require librsvg2 for the gdk-pixbuf svg loader - -* Thu Nov 05 2015 Richard Hughes - 3.18.3-1 -- Update to 3.18.3 -- Use the correct user agent string when downloading firmware -- Fix a crash in the limba plugin -- Fix installing web applications - -* Mon Oct 26 2015 Kalev Lember - 3.18.2-2 -- Fix apps reappearing as installed a few seconds after removal (#1275163) - -* Thu Oct 15 2015 Kalev Lember - 3.18.2-1 -- Update to 3.18.2 - -* Tue Oct 13 2015 Kalev Lember - 3.18.1-1 -- Update to 3.18.1 - -* Wed Oct 07 2015 Kalev Lember - 3.18.0-2 -- Backport two crasher fixes from upstream - -* Mon Sep 21 2015 Kalev Lember - 3.18.0-1 -- Update to 3.18.0 - -* Tue Sep 15 2015 Kalev Lember - 3.17.92-2 -- Update dependency versions - -* Tue Sep 15 2015 Richard Hughes - 3.17.92-1 -- Update to 3.17.92 - -* Thu Sep 10 2015 Richard Hughes - 3.17.91-2 -- Fix firmware updates - -* Thu Sep 03 2015 Kalev Lember - 3.17.91-1 -- Update to 3.17.91 - -* Wed Aug 19 2015 Kalev Lember - 3.17.90-1 -- Update to 3.17.90 - -* Wed Aug 12 2015 Richard Hughes - 3.17.3-1 -- Update to 3.17.3 - -* Wed Jul 22 2015 David King - 3.17.2-3 -- Bump for new gnome-desktop3 - -* Wed Jun 17 2015 Fedora Release Engineering - 3.17.2-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_23_Mass_Rebuild - -* Fri Jun 05 2015 Kalev Lember - 3.17.2-1 -- Update to 3.17.2 - -* Mon May 25 2015 Kalev Lember - 3.17.1-1 -- Update to 3.17.1 - -* Fri May 15 2015 Kalev Lember - 3.16.2-2 -- Fix a crash under Wayland (#1221968) - -* Mon May 11 2015 Kalev Lember - 3.16.2-1 -- Update to 3.16.2 - -* Tue Apr 14 2015 Kalev Lember - 3.16.1-1 -- Update to 3.16.1 - -* Mon Mar 23 2015 Kalev Lember - 3.16.0-1 -- Update to 3.16.0 - -* Mon Mar 16 2015 Kalev Lember - 3.15.92-1 -- Update to 3.15.92 -- Use license macro for the COPYING file -- Add a patch to adapt to gnome-terminal desktop file rename - -* Mon Mar 02 2015 Kalev Lember - 3.15.91-1 -- Update to 3.15.91 - -* Sat Feb 21 2015 Kalev Lember - 3.15.90-3 -- Export DisplayName property on the packagekit session service - -* Thu Feb 19 2015 Kalev Lember - 3.15.90-2 -- Backport a crash fix - -* Tue Feb 17 2015 Richard Hughes - 3.15.90-1 -- Update to 3.15.90 - -* Mon Jan 19 2015 Richard Hughes - 3.15.4-1 -- Update to 3.15.4 - -* Tue Nov 25 2014 Kalev Lember - 3.15.2-1 -- Update to 3.15.2 - -* Thu Nov 13 2014 Richard Hughes - 3.14.2-3 -- Fix non-Fedora build - -* Tue Nov 11 2014 Richard Hughes - 3.14.2-2 -- Backport a patch to fix compilation - -* Mon Nov 10 2014 Kalev Lember - 3.14.2-1 -- Update to 3.14.2 - -* Sat Nov 08 2014 Kalev Lember - 3.14.1-3 -- Update the list of system apps - -* Sat Nov 01 2014 David King - 3.14.1-2 -- Rebuild for new libappstream-glib (#1156494) - -* Mon Oct 13 2014 Kalev Lember - 3.14.1-1 -- Update to 3.14.1 - -* Thu Oct 09 2014 Kalev Lember - 3.14.0-2 -- Depend on gnome-menus for app folder directory entries - -* Mon Sep 22 2014 Kalev Lember - 3.14.0-1 -- Update to 3.14.0 - -* Wed Sep 17 2014 Kalev Lember - 3.13.92-2 -- Set minimum required dependency versions (#1136343) - -* Tue Sep 16 2014 Kalev Lember - 3.13.92-1 -- Update to 3.13.92 -- Replace gnome-system-log with gnome-logs in the system apps list - -* Tue Sep 02 2014 Kalev Lember - 3.13.91-1 -- Update to 3.13.91 - -* Tue Aug 19 2014 Richard Hughes - 3.13.90-1 -- Update to 3.13.90 - -* Sat Aug 16 2014 Fedora Release Engineering - 3.13.5-0.2.git5c89189 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_21_22_Mass_Rebuild - -* Mon Aug 11 2014 Kalev Lember - 3.13.5-0.1.git5c89189 -- Update to 3.13.5 git snapshot -- Ship HighContrast icons - -* Sun Aug 03 2014 Kalev Lember - 3.13.4-2 -- Replace Epiphany with Firefox in the system apps list - -* Wed Jul 23 2014 Kalev Lember - 3.13.4-1 -- Update to 3.13.4 - -* Wed Jun 25 2014 Kalev Lember - 3.13.3-1 -- Update to 3.13.3 - -* Thu Jun 12 2014 Richard Hughes - 3.13.3-0.2.git7491627 -- Depend on the newly-created appstream-data package and stop shipping - the metadata here. - -* Sat Jun 07 2014 Kalev Lember - 3.13.3-0.1.git7491627 -- Update to 3.13.3 git snapshot - -* Wed May 28 2014 Richard Hughes - 3.13.2-2 -- Rebuild with new metadata. - -* Wed May 28 2014 Kalev Lember - 3.13.2-1 -- Update to 3.13.2 - -* Thu May 15 2014 Kalev Lember - 3.13.1-4 -- Depend on gsettings-desktop-schemas - -* Mon May 12 2014 Richard Hughes - 3.13.1-3 -- Update the metadata and use appstream-util to install the metadata. - -* Wed May 07 2014 Kalev Lember - 3.13.1-2 -- Drop gnome-icon-theme dependency - -* Mon Apr 28 2014 Richard Hughes - 3.13.1-1 -- Update to 3.13.1 - -* Fri Apr 11 2014 Kalev Lember - 3.12.1-2 -- Rebuild with new metadata. - -* Fri Apr 11 2014 Richard Hughes - 3.12.1-1 -- Update to 3.12.1 - -* Mon Mar 24 2014 Richard Hughes - 3.12.0-1 -- Update to 3.12.0 - -* Thu Mar 20 2014 Richard Hughes - 3.11.92-1 -- Update to 3.11.92 - -* Tue Mar 18 2014 Richard Hughes - 3.11.91-2 -- Rebuild with new metadata. - -* Sat Mar 08 2014 Richard Hughes - 3.11.91-1 -- Update to 3.11.91 - -* Tue Feb 18 2014 Richard Hughes - 3.11.90-1 -- Update to 3.11.90 - -* Mon Feb 03 2014 Richard Hughes - 3.11.5-2 -- Require epiphany-runtime rather than the full application - -* Mon Feb 03 2014 Richard Hughes - 3.11.5-1 -- Update to 3.11.5 - -* Thu Jan 30 2014 Richard Hughes - 3.11.4-3 -- Rebuild for libpackagekit-glib soname bump - -* Wed Jan 22 2014 Richard Hughes - 3.11.4-2 -- Rebuild with metadata that has the correct screenshot url. - -* Thu Jan 16 2014 Richard Hughes - 3.11.4-1 -- Update to 3.11.4 - -* Tue Dec 17 2013 Richard Hughes - 3.11.3-1 -- Update to 3.11.3 - -* Tue Nov 19 2013 Richard Hughes - 3.11.2-1 -- Update to 3.11.2 - -* Tue Oct 29 2013 Richard Hughes - 3.11.1-1 -- Update to 3.11.1 -- Add a gnome shell search provider -- Add a module to submit the user rating to the fedora-tagger web service -- Add support for 'missing' codecs that we know exist but we can't install -- Add support for epiphany web applications -- Handle offline installation sensibly -- Save the user rating if the user clicks the rating stars -- Show a modal error message if install or remove actions failed -- Show a star rating on the application details page -- Show font screenshots -- Show more detailed version numbers when required -- Show screenshots to each application - -* Wed Sep 25 2013 Richard Hughes 3.10.0-1 -- New upstream release. -- New metadata for fedora, updates and updates-testing -- Add a plugin to query the PackageKit prepared-update file directly -- Do not clear the offline-update trigger if rebooting succeeded -- Do not load incompatible projects when parsing AppStream data -- Lots of updated translations -- Show the window right away when starting - -* Fri Sep 13 2013 Richard Hughes 3.9.3-1 -- New upstream release. -- Lots of new and fixed UI and updated metadata for Fedora 20 - -* Tue Sep 03 2013 Richard Hughes 3.9.2-1 -- New upstream release. -- Allow stock items in the AppStream XML -- Extract the AppStream URL and description from the XML -- Only present the window when the overview is complete -- Return the subcategories sorted by name - -* Mon Sep 02 2013 Richard Hughes 3.9.1-1 -- New upstream release which is a technical preview for the alpha. - -* Sun Sep 01 2013 Richard Hughes 0.1-3 -- Use buildroot not RPM_BUILD_ROOT -- Own all gnome-software directories -- Drop gtk-update-icon-cache requires and the mime database functionality - -* Thu Aug 29 2013 Richard Hughes 0.1-2 -- Add call to desktop-file-validate and fix other review comments. - -* Wed Aug 28 2013 Richard Hughes 0.1-1 -- First release for Fedora package review - +%autochangelog diff --git a/sources b/sources index da03639..dc17852 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-48.2.tar.xz) = 3a03f475de56cb2ba534a0a7eaaaeb21677cf27a54db03bb84e3953dce796bfc437daf59b41155884260006c18562c50d7e01056aeb190a18449cbcbf2f5120c +SHA512 (gnome-software-49.alpha.tar.xz) = 7616e9f3969b73651c502874ab20f78390b7284ba289451d68847e9afe47f306ef514f46fd633bc99440d98154329d2872237ffb73ae47222ab1d6273ae78b3d From b4aa6186d3ffea75de915d48f8bb4627398f2cff Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 27 Jun 2025 09:50:36 +0200 Subject: [PATCH 141/163] Bump plugin API version --- gnome-software.spec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index 5f6b255..664794e 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -21,7 +21,7 @@ %bcond dnf5 1 # this is not a library version -%define gs_plugin_version 22 +%define gs_plugin_version 23 %global tarball_version %%(echo %{version} | tr '~' '.') From 6f0144b990cf025954b7b741ae3a70beb1603f56 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 30 Jun 2025 14:48:06 +0200 Subject: [PATCH 142/163] dnf5: Install 'gnome-software-local-file-packagekit.desktop' also for dnf5 plugin --- 0001-dnf5-plugin.patch | 17 +++++++++++++++-- 1 file changed, 15 insertions(+), 2 deletions(-) diff --git a/0001-dnf5-plugin.patch b/0001-dnf5-plugin.patch index b2e8117..3277b35 100644 --- a/0001-dnf5-plugin.patch +++ b/0001-dnf5-plugin.patch @@ -1,5 +1,5 @@ -at commit f3042a5f73fc6b04e26ceca5a1a469879af30fd3 -Date: Fri Jun 20 11:20:33 2025 +0200 +at commit 523ea7ff97d4092faad730d9ddd2311d8de0fa22 +Date: Mon Jun 30 14:44:52 2025 +0200 diff --git a/meson_options.txt b/meson_options.txt index cd49cf529..27fa15e8b 100644 @@ -5595,3 +5595,16 @@ index 71aa486e2..d3e909dee 100644 plugins/eos-updater/gs-plugin-eos-updater.c plugins/epiphany/gs-plugin-epiphany.c plugins/epiphany/org.gnome.Software.Plugin.Epiphany.metainfo.xml.in +diff --git a/src/meson.build b/src/meson.build +index 99dfb409f..e91a73bac 100644 +--- a/src/meson.build ++++ b/src/meson.build +@@ -235,7 +235,7 @@ if get_option('fwupd') + ) + endif + +-if get_option('packagekit') or get_option('rpm_ostree') ++if get_option('packagekit') or get_option('rpm_ostree') or get_option('dnf5') + i18n.merge_file( + input: 'gnome-software-local-file-packagekit.desktop.in', + output: 'gnome-software-local-file-packagekit.desktop', From c924750e8af509c8256cd8163350bf323c9cd545 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 30 Jun 2025 15:42:41 +0200 Subject: [PATCH 143/163] dnf5: Update the dnf5 plugin patch to match the latest upstream main branch --- 0001-dnf5-plugin.patch | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/0001-dnf5-plugin.patch b/0001-dnf5-plugin.patch index 3277b35..70ad781 100644 --- a/0001-dnf5-plugin.patch +++ b/0001-dnf5-plugin.patch @@ -1,4 +1,4 @@ -at commit 523ea7ff97d4092faad730d9ddd2311d8de0fa22 +at commit 87d6d722ec47390682581162d5c14d9b26d4a65e Date: Mon Jun 30 14:44:52 2025 +0200 diff --git a/meson_options.txt b/meson_options.txt @@ -5596,15 +5596,15 @@ index 71aa486e2..d3e909dee 100644 plugins/epiphany/gs-plugin-epiphany.c plugins/epiphany/org.gnome.Software.Plugin.Epiphany.metainfo.xml.in diff --git a/src/meson.build b/src/meson.build -index 99dfb409f..e91a73bac 100644 +index 43e1b58e9..e8af8b058 100644 --- a/src/meson.build +++ b/src/meson.build -@@ -235,7 +235,7 @@ if get_option('fwupd') +@@ -245,7 +245,7 @@ if get_option('fwupd') ) endif -if get_option('packagekit') or get_option('rpm_ostree') +if get_option('packagekit') or get_option('rpm_ostree') or get_option('dnf5') i18n.merge_file( - input: 'gnome-software-local-file-packagekit.desktop.in', - output: 'gnome-software-local-file-packagekit.desktop', + input: + configure_file( From 91ecbf1717f7f6e0b68096998b9a79718cae3451 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 30 Jun 2025 15:57:08 +0200 Subject: [PATCH 144/163] Add script to update the dnf5-plugin patch To not have it saved on a single machine, easy to recover and run by anyone. --- .gitignore | 1 + dnf5-plugin/.gitignore | 1 + dnf5-plugin/update-patch.sh | 24 ++++++++++++++++++++++++ gnome-software.spec | 2 ++ 4 files changed, 28 insertions(+) create mode 100644 dnf5-plugin/.gitignore create mode 100755 dnf5-plugin/update-patch.sh diff --git a/.gitignore b/.gitignore index b4345b1..ba3b2b3 100644 --- a/.gitignore +++ b/.gitignore @@ -1 +1,2 @@ /gnome-software-*.tar.xz +/gnome-software-*-build diff --git a/dnf5-plugin/.gitignore b/dnf5-plugin/.gitignore new file mode 100644 index 0000000..b86f2cd --- /dev/null +++ b/dnf5-plugin/.gitignore @@ -0,0 +1 @@ +checkout-gs-dnf5 diff --git a/dnf5-plugin/update-patch.sh b/dnf5-plugin/update-patch.sh new file mode 100755 index 0000000..bf03fdd --- /dev/null +++ b/dnf5-plugin/update-patch.sh @@ -0,0 +1,24 @@ +#!/bin/bash + +if [ ! -d checkout-gs-dnf5 ]; then + git clone --branch wip/dnf5daemon https://gitlab.gnome.org/mcrha/gnome-software.git checkout-gs-dnf5 +fi + +PATCH_PATH=../0001-dnf5-plugin.patch +FIRST_COMMIT=f8b6ed17c592922c2e80667c5f122747f9c2d4ab + +cd checkout-gs-dnf5 && \ +echo "Updating gs-dnf5 git repository" && \ +git pull --rebase && \ +echo -n "at " >../${PATCH_PATH} && \ +git log HEAD | head -n 5 | grep -E "commit|Date" >>../${PATCH_PATH} && \ +echo "" >>../${PATCH_PATH} && \ +git diff ${FIRST_COMMIT}^ >>../${PATCH_PATH} && \ +cd - >/dev/null + +if [ "$?" = "0" ]; then + echo "Patch '${PATCH_PATH}' updated" +else + echo "Failed to update patch '${PATCH_PATH}'" + exit 1 +fi diff --git a/gnome-software.spec b/gnome-software.spec index 664794e..3894347 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -36,6 +36,8 @@ License: GPL-2.0-or-later URL: https://apps.gnome.org/Software Source0: https://download.gnome.org/sources/gnome-software/49/%{name}-%{tarball_version}.tar.xz +# to update the patch enter the ./dnf5-plugin/ directory and run from +# it the ./update-patch.sh script Patch: 0001-dnf5-plugin.patch # ostree and flatpak not on i686 for Fedora and RHEL 10 From cb80ea5cd1d87952fb27e0e3f7a4b69685ed8ae8 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 30 Jun 2025 17:15:57 +0200 Subject: [PATCH 145/163] dnf5-plugin: Update script to generate patch to not depend on exact commit It'll mean less changes, and less work, to keep it up to date with the repository changes. --- dnf5-plugin/update-patch.sh | 21 ++++++++++++++++----- 1 file changed, 16 insertions(+), 5 deletions(-) diff --git a/dnf5-plugin/update-patch.sh b/dnf5-plugin/update-patch.sh index bf03fdd..481ffcf 100755 --- a/dnf5-plugin/update-patch.sh +++ b/dnf5-plugin/update-patch.sh @@ -1,24 +1,35 @@ #!/bin/bash if [ ! -d checkout-gs-dnf5 ]; then - git clone --branch wip/dnf5daemon https://gitlab.gnome.org/mcrha/gnome-software.git checkout-gs-dnf5 + git clone --branch main https://gitlab.gnome.org/mcrha/gnome-software.git checkout-gs-dnf5 && \ + cd checkout-gs-dnf5 && \ + git checkout -b wip/dnf5daemon origin/wip/dnf5daemon && \ + cd - >/dev/null + + if [ "$?" != "0" ]; then + echo "Failed to clone dnf5-plugin repository" 1>&2 + exit 1; + fi fi PATCH_PATH=../0001-dnf5-plugin.patch -FIRST_COMMIT=f8b6ed17c592922c2e80667c5f122747f9c2d4ab cd checkout-gs-dnf5 && \ -echo "Updating gs-dnf5 git repository" && \ +echo "Updating gs-dnf5 git 'main' repository" && \ +git checkout main && \ +git pull --rebase && \ +echo "Updating gs-dnf5 git 'dnf5-pugin' repository" && \ +git checkout wip/dnf5daemon && \ git pull --rebase && \ echo -n "at " >../${PATCH_PATH} && \ git log HEAD | head -n 5 | grep -E "commit|Date" >>../${PATCH_PATH} && \ echo "" >>../${PATCH_PATH} && \ -git diff ${FIRST_COMMIT}^ >>../${PATCH_PATH} && \ +git diff main >>../${PATCH_PATH} && \ cd - >/dev/null if [ "$?" = "0" ]; then echo "Patch '${PATCH_PATH}' updated" else - echo "Failed to update patch '${PATCH_PATH}'" + echo "Failed to update patch '${PATCH_PATH}'" 1>&2 exit 1 fi From 9baa1e6cb69167623a41174901b16ab14ded738a Mon Sep 17 00:00:00 2001 From: Yaakov Selkowitz Date: Fri, 27 Jun 2025 12:56:22 -0400 Subject: [PATCH 146/163] Fix files list for RHEL builds gnome-software-local-file-packagekit.desktop is installed only when one or more of these options are enabled. --- gnome-software.spec | 2 ++ 1 file changed, 2 insertions(+) diff --git a/gnome-software.spec b/gnome-software.spec index 3894347..f18c59b 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -235,7 +235,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_bindir}/gnome-software %{_datadir}/applications/gnome-software-local-file-flatpak.desktop %{_datadir}/applications/gnome-software-local-file-fwupd.desktop +%if %{with packagekit} || %{with rpmostree} || %{with dnf5} %{_datadir}/applications/gnome-software-local-file-packagekit.desktop +%endif %{_datadir}/applications/org.gnome.Software.desktop %{_datadir}/bash-completion/completions/gnome-software %{_mandir}/man1/gnome-software.1* From 47f4fc83f39e1d952ac8912d7360c781da4e2ee2 Mon Sep 17 00:00:00 2001 From: Fedora Release Engineering Date: Wed, 23 Jul 2025 22:48:57 +0000 Subject: [PATCH 147/163] Rebuilt for https://fedoraproject.org/wiki/Fedora_43_Mass_Rebuild --- gnome-software.spec | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index f18c59b..32061b0 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -29,7 +29,7 @@ Name: gnome-software Version: 49~alpha -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -324,4 +324,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog +* Wed Jul 23 2025 Fedora Release Engineering - 49~alpha-2 +- Rebuilt for https://fedoraproject.org/wiki/Fedora_43_Mass_Rebuild + %autochangelog From 3a3519584163c2c69ead75a0f10e00112318d82e Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 25 Jul 2025 11:34:05 +0200 Subject: [PATCH 148/163] Resolves: #2377094 (Update dnf5 plugin with fixes for rhbz#2377094) --- 0001-dnf5-plugin.patch | 164 ++++++++++++++++++++++++++++++----------- gnome-software.spec | 5 +- 2 files changed, 120 insertions(+), 49 deletions(-) diff --git a/0001-dnf5-plugin.patch b/0001-dnf5-plugin.patch index 70ad781..c6cf3dc 100644 --- a/0001-dnf5-plugin.patch +++ b/0001-dnf5-plugin.patch @@ -1,5 +1,5 @@ -at commit 87d6d722ec47390682581162d5c14d9b26d4a65e -Date: Mon Jun 30 14:44:52 2025 +0200 +at commit f78a6ba2af27d06c77a052e7499422da22c2cd06 +Date: Fri Jul 25 11:23:46 2025 +0200 diff --git a/meson_options.txt b/meson_options.txt index cd49cf529..27fa15e8b 100644 @@ -15,10 +15,10 @@ index cd49cf529..27fa15e8b 100644 option('fwupd', type : 'boolean', value : true, description : 'enable fwupd support') diff --git a/plugins/dnf5/gs-dnf5-progress-helper.c b/plugins/dnf5/gs-dnf5-progress-helper.c new file mode 100644 -index 000000000..d720adc87 +index 000000000..cd8b861df --- /dev/null +++ b/plugins/dnf5/gs-dnf5-progress-helper.c -@@ -0,0 +1,532 @@ +@@ -0,0 +1,552 @@ +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- + * vi:set noexpandtab tabstop=8 shiftwidth=8: + * @@ -41,7 +41,8 @@ index 000000000..d720adc87 + + GsDnf5RpmRpm *rpm_proxy; /* (owned) */ + GsDnf5Base *base_proxy; /* (owned) */ -+ GsApp *app; /* (owned) */ ++ GsApp *app; /* (owned) (nullable) */ ++ GsAppList *list; /* (owned) (nullable) */ + gchar *session_object_path; /* (owned) */ + GHashTable *ongoing_downloads; /* (owned); gchar * (download_id) ~> DownloadInfo * */ + GsAppState recover_download_state; @@ -73,10 +74,20 @@ index 000000000..d720adc87 +G_DEFINE_TYPE (GsDnf5ProgressHelper, gs_dnf5_progress_helper, G_TYPE_OBJECT) + +static void ++gs_dnf5_helper_set_progress (GsDnf5ProgressHelper *self, ++ guint progress) ++{ ++ if (self->app != NULL) ++ gs_app_set_progress (self->app, progress); ++ if (self->list != NULL) ++ gs_app_list_override_progress (self->list, progress); ++} ++ ++static void +gs_dnf5_update_download_progress (GsDnf5ProgressHelper *self) +{ + if (self->to_download_total > 0) -+ gs_app_set_progress (self->app, 100 * self->downloaded_total / self->to_download_total); ++ gs_dnf5_helper_set_progress (self, 100 * self->downloaded_total / self->to_download_total); +} + +typedef struct { @@ -104,10 +115,12 @@ index 000000000..d720adc87 + return; + + if (g_hash_table_size (self->ongoing_downloads) == 0) { -+ self->recover_download_state = gs_app_get_state (self->app); ++ if (self->app != NULL) { ++ self->recover_download_state = gs_app_get_state (self->app); ++ gs_app_set_state (self->app, GS_APP_STATE_DOWNLOADING); ++ } + self->to_download_total = 0; + self->downloaded_total = 0; -+ gs_app_set_state (self->app, GS_APP_STATE_DOWNLOADING); + } + + download_info = g_new0 (DownloadInfo, 1); @@ -116,7 +129,8 @@ index 000000000..d720adc87 + g_hash_table_insert (self->ongoing_downloads, g_strdup (arg_download_id), download_info); + self->to_download_total += arg_total_to_download; + -+ gs_app_set_size_download (self->app, GS_SIZE_TYPE_VALID, self->to_download_total); ++ if (self->app != NULL) ++ gs_app_set_size_download (self->app, GS_SIZE_TYPE_VALID, self->to_download_total); + gs_dnf5_update_download_progress (self); +} + @@ -147,9 +161,11 @@ index 000000000..d720adc87 + + /* it's the last package to be downloaded */ + if (g_hash_table_size (self->ongoing_downloads) == 0) { -+ gs_app_set_state (self->app, self->recover_download_state); -+ gs_app_set_progress (self->app, GS_APP_PROGRESS_UNKNOWN); -+ gs_app_set_size_download (self->app, GS_SIZE_TYPE_UNKNOWN, 0); ++ gs_dnf5_helper_set_progress (self, GS_APP_PROGRESS_UNKNOWN); ++ if (self->app != NULL) { ++ gs_app_set_state (self->app, self->recover_download_state); ++ gs_app_set_size_download (self->app, GS_SIZE_TYPE_UNKNOWN, 0); ++ } + } else { + gs_dnf5_update_download_progress (self); + } @@ -194,7 +210,8 @@ index 000000000..d720adc87 + self->to_download_total -= download_info->total; + download_info->total = arg_total_to_download; + self->to_download_total += download_info->total; -+ gs_app_set_size_download (self->app, GS_SIZE_TYPE_VALID, self->to_download_total); ++ if (self->app != NULL) ++ gs_app_set_size_download (self->app, GS_SIZE_TYPE_VALID, self->to_download_total); + } + gs_dnf5_update_download_progress (self); + } @@ -208,7 +225,7 @@ index 000000000..d720adc87 +{ + if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) + return; -+ gs_app_set_progress (self->app, 0); ++ gs_dnf5_helper_set_progress (self, 0); + g_debug ("%s: total:%" G_GUINT64_FORMAT, G_STRFUNC, arg_total); +} + @@ -221,7 +238,7 @@ index 000000000..d720adc87 + if (g_strcmp0 (self->session_object_path, arg_session_object_path) != 0) + return; + g_debug ("%s: success:%d", G_STRFUNC, arg_success); -+ gs_app_set_progress (self->app, 100); ++ gs_dnf5_helper_set_progress (self, 100); +} + +static void @@ -236,7 +253,7 @@ index 000000000..d720adc87 + return; + g_debug ("%s: nevra:'%s' progress:%" G_GUINT64_FORMAT "/%" G_GUINT64_FORMAT, G_STRFUNC, arg_nevra, arg_processed, arg_total); + if (arg_total != 0) -+ gs_app_set_progress (self->app, arg_processed * 100 / arg_total); ++ gs_dnf5_helper_set_progress (self, arg_processed * 100 / arg_total); +} + +static void @@ -432,7 +449,7 @@ index 000000000..d720adc87 + + #undef clear_signal_handler + -+ gs_app_set_progress (self->app, GS_APP_PROGRESS_UNKNOWN); ++ gs_dnf5_helper_set_progress (self, GS_APP_PROGRESS_UNKNOWN); + + G_OBJECT_CLASS (gs_dnf5_progress_helper_parent_class)->dispose (object); +} @@ -445,6 +462,7 @@ index 000000000..d720adc87 + g_clear_object (&self->base_proxy); + g_clear_object (&self->rpm_proxy); + g_clear_object (&self->app); ++ g_clear_object (&self->list); + g_clear_pointer (&self->session_object_path, g_free); + g_clear_pointer (&self->ongoing_downloads, g_hash_table_destroy); + @@ -470,22 +488,24 @@ index 000000000..d720adc87 +gs_dnf5_progress_helper_new (GsDnf5Base *base_proxy, + GsDnf5RpmRpm *rpm_proxy, + GsApp *progress_app, ++ GsAppList *progress_list, + const gchar *session_object_path) +{ + GsDnf5ProgressHelper *self; + + g_return_val_if_fail (GS_DNF5_IS_BASE (base_proxy), NULL); + g_return_val_if_fail (GS_DNF5_IS_RPM_RPM (rpm_proxy), NULL); -+ g_return_val_if_fail (GS_IS_APP (progress_app), NULL); ++ g_return_val_if_fail (GS_IS_APP (progress_app) || GS_IS_APP_LIST (progress_list), NULL); + g_return_val_if_fail (session_object_path != NULL, NULL); + + self = g_object_new (GS_TYPE_DNF5_PROGRESS_HELPER, NULL); + self->base_proxy = g_object_ref (base_proxy); + self->rpm_proxy = g_object_ref (rpm_proxy); -+ self->app = g_object_ref (progress_app); ++ self->app = progress_app ? g_object_ref (progress_app) : NULL; ++ self->list = progress_list ? g_object_ref (progress_list) : NULL; + self->session_object_path = g_strdup (session_object_path); + -+ gs_app_set_progress (self->app, GS_APP_PROGRESS_UNKNOWN); ++ gs_dnf5_helper_set_progress (self, GS_APP_PROGRESS_UNKNOWN); + + self->download_add_new_id = + g_signal_connect_object (base_proxy, "download_add_new", @@ -553,10 +573,10 @@ index 000000000..d720adc87 +} diff --git a/plugins/dnf5/gs-dnf5-progress-helper.h b/plugins/dnf5/gs-dnf5-progress-helper.h new file mode 100644 -index 000000000..73d528d54 +index 000000000..5d522468c --- /dev/null +++ b/plugins/dnf5/gs-dnf5-progress-helper.h -@@ -0,0 +1,30 @@ +@@ -0,0 +1,31 @@ +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- + * vi:set noexpandtab tabstop=8 shiftwidth=8: + * @@ -584,15 +604,16 @@ index 000000000..73d528d54 + gs_dnf5_progress_helper_new (GsDnf5Base *base_proxy, + GsDnf5RpmRpm *rpm_proxy, + GsApp *progress_app, ++ GsAppList *progress_list, + const gchar *session_object_path); + +G_END_DECLS diff --git a/plugins/dnf5/gs-plugin-dnf5.c b/plugins/dnf5/gs-plugin-dnf5.c new file mode 100644 -index 000000000..bae3bde28 +index 000000000..fefad6961 --- /dev/null +++ b/plugins/dnf5/gs-plugin-dnf5.c -@@ -0,0 +1,3770 @@ +@@ -0,0 +1,3823 @@ +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- + * vi:set noexpandtab tabstop=8 shiftwidth=8: + * @@ -693,6 +714,7 @@ index 000000000..bae3bde28 +gs_dnf5_report_error (GsPluginDnf5 *self, + GsPluginEventCallback event_callback, + void *event_user_data, ++ GsApp *app, + const GError *error, + gboolean interactive) +{ @@ -702,6 +724,7 @@ index 000000000..bae3bde28 + return; + + event = gs_plugin_event_new ("error", error, ++ app ? "app" : NULL, app, + NULL); + if (interactive) + gs_plugin_event_add_flag (event, GS_PLUGIN_EVENT_FLAG_INTERACTIVE); @@ -1337,6 +1360,8 @@ index 000000000..bae3bde28 + GsAppState set_state; + GHashTable *nevra_to_app; /* (nullable): gchar *nevra ~> GsApp * */ + GHashTable *replaces; /* (nullable): GINT_TO_POINTER(pkg-id) ~> gchar *old_version */ ++ GHashTable *used_replaces; /* (nullable): GINT_TO_POINTER(pkg-id) ~> NULL */ ++ gboolean cover_unused_replaces; +} ReadPackageData; + +static gboolean @@ -1803,7 +1828,8 @@ index 000000000..bae3bde28 +typedef enum { + GS_DNF5_TRANSACTION_FLAG_NONE = 0, + GS_DNF5_TRANSACTION_FLAG_OFFLINE = 1 << 0, -+ GS_DNF5_TRANSACTION_FLAG_RESOLVE_ONLY = 1 << 1 ++ GS_DNF5_TRANSACTION_FLAG_RESOLVE_ONLY = 1 << 1, ++ GS_DNF5_TRANSACTION_FLAG_DISALLOW_ERASING = 1 << 2 /* negative flag, to not have it everywhere */ +} GsDnf5TransactionFlags; + +static gboolean @@ -1811,6 +1837,7 @@ index 000000000..bae3bde28 + const gchar *session_path, + GsDnf5RpmRpm *rpm_proxy, + GsApp *progress_app, ++ GsAppList *progress_list, + GsDnf5TransactionFlags flags, + GVariant **out_transaction, + GCancellable *cancellable, @@ -1870,8 +1897,11 @@ index 000000000..bae3bde28 + + options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); + -+ if (progress_app != NULL) -+ helper = gs_dnf5_progress_helper_new (base_proxy, rpm_proxy, progress_app, session_path); ++ g_variant_builder_add (options_builder, "{sv}", "allow_erasing", ++ g_variant_new_boolean ((flags & GS_DNF5_TRANSACTION_FLAG_DISALLOW_ERASING) == 0)); ++ ++ if (progress_app != NULL || progress_list != NULL) ++ helper = gs_dnf5_progress_helper_new (base_proxy, rpm_proxy, progress_app, progress_list, session_path); + + repo_key_import_data.self = self; + repo_key_import_data.session_path = session_path; @@ -2039,6 +2069,7 @@ index 000000000..bae3bde28 +typedef struct _UpdateReplacesData { + GsApp *app; + GHashTable *replaces; ++ GHashTable *used_replaces; +} UpdateReplacesData; + +static gboolean @@ -2051,8 +2082,10 @@ index 000000000..bae3bde28 + UpdateReplacesData *upd = user_data; + gint32 replaces_id = g_variant_get_int32 (item_array); + const gchar *old_version = g_hash_table_lookup (upd->replaces, GINT_TO_POINTER (replaces_id)); -+ if (old_version != NULL) ++ if (old_version != NULL) { + gs_app_set_version (upd->app, old_version); ++ g_hash_table_add (upd->used_replaces, GINT_TO_POINTER (replaces_id)); ++ } + + return TRUE; +} @@ -2073,13 +2106,27 @@ index 000000000..bae3bde28 + g_autoptr(GString) nevra = NULL; + GsApp *known_app; + -+ if (op_kind == OP_KIND_UNKNOWN || op_kind == OP_KIND_REPLACED) ++ if (op_kind == OP_KIND_UNKNOWN || (!rpd->cover_unused_replaces && op_kind == OP_KIND_REPLACED) || ++ (rpd->cover_unused_replaces && op_kind != OP_KIND_REPLACED)) + return TRUE; + + value = g_variant_get_child_value (item_array, 4); + dict = g_variant_dict_new (value); + g_clear_pointer (&value, g_variant_unref); + ++ if (rpd->cover_unused_replaces) { ++ value = g_variant_dict_lookup_value (dict, "id", G_VARIANT_TYPE_INT32); ++ if (value != NULL) { ++ gint32 id = g_variant_get_int32 (value); ++ if (g_hash_table_contains (rpd->used_replaces, GINT_TO_POINTER (id))) ++ return TRUE; ++ } else { ++ return TRUE; ++ } ++ ++ g_clear_pointer (&value, g_variant_unref); ++ } ++ + value = g_variant_dict_lookup_value (dict, "name", G_VARIANT_TYPE_STRING); + if (value == NULL) + return TRUE; @@ -2132,6 +2179,7 @@ index 000000000..bae3bde28 + + upd.app = upd_app; + upd.replaces = rpd->replaces; ++ upd.used_replaces = rpd->used_replaces; + + if (!gs_dnf5_foreach_item (self, value, gs_dnf5_gather_update_replaced_pkgs_cb, &upd, cancellable, error)) + return FALSE; @@ -2170,9 +2218,10 @@ index 000000000..bae3bde28 + gs_app_set_state (upd_app, GS_APP_STATE_UPDATABLE); + break; + case OP_KIND_REMOVE: -+ gs_app_set_state (upd_app, GS_APP_STATE_UNAVAILABLE); -+ break; + case OP_KIND_REPLACED: ++ gs_app_set_state (upd_app, GS_APP_STATE_UNAVAILABLE); ++ gs_app_set_size_download (upd_app, GS_SIZE_TYPE_VALID, 0); ++ break; + case OP_KIND_UNKNOWN: + default: + g_warn_if_reached (); @@ -2274,15 +2323,17 @@ index 000000000..bae3bde28 + if (success) { + g_autoptr(GHashTable) nevra_to_app = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_object_unref); + g_autoptr(GHashTable) replaces = g_hash_table_new_full (g_direct_hash, g_direct_equal, NULL, g_free); ++ g_autoptr(GHashTable) used_replaces = g_hash_table_new (g_direct_hash, g_direct_equal); + ReadPackageData rpd = { 0, }; + rpd.list = list; + rpd.set_state = GS_APP_STATE_UPDATABLE; + rpd.nevra_to_app = nevra_to_app; + rpd.replaces = replaces; ++ rpd.used_replaces = used_replaces; + + success = gs_dnf5_foreach_item (self, result, gs_dnf5_read_package_cb, &rpd, cancellable, &local_error); + -+ if (success && g_hash_table_size (nevra_to_app) > 0) { ++ if (success) { + g_autoptr(GVariantBuilder) options_builder2 = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); + g_autoptr(GVariant) transaction = NULL; + const gchar * const packages[2] = { NULL, NULL }; @@ -2296,13 +2347,19 @@ index 000000000..bae3bde28 + cancellable, + &local_error); + success = success && -+ gs_dnf5_run_transaction (self, session_path, rpm_proxy, NULL, ++ gs_dnf5_run_transaction (self, session_path, rpm_proxy, NULL, NULL, + GS_DNF5_TRANSACTION_FLAG_RESOLVE_ONLY, + &transaction, cancellable, &local_error); + if (success && transaction != NULL) { + success = gs_dnf5_foreach_item (self, transaction, + gs_dnf5_gather_update_replaces_cb, &rpd, + cancellable, &local_error); ++ rpd.cover_unused_replaces = FALSE; ++ success = success && ++ gs_dnf5_foreach_item (self, transaction, ++ gs_dnf5_gather_updates_from_transaction_cb, &rpd, ++ cancellable, &local_error); ++ rpd.cover_unused_replaces = TRUE; + success = success && + gs_dnf5_foreach_item (self, transaction, + gs_dnf5_gather_updates_from_transaction_cb, &rpd, @@ -2697,7 +2754,7 @@ index 000000000..bae3bde28 + cancellable, + &local_error); + success = success && -+ gs_dnf5_run_transaction (self, session_path, rpm_proxy, NULL, ++ gs_dnf5_run_transaction (self, session_path, rpm_proxy, NULL, NULL, + GS_DNF5_TRANSACTION_FLAG_RESOLVE_ONLY, + &transaction, cancellable, &local_error); + if (success && transaction != NULL) @@ -3120,6 +3177,7 @@ index 000000000..bae3bde28 + g_autoptr(GsDnf5SessionManager) session_manager = NULL; + g_autoptr(GsDnf5RpmRpm) rpm_proxy = NULL; + g_autoptr(GsApp) progress_app = NULL; ++ GsAppList *progress_list = is_install ? NULL : list; + gboolean success; + + /* queue for install if installation needs the network */ @@ -3154,14 +3212,18 @@ index 000000000..bae3bde28 + else + g_ptr_array_add (packages, g_strdup (source)); + gs_app_list_add (used_apps, app); -+ if (progress_app == NULL) ++ if (progress_list == NULL && progress_app == NULL) + progress_app = g_object_ref (app); + } + } else if (gs_app_has_quirk (app, GS_APP_QUIRK_IS_PROXY)) { + GsAppList *related = gs_app_get_related (app); ++ gboolean is_os_update = gs_app_get_special_kind (app) == GS_APP_SPECIAL_KIND_OS_UPDATE; + for (guint j = 0; j < gs_app_list_length (related); j++) { + GsApp *rel_app = gs_app_list_index (related, j); -+ if (gs_app_has_management_plugin (rel_app, plugin)) { ++ /* add only updatable packages into the list when it's an OS Update, otherwise ++ dnf5 claims "Packages for argument '$pkgname' available, but not installed." */ ++ if (gs_app_has_management_plugin (rel_app, plugin) && (!is_install || !is_os_update || ++ gs_app_get_state (rel_app) == GS_APP_STATE_UPDATABLE)) { + const gchar *source = gs_app_get_default_source (rel_app); + if (source != NULL) { + GFile *local_file = gs_app_get_local_file (rel_app); @@ -3173,7 +3235,7 @@ index 000000000..bae3bde28 + } + } + } -+ if (progress_app == NULL) ++ if (progress_list == NULL && progress_app == NULL) + progress_app = g_object_ref (app); + } + } @@ -3244,13 +3306,16 @@ index 000000000..bae3bde28 + cancellable, + error); + } else if (success) { ++ /* ignore package list for update, it's an offline action, which should update ++ everything possible, not only a specific package */ ++ const gchar * const all_packages[2] = { NULL, NULL }; + success = gs_dnf5_rpm_rpm_call_upgrade_sync (rpm_proxy, -+ (const gchar * const *) packages->pdata, ++ all_packages, + g_variant_builder_end (options_builder), + cancellable, + error); + } -+ success = success && gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, ++ success = success && gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, progress_list, + is_install ? GS_DNF5_TRANSACTION_FLAG_NONE : GS_DNF5_TRANSACTION_FLAG_OFFLINE, + NULL, cancellable, error); + if (success && !is_install) { @@ -3296,8 +3361,13 @@ index 000000000..bae3bde28 + } else { + gs_dnf5_convert_error (error); + -+ if (error != NULL && *error != NULL) -+ gs_dnf5_report_error (self, event_callback, event_user_data, *error, interactive); ++ if (error != NULL && *error != NULL) { ++ GsApp *app = NULL; ++ if (gs_app_list_length (list) == 1) ++ app = gs_app_list_index (list, 0); ++ ++ gs_dnf5_report_error (self, event_callback, event_user_data, app, *error, interactive); ++ } + } + + for (guint i = 0; i < gs_app_list_length (used_apps); i++) { @@ -3505,7 +3575,7 @@ index 000000000..bae3bde28 + g_variant_builder_end (options_builder), + cancellable, + &local_error); -+ success = success && gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, GS_DNF5_TRANSACTION_FLAG_NONE, NULL, cancellable, &local_error); ++ success = success && gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, NULL, GS_DNF5_TRANSACTION_FLAG_NONE, NULL, cancellable, &local_error); + } else { + gs_dnf5_convert_error (&local_error); + g_prefix_error_literal (&local_error, "Failed to create Rpm proxy: "); @@ -3517,8 +3587,12 @@ index 000000000..bae3bde28 + if (success) { + gs_dnf5_mark_session_needs_reset (self); + } else { ++ GsApp *app = NULL; ++ if (gs_app_list_length (data->apps) == 1) ++ app = gs_app_list_index (data->apps, 0); ++ + gs_dnf5_convert_error (&local_error); -+ gs_dnf5_report_error (self, data->event_callback, data->event_user_data, ++ gs_dnf5_report_error (self, data->event_callback, data->event_user_data, app, + local_error, (data->flags & GS_PLUGIN_UNINSTALL_APPS_FLAGS_INTERACTIVE) != 0); + } + @@ -4088,7 +4162,7 @@ index 000000000..bae3bde28 + error); + + if (success) { -+ success = gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, GS_DNF5_TRANSACTION_FLAG_OFFLINE, NULL, cancellable, error); ++ success = gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, NULL, GS_DNF5_TRANSACTION_FLAG_OFFLINE, NULL, cancellable, error); + + if (success && !download_only) { + g_autofree gchar *op_error_msg = NULL; @@ -4139,7 +4213,7 @@ index 000000000..bae3bde28 + } else { + gs_app_set_state (data->app, GS_APP_STATE_AVAILABLE); + gs_dnf5_convert_error (&local_error); -+ gs_dnf5_report_error (self, data->event_callback, data->event_user_data, ++ gs_dnf5_report_error (self, data->event_callback, data->event_user_data, data->app, + local_error, (data->flags & GS_PLUGIN_DOWNLOAD_UPGRADE_FLAGS_INTERACTIVE) != 0); + g_task_return_error (task, g_steal_pointer (&local_error)); + } diff --git a/gnome-software.spec b/gnome-software.spec index 32061b0..abe7752 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -29,7 +29,7 @@ Name: gnome-software Version: 49~alpha -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -324,7 +324,4 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/gtk-doc/html/gnome-software/ %changelog -* Wed Jul 23 2025 Fedora Release Engineering - 49~alpha-2 -- Rebuilt for https://fedoraproject.org/wiki/Fedora_43_Mass_Rebuild - %autochangelog From 06b236a7381b97d04c1cb6fa5e829582bbb24dd2 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 1 Aug 2025 09:54:42 +0200 Subject: [PATCH 149/163] Update to 49.beta --- 0001-dnf5-plugin.patch | 4 ++-- gnome-software.spec | 9 ++++++--- sources | 2 +- 3 files changed, 9 insertions(+), 6 deletions(-) diff --git a/0001-dnf5-plugin.patch b/0001-dnf5-plugin.patch index c6cf3dc..c2353ab 100644 --- a/0001-dnf5-plugin.patch +++ b/0001-dnf5-plugin.patch @@ -1,4 +1,4 @@ -at commit f78a6ba2af27d06c77a052e7499422da22c2cd06 +at commit 238692b2cfb9cf3db85e1a0b2df369da97d7c639 Date: Fri Jul 25 11:23:46 2025 +0200 diff --git a/meson_options.txt b/meson_options.txt @@ -5670,7 +5670,7 @@ index 71aa486e2..d3e909dee 100644 plugins/epiphany/gs-plugin-epiphany.c plugins/epiphany/org.gnome.Software.Plugin.Epiphany.metainfo.xml.in diff --git a/src/meson.build b/src/meson.build -index 43e1b58e9..e8af8b058 100644 +index f8b918539..7df81d130 100644 --- a/src/meson.build +++ b/src/meson.build @@ -245,7 +245,7 @@ if get_option('fwupd') diff --git a/gnome-software.spec b/gnome-software.spec index abe7752..46397ad 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -28,8 +28,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 49~alpha -Release: 3%{?dist} +Version: 49~beta +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -83,6 +83,7 @@ BuildRequires: pkgconfig(rpm-ostree-1) %endif BuildRequires: pkgconfig(sysprof-capture-4) BuildRequires: pkgconfig(xmlb) >= %{libxmlb_version} +BuildRequires: systemd Requires: appstream-data Requires: appstream%{?_isa} >= %{appstream_version} @@ -284,7 +285,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance-license.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_provenance.so %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_repos.so -%{_sysconfdir}/xdg/autostart/org.gnome.Software.desktop %if %{with webapps} %dir %{_datadir}/swcatalog %dir %{_datadir}/swcatalog/xml @@ -314,6 +314,9 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rpm-ostree.so %endif +%{_datadir}/dbus-1/services/org.gnome.Software.service +%{_userunitdir}/gnome-software.service + %files devel %{_libdir}/pkgconfig/gnome-software.pc %dir %{_includedir}/gnome-software diff --git a/sources b/sources index dc17852..f212fbd 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-49.alpha.tar.xz) = 7616e9f3969b73651c502874ab20f78390b7284ba289451d68847e9afe47f306ef514f46fd633bc99440d98154329d2872237ffb73ae47222ab1d6273ae78b3d +SHA512 (gnome-software-49.beta.tar.xz) = 9cb6d67216193840b2661871ef43da5e726a284d1164781f13423ee8dd86359334f199efc29f4b3a0b3eddfa8a3811d7dd38cd412fa53aaebb2e1c35ddc1f9df From 7fb63f649d3ade06860bf6fce2e8a0537b482a73 Mon Sep 17 00:00:00 2001 From: Adam Williamson Date: Fri, 1 Aug 2025 12:08:46 -0700 Subject: [PATCH 150/163] Move the user service file to the main package In the 49-beta bump, this new file was inadvertently put into the rpm-ostree subpackage, it doesn't make any sense for it to be there. --- gnome-software.spec | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 46397ad..198e7c9 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -29,7 +29,7 @@ Name: gnome-software Version: 49~beta -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -299,6 +299,7 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_datadir}/glib-2.0/schemas/org.gnome.software-fedora.gschema.override %{_libexecdir}/gnome-software-cmd %{_libexecdir}/gnome-software-restarter +%{_userunitdir}/gnome-software.service %if %{with dkms} %{_datadir}/polkit-1/actions/org.gnome.software.dkms-helper.policy @@ -314,9 +315,6 @@ desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %{_libdir}/gnome-software/plugins-%{gs_plugin_version}/libgs_plugin_rpm-ostree.so %endif -%{_datadir}/dbus-1/services/org.gnome.Software.service -%{_userunitdir}/gnome-software.service - %files devel %{_libdir}/pkgconfig/gnome-software.pc %dir %{_includedir}/gnome-software From e4f244856b78751a56f757d91d247602862429d0 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 11 Aug 2025 17:10:38 +0200 Subject: [PATCH 151/163] dnf5-pugin: Use 'interactive' option, where supported - dnf5-plugin: Add support to provide update history --- 0001-dnf5-plugin.patch | 940 +++++++++++++++++++++++++++++++++++++---- gnome-software.spec | 5 +- 2 files changed, 859 insertions(+), 86 deletions(-) diff --git a/0001-dnf5-plugin.patch b/0001-dnf5-plugin.patch index c2353ab..3e9a13f 100644 --- a/0001-dnf5-plugin.patch +++ b/0001-dnf5-plugin.patch @@ -1,5 +1,5 @@ -at commit 238692b2cfb9cf3db85e1a0b2df369da97d7c639 -Date: Fri Jul 25 11:23:46 2025 +0200 +at commit 8a1f0ca6564157dd688c84ffd25af9747c1e038e +Date: Mon Aug 11 17:07:06 2025 +0200 diff --git a/meson_options.txt b/meson_options.txt index cd49cf529..27fa15e8b 100644 @@ -610,10 +610,10 @@ index 000000000..5d522468c +G_END_DECLS diff --git a/plugins/dnf5/gs-plugin-dnf5.c b/plugins/dnf5/gs-plugin-dnf5.c new file mode 100644 -index 000000000..fefad6961 +index 000000000..88d7e25d8 --- /dev/null +++ b/plugins/dnf5/gs-plugin-dnf5.c -@@ -0,0 +1,3823 @@ +@@ -0,0 +1,4275 @@ +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- + * vi:set noexpandtab tabstop=8 shiftwidth=8: + * @@ -642,10 +642,15 @@ index 000000000..fefad6961 + +#include "gs-plugin-dnf5.h" + ++#include "../packagekit/gs-markdown.h" ++ +#define GS_DNF5_RELEASEVER_DEFAULT NULL +#define GS_DNF5_INTERFACE_RPM_DNF "org.rpm.dnf.v0" +#define GS_DNF5_OBJECT_PATH_RPM_DNF "/org/rpm/dnf/v0" + ++#define GS_DNF5_ADVISORIES_KEY "gs-dnf5::advisories" ++#define GS_DNF5_CHANGELOGS_KEY "gs-dnf5::changelogs" ++ +/* for how long a session can be left opened until it's auto-closed */ +#define GS_SESSION_LIFETIME_SECS (5 * 60) + @@ -1302,8 +1307,15 @@ index 000000000..fefad6961 + gs_app_set_state (app, state); +} + ++typedef enum { ++ GS_DNF5_READ_PACKAGE_FLAG_NONE = 0, ++ GS_DNF5_READ_PACKAGE_FLAG_CAN_CACHED = 1 << 0, ++ GS_DNF5_READ_PACKAGE_FLAG_CHANGELOGS = 1 << 1 ++} GsDnf5ReadPackageFlags; ++ +static void +gs_dnf5_update_app_changelogs (GsApp *app, ++ GsDnf5ReadPackageFlags flags, + GVariantDict *dict) +{ + GVariantIter iter; @@ -1351,43 +1363,33 @@ index 000000000..fefad6961 + g_variant_unref (child); + } + -+ if (changes != NULL) -+ gs_app_set_update_details_text (app, changes->str); ++ if (changes != NULL) { ++ if ((flags & GS_DNF5_READ_PACKAGE_FLAG_CHANGELOGS) != 0) ++ gs_app_set_update_details_text (app, changes->str); ++ else ++ gs_app_set_metadata (app, GS_DNF5_CHANGELOGS_KEY, changes->str); ++ } +} + -+typedef struct { -+ GsAppList *list; -+ GsAppState set_state; -+ GHashTable *nevra_to_app; /* (nullable): gchar *nevra ~> GsApp * */ -+ GHashTable *replaces; /* (nullable): GINT_TO_POINTER(pkg-id) ~> gchar *old_version */ -+ GHashTable *used_replaces; /* (nullable): GINT_TO_POINTER(pkg-id) ~> NULL */ -+ gboolean cover_unused_replaces; -+} ReadPackageData; -+ -+static gboolean -+gs_dnf5_read_package_cb (GsPluginDnf5 *self, -+ GVariant *package_array, -+ gpointer user_data, -+ GCancellable *cancellable, -+ GError **error) ++static GsApp * /* (transfer full) */ ++gs_dnf5_read_package_from_dict (GsPluginDnf5 *self, ++ GVariantDict *dict, ++ GsDnf5ReadPackageFlags flags, ++ GsAppState set_state) +{ -+ ReadPackageData *rpd = user_data; -+ GsAppList *list = rpd->list; -+ GHashTable *nevra_to_app = rpd->nevra_to_app; -+ g_autofree gchar *name = NULL; + g_autoptr(GsApp) app = NULL; -+ g_autoptr(GVariantDict) dict = NULL; + g_autoptr(GVariant) value = NULL; ++ g_autofree gchar *name = NULL; + -+ dict = g_variant_dict_new (package_array); -+ -+ value = g_variant_dict_lookup_value (dict, "name", G_VARIANT_TYPE_STRING); -+ if (value != NULL) { -+ const gchar *name_const = g_variant_get_string (value, NULL); -+ app = gs_plugin_cache_lookup (GS_PLUGIN (self), name_const); -+ if (app == NULL) -+ name = g_strdup (name_const); -+ g_clear_pointer (&value, g_variant_unref); ++ if ((flags & GS_DNF5_READ_PACKAGE_FLAG_CAN_CACHED) != 0) { ++ value = g_variant_dict_lookup_value (dict, "name", G_VARIANT_TYPE_STRING); ++ if (value != NULL) { ++ const gchar *name_const = g_variant_get_string (value, NULL); ++ app = gs_plugin_cache_lookup (GS_PLUGIN (self), name_const); ++ if (app == NULL) ++ name = g_strdup (name_const); ++ g_clear_pointer (&value, g_variant_unref); ++ } + } + + if (app == NULL) { @@ -1414,21 +1416,58 @@ index 000000000..fefad6961 + g_clear_pointer (&value, g_variant_unref); + } + -+ gs_plugin_cache_add (GS_PLUGIN (self), name, app); ++ value = g_variant_dict_lookup_value (dict, "buildtime", G_VARIANT_TYPE_UINT64); ++ if (value != NULL) { ++ gs_app_set_install_date (app, (gint64) g_variant_get_uint64 (value)); ++ g_clear_pointer (&value, g_variant_unref); ++ } ++ ++ if ((flags & GS_DNF5_READ_PACKAGE_FLAG_CAN_CACHED) != 0) ++ gs_plugin_cache_add (GS_PLUGIN (self), name, app); + } + -+ gs_dnf5_update_app_changelogs (app, dict); -+ gs_dnf5_update_app_state (app, rpd->set_state, dict); ++ gs_dnf5_update_app_changelogs (app, flags, dict); ++ gs_dnf5_update_app_state (app, set_state, dict); + -+ if (rpd->set_state == GS_APP_STATE_UPDATABLE) { ++ if (set_state == GS_APP_STATE_UPDATABLE) { + gs_dnf5_app_set_version (dict, app, gs_app_set_update_version); + gs_app_add_quirk (app, GS_APP_QUIRK_NEEDS_REBOOT); + } else { + gs_dnf5_app_set_version (dict, app, gs_app_set_version); + } + ++ return g_steal_pointer (&app); ++} ++ ++typedef struct { ++ GsAppList *list; ++ GsAppState set_state; ++ GHashTable *nevra_to_app; /* (nullable): gchar *nevra ~> GsApp * */ ++ GHashTable *replaces; /* (nullable): GINT_TO_POINTER(pkg-id) ~> gchar *old_version */ ++ GHashTable *used_replaces; /* (nullable): GINT_TO_POINTER(pkg-id) ~> NULL */ ++ gboolean cover_unused_replaces; ++ gint64 timestamp; ++} ReadPackageData; ++ ++static gboolean ++gs_dnf5_read_package_cb (GsPluginDnf5 *self, ++ GVariant *package_array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ ReadPackageData *rpd = user_data; ++ GsAppList *list = rpd->list; ++ GHashTable *nevra_to_app = rpd->nevra_to_app; ++ g_autoptr(GsApp) app = NULL; ++ g_autoptr(GVariantDict) dict = NULL; ++ ++ dict = g_variant_dict_new (package_array); ++ ++ app = gs_dnf5_read_package_from_dict (self, dict, GS_DNF5_READ_PACKAGE_FLAG_CAN_CACHED | GS_DNF5_READ_PACKAGE_FLAG_CHANGELOGS, rpd->set_state); ++ + if (nevra_to_app != NULL) { -+ g_clear_pointer (&value, g_variant_unref); ++ g_autoptr(GVariant) value = NULL; + value = g_variant_dict_lookup_value (dict, "nevra", G_VARIANT_TYPE_STRING); + if (value != NULL) { + const gchar *nevra_const = g_variant_get_string (value, NULL); @@ -1600,6 +1639,7 @@ index 000000000..fefad6961 + g_variant_builder_add (attrs_builder, "s", "url"); + g_variant_builder_add (attrs_builder, "s", "license"); + g_variant_builder_add (attrs_builder, "s", "description"); ++ g_variant_builder_add (attrs_builder, "s", "buildtime"); + g_variant_builder_add (attrs_builder, "s", "changelogs"); + + return g_variant_builder_end (attrs_builder); @@ -1633,6 +1673,7 @@ index 000000000..fefad6961 + gchar *key_id; + GsPluginDnf5 *self; /* (owned) */ + GWeakRef repo_proxy_weakref; /* GsDnf5RpmRepo */ ++ gboolean interactive; +} QuestionData; + +static void @@ -1658,11 +1699,22 @@ index 000000000..fefad6961 + + repo_proxy = g_weak_ref_get (&data->repo_proxy_weakref); + if (repo_proxy != NULL) { ++ g_autoptr(GVariantBuilder) options_builder = NULL; + gboolean confirmed; + + confirmed = gs_plugin_ask_untrusted (GS_PLUGIN (data->self), data->title, data->msg, data->details, data->accept_label); + -+ gs_dnf5_rpm_repo_call_confirm_key (repo_proxy, data->key_id, confirmed, NULL, gs_dnf5_confirm_key_response_cb, NULL); ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "interactive", ++ g_variant_new_boolean (data->interactive)); ++ ++ gs_dnf5_rpm_repo_call_confirm_key_with_options (repo_proxy, ++ data->key_id, ++ confirmed, ++ g_variant_builder_end (options_builder), ++ NULL, ++ gs_dnf5_confirm_key_response_cb, ++ NULL); + } + + return G_SOURCE_REMOVE; @@ -1672,6 +1724,7 @@ index 000000000..fefad6961 + GsPluginDnf5 *self; /* (not owned) */ + const gchar *session_path; /* (not owned) */ + GsDnf5RpmRepo *repo_proxy; /* (not owned) */ ++ gboolean interactive; +} RepoKeyImportData; + +static void @@ -1746,6 +1799,7 @@ index 000000000..fefad6961 + data->accept_label = g_strdup (_("_Import Key")); + data->key_id = g_strdup (arg_key_id); + data->self = g_object_ref (repo_key_import_data->self); ++ data->interactive = repo_key_import_data->interactive; + g_weak_ref_init (&data->repo_proxy_weakref, repo_key_import_data->repo_proxy); + + g_idle_add_full (G_PRIORITY_HIGH_IDLE, gs_dnf5_ask_question_idle_cb, data, (GDestroyNotify) question_data_free); @@ -1829,7 +1883,8 @@ index 000000000..fefad6961 + GS_DNF5_TRANSACTION_FLAG_NONE = 0, + GS_DNF5_TRANSACTION_FLAG_OFFLINE = 1 << 0, + GS_DNF5_TRANSACTION_FLAG_RESOLVE_ONLY = 1 << 1, -+ GS_DNF5_TRANSACTION_FLAG_DISALLOW_ERASING = 1 << 2 /* negative flag, to not have it everywhere */ ++ GS_DNF5_TRANSACTION_FLAG_DISALLOW_ERASING = 1 << 2, /* negative flag, to not have it everywhere */ ++ GS_DNF5_TRANSACTION_FLAG_INTERACTIVE = 1 << 3 +} GsDnf5TransactionFlags; + +static gboolean @@ -1855,6 +1910,7 @@ index 000000000..fefad6961 + gulong repo_key_import_id; + gulong cancellable_id = 0; + guint result = 0; ++ gboolean interactive = (flags & GS_DNF5_TRANSACTION_FLAG_INTERACTIVE) != 0; + gboolean success; + + base_proxy = gs_dnf5_base_proxy_new_sync (self->connection, @@ -1906,6 +1962,7 @@ index 000000000..fefad6961 + repo_key_import_data.self = self; + repo_key_import_data.session_path = session_path; + repo_key_import_data.repo_proxy = repo_proxy; ++ repo_key_import_data.interactive = interactive; + repo_key_import_id = g_signal_connect (base_proxy, "repo_key_import_request", + G_CALLBACK (gs_dnf5_repo_key_import_request_cb), &repo_key_import_data); + @@ -1958,6 +2015,8 @@ index 000000000..fefad6961 + g_variant_builder_add (options_builder, "{sv}", "offline", + g_variant_new_boolean (TRUE)); + } ++ g_variant_builder_add (options_builder, "{sv}", "interactive", ++ g_variant_new_boolean (interactive)); + + run_cancellable = g_cancellable_new (); + if (cancellable != NULL) { @@ -2231,6 +2290,91 @@ index 000000000..fefad6961 + return TRUE; +} + ++static gboolean ++gs_dnf5_read_history_packages_cb (GsPluginDnf5 *self, ++ GVariant *array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ ReadPackageData *rpd = user_data; ++ g_autoptr(GsApp) app = NULL; ++ g_autoptr(GVariantDict) dict = NULL; ++ ++ dict = g_variant_dict_new (array); ++ ++ app = gs_dnf5_read_package_from_dict (self, dict, GS_DNF5_READ_PACKAGE_FLAG_NONE, rpd->set_state); ++ if (app != NULL) { ++ g_autoptr(GVariant) value = NULL; ++ value = g_variant_dict_lookup_value (dict, "original_evr", G_VARIANT_TYPE_STRING); ++ if (value != NULL) { ++ const gchar *str = g_variant_get_string (value, NULL); ++ if (str != NULL) { ++ const gchar *delim = strchr (str, ':'); ++ /* skip the epoch, if set, because it's skipped in the current version too */ ++ gs_app_set_version (app, delim ? delim + 1 : str); ++ } ++ } ++ ++ g_clear_pointer (&value, g_variant_unref); ++ value = g_variant_dict_lookup_value (dict, "advisories", G_VARIANT_TYPE_ARRAY); ++ if (value != NULL) { ++ gs_app_set_metadata_variant (app, GS_DNF5_ADVISORIES_KEY, value); ++ } ++ ++ /* do not know the exact change date/time, it uses the build time and the one from the settings as a fallback */ ++ if (!gs_app_get_install_date (app)) ++ gs_app_set_install_date (app, rpd->timestamp); ++ gs_app_list_add (rpd->list, app); ++ } ++ ++ return TRUE; ++} ++ ++static gboolean ++gs_dnf5_read_history_items_cb (GsPluginDnf5 *self, ++ GVariant *array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ struct _known_changes { ++ const gchar *type_of_change; ++ GsAppState set_state; ++ } known_changes[] = { ++ { "installed", GS_APP_STATE_UPDATABLE }, ++ { "removed", GS_APP_STATE_UNAVAILABLE }, ++ { "upgraded", GS_APP_STATE_UPDATABLE }, ++ { "downgraded", GS_APP_STATE_UPDATABLE } ++ }; ++ ReadPackageData *rpd = user_data; ++ g_autoptr(GVariant) value = NULL; ++ const gchar *type_of_change; ++ guint ii; ++ ++ value = g_variant_get_child_value (array, 0); ++ if (value == NULL) ++ return TRUE; ++ ++ type_of_change = g_variant_get_string (value, NULL); ++ if (!type_of_change) ++ return TRUE; ++ ++ for (ii = 0; ii < G_N_ELEMENTS (known_changes); ii++) { ++ if (g_strcmp0 (type_of_change, known_changes[ii].type_of_change) == 0) { ++ g_autoptr(GVariant) packages = NULL; ++ packages = g_variant_get_child_value (array, 1); ++ if (packages != NULL) { ++ rpd->set_state = known_changes[ii].set_state; ++ gs_dnf5_foreach_item (self, packages, gs_dnf5_read_history_packages_cb, rpd, cancellable, error); ++ } ++ break; ++ } ++ } ++ ++ return TRUE; ++} ++ +/* Run in @worker. */ +static void +gs_dnf5_list_apps_thread_cb (GTask *task, @@ -2240,6 +2384,7 @@ index 000000000..fefad6961 +{ + GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); + GsAppQueryTristate is_for_update = GS_APP_QUERY_TRISTATE_UNSET; ++ GsAppQueryTristate is_historical_update = GS_APP_QUERY_TRISTATE_UNSET; + const AsComponentKind *component_kinds = NULL; + GsPluginListAppsData *data = task_data; + const gchar * const *provides_files = NULL; @@ -2256,16 +2401,19 @@ index 000000000..fefad6961 + + if (data->query != NULL) { + is_for_update = gs_app_query_get_is_for_update (data->query); ++ is_historical_update = gs_app_query_get_is_historical_update (data->query); + component_kinds = gs_app_query_get_component_kinds (data->query); + provides_files = gs_app_query_get_provides_files (data->query); + provides_type = gs_app_query_get_provides (data->query, &provides_tag); + } + + if ((is_for_update == GS_APP_QUERY_TRISTATE_UNSET && ++ is_historical_update == GS_APP_QUERY_TRISTATE_UNSET && + component_kinds == NULL && + provides_tag == NULL && + provides_files == NULL) || + is_for_update == GS_APP_QUERY_TRISTATE_FALSE || ++ is_historical_update == GS_APP_QUERY_TRISTATE_FALSE || + (component_kinds != NULL && !gs_component_kind_array_contains (component_kinds, AS_COMPONENT_KIND_REPOSITORY)) || + gs_app_query_get_n_properties_set (data->query) != 1) { + g_task_return_new_error (task, G_IO_ERROR, G_IO_ERROR_NOT_SUPPORTED, @@ -2421,6 +2569,57 @@ index 000000000..fefad6961 + gs_dnf5_convert_error (&local_error); + g_prefix_error_literal (&local_error, "Failed to call Rpm::list: "); + } ++ } else if (is_historical_update == GS_APP_QUERY_TRISTATE_TRUE) { ++ g_autoptr(GsDnf5History) history_proxy = NULL; ++ ++ history_proxy = gs_dnf5_history_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ &local_error); ++ success = history_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to create History proxy: "); ++ } ++ ++ if (success) { ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariant) result = NULL; ++ g_autoptr(GSettings) settings; ++ gint64 timestamp; ++ ++ /* use the option the GUI part uses */ ++ settings = g_settings_new ("org.gnome.software"); ++ timestamp = g_settings_get_int64 (settings, "install-timestamp"); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "since", ++ g_variant_new_int64 (timestamp)); ++ g_variant_builder_add (options_builder, "{sv}", "package_attrs", ++ gs_dnf5_dup_package_attrs ()); ++ ++ success = gs_dnf5_history_call_recent_changes_sync (history_proxy, ++ g_variant_builder_end (options_builder), ++ &result, ++ cancellable, ++ &local_error); ++ ++ if (success) { ++ ReadPackageData rpd = { 0, }; ++ ++ rpd.list = list; ++ rpd.set_state = GS_APP_STATE_UNKNOWN; ++ rpd.nevra_to_app = NULL; ++ rpd.timestamp = timestamp; ++ ++ success = gs_dnf5_foreach_item (self, result, gs_dnf5_read_history_items_cb, &rpd, cancellable, &local_error); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to call recent_changes: "); ++ } ++ } + } else if (gs_component_kind_array_contains (component_kinds, AS_COMPONENT_KIND_REPOSITORY)) { + g_autoptr(GsDnf5RpmRepo) repo_proxy = NULL; + @@ -2867,6 +3066,87 @@ index 000000000..fefad6961 + return TRUE; +} + ++static gboolean ++gs_dnf5_add_advisories_cb (GsPluginDnf5 *self, ++ GVariant *value, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ GHashTable *advisories = user_data; /* gchar *name ~> gchar *description */ ++ g_autofree gchar *str = NULL; ++ ++ str = g_variant_dup_string (value, NULL); ++ if (str != NULL && *str != '\0') ++ g_hash_table_insert (advisories, g_steal_pointer (&str), NULL); ++ ++ return TRUE; ++} ++ ++static gboolean ++gs_dnf5_gather_update_description_for_advisory_cb (GsPluginDnf5 *self, ++ GVariant *value, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ GHashTable *advisories = user_data; /* gchar *name ~> gchar *description */ ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) name = NULL; ++ g_autoptr(GVariant) description = NULL; ++ const gchar *name_str, *description_str; ++ ++ dict = g_variant_dict_new (value); ++ ++ name = g_variant_dict_lookup_value (dict, "name", G_VARIANT_TYPE_STRING); ++ if (name == NULL) ++ return TRUE; ++ ++ description = g_variant_dict_lookup_value (dict, "description", G_VARIANT_TYPE_STRING); ++ if (description == NULL) ++ return TRUE; ++ ++ name_str = g_variant_get_string (name, NULL); ++ description_str = g_variant_get_string (description, NULL); ++ ++ if (name_str != NULL && description_str != NULL && *description_str != '\0') ++ g_hash_table_replace (advisories, g_strdup (name_str), g_strdup (description_str)); ++ ++ return TRUE; ++} ++ ++typedef struct _AdvisoryUpdateDescriptionData { ++ GHashTable *advisories; /* gchar *name ~> gchar *description */ ++ GString *description; ++} AdvisoryUpdateDescriptionData; ++ ++static gboolean ++gs_dnf5_refine_update_description_from_advisory_cb (GsPluginDnf5 *self, ++ GVariant *value, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ AdvisoryUpdateDescriptionData *adv_data = user_data; ++ const gchar *name = NULL; ++ ++ name = g_variant_get_string (value, NULL); ++ if (name != NULL && *name != '\0') { ++ const gchar *description = g_hash_table_lookup (adv_data->advisories, name); ++ if (description != NULL && *description != '\0') { ++ if (adv_data->description == NULL) { ++ adv_data->description = g_string_new (description); ++ } else { ++ g_string_append (adv_data->description, "\n\n"); ++ g_string_append (adv_data->description, description); ++ } ++ } ++ } ++ ++ return TRUE; ++} ++ ++ +/* Run in @worker. */ +static void +gs_dnf5_refine_thread_cb (GTask *task, @@ -2891,6 +3171,7 @@ index 000000000..fefad6961 + GsApp *app = gs_app_list_index (data->list, i); + if (!gs_app_has_quirk (app, GS_APP_QUIRK_IS_WILDCARD) && ( + gs_app_get_state (app) == GS_APP_STATE_UNKNOWN || ++ (data->require_flags & GS_PLUGIN_REFINE_REQUIRE_FLAGS_UPDATE_DETAILS) != 0 || + ((data->require_flags & GS_PLUGIN_REFINE_REQUIRE_FLAGS_SIZE_DATA) != 0 && + gs_app_list_length (gs_app_get_related (app)) == 0))) { + if (gs_app_get_default_source (app) != NULL && @@ -2926,7 +3207,127 @@ index 000000000..fefad6961 + g_prefix_error_literal (&local_error, "Failed to create Rpm proxy: "); + } + -+ if (success) { ++ if (success && (data->require_flags & GS_PLUGIN_REFINE_REQUIRE_FLAGS_UPDATE_DETAILS) != 0) { ++ g_autoptr(GHashTable) advisories = NULL; /* gchar *name ~> gchar *description */ ++ GHashTableIter iter; ++ gpointer value = NULL; ++ ++ data->require_flags = data->require_flags & (~GS_PLUGIN_REFINE_REQUIRE_FLAGS_UPDATE_DETAILS); ++ ++ advisories = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_free); ++ ++ g_hash_table_iter_init (&iter, apps); ++ while (success && g_hash_table_iter_next (&iter, NULL, &value)) { ++ GsApp *app = value; ++ GVariant *advisories_array; ++ ++ advisories_array = gs_app_get_metadata_variant (app, GS_DNF5_ADVISORIES_KEY); ++ if (advisories_array != NULL) ++ success = gs_dnf5_foreach_item (self, advisories_array, gs_dnf5_add_advisories_cb, advisories, cancellable, &local_error); ++ } ++ ++ if (success && g_hash_table_size (advisories) > 0) { ++ g_autoptr(GsDnf5Advisory) advisory_proxy = NULL; ++ ++ advisory_proxy = gs_dnf5_advisory_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ &local_error); ++ success = advisory_proxy != NULL; ++ ++ if (success) { ++ g_autoptr(GVariantBuilder) adv_options_builder = NULL; ++ g_autoptr(GVariantBuilder) attrs_builder = NULL; ++ g_autoptr(GVariantBuilder) names_builder = NULL; ++ g_autoptr(GVariant) adv_result = NULL; ++ gpointer key = NULL; ++ ++ attrs_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_variant_builder_add (attrs_builder, "s", "name"); ++ g_variant_builder_add (attrs_builder, "s", "description"); ++ ++ names_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_hash_table_iter_init (&iter, advisories); ++ while (g_hash_table_iter_next (&iter, &key, NULL)) { ++ const gchar *name = key; ++ g_variant_builder_add (names_builder, "s", name); ++ } ++ ++ adv_options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (adv_options_builder, "{sv}", "advisory_attrs", ++ g_variant_builder_end (attrs_builder)); ++ g_variant_builder_add (adv_options_builder, "{sv}", "names", ++ g_variant_builder_end (names_builder)); ++ g_variant_builder_add (adv_options_builder, "{sv}", "availability", ++ g_variant_new_string ("all")); ++ ++ success = gs_dnf5_advisory_call_list_sync (advisory_proxy, ++ g_variant_builder_end (adv_options_builder), ++ &adv_result, ++ cancellable, ++ &local_error); ++ if (success) { ++ success = gs_dnf5_foreach_item (self, adv_result, ++ gs_dnf5_gather_update_description_for_advisory_cb, advisories, ++ cancellable, &local_error); ++ if (success) { ++ g_hash_table_iter_init (&iter, apps); ++ while (success && g_hash_table_iter_next (&iter, NULL, &value)) { ++ GsApp *app = value; ++ GVariant *advisories_array; ++ ++ advisories_array = gs_app_get_metadata_variant (app, GS_DNF5_ADVISORIES_KEY); ++ if (advisories_array != NULL) { ++ AdvisoryUpdateDescriptionData adv_data = { NULL, }; ++ adv_data.advisories = advisories; ++ adv_data.description = NULL; ++ ++ success = gs_dnf5_foreach_item (self, advisories_array, ++ gs_dnf5_refine_update_description_from_advisory_cb, ++ &adv_data, cancellable, &local_error); ++ ++ if (adv_data.description) { ++ g_autoptr(GsMarkdown) markdown = gs_markdown_new (GS_MARKDOWN_OUTPUT_PANGO); ++ g_autofree gchar *markup = gs_markdown_parse (markdown, adv_data.description->str); ++ if (markup != NULL && *markup != '\0') ++ gs_app_set_update_details_markup (app, markup); ++ else ++ gs_app_set_update_details_text (app, adv_data.description->str); ++ g_string_free (adv_data.description, TRUE); ++ } ++ } ++ } ++ ++ if (!success) ++ g_debug ("Failed to refine update description from advisory: %s", local_error->message); ++ } else { ++ g_debug ("Failed to gather update description for advisory: %s", local_error->message); ++ } ++ } else { ++ g_debug ("Failed to call Advisory::list: %s", local_error->message); ++ } ++ } else { ++ g_debug ("Failed to create Advisory proxy: %s", local_error->message); ++ } ++ } ++ ++ /* fallback to changelogs where advisory was not known */ ++ g_hash_table_iter_init (&iter, apps); ++ while (success && g_hash_table_iter_next (&iter, NULL, &value)) { ++ GsApp *app = value; ++ if (!gs_app_get_update_details_markup (app)) { ++ const gchar *changelogs = gs_app_get_metadata_item (app, GS_DNF5_CHANGELOGS_KEY); ++ if (changelogs != NULL && *changelogs != '\0') { ++ gs_app_set_update_details_text (app, changelogs); ++ gs_app_set_metadata (app, GS_DNF5_CHANGELOGS_KEY, NULL); ++ } ++ } ++ } ++ } ++ ++ if (success && data->require_flags != 0) { + g_autoptr(GVariantBuilder) attrs_builder = NULL; + g_autoptr(GVariantBuilder) options_builder = NULL; + g_autoptr(GVariantBuilder) patterns_builder = NULL; @@ -3041,6 +3442,7 @@ index 000000000..fefad6961 + GCancellable *cancellable) +{ + GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsPluginRefreshMetadataData *data = task_data; + g_autofree gchar *session_path = NULL; + g_autoptr(GsDnf5SessionManager) session_manager = NULL; + g_autoptr(GsDnf5Base) base_proxy = NULL; @@ -3068,16 +3470,23 @@ index 000000000..fefad6961 + g_prefix_error_literal (&local_error, "Failed to create Base proxy: "); + } + -+ if (success && GPOINTER_TO_INT (task_data) == 1) { ++ if (success && data->cache_age_secs < 60) { ++ g_autoptr(GVariantBuilder) options_builder = NULL; + g_autofree gchar *op_error_msg = NULL; + gboolean op_success = FALSE; + -+ success = gs_dnf5_base_call_clean_sync (base_proxy, -+ "expire-cache", -+ &op_success, -+ &op_error_msg, -+ cancellable, -+ &local_error); ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ ++ g_variant_builder_add (options_builder, "{sv}", "interactive", ++ g_variant_new_boolean ((data->flags & GS_PLUGIN_REFRESH_METADATA_FLAGS_INTERACTIVE) != 0)); ++ ++ success = gs_dnf5_base_call_clean_with_options_sync (base_proxy, ++ "expire-cache", ++ g_variant_builder_end (options_builder), ++ &op_success, ++ &op_error_msg, ++ cancellable, ++ &local_error); + if (!success) + g_debug ("Failed to call expire-cache: %s", local_error->message); + else if (!op_success) @@ -3130,9 +3539,9 @@ index 000000000..fefad6961 + + task = g_task_new (self, cancellable, callback, user_data); + g_task_set_source_tag (task, gs_plugin_dnf5_refresh_metadata_async); -+ /* no need to save whole structure, the seconds are not used at all, -+ thus make it only a flag whether to invalidate the cache or not first */ -+ g_task_set_task_data (task, GINT_TO_POINTER (cache_age_secs < 60 ? 1 : 0), NULL); ++ g_task_set_task_data (task, ++ gs_plugin_refresh_metadata_data_new (cache_age_secs, flags, event_callback, event_user_data), ++ (GDestroyNotify) gs_plugin_refresh_metadata_data_free); + + gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), + gs_dnf5_refresh_metadata_thread_cb, g_steal_pointer (&task)); @@ -3289,10 +3698,13 @@ index 000000000..fefad6961 + success = rpm_proxy != NULL; + if (success) { + g_autoptr(GVariantBuilder) options_builder = NULL; ++ GsDnf5TransactionFlags flags = interactive ? GS_DNF5_TRANSACTION_FLAG_INTERACTIVE : GS_DNF5_TRANSACTION_FLAG_NONE; + + g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); + + options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "interactive", ++ g_variant_new_boolean (interactive)); + + /* NULL-terminate the array, to be like strv */ + g_ptr_array_add (packages, NULL); @@ -3316,7 +3728,7 @@ index 000000000..fefad6961 + error); + } + success = success && gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, progress_list, -+ is_install ? GS_DNF5_TRANSACTION_FLAG_NONE : GS_DNF5_TRANSACTION_FLAG_OFFLINE, ++ flags | (is_install ? 0 : GS_DNF5_TRANSACTION_FLAG_OFFLINE), + NULL, cancellable, error); + if (success && !is_install) { + /* ensure the update is finished with the 'reboot' action */ @@ -3333,7 +3745,19 @@ index 000000000..fefad6961 + g_autofree gchar *op_error_msg = NULL; + gboolean op_success = FALSE; + -+ success = gs_dnf5_offline_call_set_finish_action_sync (offline_proxy, "reboot", &op_success, &op_error_msg, cancellable, error); ++ g_clear_pointer (&options_builder, g_variant_builder_unref); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "interactive", ++ g_variant_new_boolean (interactive)); ++ ++ success = gs_dnf5_offline_call_set_finish_action_with_options_sync (offline_proxy, ++ "reboot", ++ g_variant_builder_end (options_builder), ++ &op_success, ++ &op_error_msg, ++ cancellable, ++ error); + if (success && !op_success) { + success = FALSE; + if (op_error_msg != NULL) { @@ -3556,6 +3980,8 @@ index 000000000..fefad6961 + &local_error); + success = rpm_proxy != NULL; + if (success) { ++ GsDnf5TransactionFlags flags = (data->flags & GS_PLUGIN_UNINSTALL_APPS_FLAGS_INTERACTIVE) != 0 ? ++ GS_DNF5_TRANSACTION_FLAG_INTERACTIVE : GS_DNF5_TRANSACTION_FLAG_NONE; + g_autoptr(GVariantBuilder) options_builder = NULL; + + g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); @@ -3575,7 +4001,7 @@ index 000000000..fefad6961 + g_variant_builder_end (options_builder), + cancellable, + &local_error); -+ success = success && gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, NULL, GS_DNF5_TRANSACTION_FLAG_NONE, NULL, cancellable, &local_error); ++ success = success && gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, NULL, flags, NULL, cancellable, &local_error); + } else { + gs_dnf5_convert_error (&local_error); + g_prefix_error_literal (&local_error, "Failed to create Rpm proxy: "); @@ -3718,6 +4144,7 @@ index 000000000..fefad6961 +gs_dnf5_manage_repository_sync (GsPluginDnf5 *self, + GsApp *repository, + gboolean enable, ++ gboolean interactive, + GCancellable *cancellable, + GError **error) +{ @@ -3758,15 +4185,20 @@ index 000000000..fefad6961 + + if (success) { + const gchar *ids[2] = { NULL, NULL }; ++ g_autoptr(GVariantBuilder) options_builder = NULL; + + g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (repo_proxy), G_MAXINT); + + ids[0] = gs_app_get_id (repository); + ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "interactive", ++ g_variant_new_boolean (interactive)); ++ + if (enable) -+ success = gs_dnf5_rpm_repo_call_enable_sync (repo_proxy, ids, cancellable, error); ++ success = gs_dnf5_rpm_repo_call_enable_with_options_sync (repo_proxy, ids, g_variant_builder_end (options_builder), cancellable, error); + else -+ success = gs_dnf5_rpm_repo_call_disable_sync (repo_proxy, ids, cancellable, error); ++ success = gs_dnf5_rpm_repo_call_disable_with_options_sync (repo_proxy, ids, g_variant_builder_end (options_builder), cancellable, error); + + if (success) { + if (enable) @@ -3797,7 +4229,9 @@ index 000000000..fefad6961 + + assert_in_worker (self); + -+ if (gs_dnf5_manage_repository_sync (self, data->repository, TRUE, cancellable, &local_error)) { ++ if (gs_dnf5_manage_repository_sync (self, data->repository, TRUE, ++ (data->flags & GS_PLUGIN_MANAGE_REPOSITORY_FLAGS_INTERACTIVE) != 0, ++ cancellable, &local_error)) { + g_task_return_boolean (task, TRUE); + } else { + gs_dnf5_convert_error (&local_error); @@ -3848,7 +4282,9 @@ index 000000000..fefad6961 + + assert_in_worker (self); + -+ if (gs_dnf5_manage_repository_sync (self, data->repository, FALSE, cancellable, &local_error)) { ++ if (gs_dnf5_manage_repository_sync (self, data->repository, FALSE, ++ (data->flags & GS_PLUGIN_MANAGE_REPOSITORY_FLAGS_INTERACTIVE) != 0, ++ cancellable, &local_error)) { + g_task_return_boolean (task, TRUE); + } else { + gs_dnf5_convert_error (&local_error); @@ -4085,6 +4521,7 @@ index 000000000..fefad6961 + const gchar *releasever, + GsApp *progress_app, + gboolean download_only, ++ gboolean interactive, + GCancellable *cancellable, + GError **error) +{ @@ -4152,6 +4589,8 @@ index 000000000..fefad6961 + g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); + + options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "interactive", ++ g_variant_new_boolean (interactive)); + + success = gs_dnf5_reset_transaction_sync (self, session_path, rpm_proxy, cancellable, error); + @@ -4162,14 +4601,23 @@ index 000000000..fefad6961 + error); + + if (success) { -+ success = gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, NULL, GS_DNF5_TRANSACTION_FLAG_OFFLINE, NULL, cancellable, error); ++ GsDnf5TransactionFlags flags = interactive ? GS_DNF5_TRANSACTION_FLAG_INTERACTIVE : GS_DNF5_TRANSACTION_FLAG_NONE; ++ ++ success = gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, NULL, flags | GS_DNF5_TRANSACTION_FLAG_OFFLINE, NULL, cancellable, error); + + if (success && !download_only) { + g_autofree gchar *op_error_msg = NULL; + gboolean op_success = FALSE; + ++ g_clear_pointer (&options_builder, g_variant_builder_unref); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "interactive", ++ g_variant_new_boolean (interactive)); ++ + /* ensure the upgrade is finished with the 'reboot' action */ -+ success = gs_dnf5_offline_call_set_finish_action_sync (offline_proxy, "reboot", &op_success, &op_error_msg, cancellable, error); ++ success = gs_dnf5_offline_call_set_finish_action_with_options_sync (offline_proxy, "reboot", g_variant_builder_end (options_builder), ++ &op_success, &op_error_msg, cancellable, error); + if (success && !op_success) { + success = FALSE; + if (op_error_msg != NULL) { @@ -4207,7 +4655,9 @@ index 000000000..fefad6961 + + gs_app_set_state (data->app, GS_APP_STATE_DOWNLOADING); + -+ if (gs_dnf5_system_upgrade_sync (self, gs_app_get_version (data->app), data->app, TRUE, cancellable, &local_error)) { ++ if (gs_dnf5_system_upgrade_sync (self, gs_app_get_version (data->app), data->app, TRUE, ++ (data->flags & GS_PLUGIN_DOWNLOAD_UPGRADE_FLAGS_INTERACTIVE) != 0, ++ cancellable, &local_error)) { + gs_app_set_state (data->app, GS_APP_STATE_UPDATABLE); + g_task_return_boolean (task, TRUE); + } else { @@ -4275,7 +4725,9 @@ index 000000000..fefad6961 + + gs_app_set_state (data->app, GS_APP_STATE_PENDING_INSTALL); + -+ if (gs_dnf5_system_upgrade_sync (self, gs_app_get_version (data->app), data->app, FALSE, cancellable, &local_error)) { ++ if (gs_dnf5_system_upgrade_sync (self, gs_app_get_version (data->app), data->app, FALSE, ++ (data->flags & GS_PLUGIN_TRIGGER_UPGRADE_FLAGS_INTERACTIVE) != 0, ++ cancellable, &local_error)) { + gs_app_set_state (data->app, GS_APP_STATE_UPDATABLE); + g_task_return_boolean (task, TRUE); + } else { @@ -4465,17 +4917,19 @@ index 000000000..319d5843c +G_END_DECLS diff --git a/plugins/dnf5/meson.build b/plugins/dnf5/meson.build new file mode 100644 -index 000000000..6059a9da1 +index 000000000..12b2137e1 --- /dev/null +++ b/plugins/dnf5/meson.build -@@ -0,0 +1,39 @@ +@@ -0,0 +1,42 @@ +cargs = ['-DG_LOG_DOMAIN="GsDnf5"'] + +dnf5_generated = gnome.gdbus_codegen( + 'gs-dnf5-generated', + sources: [ 'org.rpm.dnf.v0.Advisory.xml', + 'org.rpm.dnf.v0.Base.xml', ++ 'org.rpm.dnf.v0.comps.Group.xml', + 'org.rpm.dnf.v0.Goal.xml', ++ 'org.rpm.dnf.v0.History.xml', + 'org.rpm.dnf.v0.Offline.xml', + 'org.rpm.dnf.v0.rpm.Repo.xml', + 'org.rpm.dnf.v0.rpm.Rpm.xml', @@ -4497,7 +4951,8 @@ index 000000000..6059a9da1 + dnf5_generated, + sources : [ + 'gs-dnf5-progress-helper.c', -+ 'gs-plugin-dnf5.c' ++ 'gs-plugin-dnf5.c', ++ '../packagekit/gs-markdown.c', + ], + include_directories : [ + include_directories('../..'), @@ -4622,10 +5077,10 @@ index 000000000..6aecee9fa + diff --git a/plugins/dnf5/org.rpm.dnf.v0.Base.xml b/plugins/dnf5/org.rpm.dnf.v0.Base.xml new file mode 100644 -index 000000000..dfdc1745a +index 000000000..e596e60b9 --- /dev/null +++ b/plugins/dnf5/org.rpm.dnf.v0.Base.xml -@@ -0,0 +1,153 @@ +@@ -0,0 +1,176 @@ + + @@ -4664,13 +5119,36 @@ index 000000000..dfdc1745a + + + ++ ++ ++ ++ ++ ++ ++ ++ + + @@ -4680,7 +5158,7 @@ index 000000000..dfdc1745a + + @@ -4883,7 +5365,7 @@ index 000000000..f1ba08953 + + ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ diff --git a/plugins/dnf5/org.rpm.dnf.v0.Offline.xml b/plugins/dnf5/org.rpm.dnf.v0.Offline.xml new file mode 100644 -index 000000000..083b5b17c +index 000000000..8d84c22aa --- /dev/null +++ b/plugins/dnf5/org.rpm.dnf.v0.Offline.xml -@@ -0,0 +1,82 @@ +@@ -0,0 +1,151 @@ + + @@ -4948,6 +5520,25 @@ index 000000000..083b5b17c + + + ++ ++ ++ ++ ++ ++ + + + + @@ -4962,13 +5555,58 @@ index 000000000..083b5b17c + + + ++ ++ ++ ++ ++ ++ + ++ ++ ++ ++ ++ ++ ++ ++ ++ + + + @@ -4981,6 +5619,9 @@ index 000000000..083b5b17c + + Set the action that should be performed after the offline transaction is applied. If the `action` is "poweroff", the system will be powered off, otherwise it will be rebooted (which is default). + The call might fail in case there is no scheduled offline transaction, or the transaction was not scheduled using libdnf5. ++ ++ ++ This is equivalent to call "set_finish_action_with_options()" with empty options. + --> + + @@ -5066,12 +5707,79 @@ index 000000000..a0facd692 + + + +diff --git a/plugins/dnf5/org.rpm.dnf.v0.comps.Group.xml b/plugins/dnf5/org.rpm.dnf.v0.comps.Group.xml +new file mode 100644 +index 000000000..b12e0ac6d +--- /dev/null ++++ b/plugins/dnf5/org.rpm.dnf.v0.comps.Group.xml +@@ -0,0 +1,61 @@ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ ++ diff --git a/plugins/dnf5/org.rpm.dnf.v0.rpm.Repo.xml b/plugins/dnf5/org.rpm.dnf.v0.rpm.Repo.xml new file mode 100644 -index 000000000..13c4cf1f8 +index 000000000..50b2ba3bf --- /dev/null +++ b/plugins/dnf5/org.rpm.dnf.v0.rpm.Repo.xml -@@ -0,0 +1,85 @@ +@@ -0,0 +1,147 @@ + + @@ -5123,11 +5831,33 @@ index 000000000..13c4cf1f8 + + + ++ ++ ++ ++ ++ ++ ++ + + @@ -5135,20 +5865,60 @@ index 000000000..13c4cf1f8 + + + ++ ++ ++ ++ ++ ++ + + + + + ++ ++ ++ ++ ++ ++ + + @@ -5159,10 +5929,10 @@ index 000000000..13c4cf1f8 + diff --git a/plugins/dnf5/org.rpm.dnf.v0.rpm.Rpm.xml b/plugins/dnf5/org.rpm.dnf.v0.rpm.Rpm.xml new file mode 100644 -index 000000000..5df68cd91 +index 000000000..f24b14d39 --- /dev/null +++ b/plugins/dnf5/org.rpm.dnf.v0.rpm.Rpm.xml -@@ -0,0 +1,468 @@ +@@ -0,0 +1,470 @@ + + @@ -5388,6 +6158,8 @@ index 000000000..5df68cd91 + + - mode: string (one of "distrosync", "upgrade", default is "distrosync") + By default the system_upgrade behaves like `dnf distro-sync`, always installing packages from the new release, even if they are older than the currently installed version. If set to "upgrade", packages from the new release are not installed if they are older than what is currently installed (behave like `dnf upgrade`). ++ - interactive: boolean, default true ++ Set to "true", when the operation is done by a user, thus user interaction like password prompts can be done. + + Unknown options are ignored. + --> diff --git a/gnome-software.spec b/gnome-software.spec index 198e7c9..10c8d74 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -7,6 +7,7 @@ %global libadwaita_version 1.6.0 %global libxmlb_version 0.3.4 %global packagekit_version 1.2.5 +%global dnf5_version 5.2.16 # Disable WebApps for RHEL builds %bcond webapps %[!0%{?rhel}] @@ -29,7 +30,7 @@ Name: gnome-software Version: 49~beta -Release: 2%{?dist} +Release: 3%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -91,7 +92,7 @@ Requires: appstream%{?_isa} >= %{appstream_version} Requires: epiphany-runtime%{?_isa} %endif %if %{with dnf5} -Requires: dnf5daemon-server%{?_isa} +Requires: dnf5daemon-server%{?_isa} >= %{dnf5_version} Requires: dnf5daemon-server-polkit Requires: libdnf5-plugin-appstream%{?_isa} Requires: rpm-plugin-dbus-announce%{?_isa} From eaee792f9f386eb90797895cb9f6637e2b0ff6bc Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Wed, 13 Aug 2025 18:32:50 +0200 Subject: [PATCH 152/163] dnf5-plugin: Auto-accept new RPM keys --- 0001-dnf5-plugin.patch | 12 +++++++----- gnome-software.spec | 2 +- 2 files changed, 8 insertions(+), 6 deletions(-) diff --git a/0001-dnf5-plugin.patch b/0001-dnf5-plugin.patch index 3e9a13f..0ba8881 100644 --- a/0001-dnf5-plugin.patch +++ b/0001-dnf5-plugin.patch @@ -1,5 +1,5 @@ -at commit 8a1f0ca6564157dd688c84ffd25af9747c1e038e -Date: Mon Aug 11 17:07:06 2025 +0200 +at commit d7f516e25742e1c0631194df5829bf73668f7df5 +Date: Wed Aug 13 18:23:59 2025 +0200 diff --git a/meson_options.txt b/meson_options.txt index cd49cf529..27fa15e8b 100644 @@ -610,10 +610,10 @@ index 000000000..5d522468c +G_END_DECLS diff --git a/plugins/dnf5/gs-plugin-dnf5.c b/plugins/dnf5/gs-plugin-dnf5.c new file mode 100644 -index 000000000..88d7e25d8 +index 000000000..36d10163a --- /dev/null +++ b/plugins/dnf5/gs-plugin-dnf5.c -@@ -0,0 +1,4275 @@ +@@ -0,0 +1,4277 @@ +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- + * vi:set noexpandtab tabstop=8 shiftwidth=8: + * @@ -1702,7 +1702,9 @@ index 000000000..88d7e25d8 + g_autoptr(GVariantBuilder) options_builder = NULL; + gboolean confirmed; + -+ confirmed = gs_plugin_ask_untrusted (GS_PLUGIN (data->self), data->title, data->msg, data->details, data->accept_label); ++ /* auto-accept new keys, just as PacakgeKit plugin used to do */ ++ confirmed = TRUE; ++ /* confirmed = gs_plugin_ask_untrusted (GS_PLUGIN (data->self), data->title, data->msg, data->details, data->accept_label); */ + + options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); + g_variant_builder_add (options_builder, "{sv}", "interactive", diff --git a/gnome-software.spec b/gnome-software.spec index 10c8d74..21466da 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -30,7 +30,7 @@ Name: gnome-software Version: 49~beta -Release: 3%{?dist} +Release: 4%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later From 446ce42aa8d01622a25810693ed527f115afddbe Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 25 Aug 2025 12:05:46 +0200 Subject: [PATCH 153/163] dnf5-plugin: Auto-accept new RPM keys only when installed from repos - dnf5-plugin: Download offline updates also by regular users --- 0001-dnf5-plugin.patch | 327 +++++++++++++++++++++++++++++++++++++++-- gnome-software.spec | 2 +- 2 files changed, 317 insertions(+), 12 deletions(-) diff --git a/0001-dnf5-plugin.patch b/0001-dnf5-plugin.patch index 0ba8881..088ad51 100644 --- a/0001-dnf5-plugin.patch +++ b/0001-dnf5-plugin.patch @@ -1,5 +1,5 @@ -at commit d7f516e25742e1c0631194df5829bf73668f7df5 -Date: Wed Aug 13 18:23:59 2025 +0200 +at commit 55ca6d4d49d5edd682b8ca15904ec556eb5d0874 +Date: Tue Aug 19 13:13:48 2025 +0200 diff --git a/meson_options.txt b/meson_options.txt index cd49cf529..27fa15e8b 100644 @@ -610,10 +610,10 @@ index 000000000..5d522468c +G_END_DECLS diff --git a/plugins/dnf5/gs-plugin-dnf5.c b/plugins/dnf5/gs-plugin-dnf5.c new file mode 100644 -index 000000000..36d10163a +index 000000000..c8d9ed83d --- /dev/null +++ b/plugins/dnf5/gs-plugin-dnf5.c -@@ -0,0 +1,4277 @@ +@@ -0,0 +1,4582 @@ +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- + * vi:set noexpandtab tabstop=8 shiftwidth=8: + * @@ -1671,9 +1671,13 @@ index 000000000..36d10163a + gchar *details; + gchar *accept_label; + gchar *key_id; ++ gchar *key_filename; ++ gchar *session_path; ++ GCancellable *cancellable; /* (owned) */ + GsPluginDnf5 *self; /* (owned) */ + GWeakRef repo_proxy_weakref; /* GsDnf5RpmRepo */ + gboolean interactive; ++ gboolean confirmed_by_repo; +} QuestionData; + +static void @@ -1685,6 +1689,9 @@ index 000000000..36d10163a + g_free (data->details); + g_free (data->accept_label); + g_free (data->key_id); ++ g_free (data->key_filename); ++ g_free (data->session_path); ++ g_clear_object (&data->cancellable); + g_clear_object (&data->self); + g_weak_ref_clear (&data->repo_proxy_weakref); + g_free (data); @@ -1703,8 +1710,9 @@ index 000000000..36d10163a + gboolean confirmed; + + /* auto-accept new keys, just as PacakgeKit plugin used to do */ -+ confirmed = TRUE; -+ /* confirmed = gs_plugin_ask_untrusted (GS_PLUGIN (data->self), data->title, data->msg, data->details, data->accept_label); */ ++ confirmed = data->confirmed_by_repo; ++ if (!confirmed) ++ confirmed = gs_plugin_ask_untrusted (GS_PLUGIN (data->self), data->title, data->msg, data->details, data->accept_label); + + options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); + g_variant_builder_add (options_builder, "{sv}", "interactive", @@ -1714,7 +1722,7 @@ index 000000000..36d10163a + data->key_id, + confirmed, + g_variant_builder_end (options_builder), -+ NULL, ++ data->cancellable, + gs_dnf5_confirm_key_response_cb, + NULL); + } @@ -1722,10 +1730,184 @@ index 000000000..36d10163a + return G_SOURCE_REMOVE; +} + ++static gboolean ++gs_dnf5_read_package_repo_ids_cb (GsPluginDnf5 *self, ++ GVariant *package_array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ GPtrArray **out_repo_ids = user_data; ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) value = NULL; ++ ++ dict = g_variant_dict_new (package_array); ++ ++ value = g_variant_dict_lookup_value (dict, "from_repo_id", G_VARIANT_TYPE_STRING); ++ if (value != NULL) { ++ const gchar *repo_id_const = g_variant_get_string (value, NULL); ++ if (repo_id_const != NULL && *repo_id_const != '\0') { ++ if (*out_repo_ids == NULL) ++ *out_repo_ids = g_ptr_array_new_with_free_func (g_free); ++ g_ptr_array_add (*out_repo_ids, g_strdup (repo_id_const)); ++ } ++ } ++ ++ return TRUE; ++} ++ ++static gboolean ++gs_dnf5_read_repo_gpg_info_cb (GsPluginDnf5 *self, ++ GVariant *package_array, ++ gpointer user_data, ++ GCancellable *cancellable, ++ GError **error) ++{ ++ guint *out_n_good = user_data; ++ g_autoptr(GVariantDict) dict = NULL; ++ g_autoptr(GVariant) id_value = NULL; ++ g_autoptr(GVariant) gpgcheck_value = NULL; ++ ++ dict = g_variant_dict_new (package_array); ++ ++ id_value = g_variant_dict_lookup_value (dict, "id", G_VARIANT_TYPE_STRING); ++ gpgcheck_value = g_variant_dict_lookup_value (dict, "gpgcheck", G_VARIANT_TYPE_BOOLEAN); ++ ++ if (id_value != NULL && gpgcheck_value != NULL) { ++ gboolean gpgcheck = g_variant_get_boolean (gpgcheck_value); ++ ++ if (gpgcheck) ++ *out_n_good = (*out_n_good) + 1; ++ } ++ ++ return TRUE; ++} ++ ++static gpointer ++gs_dnf5_check_key_source_thread (gpointer user_data) ++{ ++ QuestionData *data = user_data; ++ g_autoptr(GsDnf5RpmRpm) rpm_proxy = NULL; ++ g_autoptr(GPtrArray) repo_ids = NULL; ++ g_autoptr(GError) local_error = NULL; ++ gboolean success; ++ ++ rpm_proxy = gs_dnf5_rpm_rpm_proxy_new_sync (data->self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ data->session_path, ++ data->cancellable, ++ &local_error); ++ success = rpm_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to create Rpm proxy: "); ++ } ++ ++ /* try to get whether the key comes from any package */ ++ if (success) { ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariantBuilder) package_attrs_builder = NULL; ++ g_autoptr(GVariantBuilder) whatprovides_builder = NULL; ++ g_autoptr(GVariant) result = NULL; ++ ++ g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); ++ ++ package_attrs_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_variant_builder_add (package_attrs_builder, "s", "from_repo_id"); ++ ++ whatprovides_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_variant_builder_add (whatprovides_builder, "s", data->key_filename); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "package_attrs", ++ g_variant_builder_end (package_attrs_builder)); ++ g_variant_builder_add (options_builder, "{sv}", "whatprovides", ++ g_variant_builder_end (whatprovides_builder)); ++ g_variant_builder_add (options_builder, "{sv}", "scope", ++ g_variant_new_string ("installed")); ++ ++ success = gs_dnf5_rpm_rpm_call_list_sync (rpm_proxy, ++ g_variant_builder_end (options_builder), ++ &result, ++ data->cancellable, ++ &local_error); ++ ++ if (success) { ++ success = gs_dnf5_foreach_item (data->self, result, gs_dnf5_read_package_repo_ids_cb, &repo_ids, data->cancellable, &local_error); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to call rpm::list: "); ++ } ++ } ++ ++ if (success && repo_ids != NULL) { ++ g_autoptr(GVariantBuilder) patterns_builder = NULL; ++ guint n_verify = 0; ++ ++ for (guint i = 0; i < repo_ids->len; i++) { ++ const gchar *repo_id = g_ptr_array_index (repo_ids, i); ++ /* those are special repos, like `@commandline` */ ++ if (*repo_id != '@') { ++ if (patterns_builder == NULL) ++ patterns_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_variant_builder_add (patterns_builder, "s", repo_id); ++ n_verify++; ++ } ++ } ++ ++ if (patterns_builder != NULL) { ++ g_autoptr(GsDnf5RpmRepo) repo_proxy = NULL; ++ ++ repo_proxy = g_weak_ref_get (&data->repo_proxy_weakref); ++ if (repo_proxy != NULL) { ++ g_autoptr(GVariantBuilder) repo_attrs_builder = NULL; ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariant) result = NULL; ++ ++ repo_attrs_builder = g_variant_builder_new (G_VARIANT_TYPE ("as")); ++ g_variant_builder_add (repo_attrs_builder, "s", "id"); ++ g_variant_builder_add (repo_attrs_builder, "s", "gpgcheck"); ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "patterns", ++ g_variant_builder_end (patterns_builder)); ++ g_variant_builder_add (options_builder, "{sv}", "repo_attrs", ++ g_variant_builder_end (repo_attrs_builder)); ++ ++ success = gs_dnf5_rpm_repo_call_list_sync (repo_proxy, ++ g_variant_builder_end (options_builder), ++ &result, ++ data->cancellable, ++ &local_error); ++ ++ if (success) { ++ guint n_good = 0; ++ ++ success = gs_dnf5_foreach_item (data->self, result, gs_dnf5_read_repo_gpg_info_cb, &n_good, data->cancellable, &local_error); ++ ++ data->confirmed_by_repo = success && n_verify == n_good; ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to call repo::list: "); ++ } ++ } else { ++ success = FALSE; ++ g_set_error_literal (&local_error, G_IO_ERROR, G_IO_ERROR_FAILED, "Repo proxy vanished"); ++ } ++ } ++ } ++ ++ g_idle_add_full (G_PRIORITY_HIGH_IDLE, gs_dnf5_ask_question_idle_cb, data, (GDestroyNotify) question_data_free); ++ ++ return NULL; ++} ++ +typedef struct { + GsPluginDnf5 *self; /* (not owned) */ + const gchar *session_path; /* (not owned) */ + GsDnf5RpmRepo *repo_proxy; /* (not owned) */ ++ GCancellable *cancellable; /* (not owned) */ + gboolean interactive; +} RepoKeyImportData; + @@ -1800,11 +1982,18 @@ index 000000000..36d10163a + data->details = g_string_free (details, FALSE); + data->accept_label = g_strdup (_("_Import Key")); + data->key_id = g_strdup (arg_key_id); ++ data->key_filename = g_steal_pointer (&key_filename); ++ data->session_path = g_strdup (repo_key_import_data->session_path); + data->self = g_object_ref (repo_key_import_data->self); + data->interactive = repo_key_import_data->interactive; ++ data->confirmed_by_repo = FALSE; ++ g_set_object (&data->cancellable, repo_key_import_data->cancellable); + g_weak_ref_init (&data->repo_proxy_weakref, repo_key_import_data->repo_proxy); + -+ g_idle_add_full (G_PRIORITY_HIGH_IDLE, gs_dnf5_ask_question_idle_cb, data, (GDestroyNotify) question_data_free); ++ if (data->key_filename != NULL) ++ g_thread_unref (g_thread_new ("gs-dnf5-check-key-source_thread", gs_dnf5_check_key_source_thread, data)); ++ else ++ g_idle_add_full (G_PRIORITY_HIGH_IDLE, gs_dnf5_ask_question_idle_cb, data, (GDestroyNotify) question_data_free); +} + +static void @@ -1886,7 +2075,8 @@ index 000000000..36d10163a + GS_DNF5_TRANSACTION_FLAG_OFFLINE = 1 << 0, + GS_DNF5_TRANSACTION_FLAG_RESOLVE_ONLY = 1 << 1, + GS_DNF5_TRANSACTION_FLAG_DISALLOW_ERASING = 1 << 2, /* negative flag, to not have it everywhere */ -+ GS_DNF5_TRANSACTION_FLAG_INTERACTIVE = 1 << 3 ++ GS_DNF5_TRANSACTION_FLAG_INTERACTIVE = 1 << 3, ++ GS_DNF5_TRANSACTION_FLAG_DOWNLOAD_ONLY = 1 << 4 +} GsDnf5TransactionFlags; + +static gboolean @@ -1965,6 +2155,7 @@ index 000000000..36d10163a + repo_key_import_data.session_path = session_path; + repo_key_import_data.repo_proxy = repo_proxy; + repo_key_import_data.interactive = interactive; ++ repo_key_import_data.cancellable = cancellable; + repo_key_import_id = g_signal_connect (base_proxy, "repo_key_import_request", + G_CALLBACK (gs_dnf5_repo_key_import_request_cb), &repo_key_import_data); + @@ -2017,6 +2208,10 @@ index 000000000..36d10163a + g_variant_builder_add (options_builder, "{sv}", "offline", + g_variant_new_boolean (TRUE)); + } ++ if ((flags & GS_DNF5_TRANSACTION_FLAG_DOWNLOAD_ONLY) != 0) { ++ g_variant_builder_add (options_builder, "{sv}", "downloadonly", ++ g_variant_new_boolean (TRUE)); ++ } + g_variant_builder_add (options_builder, "{sv}", "interactive", + g_variant_new_boolean (interactive)); + @@ -3576,6 +3771,7 @@ index 000000000..36d10163a + GsAppList *list, + gboolean is_install, + gboolean interactive, ++ gboolean can_apply, + GsPluginEventCallback event_callback, + void *event_user_data, + GCancellable *cancellable, @@ -3700,7 +3896,8 @@ index 000000000..36d10163a + success = rpm_proxy != NULL; + if (success) { + g_autoptr(GVariantBuilder) options_builder = NULL; -+ GsDnf5TransactionFlags flags = interactive ? GS_DNF5_TRANSACTION_FLAG_INTERACTIVE : GS_DNF5_TRANSACTION_FLAG_NONE; ++ GsDnf5TransactionFlags flags = (interactive ? GS_DNF5_TRANSACTION_FLAG_INTERACTIVE : GS_DNF5_TRANSACTION_FLAG_NONE) | ++ (!can_apply ? GS_DNF5_TRANSACTION_FLAG_DOWNLOAD_ONLY : GS_DNF5_TRANSACTION_FLAG_NONE); + + g_dbus_proxy_set_default_timeout (G_DBUS_PROXY (rpm_proxy), G_MAXINT); + @@ -3732,7 +3929,7 @@ index 000000000..36d10163a + success = success && gs_dnf5_run_transaction (self, session_path, rpm_proxy, progress_app, progress_list, + flags | (is_install ? 0 : GS_DNF5_TRANSACTION_FLAG_OFFLINE), + NULL, cancellable, error); -+ if (success && !is_install) { ++ if (success && !is_install && can_apply) { + /* ensure the update is finished with the 'reboot' action */ + g_autoptr(GsDnf5Offline) offline_proxy = NULL; + @@ -3852,6 +4049,7 @@ index 000000000..36d10163a + + success = gs_dnf5_install_update (plugin, data->apps, TRUE, + (data->flags & GS_PLUGIN_INSTALL_APPS_FLAGS_INTERACTIVE) != 0, ++ (data->flags & GS_PLUGIN_INSTALL_APPS_FLAGS_NO_APPLY) == 0, + data->event_callback, data->event_user_data, + cancellable, &local_error); + @@ -4095,6 +4293,7 @@ index 000000000..36d10163a + + success = gs_dnf5_install_update (plugin, data->apps, FALSE, + (data->flags & GS_PLUGIN_UPDATE_APPS_FLAGS_INTERACTIVE) != 0, ++ (data->flags & GS_PLUGIN_UPDATE_APPS_FLAGS_NO_APPLY) == 0, + data->event_callback, data->event_user_data, + cancellable, &local_error); + @@ -4780,6 +4979,110 @@ index 000000000..36d10163a + return g_task_propagate_boolean (G_TASK (result), error); +} + ++/* Run in @worker. */ ++static void ++gs_dnf5_cancel_offline_update_thread_cb (GTask *task, ++ gpointer source_object, ++ gpointer task_data, ++ GCancellable *cancellable) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (source_object); ++ GsPluginCancelOfflineUpdateData *data = task_data; ++ g_autofree gchar *session_path = NULL; ++ g_autoptr(GsAppList) list = NULL; ++ g_autoptr(GsDnf5SessionManager) session_manager = NULL; ++ g_autoptr(GsDnf5Offline) offline_proxy = NULL; ++ gboolean success; ++ g_autoptr(GError) local_error = NULL; ++ ++ assert_in_worker (self); ++ ++ session_path = gs_dnf5_open_session (self, GS_DNF5_RELEASEVER_DEFAULT, &session_manager, cancellable, &local_error); ++ if (session_path == NULL) { ++ gs_dnf5_convert_error (&local_error); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ return; ++ } ++ ++ offline_proxy = gs_dnf5_offline_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ &local_error); ++ success = offline_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to create Offline proxy: "); ++ } ++ ++ if (success) { ++ gboolean pending = FALSE; ++ g_autoptr(GVariant) transaction_status = NULL; ++ ++ if (gs_dnf5_offline_call_get_status_sync (offline_proxy, &pending, &transaction_status, cancellable, &local_error) && ++ pending && transaction_status != NULL) { ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autofree gchar *op_error_msg = NULL; ++ gboolean op_success = FALSE; ++ ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "interactive", ++ g_variant_new_boolean ((data->flags & GS_PLUGIN_CANCEL_OFFLINE_UPDATE_FLAGS_INTERACTIVE) != 0)); ++ ++ success = gs_dnf5_offline_call_cancel_with_options_sync (offline_proxy, g_variant_builder_end (options_builder), ++ &op_success, &op_error_msg, cancellable, &local_error); ++ if (!success) { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to call OfflineProxy::cancel: "); ++ } else if (!op_success) { ++ success = FALSE; ++ if (op_error_msg != NULL) { ++ g_set_error_literal (&local_error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_FAILED, op_error_msg); ++ g_prefix_error_literal (&local_error, "Failed to call OfflineProxy::cancel op: "); ++ } else { ++ g_set_error_literal (&local_error, GS_PLUGIN_ERROR, GS_PLUGIN_ERROR_FAILED, "Failed to call OfflineProxy::cancel op"); ++ } ++ } ++ } ++ } ++ ++ gs_dnf5_close_session (self, session_manager, session_path); ++ ++ if (success) { ++ g_task_return_boolean (task, TRUE); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_task_return_error (task, g_steal_pointer (&local_error)); ++ } ++} ++ ++static void ++gs_plugin_dnf5_cancel_offline_update_async (GsPlugin *plugin, ++ GsPluginCancelOfflineUpdateFlags flags, ++ GCancellable *cancellable, ++ GAsyncReadyCallback callback, ++ gpointer user_data) ++{ ++ GsPluginDnf5 *self = GS_PLUGIN_DNF5 (plugin); ++ g_autoptr(GTask) task = NULL; ++ gboolean interactive = (flags & GS_PLUGIN_CANCEL_OFFLINE_UPDATE_FLAGS_INTERACTIVE) != 0; ++ ++ task = gs_plugin_cancel_offline_update_data_new_task (plugin, flags, cancellable, callback, user_data); ++ g_task_set_source_tag (task, gs_plugin_dnf5_cancel_offline_update_async); ++ ++ gs_worker_thread_queue (self->worker, gs_dnf5_get_priority_for_interactivity (interactive), ++ gs_dnf5_cancel_offline_update_thread_cb, g_steal_pointer (&task)); ++} ++ ++static gboolean ++gs_plugin_dnf5_cancel_offline_update_finish (GsPlugin *plugin, ++ GAsyncResult *result, ++ GError **error) ++{ ++ return g_task_propagate_boolean (G_TASK (result), error); ++} ++ +static void +gs_plugin_dnf5_dispose (GObject *object) +{ @@ -4865,6 +5168,8 @@ index 000000000..36d10163a + plugin_class->download_upgrade_finish = gs_plugin_dnf5_download_upgrade_finish; + plugin_class->trigger_upgrade_async = gs_plugin_dnf5_trigger_upgrade_async; + plugin_class->trigger_upgrade_finish = gs_plugin_dnf5_trigger_upgrade_finish; ++ plugin_class->cancel_offline_update_async = gs_plugin_dnf5_cancel_offline_update_async; ++ plugin_class->cancel_offline_update_finish = gs_plugin_dnf5_cancel_offline_update_finish; +} + +static void diff --git a/gnome-software.spec b/gnome-software.spec index 21466da..2cce046 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -30,7 +30,7 @@ Name: gnome-software Version: 49~beta -Release: 4%{?dist} +Release: 5%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later From e95633c7038667767acefda20b67d7f50d928c98 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Tue, 26 Aug 2025 19:02:10 +0200 Subject: [PATCH 154/163] dnf5-plugin: Skip historical updates search when no last date is set --- 0001-dnf5-plugin.patch | 97 ++++++++++++++++++++++-------------------- gnome-software.spec | 2 +- 2 files changed, 53 insertions(+), 46 deletions(-) diff --git a/0001-dnf5-plugin.patch b/0001-dnf5-plugin.patch index 088ad51..43864c1 100644 --- a/0001-dnf5-plugin.patch +++ b/0001-dnf5-plugin.patch @@ -1,5 +1,5 @@ -at commit 55ca6d4d49d5edd682b8ca15904ec556eb5d0874 -Date: Tue Aug 19 13:13:48 2025 +0200 +at commit 73640bc9127fb2200189433f935445208bf0b472 +Date: Tue Aug 26 18:59:16 2025 +0200 diff --git a/meson_options.txt b/meson_options.txt index cd49cf529..27fa15e8b 100644 @@ -610,10 +610,10 @@ index 000000000..5d522468c +G_END_DECLS diff --git a/plugins/dnf5/gs-plugin-dnf5.c b/plugins/dnf5/gs-plugin-dnf5.c new file mode 100644 -index 000000000..c8d9ed83d +index 000000000..b9b698a81 --- /dev/null +++ b/plugins/dnf5/gs-plugin-dnf5.c -@@ -0,0 +1,4582 @@ +@@ -0,0 +1,4589 @@ +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- + * vi:set noexpandtab tabstop=8 shiftwidth=8: + * @@ -2767,55 +2767,62 @@ index 000000000..c8d9ed83d + g_prefix_error_literal (&local_error, "Failed to call Rpm::list: "); + } + } else if (is_historical_update == GS_APP_QUERY_TRISTATE_TRUE) { -+ g_autoptr(GsDnf5History) history_proxy = NULL; ++ g_autoptr(GSettings) settings = NULL; ++ gint64 timestamp; ++ gboolean interactive = (data->flags & GS_PLUGIN_LIST_APPS_FLAGS_INTERACTIVE) != 0; + -+ history_proxy = gs_dnf5_history_proxy_new_sync (self->connection, -+ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, -+ GS_DNF5_INTERFACE_RPM_DNF, -+ session_path, -+ cancellable, -+ &local_error); -+ success = history_proxy != NULL; -+ if (!success) { -+ gs_dnf5_convert_error (&local_error); -+ g_prefix_error_literal (&local_error, "Failed to create History proxy: "); -+ } ++ /* use the option the GUI part uses */ ++ settings = g_settings_new ("org.gnome.software"); ++ timestamp = g_settings_get_int64 (settings, "install-timestamp"); + -+ if (success) { -+ g_autoptr(GVariantBuilder) options_builder = NULL; -+ g_autoptr(GVariant) result = NULL; -+ g_autoptr(GSettings) settings; -+ gint64 timestamp; ++ if (timestamp > 0 || interactive) { ++ g_autoptr(GsDnf5History) history_proxy = NULL; + -+ /* use the option the GUI part uses */ -+ settings = g_settings_new ("org.gnome.software"); -+ timestamp = g_settings_get_int64 (settings, "install-timestamp"); -+ -+ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); -+ g_variant_builder_add (options_builder, "{sv}", "since", -+ g_variant_new_int64 (timestamp)); -+ g_variant_builder_add (options_builder, "{sv}", "package_attrs", -+ gs_dnf5_dup_package_attrs ()); -+ -+ success = gs_dnf5_history_call_recent_changes_sync (history_proxy, -+ g_variant_builder_end (options_builder), -+ &result, -+ cancellable, -+ &local_error); ++ history_proxy = gs_dnf5_history_proxy_new_sync (self->connection, ++ G_DBUS_PROXY_FLAGS_DO_NOT_AUTO_START, ++ GS_DNF5_INTERFACE_RPM_DNF, ++ session_path, ++ cancellable, ++ &local_error); ++ success = history_proxy != NULL; ++ if (!success) { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to create History proxy: "); ++ } + + if (success) { -+ ReadPackageData rpd = { 0, }; ++ g_autoptr(GVariantBuilder) options_builder = NULL; ++ g_autoptr(GVariant) result = NULL; + -+ rpd.list = list; -+ rpd.set_state = GS_APP_STATE_UNKNOWN; -+ rpd.nevra_to_app = NULL; -+ rpd.timestamp = timestamp; ++ options_builder = g_variant_builder_new (G_VARIANT_TYPE ("a{sv}")); ++ g_variant_builder_add (options_builder, "{sv}", "since", ++ g_variant_new_int64 (timestamp)); ++ g_variant_builder_add (options_builder, "{sv}", "package_attrs", ++ gs_dnf5_dup_package_attrs ()); + -+ success = gs_dnf5_foreach_item (self, result, gs_dnf5_read_history_items_cb, &rpd, cancellable, &local_error); -+ } else { -+ gs_dnf5_convert_error (&local_error); -+ g_prefix_error_literal (&local_error, "Failed to call recent_changes: "); ++ success = gs_dnf5_history_call_recent_changes_sync (history_proxy, ++ g_variant_builder_end (options_builder), ++ &result, ++ cancellable, ++ &local_error); ++ ++ if (success) { ++ ReadPackageData rpd = { 0, }; ++ ++ rpd.list = list; ++ rpd.set_state = GS_APP_STATE_UNKNOWN; ++ rpd.nevra_to_app = NULL; ++ rpd.timestamp = timestamp; ++ ++ success = gs_dnf5_foreach_item (self, result, gs_dnf5_read_history_items_cb, &rpd, cancellable, &local_error); ++ } else { ++ gs_dnf5_convert_error (&local_error); ++ g_prefix_error_literal (&local_error, "Failed to call recent_changes: "); ++ } + } ++ } else { ++ /* initialize the value to today */ ++ g_settings_set (settings, "install-timestamp", "x", g_get_real_time () / G_USEC_PER_SEC); + } + } else if (gs_component_kind_array_contains (component_kinds, AS_COMPONENT_KIND_REPOSITORY)) { + g_autoptr(GsDnf5RpmRepo) repo_proxy = NULL; diff --git a/gnome-software.spec b/gnome-software.spec index 2cce046..ad7833b 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -30,7 +30,7 @@ Name: gnome-software Version: 49~beta -Release: 5%{?dist} +Release: 6%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later From 4a71393113c82fe2afd330153fd30851504aa0da Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 29 Aug 2025 09:11:51 +0200 Subject: [PATCH 155/163] Update to 49.rc --- gnome-software.spec | 4 ++-- sources | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index ad7833b..c6f4ac8 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -29,8 +29,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 49~beta -Release: 6%{?dist} +Version: 49~rc +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later diff --git a/sources b/sources index f212fbd..c3ec757 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-49.beta.tar.xz) = 9cb6d67216193840b2661871ef43da5e726a284d1164781f13423ee8dd86359334f199efc29f4b3a0b3eddfa8a3811d7dd38cd412fa53aaebb2e1c35ddc1f9df +SHA512 (gnome-software-49.rc.tar.xz) = cecebbff1163f0179c5699ecc8325e2c4f68c811ec7633e6cf32e18ad2f03592b55daa16b9b5497a117cbfbf63f3d9162dd8e8191e6a6213d35261fa1bad15a5 From 90da5737b3044a752d2f4d7ebc5513123b46113d Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 1 Sep 2025 18:28:21 +0200 Subject: [PATCH 156/163] Resolves: #2392057 (dnf5-pugin: No update notifications shown) --- 0001-dnf5-plugin.patch | 18 +++++++++--------- gnome-software.spec | 2 +- 2 files changed, 10 insertions(+), 10 deletions(-) diff --git a/0001-dnf5-plugin.patch b/0001-dnf5-plugin.patch index 43864c1..3b4b355 100644 --- a/0001-dnf5-plugin.patch +++ b/0001-dnf5-plugin.patch @@ -1,5 +1,5 @@ -at commit 73640bc9127fb2200189433f935445208bf0b472 -Date: Tue Aug 26 18:59:16 2025 +0200 +at commit 786bab5f1928920251ee9e93d51953ff9dd9faa4 +Date: Mon Sep 1 18:23:09 2025 +0200 diff --git a/meson_options.txt b/meson_options.txt index cd49cf529..27fa15e8b 100644 @@ -610,7 +610,7 @@ index 000000000..5d522468c +G_END_DECLS diff --git a/plugins/dnf5/gs-plugin-dnf5.c b/plugins/dnf5/gs-plugin-dnf5.c new file mode 100644 -index 000000000..b9b698a81 +index 000000000..82f3e19a8 --- /dev/null +++ b/plugins/dnf5/gs-plugin-dnf5.c @@ -0,0 +1,4589 @@ @@ -2769,13 +2769,12 @@ index 000000000..b9b698a81 + } else if (is_historical_update == GS_APP_QUERY_TRISTATE_TRUE) { + g_autoptr(GSettings) settings = NULL; + gint64 timestamp; -+ gboolean interactive = (data->flags & GS_PLUGIN_LIST_APPS_FLAGS_INTERACTIVE) != 0; + + /* use the option the GUI part uses */ + settings = g_settings_new ("org.gnome.software"); -+ timestamp = g_settings_get_int64 (settings, "install-timestamp"); ++ timestamp = (gint64) g_settings_get_uint64 (settings, "packagekit-historical-updates-timestamp"); + -+ if (timestamp > 0 || interactive) { ++ if (timestamp > 0) { + g_autoptr(GsDnf5History) history_proxy = NULL; + + history_proxy = gs_dnf5_history_proxy_new_sync (self->connection, @@ -2820,9 +2819,6 @@ index 000000000..b9b698a81 + g_prefix_error_literal (&local_error, "Failed to call recent_changes: "); + } + } -+ } else { -+ /* initialize the value to today */ -+ g_settings_set (settings, "install-timestamp", "x", g_get_real_time () / G_USEC_PER_SEC); + } + } else if (gs_component_kind_array_contains (component_kinds, AS_COMPONENT_KIND_REPOSITORY)) { + g_autoptr(GsDnf5RpmRepo) repo_proxy = NULL; @@ -3973,6 +3969,10 @@ index 000000000..b9b698a81 + } else if (!success) { + gs_dnf5_convert_error (error); + g_prefix_error_literal (error, "Failed to set finish action: "); ++ } else { ++ g_autoptr(GSettings) settings = g_settings_new ("org.gnome.software"); ++ /* to check anything installed/updated after today */ ++ g_settings_set (settings, "packagekit-historical-updates-timestamp", "t", g_get_real_time () / G_USEC_PER_SEC); + } + } else { + gs_dnf5_convert_error (error); diff --git a/gnome-software.spec b/gnome-software.spec index c6f4ac8..09c8546 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -30,7 +30,7 @@ Name: gnome-software Version: 49~rc -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later From ac8dbc92e832cb6c72963e90cd49f7d92a6b05ee Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 12 Sep 2025 10:01:34 +0200 Subject: [PATCH 157/163] Update to 49.0 --- gnome-software.spec | 8 ++++---- sources | 2 +- 2 files changed, 5 insertions(+), 5 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 09c8546..34328cf 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -29,17 +29,19 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 49~rc -Release: 2%{?dist} +Version: 49.0 +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later URL: https://apps.gnome.org/Software Source0: https://download.gnome.org/sources/gnome-software/49/%{name}-%{tarball_version}.tar.xz +%if %{with dnf5} # to update the patch enter the ./dnf5-plugin/ directory and run from # it the ./update-patch.sh script Patch: 0001-dnf5-plugin.patch +%endif # ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 @@ -177,8 +179,6 @@ This package includes the rpm-ostree backend. %endif %if %{with dnf5} -Ddnf5=true \ -%else - -Ddnf5=false \ %endif -Dexternal_appstream=false \ %if %{with rpmostree} diff --git a/sources b/sources index c3ec757..469fb06 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-49.rc.tar.xz) = cecebbff1163f0179c5699ecc8325e2c4f68c811ec7633e6cf32e18ad2f03592b55daa16b9b5497a117cbfbf63f3d9162dd8e8191e6a6213d35261fa1bad15a5 +SHA512 (gnome-software-49.0.tar.xz) = 7c63b0bd59e6ebe7ef526b438c6d0b234897edacfa72ab4846358ffa9e3d63ced2945f52a4d3111307e349b846be80cb4039b4cec25f7bc5ceba135d0a4fe343 From 2c29600426d9ef7d1ef04b90d8b3af73ba1c07c1 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 19 Sep 2025 13:25:37 +0200 Subject: [PATCH 158/163] Resolves: #2395811 (Packages not found for "what-provides" searches) --- ...ackages-not-found-for-what-provides-.patch | 28 +++++++++++++++++++ gnome-software.spec | 4 ++- 2 files changed, 31 insertions(+), 1 deletion(-) create mode 100644 0002-gs-extras-page-Packages-not-found-for-what-provides-.patch diff --git a/0002-gs-extras-page-Packages-not-found-for-what-provides-.patch b/0002-gs-extras-page-Packages-not-found-for-what-provides-.patch new file mode 100644 index 0000000..5d14caf --- /dev/null +++ b/0002-gs-extras-page-Packages-not-found-for-what-provides-.patch @@ -0,0 +1,28 @@ +From 272cdf10b69a84f773ce203a4d1fa9e7be9cd225 Mon Sep 17 00:00:00 2001 +Date: Fri, 19 Sep 2025 12:52:43 +0200 +Subject: [PATCH] gs-extras-page: Packages not found for "what-provides" + searches + +This is a regression after commit 22926c20b3f062082f689379b0d7b2946c35c958, +accidentally removed "allow-packages" flag for the app listing for one branch. + +Reported downstream at: https://bugzilla.redhat.com/show_bug.cgi?id=2395811 +--- + src/gs-extras-page.c | 1 + + 1 file changed, 1 insertion(+) + +diff --git a/src/gs-extras-page.c b/src/gs-extras-page.c +index 9d16c0eb9..0d8d786c1 100644 +--- a/src/gs-extras-page.c ++++ b/src/gs-extras-page.c +@@ -853,6 +853,7 @@ gs_extras_page_load (GsExtrasPage *self, GPtrArray *array_search_data) + + query = gs_app_query_new ("provides-tag", search_data->search, + "provides-type", search_data->search_provides_type, ++ "refine-flags", GS_PLUGIN_REFINE_FLAGS_ALLOW_PACKAGES, + "refine-require-flags", require_flags, + "license-type", gs_page_get_query_license_type (GS_PAGE (self)), + "developer-verified-type", gs_page_get_query_developer_verified_type (GS_PAGE (self)), +-- +2.49.0 + diff --git a/gnome-software.spec b/gnome-software.spec index 34328cf..91e0bd4 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -30,7 +30,7 @@ Name: gnome-software Version: 49.0 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -43,6 +43,8 @@ Source0: https://download.gnome.org/sources/gnome-software/49/%{name}-%{tarbal Patch: 0001-dnf5-plugin.patch %endif +Patch: 0002-gs-extras-page-Packages-not-found-for-what-provides-.patch + # ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 %if 0%{?fedora} || 0%{?rhel} >= 10 From 3364ed6d8c4f5b3536689bb260aac812ad3c6134 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 10 Oct 2025 08:47:16 +0200 Subject: [PATCH 159/163] Update to 49.1 --- ...ackages-not-found-for-what-provides-.patch | 28 ------------------- gnome-software.spec | 8 ++---- sources | 2 +- 3 files changed, 4 insertions(+), 34 deletions(-) delete mode 100644 0002-gs-extras-page-Packages-not-found-for-what-provides-.patch diff --git a/0002-gs-extras-page-Packages-not-found-for-what-provides-.patch b/0002-gs-extras-page-Packages-not-found-for-what-provides-.patch deleted file mode 100644 index 5d14caf..0000000 --- a/0002-gs-extras-page-Packages-not-found-for-what-provides-.patch +++ /dev/null @@ -1,28 +0,0 @@ -From 272cdf10b69a84f773ce203a4d1fa9e7be9cd225 Mon Sep 17 00:00:00 2001 -Date: Fri, 19 Sep 2025 12:52:43 +0200 -Subject: [PATCH] gs-extras-page: Packages not found for "what-provides" - searches - -This is a regression after commit 22926c20b3f062082f689379b0d7b2946c35c958, -accidentally removed "allow-packages" flag for the app listing for one branch. - -Reported downstream at: https://bugzilla.redhat.com/show_bug.cgi?id=2395811 ---- - src/gs-extras-page.c | 1 + - 1 file changed, 1 insertion(+) - -diff --git a/src/gs-extras-page.c b/src/gs-extras-page.c -index 9d16c0eb9..0d8d786c1 100644 ---- a/src/gs-extras-page.c -+++ b/src/gs-extras-page.c -@@ -853,6 +853,7 @@ gs_extras_page_load (GsExtrasPage *self, GPtrArray *array_search_data) - - query = gs_app_query_new ("provides-tag", search_data->search, - "provides-type", search_data->search_provides_type, -+ "refine-flags", GS_PLUGIN_REFINE_FLAGS_ALLOW_PACKAGES, - "refine-require-flags", require_flags, - "license-type", gs_page_get_query_license_type (GS_PAGE (self)), - "developer-verified-type", gs_page_get_query_developer_verified_type (GS_PAGE (self)), --- -2.49.0 - diff --git a/gnome-software.spec b/gnome-software.spec index 91e0bd4..e62923e 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -29,8 +29,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 49.0 -Release: 2%{?dist} +Version: 49.1 +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -43,8 +43,6 @@ Source0: https://download.gnome.org/sources/gnome-software/49/%{name}-%{tarbal Patch: 0001-dnf5-plugin.patch %endif -Patch: 0002-gs-extras-page-Packages-not-found-for-what-provides-.patch - # ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 %if 0%{?fedora} || 0%{?rhel} >= 10 @@ -162,7 +160,7 @@ This package includes the rpm-ostree backend. %endif %prep -%autosetup -p1 -S git -n %{name}-%{tarball_version} +%autosetup -p1 -S gendiff -n %{name}-%{tarball_version} %build %meson \ diff --git a/sources b/sources index 469fb06..f738461 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-49.0.tar.xz) = 7c63b0bd59e6ebe7ef526b438c6d0b234897edacfa72ab4846358ffa9e3d63ced2945f52a4d3111307e349b846be80cb4039b4cec25f7bc5ceba135d0a4fe343 +SHA512 (gnome-software-49.1.tar.xz) = 3475ea7d7062679192d4317a6ae278601acd5316d20eb6db9512407058e3b39bf6804443a272016d206cd97d12c8c9fdd883db96297e6b5866d80300ff48503a From 93f854207d7f0b44f2019701a3c1a2b854319f8f Mon Sep 17 00:00:00 2001 From: Yanko Kaneti Date: Fri, 10 Oct 2025 10:04:05 +0300 Subject: [PATCH 160/163] Add NEWS to docs --- gnome-software.spec | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gnome-software.spec b/gnome-software.spec index e62923e..78d502f 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -232,7 +232,7 @@ FOE desktop-file-validate %{buildroot}%{_datadir}/applications/*.desktop %files -f %{name}.lang -%doc AUTHORS README.md +%doc AUTHORS NEWS README.md %license COPYING %{_bindir}/gnome-software %{_datadir}/applications/gnome-software-local-file-flatpak.desktop From 2a31982d3e20fec1a199d87dbb4013d39de293a9 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Fri, 21 Nov 2025 11:10:15 +0100 Subject: [PATCH 161/163] Update to 49.2 --- gnome-software.spec | 2 +- sources | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/gnome-software.spec b/gnome-software.spec index 78d502f..3552763 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -29,7 +29,7 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 49.1 +Version: 49.2 Release: 1%{?dist} Summary: A software center for GNOME diff --git a/sources b/sources index f738461..0e06aac 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-49.1.tar.xz) = 3475ea7d7062679192d4317a6ae278601acd5316d20eb6db9512407058e3b39bf6804443a272016d206cd97d12c8c9fdd883db96297e6b5866d80300ff48503a +SHA512 (gnome-software-49.2.tar.xz) = 9ce33e2046b776f2a56c96d17eec85817e04bada9af9590125530c84bcc529f278bcba0c0ccdabcb459f92b326e0837cd63a9e316551ec313ac2f8720bf69835 From 095b81906e30c01f354627060e7229af28eafb36 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 24 Nov 2025 16:20:33 +0100 Subject: [PATCH 162/163] Add patch for bug #2416542 (Crash under gs_flatpak_refine_wildcard()) --- ...ash-under-gs_flatpak_refine_wildcard.patch | 155 ++++++++++++++++++ gnome-software.spec | 5 +- 2 files changed, 159 insertions(+), 1 deletion(-) create mode 100644 0002-rhbug2416542-crash-under-gs_flatpak_refine_wildcard.patch diff --git a/0002-rhbug2416542-crash-under-gs_flatpak_refine_wildcard.patch b/0002-rhbug2416542-crash-under-gs_flatpak_refine_wildcard.patch new file mode 100644 index 0000000..0150264 --- /dev/null +++ b/0002-rhbug2416542-crash-under-gs_flatpak_refine_wildcard.patch @@ -0,0 +1,155 @@ +diff --git a/plugins/flatpak/gs-flatpak.c b/plugins/flatpak/gs-flatpak.c +index b409475c7..a40ab54fb 100644 +--- a/plugins/flatpak/gs-flatpak.c ++++ b/plugins/flatpak/gs-flatpak.c +@@ -3748,16 +3748,19 @@ gboolean + gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, + GsAppList *list, GsPluginRefineRequireFlags require_flags, + gboolean interactive, ++ XbSilo **inout_silo, ++ gchar **inout_silo_filename, ++ GHashTable **inout_installed_by_desktopid, + GHashTable **inout_components_by_id, + GHashTable **inout_components_by_bundle, + GCancellable *cancellable, GError **error) + { + const gchar *id; + GPtrArray* components = NULL; ++ XbSilo *silo; ++ GHashTable *silo_installed_by_desktopid; ++ const gchar *silo_filename; + g_autoptr(GError) error_local = NULL; +- g_autoptr(XbSilo) silo = NULL; +- g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; +- g_autofree gchar *silo_filename = NULL; + + GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcard, "Flatpak (refine wildcard)", NULL); + +@@ -3766,10 +3769,15 @@ gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, + if (id == NULL) + return TRUE; + +- silo = gs_flatpak_ref_silo (self, interactive, &silo_filename, &silo_installed_by_desktopid, cancellable, error); +- if (silo == NULL) ++ if (*inout_silo == NULL) ++ *inout_silo = gs_flatpak_ref_silo (self, interactive, inout_silo_filename, inout_installed_by_desktopid, cancellable, error); ++ if (*inout_silo == NULL) + return FALSE; + ++ silo = *inout_silo; ++ silo_filename = *inout_silo_filename; ++ silo_installed_by_desktopid = *inout_installed_by_desktopid; ++ + GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardQuerySilo, "Flatpak (query silo)", NULL); + + if (*inout_components_by_id != NULL) { +diff --git a/plugins/flatpak/gs-flatpak.h b/plugins/flatpak/gs-flatpak.h +index 66ff59967..34e1416b5 100644 +--- a/plugins/flatpak/gs-flatpak.h ++++ b/plugins/flatpak/gs-flatpak.h +@@ -11,6 +11,7 @@ + + #include + #include ++#include + + G_BEGIN_DECLS + +@@ -108,6 +109,9 @@ gboolean gs_flatpak_refine_wildcard (GsFlatpak *self, + GsAppList *list, + GsPluginRefineRequireFlags require_flags, + gboolean interactive, ++ XbSilo **inout_silo, ++ gchar **inout_silo_filename, ++ GHashTable **inout_installed_by_desktopid, + GHashTable **inout_components_by_id, + GHashTable **inout_components_by_bundle, + GCancellable *cancellable, +diff --git a/plugins/flatpak/gs-plugin-flatpak.c b/plugins/flatpak/gs-plugin-flatpak.c +index 3d0503d46..f5d4a1d67 100644 +--- a/plugins/flatpak/gs-plugin-flatpak.c ++++ b/plugins/flatpak/gs-plugin-flatpak.c +@@ -667,12 +667,29 @@ gs_plugin_flatpak_refine_app (GsPluginFlatpak *self, + return gs_flatpak_refine_app (flatpak, app, require_flags, interactive, FALSE, event_callback, event_user_data, cancellable, error); + } + ++typedef struct { ++ XbSilo *silo; ++ gchar *silo_filename; ++ GHashTable *installed_by_desktopid; ++ GHashTable *components_by_id; ++ GHashTable *components_by_bundle; ++} RefineInstallationData; ++ + static void +-unref_nonnull_hash_table (gpointer ptr) ++refine_installation_data_free (gpointer ptr) + { +- GHashTable *hash_table = ptr; +- if (hash_table != NULL) +- g_hash_table_unref (hash_table); ++ RefineInstallationData *data = ptr; ++ ++ if (data == NULL) ++ return; ++ ++ g_clear_pointer (&data->silo_filename, g_free); ++ g_clear_pointer (&data->installed_by_desktopid, g_hash_table_unref); ++ g_clear_pointer (&data->components_by_id, g_hash_table_unref); ++ g_clear_pointer (&data->components_by_bundle, g_hash_table_unref); ++ /* free the silo as the last, just in case, because the data from it is in the above hash tables */ ++ g_clear_object (&data->silo); ++ g_free (data); + } + + static gboolean +@@ -761,8 +778,7 @@ refine_thread_cb (GTask *task, + gboolean interactive = (data->job_flags & GS_PLUGIN_REFINE_FLAGS_INTERACTIVE) != 0; + GsPluginEventCallback event_callback = data->event_callback; + void *event_user_data = data->event_user_data; +- g_autoptr(GPtrArray) array_components_by_id = NULL; /* (element-type GHashTable) */ +- g_autoptr(GPtrArray) array_components_by_bundle = NULL; /* (element-type GHashTable) */ ++ g_autoptr(GPtrArray) installation_data = NULL; /* (element-type RefineInstallationData) */ + g_autoptr(GsAppList) app_list = NULL; + g_autoptr(GError) local_error = NULL; + +@@ -783,10 +799,9 @@ refine_thread_cb (GTask *task, + * (e.g. inserting an app in the list on every call results in + * an infinite loop) */ + app_list = gs_app_list_copy (list); +- array_components_by_id = g_ptr_array_new_full (self->installations->len, unref_nonnull_hash_table); +- g_ptr_array_set_size (array_components_by_id, self->installations->len); +- array_components_by_bundle = g_ptr_array_new_full (self->installations->len, unref_nonnull_hash_table); +- g_ptr_array_set_size (array_components_by_bundle, self->installations->len); ++ ++ installation_data = g_ptr_array_new_full (self->installations->len, refine_installation_data_free); ++ g_ptr_array_set_size (installation_data, self->installations->len); + + for (guint j = 0; j < gs_app_list_length (app_list); j++) { + GsApp *app = gs_app_list_index (app_list, j); +@@ -796,16 +811,20 @@ refine_thread_cb (GTask *task, + + for (guint i = 0; i < self->installations->len; i++) { + GsFlatpak *flatpak = g_ptr_array_index (self->installations, i); +- GHashTable *components_by_id = array_components_by_id->pdata[i]; +- GHashTable *components_by_bundle = array_components_by_bundle->pdata[i]; ++ RefineInstallationData *inst_data = g_ptr_array_index (installation_data, i); ++ ++ if (inst_data == NULL) { ++ inst_data = g_new0 (RefineInstallationData, 1); ++ installation_data->pdata[i] = inst_data; ++ } + +- if (!gs_flatpak_refine_wildcard (flatpak, app, list, require_flags, interactive, &components_by_id, &components_by_bundle, ++ if (!gs_flatpak_refine_wildcard (flatpak, app, list, require_flags, interactive, &inst_data->silo, ++ &inst_data->silo_filename, &inst_data->installed_by_desktopid, ++ &inst_data->components_by_id, &inst_data->components_by_bundle, + cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } +- array_components_by_id->pdata[i] = components_by_id; +- array_components_by_bundle->pdata[i] = components_by_bundle; + } + } + diff --git a/gnome-software.spec b/gnome-software.spec index 3552763..6830ae0 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -30,7 +30,7 @@ Name: gnome-software Version: 49.2 -Release: 1%{?dist} +Release: 2%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later @@ -43,6 +43,9 @@ Source0: https://download.gnome.org/sources/gnome-software/49/%{name}-%{tarbal Patch: 0001-dnf5-plugin.patch %endif +# https://bugzilla.redhat.com/show_bug.cgi?id=2416542 +Patch: 0002-rhbug2416542-crash-under-gs_flatpak_refine_wildcard.patch + # ostree and flatpak not on i686 for Fedora and RHEL 10 # https://github.com/containers/composefs/pull/229#issuecomment-1838735764 %if 0%{?fedora} || 0%{?rhel} >= 10 From a10b3cf10fff31405ee2087b87c1a7d8d139fd29 Mon Sep 17 00:00:00 2001 From: Milan Crha Date: Mon, 12 Jan 2026 17:23:11 +0100 Subject: [PATCH 163/163] Update to 49.3 --- ...ash-under-gs_flatpak_refine_wildcard.patch | 531 ++++++++++++++++++ gnome-software.spec | 4 +- sources | 2 +- 3 files changed, 534 insertions(+), 3 deletions(-) diff --git a/0002-rhbug2416542-crash-under-gs_flatpak_refine_wildcard.patch b/0002-rhbug2416542-crash-under-gs_flatpak_refine_wildcard.patch index 0150264..33140df 100644 --- a/0002-rhbug2416542-crash-under-gs_flatpak_refine_wildcard.patch +++ b/0002-rhbug2416542-crash-under-gs_flatpak_refine_wildcard.patch @@ -1,3 +1,26 @@ +From 0c79d9fb08a348a45a18f15427c945a63b44982e Mon Sep 17 00:00:00 2001 +Date: Mon, 24 Nov 2025 16:06:51 +0100 +Subject: [PATCH 1/3] flatpak: Fix XbSilo lifetime in + gs_flatpak_refine_wildcard() + +The function uses pre-cached data in the hash tables, consisting of XbNode-s +from an XbSilo. The nodes are referenced, but the silos the node belongs to +is not referenced (by the XbNode). + +This change keeps the XbSilo alive as long as it's needed for the nodes +in the pre-cached data. It also does not call gs_flatpak_ref_silo() multiple +times for the same GsFlatpak instance, which could invalidate the XbNode-s +in the pre-cached data when a change in the silo or in the installation +had been received while the function was still processing the apps. + +Related downstream bug https://bugzilla.redhat.com/show_bug.cgi?id=2416542 +Closes https://gitlab.gnome.org/GNOME/gnome-software/-/issues/2900 +--- + plugins/flatpak/gs-flatpak.c | 18 ++++++++--- + plugins/flatpak/gs-flatpak.h | 4 +++ + plugins/flatpak/gs-plugin-flatpak.c | 49 ++++++++++++++++++++--------- + 3 files changed, 51 insertions(+), 20 deletions(-) + diff --git a/plugins/flatpak/gs-flatpak.c b/plugins/flatpak/gs-flatpak.c index b409475c7..a40ab54fb 100644 --- a/plugins/flatpak/gs-flatpak.c @@ -153,3 +176,511 @@ index 3d0503d46..f5d4a1d67 100644 } } +-- +GitLab + + +From 546c6ee17b5959d2a696a6cb346a1f8b94aba303 Mon Sep 17 00:00:00 2001 +Date: Wed, 7 Jan 2026 18:37:52 +0100 +Subject: [PATCH 2/3] flatpak: Simplify wildcard app lookup function + +By flipping the order of traversing app and installation the code +can be simplified to not have too many in/out arguments. + +Suggested by Philip Withnall +--- + plugins/flatpak/gs-flatpak.c | 251 ++++++++++++++-------------- + plugins/flatpak/gs-flatpak.h | 9 +- + plugins/flatpak/gs-plugin-flatpak.c | 61 +------ + 3 files changed, 130 insertions(+), 191 deletions(-) + +diff --git a/plugins/flatpak/gs-flatpak.c b/plugins/flatpak/gs-flatpak.c +index a40ab54fb..782b0bb48 100644 +--- a/plugins/flatpak/gs-flatpak.c ++++ b/plugins/flatpak/gs-flatpak.c +@@ -3745,167 +3745,158 @@ gs_flatpak_refine_app (GsFlatpak *self, + } + + gboolean +-gs_flatpak_refine_wildcard (GsFlatpak *self, GsApp *app, +- GsAppList *list, GsPluginRefineRequireFlags require_flags, +- gboolean interactive, +- XbSilo **inout_silo, +- gchar **inout_silo_filename, +- GHashTable **inout_installed_by_desktopid, +- GHashTable **inout_components_by_id, +- GHashTable **inout_components_by_bundle, +- GCancellable *cancellable, GError **error) ++gs_flatpak_refine_wildcards (GsFlatpak *self, ++ GPtrArray *wildcard_apps, ++ GsAppList *list, ++ GsPluginRefineRequireFlags require_flags, ++ gboolean interactive, ++ GCancellable *cancellable, ++ GError **error) + { +- const gchar *id; +- GPtrArray* components = NULL; +- XbSilo *silo; +- GHashTable *silo_installed_by_desktopid; +- const gchar *silo_filename; + g_autoptr(GError) error_local = NULL; ++ g_autoptr(XbSilo) silo = NULL; ++ g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; ++ g_autoptr(GHashTable) components_by_id = NULL; ++ g_autoptr(GHashTable) components_by_bundle = NULL; ++ g_autoptr(GPtrArray) components_with_id = NULL; ++ g_autoptr(GPtrArray) bundles = NULL; ++ g_autofree gchar *silo_filename = NULL; + + GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcard, "Flatpak (refine wildcard)", NULL); + +- /* not enough info to find */ +- id = gs_app_get_id (app); +- if (id == NULL) +- return TRUE; +- +- if (*inout_silo == NULL) +- *inout_silo = gs_flatpak_ref_silo (self, interactive, inout_silo_filename, inout_installed_by_desktopid, cancellable, error); +- if (*inout_silo == NULL) ++ silo = gs_flatpak_ref_silo (self, interactive, &silo_filename, &silo_installed_by_desktopid, cancellable, error); ++ if (silo == NULL) + return FALSE; + +- silo = *inout_silo; +- silo_filename = *inout_silo_filename; +- silo_installed_by_desktopid = *inout_installed_by_desktopid; +- + GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardQuerySilo, "Flatpak (query silo)", NULL); + +- if (*inout_components_by_id != NULL) { +- components = g_hash_table_lookup (*inout_components_by_id, gs_app_get_id (app)); +- } else { +- g_autoptr(GPtrArray) components_with_id = NULL; +- *inout_components_by_id = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify) g_ptr_array_unref); +- components_with_id = xb_silo_query (silo, "components/component/id", 0, &error_local); +- if (components_with_id == NULL) { +- if (g_error_matches (error_local, G_IO_ERROR, G_IO_ERROR_NOT_FOUND)) +- return TRUE; +- g_propagate_error (error, g_steal_pointer (&error_local)); +- return FALSE; ++ components_by_id = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify) g_ptr_array_unref); ++ components_with_id = xb_silo_query (silo, "components/component/id", 0, &error_local); ++ if (components_with_id == NULL) { ++ if (g_error_matches (error_local, G_IO_ERROR, G_IO_ERROR_NOT_FOUND)) ++ return TRUE; ++ g_propagate_error (error, g_steal_pointer (&error_local)); ++ return FALSE; ++ } ++ ++ for (guint i = 0; i < components_with_id->len; i++) { ++ XbNode *node = g_ptr_array_index (components_with_id, i); ++ XbNode *comp_node = xb_node_get_parent (node); ++ const gchar *comp_id = xb_node_get_text (node); ++ GPtrArray *comps = g_hash_table_lookup (components_by_id, comp_id); ++ if (comps == NULL) { ++ comps = g_ptr_array_new_with_free_func (g_object_unref); ++ g_hash_table_insert (components_by_id, g_strdup (comp_id), comps); + } +- for (guint i = 0; i < components_with_id->len; i++) { +- XbNode *node = g_ptr_array_index (components_with_id, i); +- XbNode *comp_node = xb_node_get_parent (node); +- const gchar *comp_id = xb_node_get_text (node); +- GPtrArray *comps = g_hash_table_lookup (*inout_components_by_id, comp_id); +- if (comps == NULL) { +- comps = g_ptr_array_new_with_free_func (g_object_unref); +- g_hash_table_insert (*inout_components_by_id, g_strdup (comp_id), comps); ++ g_ptr_array_add (comps, comp_node); ++ } ++ ++ components_by_bundle = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_object_unref); ++ bundles = xb_silo_query (silo, "/components/component/bundle[@type='flatpak']", 0, NULL); ++ for (guint b = 0; bundles != NULL && b < bundles->len; b++) { ++ XbNode *bundle_node = g_ptr_array_index (bundles, b); ++ g_autoptr(XbNode) component_node = xb_node_get_parent (bundle_node); ++ g_autoptr(XbNode) components_node = xb_node_get_parent (component_node); ++ const gchar *origin = xb_node_get_attr (components_node, "origin"); ++ if (origin != NULL) { ++ const gchar *bundle = xb_node_get_text (bundle_node); ++ if (bundle != NULL) { ++ g_autofree gchar *key = g_strconcat (origin, "\n", bundle, NULL); ++ g_hash_table_insert (components_by_bundle, g_steal_pointer (&key), g_steal_pointer (&component_node)); + } +- g_ptr_array_add (comps, comp_node); +- if (components == NULL && g_strcmp0 (id, comp_id) == 0) +- components = comps; + } + } + + GS_PROFILER_END_SCOPED (FlatpakRefineWildcardQuerySilo); + +- if (components == NULL) +- return TRUE; +- + gs_flatpak_ensure_remote_title (self, interactive, cancellable); + +- if (*inout_components_by_bundle == NULL) { +- g_autoptr(GPtrArray) bundles = NULL; +- +- *inout_components_by_bundle = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_object_unref); +- bundles = xb_silo_query (silo, "/components/component/bundle[@type='flatpak']", 0, NULL); +- for (guint b = 0; bundles != NULL && b < bundles->len; b++) { +- XbNode *bundle_node = g_ptr_array_index (bundles, b); +- g_autoptr(XbNode) component_node = xb_node_get_parent (bundle_node); +- g_autoptr(XbNode) components_node = xb_node_get_parent (component_node); +- const gchar *origin = xb_node_get_attr (components_node, "origin"); +- if (origin != NULL) { +- const gchar *bundle = xb_node_get_text (bundle_node); +- if (bundle != NULL) { +- g_autofree gchar *key = g_strconcat (origin, "\n", bundle, NULL); +- g_hash_table_insert (*inout_components_by_bundle, g_steal_pointer (&key), g_steal_pointer (&component_node)); +- } +- } +- } +- } ++ for (guint j = 0; j < wildcard_apps->len; j++) { ++ GsApp *app = g_ptr_array_index (wildcard_apps, j); ++ GPtrArray *components = NULL; ++ const gchar *id; + ++ /* not enough info to find */ ++ id = gs_app_get_id (app); ++ if (id == NULL) ++ continue; + +- GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardGenerateApps, "Flatpak (create app)", NULL); +- for (guint i = 0; i < components->len; i++) { +- XbNode *component = g_ptr_array_index (components, i); +- g_autoptr(GsApp) new = NULL; ++ components = g_hash_table_lookup (components_by_id, id); ++ if (components == NULL) ++ continue; + +- GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardCreateAppstreamApp, "Flatpak (create Appstream app)", NULL); +- new = gs_appstream_create_app (self->plugin, silo, component, silo_filename ? silo_filename : "", +- self->scope, error); +- GS_PROFILER_END_SCOPED (FlatpakRefineWildcardCreateAppstreamApp); ++ GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardGenerateApps, "Flatpak (create app)", NULL); ++ for (guint i = 0; i < components->len; i++) { ++ XbNode *component = g_ptr_array_index (components, i); ++ g_autoptr(GsApp) new = NULL; + +- if (new == NULL) +- return FALSE; ++ GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardCreateAppstreamApp, "Flatpak (create Appstream app)", NULL); ++ new = gs_appstream_create_app (self->plugin, silo, component, silo_filename ? silo_filename : "", ++ self->scope, error); ++ GS_PROFILER_END_SCOPED (FlatpakRefineWildcardCreateAppstreamApp); + +- gs_flatpak_claim_app (self, new); +- +- /* The appstream plugin did not find the component in the plugin's cache, +- thus read the required info from the 'bundle' element. */ +- if (gs_flatpak_app_get_ref_name (new) == NULL || +- gs_flatpak_app_get_ref_arch (new) == NULL) { +- const gchar *xref_str = NULL; +- g_autoptr(XbNode) child = NULL; +- g_autoptr(XbNode) next = NULL; +- for (child = xb_node_get_child (component); child != NULL && xref_str == NULL; +- g_object_unref (child), child = g_steal_pointer (&next)) { +- next = xb_node_get_next (child); +- if (g_strcmp0 (xb_node_get_element (child), "bundle") == 0 && +- g_strcmp0 (xb_node_get_attr (child, "type"), "flatpak") == 0) { +- xref_str = xb_node_get_text (child); +- break; ++ if (new == NULL) ++ return FALSE; ++ ++ gs_flatpak_claim_app (self, new); ++ ++ /* The appstream plugin did not find the component in the plugin's cache, ++ thus read the required info from the 'bundle' element. */ ++ if (gs_flatpak_app_get_ref_name (new) == NULL || ++ gs_flatpak_app_get_ref_arch (new) == NULL) { ++ const gchar *xref_str = NULL; ++ g_autoptr(XbNode) child = NULL; ++ g_autoptr(XbNode) next = NULL; ++ for (child = xb_node_get_child (component); child != NULL && xref_str == NULL; ++ g_object_unref (child), child = g_steal_pointer (&next)) { ++ next = xb_node_get_next (child); ++ if (g_strcmp0 (xb_node_get_element (child), "bundle") == 0 && ++ g_strcmp0 (xb_node_get_attr (child, "type"), "flatpak") == 0) { ++ xref_str = xb_node_get_text (child); ++ break; ++ } + } +- } +- if (xref_str != NULL) { +- g_auto(GStrv) split = NULL; +- +- /* get the kind/name/arch/branch */ +- split = g_strsplit (xref_str, "/", -1); +- if (g_strv_length (split) == 4) { +- const gchar *comp_type = xb_node_get_attr (component, "type"); +- AsComponentKind kind = as_component_kind_from_string (comp_type); +- if (kind != AS_COMPONENT_KIND_UNKNOWN) +- gs_app_set_kind (new, kind); +- else if (g_ascii_strcasecmp (split[0], "app") == 0) +- gs_app_set_kind (new, AS_COMPONENT_KIND_DESKTOP_APP); +- else if (g_ascii_strcasecmp (split[0], "runtime") == 0) +- gs_flatpak_set_runtime_kind_from_id (new); +- gs_flatpak_app_set_ref_name (new, split[1]); +- gs_flatpak_app_set_ref_arch (new, split[2]); +- gs_app_set_branch (new, split[3]); +- gs_app_set_metadata (new, "GnomeSoftware::packagename-value", xref_str); ++ if (xref_str != NULL) { ++ g_auto(GStrv) split = NULL; ++ ++ /* get the kind/name/arch/branch */ ++ split = g_strsplit (xref_str, "/", -1); ++ if (g_strv_length (split) == 4) { ++ const gchar *comp_type = xb_node_get_attr (component, "type"); ++ AsComponentKind kind = as_component_kind_from_string (comp_type); ++ if (kind != AS_COMPONENT_KIND_UNKNOWN) ++ gs_app_set_kind (new, kind); ++ else if (g_ascii_strcasecmp (split[0], "app") == 0) ++ gs_app_set_kind (new, AS_COMPONENT_KIND_DESKTOP_APP); ++ else if (g_ascii_strcasecmp (split[0], "runtime") == 0) ++ gs_flatpak_set_runtime_kind_from_id (new); ++ gs_flatpak_app_set_ref_name (new, split[1]); ++ gs_flatpak_app_set_ref_arch (new, split[2]); ++ gs_app_set_branch (new, split[3]); ++ gs_app_set_metadata (new, "GnomeSoftware::packagename-value", xref_str); ++ } + } + } +- } + +- if (gs_flatpak_app_get_ref_name (new) == NULL || +- gs_flatpak_app_get_ref_arch (new) == NULL) { +- g_debug ("Failed to get ref info for '%s' from wildcard '%s', skipping it...", gs_app_get_id (new), id); +- } else { +- GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardRefineNewApp, "Flatpak (refine new app)", NULL); +- if (!gs_flatpak_refine_app_internal (self, new, require_flags, interactive, FALSE, *inout_components_by_bundle, +- silo, silo_filename, silo_installed_by_desktopid, cancellable, error)) +- return FALSE; +- GS_PROFILER_END_SCOPED (FlatpakRefineWildcardRefineNewApp); ++ if (gs_flatpak_app_get_ref_name (new) == NULL || ++ gs_flatpak_app_get_ref_arch (new) == NULL) { ++ g_debug ("Failed to get ref info for '%s' from wildcard '%s', skipping it...", gs_app_get_id (new), id); ++ } else { ++ GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardRefineNewApp, "Flatpak (refine new app)", NULL); ++ if (!gs_flatpak_refine_app_internal (self, new, require_flags, interactive, FALSE, components_by_bundle, ++ silo, silo_filename, silo_installed_by_desktopid, cancellable, error)) ++ return FALSE; ++ GS_PROFILER_END_SCOPED (FlatpakRefineWildcardRefineNewApp); + +- GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardSubsumeMetadata, "Flatpak (subsume metadata)", NULL); +- gs_app_subsume_metadata (new, app); +- GS_PROFILER_END_SCOPED (FlatpakRefineWildcardSubsumeMetadata); ++ GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcardSubsumeMetadata, "Flatpak (subsume metadata)", NULL); ++ gs_app_subsume_metadata (new, app); ++ GS_PROFILER_END_SCOPED (FlatpakRefineWildcardSubsumeMetadata); + +- gs_app_list_add (list, new); ++ gs_app_list_add (list, new); ++ } + } ++ GS_PROFILER_END_SCOPED (FlatpakRefineWildcardGenerateApps); + } +- GS_PROFILER_END_SCOPED (FlatpakRefineWildcardGenerateApps); + + GS_PROFILER_END_SCOPED (FlatpakRefineWildcard); + +diff --git a/plugins/flatpak/gs-flatpak.h b/plugins/flatpak/gs-flatpak.h +index 34e1416b5..1f7d35a8f 100644 +--- a/plugins/flatpak/gs-flatpak.h ++++ b/plugins/flatpak/gs-flatpak.h +@@ -104,16 +104,11 @@ gboolean gs_flatpak_refine_app_state (GsFlatpak *self, + void *event_user_data, + GCancellable *cancellable, + GError **error); +-gboolean gs_flatpak_refine_wildcard (GsFlatpak *self, +- GsApp *app, ++gboolean gs_flatpak_refine_wildcards (GsFlatpak *self, ++ GPtrArray *wildcard_apps, + GsAppList *list, + GsPluginRefineRequireFlags require_flags, + gboolean interactive, +- XbSilo **inout_silo, +- gchar **inout_silo_filename, +- GHashTable **inout_installed_by_desktopid, +- GHashTable **inout_components_by_id, +- GHashTable **inout_components_by_bundle, + GCancellable *cancellable, + GError **error); + gboolean gs_flatpak_launch (GsFlatpak *self, +diff --git a/plugins/flatpak/gs-plugin-flatpak.c b/plugins/flatpak/gs-plugin-flatpak.c +index f5d4a1d67..c06b1fb5f 100644 +--- a/plugins/flatpak/gs-plugin-flatpak.c ++++ b/plugins/flatpak/gs-plugin-flatpak.c +@@ -667,31 +667,6 @@ gs_plugin_flatpak_refine_app (GsPluginFlatpak *self, + return gs_flatpak_refine_app (flatpak, app, require_flags, interactive, FALSE, event_callback, event_user_data, cancellable, error); + } + +-typedef struct { +- XbSilo *silo; +- gchar *silo_filename; +- GHashTable *installed_by_desktopid; +- GHashTable *components_by_id; +- GHashTable *components_by_bundle; +-} RefineInstallationData; +- +-static void +-refine_installation_data_free (gpointer ptr) +-{ +- RefineInstallationData *data = ptr; +- +- if (data == NULL) +- return; +- +- g_clear_pointer (&data->silo_filename, g_free); +- g_clear_pointer (&data->installed_by_desktopid, g_hash_table_unref); +- g_clear_pointer (&data->components_by_id, g_hash_table_unref); +- g_clear_pointer (&data->components_by_bundle, g_hash_table_unref); +- /* free the silo as the last, just in case, because the data from it is in the above hash tables */ +- g_clear_object (&data->silo); +- g_free (data); +-} +- + static gboolean + refine_app (GsPluginFlatpak *self, + GsApp *app, +@@ -778,8 +753,7 @@ refine_thread_cb (GTask *task, + gboolean interactive = (data->job_flags & GS_PLUGIN_REFINE_FLAGS_INTERACTIVE) != 0; + GsPluginEventCallback event_callback = data->event_callback; + void *event_user_data = data->event_user_data; +- g_autoptr(GPtrArray) installation_data = NULL; /* (element-type RefineInstallationData) */ +- g_autoptr(GsAppList) app_list = NULL; ++ g_autoptr(GPtrArray) wildcard_apps = g_ptr_array_new_with_free_func (g_object_unref); /* (element-type GsApp) (owned) */ + g_autoptr(GError) local_error = NULL; + + assert_in_worker (self); +@@ -790,38 +764,17 @@ refine_thread_cb (GTask *task, + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } +- } +- +- /* Refine wildcards. +- * +- * Use a copy of the list for the loop because a function called +- * on the plugin may affect the list which can lead to problems +- * (e.g. inserting an app in the list on every call results in +- * an infinite loop) */ +- app_list = gs_app_list_copy (list); +- +- installation_data = g_ptr_array_new_full (self->installations->len, refine_installation_data_free); +- g_ptr_array_set_size (installation_data, self->installations->len); +- +- for (guint j = 0; j < gs_app_list_length (app_list); j++) { +- GsApp *app = gs_app_list_index (app_list, j); + +- if (!gs_app_has_quirk (app, GS_APP_QUIRK_IS_WILDCARD)) +- continue; ++ if (gs_app_has_quirk (app, GS_APP_QUIRK_IS_WILDCARD) && gs_app_get_id (app) != NULL) ++ g_ptr_array_add (wildcard_apps, g_object_ref (app)); ++ } + ++ /* Refine wildcards. */ ++ if (wildcard_apps->len > 0) { + for (guint i = 0; i < self->installations->len; i++) { + GsFlatpak *flatpak = g_ptr_array_index (self->installations, i); +- RefineInstallationData *inst_data = g_ptr_array_index (installation_data, i); +- +- if (inst_data == NULL) { +- inst_data = g_new0 (RefineInstallationData, 1); +- installation_data->pdata[i] = inst_data; +- } + +- if (!gs_flatpak_refine_wildcard (flatpak, app, list, require_flags, interactive, &inst_data->silo, +- &inst_data->silo_filename, &inst_data->installed_by_desktopid, +- &inst_data->components_by_id, &inst_data->components_by_bundle, +- cancellable, &local_error)) { ++ if (!gs_flatpak_refine_wildcards (flatpak, wildcard_apps, list, require_flags, interactive, cancellable, &local_error)) { + g_task_return_error (task, g_steal_pointer (&local_error)); + return; + } +-- +GitLab + + +From 8472d717356a801e6c0171156738ea48480fa695 Mon Sep 17 00:00:00 2001 +Date: Wed, 7 Jan 2026 18:45:47 +0100 +Subject: [PATCH 3/3] flatpak: Hold silo lock when refining wildcard apps + +The refine can take a long time, thus hold the silo lock to not have +it invalidated from another thread. Object reference is not enough +for the XbSilo, it breaks as soon as the underlying file changes. +--- + plugins/flatpak/gs-flatpak.c | 16 +++++++++++----- + 1 file changed, 11 insertions(+), 5 deletions(-) + +diff --git a/plugins/flatpak/gs-flatpak.c b/plugins/flatpak/gs-flatpak.c +index 782b0bb48..c5437125d 100644 +--- a/plugins/flatpak/gs-flatpak.c ++++ b/plugins/flatpak/gs-flatpak.c +@@ -59,7 +59,7 @@ struct _GsFlatpak { + AsComponentScope scope; + GsPlugin *plugin; + XbSilo *silo; +- GMutex silo_lock; ++ GRecMutex silo_lock; + gchar *silo_filename; + GHashTable *silo_installed_by_desktopid; + gint silo_change_stamp; +@@ -1187,11 +1187,11 @@ gs_flatpak_ref_silo (GsFlatpak *self, + g_autoptr(GFile) file = NULL; + g_autoptr(GPtrArray) xremotes = NULL; + g_autoptr(GPtrArray) desktop_paths = NULL; +- g_autoptr(GMutexLocker) locker = NULL; ++ g_autoptr(GRecMutexLocker) locker = NULL; + g_autoptr(XbBuilder) builder = NULL; + g_autoptr(GMainContext) old_thread_default = NULL; + +- locker = g_mutex_locker_new (&self->silo_lock); ++ locker = g_rec_mutex_locker_new (&self->silo_lock); + /* everything is okay */ + if (self->silo != NULL && xb_silo_is_valid (self->silo) && + g_atomic_int_get (&self->silo_change_stamp_current) == g_atomic_int_get (&self->silo_change_stamp)) { +@@ -3754,6 +3754,7 @@ gs_flatpak_refine_wildcards (GsFlatpak *self, + GError **error) + { + g_autoptr(GError) error_local = NULL; ++ g_autoptr(GRecMutexLocker) silo_locker = NULL; + g_autoptr(XbSilo) silo = NULL; + g_autoptr(GHashTable) silo_installed_by_desktopid = NULL; + g_autoptr(GHashTable) components_by_id = NULL; +@@ -3764,6 +3765,11 @@ gs_flatpak_refine_wildcards (GsFlatpak *self, + + GS_PROFILER_BEGIN_SCOPED (FlatpakRefineWildcard, "Flatpak (refine wildcard)", NULL); + ++ /* the refine can take a long time, thus hold the silo lock to not have ++ it invalidated from another thread; object reference is not enough ++ for the XbSilo, it breaks as soon as the underlying file changes */ ++ silo_locker = g_rec_mutex_locker_new (&self->silo_lock); ++ + silo = gs_flatpak_ref_silo (self, interactive, &silo_filename, &silo_installed_by_desktopid, cancellable, error); + if (silo == NULL) + return FALSE; +@@ -4810,7 +4816,7 @@ gs_flatpak_finalize (GObject *object) + g_object_unref (self->plugin); + g_hash_table_unref (self->broken_remotes); + g_mutex_clear (&self->broken_remotes_mutex); +- g_mutex_clear (&self->silo_lock); ++ g_rec_mutex_clear (&self->silo_lock); + g_hash_table_unref (self->app_silos); + g_mutex_clear (&self->app_silos_mutex); + g_clear_pointer (&self->remote_title, g_hash_table_unref); +@@ -4831,7 +4837,7 @@ gs_flatpak_init (GsFlatpak *self) + { + /* XbSilo needs external locking as we destroy the silo and build a new + * one when something changes */ +- g_mutex_init (&self->silo_lock); ++ g_rec_mutex_init (&self->silo_lock); + + g_mutex_init (&self->installed_refs_mutex); + self->installed_refs = NULL; +-- +GitLab + diff --git a/gnome-software.spec b/gnome-software.spec index 6830ae0..c080ede 100644 --- a/gnome-software.spec +++ b/gnome-software.spec @@ -29,8 +29,8 @@ %global __provides_exclude_from ^%{_libdir}/%{name}/plugins-%{gs_plugin_version}/.*\\.so.*$ Name: gnome-software -Version: 49.2 -Release: 2%{?dist} +Version: 49.3 +Release: 1%{?dist} Summary: A software center for GNOME License: GPL-2.0-or-later diff --git a/sources b/sources index 0e06aac..c24e704 100644 --- a/sources +++ b/sources @@ -1 +1 @@ -SHA512 (gnome-software-49.2.tar.xz) = 9ce33e2046b776f2a56c96d17eec85817e04bada9af9590125530c84bcc529f278bcba0c0ccdabcb459f92b326e0837cd63a9e316551ec313ac2f8720bf69835 +SHA512 (gnome-software-49.3.tar.xz) = 0414ea55ad3b83bcd50514985e3d2026207801c040934805bb26d162e88f0619a9d70aa6ba324a29acfab02573490b928c83594b54f57ec2a8ad00e6c127f657