Skip to content

Commit

Permalink
hawkey.subject: get_best_selectors only obsoleters of latest
Browse files Browse the repository at this point in the history
In situation where a package exists in multiple versions and some older
version is being obsoleted, any of obsoleters was considered a valid
solution.

The result could be really misleading. For example let's have this package set:

systemd-udev-1.0

systemd-udev-2.0
Obsoletes: systemd-udev < 2

systemd-boot-unsigned-2.0
Obsoletes: systemd-udev < 2

In this case `dnf install systemd-udev` may lead to installation of
systemd-boot-unsigned which is probably not what the user expected. The
reason is the split in the upgrade-path created by obsolete and both
branches - systemd-udev-2.0 and systemd-boot-unsigned-2.0 are considered
valid.

With this patch install command takes into account only obsoleters of
the best version of the package so the `dnf install systemd-udev`
results in correct installation of systemd-udev-2.0 package.

Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=2183279
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=2176263
  • Loading branch information
m-blaha authored and j-mracek committed Sep 22, 2023
1 parent 10958ca commit 5363ff0
Showing 1 changed file with 14 additions and 3 deletions.
17 changes: 14 additions & 3 deletions python/hawkey/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -291,13 +291,13 @@ def _get_best_selectors(self, base, forms=None, obsoletes=True, reponame=None, r
# after movement of base.install() or base.distro_sync()
return []

installed_query = q.installed()
if not self._filename_pattern and is_glob_pattern(self.pattern) \
or solution['nevra'] and solution['nevra'].name is None:
with_obsoletes = False

if obsoletes and solution['nevra'] and solution['nevra'].has_just_name():
with_obsoletes = True
installed_query = q.installed()
if reponame:
q = q.filter(reponame=reponame)
available_query = q.available()
Expand All @@ -309,13 +309,24 @@ def _get_best_selectors(self, base, forms=None, obsoletes=True, reponame=None, r
sltrs = []
for name, pkgs_list in q._name_dict().items():
if with_obsoletes:
# If there is no installed package in the pkgs_list, add only
# obsoleters of the latest versions. Otherwise behave consistently
# with upgrade and add all obsoleters.
# See https://bugzilla.redhat.com/show_bug.cgi?id=2176263
# for details of the problem.
obsoletes_query = base.sack.query().filterm(pkg=pkgs_list)
if not obsoletes_query.installed():
obsoletes_query.filterm(latest_per_arch_by_priority=True)
pkgs_list = pkgs_list + base.sack.query().filter(
obsoletes=pkgs_list).run()
obsoletes=obsoletes_query).run()
sltrs.append(self._list_or_query_to_selector(base.sack, pkgs_list))
return sltrs
else:
if obsoletes and solution['nevra'] and solution['nevra'].has_just_name():
q = q.union(base.sack.query().filter(obsoletes=q))
if installed_query:
q = q.union(base.sack.query().filter(obsoletes=q))
else:
q = q.union(base.sack.query().filter(obsoletes=q.filter(latest_per_arch_by_priority=True)))
installed_query = q.installed()

if reports:
Expand Down

0 comments on commit 5363ff0

Please sign in to comment.