python-poetry/poetry · error · PackageNotFoundError

No valid distribution links found for package: "{data.name}"

Error message

No valid distribution links found for package: "{data.name}" version: "{data.version}"

What it means

Raised by HTTPRepository._links_to_data when the list of distribution links for a package version is empty (http_repository.py:443-448). It means the repository's simple index page for that release contained no usable distribution files (wheels or sdists). The release may be all-yanked (and the release itself not marked yanked), deleted, or the index is malformed.

Source

Thrown at src/poetry/repositories/http_repository.py:445

            if universal_python2_wheel:
                return self._get_info_from_metadata(
                    universal_python2_wheel
                ) or self._get_info_from_wheel(universal_python2_wheel)

            if platform_specific_wheels:
                first_wheel = platform_specific_wheels[0]
                return self._get_info_from_metadata(
                    first_wheel
                ) or self._get_info_from_wheel(first_wheel)

        return self._get_info_from_metadata(sdists[0]) or self._get_info_from_sdist(
            sdists[0]
        )

    def _links_to_data(self, links: list[Link], data: PackageInfo) -> dict[str, Any]:
        if not links:
            raise PackageNotFoundError(
                f'No valid distribution links found for package: "{data.name}" version:'
                f' "{data.version}"'
            )

        files: list[PackageFile] = []
        for link in links:
            if link.yanked and not data.yanked:
                # drop yanked files unless the entire release is yanked
                continue

            file_hash: str | None
            for hash_name in ("sha512", "sha384", "sha256"):
                if hash_name in link.hashes:
                    file_hash = f"{hash_name}:{link.hashes[hash_name]}"
                    break
            else:
                file_hash = self.calculate_sha256(link)

View on GitHub (pinned to 92b74dcfe3)

Solutions

  1. Open the package's simple index page in a browser/curl and confirm whether files exist for that version.
  2. If the release is yanked, choose a different (non-yanked) version in your constraint.
  3. If using a private index, re-publish or fix the release so it exposes at least one sdist/wheel.
  4. Pin to a known-good version that has published files.

Example fix

// before
[tool.poetry.dependencies]
brokenpkg = "==1.4.0"   # 1.4.0 has no files / all yanked
// after
[tool.poetry.dependencies]
brokenpkg = "==1.3.2"   # a version with valid distribution files
Defensive patterns

Strategy: validation

Validate before calling

release_files = repository.find_links_for_package(Package(name, version))
if not release_files:
    raise ValueError(f"{name} {version} has no distribution files; pick another version")
data = repository.package(name, version)

Try / catch

from poetry.repositories.exceptions import PackageNotFoundError
try:
    data = repository.package(name, version)
except PackageNotFoundError as e:
    if "No valid distribution links" in str(e):
        log.warning("release %s %s has no files; skipping", name, version)
    raise

Prevention

When it happens

Trigger: Calling repository.package(name, version) (during lock/install) for a release whose simple-index page lists zero files; a release where every file is yanked while data.yanked is False (http_repository.py:452-454 skips them).

Common situations: A release was deleted from a private index but metadata still references it; all files of a release were yanked on PyPI; a custom index returns a valid HTML/JSON page with an empty file list.

Related errors


AI-assisted analysis of python-poetry/poetry@92b74dcfe3 (2026-08-04). Data as JSON: /data/errors/d6e3b9ab00c72249.json. Report an issue: GitHub.