Skip to content

RpmPackageProvides fails to handle some virtual packages #1643

@yacoob

Description

@yacoob

Describe the bug

Affected code: pyinfra/facts/rpm.py, RpmPackageProvides class

On Fedora 43+, repoquery is no longer a standalone binary; it's a subcommand of dnf5. The fact's requires_command returns "repoquery", which generates a ! command -v repoquery >/dev/null guard that short-circuits the entire lookup. Result: virtual package provides are never resolved, and dnf.packages always tries to reinstall packages like iotop (provided by iotop-c). There's dnf-utils that provides repoquery command, but that only solves half of the problem.

On top of that, I think this code path also fails to account for situation where there are multiple packages that provide the same package as the one requested. Even with repoquery available as a standalone binary:

    [@docker/51ac0676abff] Loaded fact rpm.RpmPackages
[@docker/51ac0676abff] >>> sh -c 'docker exec -i 51ac0676abff sh -c '"'"'sh -c '"'"'"'"'"'"'"'"'! command -v repoquery >/dev/null || ( repoquery --queryformat '"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'%{NAME} %{VERSION}-%{RELEASE}\n'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"'"' --whatprovides wget || true )'"'"'"'"'"'"'"'"''"'"''
[@docker/51ac0676abff] Emulate Docker CLI using podman. Create /etc/containers/nodocker to quiet msg.
[@docker/51ac0676abff] Last metadata expiration check: 0:10:31 ago on Sun Mar 29 20:53:43 2026.
[@docker/51ac0676abff] wget1-wget 1.25.0-2.fc43
[@docker/51ac0676abff]
[@docker/51ac0676abff] wget2-wget 2.2.0-6.fc43
[@docker/51ac0676abff]
[@docker/51ac0676abff] wget2-wget 2.2.1-1.fc43
[@docker/51ac0676abff]
    [@docker/51ac0676abff] Loaded fact rpm.RpmPackageProvides (package=wget)
[@docker/51ac0676abff] >>> sh -c 'docker exec -i 51ac0676abff sh -c '"'"'sh -c '"'"'"'"'"'"'"'"'dnf install -y wget'"'"'"'"'"'"'"'"''"'"''
[@docker/51ac0676abff] Emulate Docker CLI using podman. Create /etc/containers/nodocker to quiet msg.
[@docker/51ac0676abff] Updating and loading repositories:
[@docker/51ac0676abff] Repositories loaded.
[@docker/51ac0676abff] Nothing to do.
[@docker/51ac0676abff] Package "wget2-wget-2.2.1-1.fc43.x86_64" is already installed.
[@docker/51ac0676abff]

To Reproduce

  1. Start a Fedora 43+ container (docker run -it fedora), keep it running, grab its ID
  2. Run pyinfra -vvv @docker/51ac0676abff dnf.packages iotop - iotop-c should get installed
  3. Run the same command again - notice that pyinfra tried to reinstall iotop-c
  4. Install dnf-utils on that container
  5. Run pyinfra -vvv @docker/51ac0676abff dnf.packages iotop - wget2-wget should be installed
  6. Run the same command again - pyinfra will try to reinstall wget2-wget

Meta

❯ pyinfra --support

    If you are having issues with pyinfra or wish to make feature requests, please
    check out the GitHub issues at https://github.com/Fizzadar/pyinfra/issues .
    When adding an issue, be sure to include the following:

    System: Linux
      Platform: Linux-6.19.9-200.fc43.x86_64-x86_64-with-glibc2.42
      Release: 6.19.9-200.fc43.x86_64
      Machine: x86_64
    pyinfra: v3.7
      click: v8.3.1
      distro: v1.9.0
      gevent: v25.9.1
      jinja2: v3.1.6
      packaging: v26.0
      paramiko: v3.5.1
      pydantic: v2.12.5
      python-dateutil: v2.9.0.post0
      typeguard: v4.5.1
      typing-extensions: v4.15.0
    Executable: /home/yacoob/workarea/homelab/.venv/bin/pyinfra
    Python: 3.14.3 (CPython, Clang 21.1.4 )

Installed via uv in a local venv.

Metadata

Metadata

Assignees

Labels

bugLabel for all kind of bugs.factsIssues with facts.operationsIssues with operations.

Type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions