Skip to content

Error "Backend 'X' is not available" when PYTHONPATH contains a build dependency #1037

@AWhetter

Description

@AWhetter

Problem

I have a situation where PYTHONPATH is set such that it contains a directory that has a build dependency in it, and running python -m build fails with the error "Backend 'X' is not available".

As an example:

$ cat <<EOF > pyproject.toml
[build-system]
requires = ["setuptools"]
build-backend = "setuptools.build_meta"

[project]
name = "myemptypkg"
version = "0.1.0"
description = "Nothing"
EOF
$ python -m venv .venv
$ .venv/bin/pip install --upgrade pip build
$ .venv/bin/pip list
Package         Version
--------------- -------
build           1.4.3
packaging       26.0
pip             26.0.1
pyproject_hooks 1.2.0
setuptools      65.5.1
$ PYTHONPATH=.venv/lib/python3.11/site-packages .venv/bin/python -m build
* Creating isolated environment: venv+pip...
* Installing packages in isolated environment:
  - setuptools
* Getting build dependencies for sdist...

Traceback (most recent call last):
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/pyproject_hooks/_impl.py", line 402, in _call_hook
    raise BackendUnavailable(
pyproject_hooks._impl.BackendUnavailable: Cannot import 'setuptools.build_meta'

ERROR Backend 'setuptools.build_meta' is not available.

Note that the use of pip >=22.3 is important to trigger this code path:

if dist := _has_dependency('pip', '22.3'): # pragma: no cover

Explanation of the issue

This comes about because the command to install the build dependencies has PYTHONPATH available to it, via _PipBackend.install_dependencies (

run_subprocess(cmd, env=_pip_env())
). This differs from the environment that is used to execute pyproject_hooks, where PYTHONPATH is unset by DefaultIsolatedEnv.make_extra_environ.

Here's the tracebacks of where the two different subprocesses occur:

* Creating isolated environment: venv+pip...
* Installing packages in isolated environment:
  - setuptools
  File "<frozen runpy>", line 198, in _run_module_as_main
  File "<frozen runpy>", line 88, in _run_code
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/__main__.py", line 643, in <module>
    main(sys.argv[1:], 'python -m build')
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/__main__.py", line 622, in main
    built = build(
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/__main__.py", line 325, in build_package_via_sdist
    sdist = _build(
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/__main__.py", line 209, in _build
    with _bootstrap_build_env(
  File "/usr/lib64/python3.11/contextlib.py", line 137, in __enter__
    return next(self.gen)
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/__main__.py", line 177, in _bootstrap_build_env
    install(builder.build_system_requires)
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/env.py", line 180, in install
    self._env_backend.install_dependencies(requirements, constraints)
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/env.py", line 358, in install_dependencies
    import traceback; traceback.print_stack()
* Getting build dependencies for sdist...
  File "<frozen runpy>", line 198, in _run_module_as_main
  File "<frozen runpy>", line 88, in _run_code
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/__main__.py", line 643, in <module>
    main(sys.argv[1:], 'python -m build')
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/__main__.py", line 622, in main
    built = build(
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/__main__.py", line 325, in build_package_via_sdist
    sdist = _build(
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/__main__.py", line 209, in _build
    with _bootstrap_build_env(
  File "/usr/lib64/python3.11/contextlib.py", line 137, in __enter__
    return next(self.gen)
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/__main__.py", line 179, in _bootstrap_build_env
    install(builder.get_requires_for_build(distribution, config_settings))
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/_builder.py", line 260, in get_requires_for_build
    return set(get_requires(config_settings))
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/pyproject_hooks/_impl.py", line 356, in get_requires_for_build_sdist
    return self._call_hook(
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/pyproject_hooks/_impl.py", line 392, in _call_hook
    self._subprocess_runner(
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/_builder.py", line 153, in _invoke_wrapped_runner
    runner(cmd, cwd, {**(env.make_extra_environ() or {}), **(extra_environ or {})})
  File "/u/asw/temp/build_test/.venv/lib/python3.11/site-packages/build/env.py", line 153, in make_extra_environ
    import traceback; traceback.print_stack()

Possible solution

I can't speak to the best way to structure code changes for a solution, but if I make the installation of build dependencies ignore PYTHONPATH then the package successfully builds.

--- a/.venv/lib/python3.11/site-packages/build/env.py	2026-04-14 13:53:29.496225357 -0400
+++ b/.venv/lib/python3.11/site-packages/build/env.py	2026-04-14 13:53:18.959692000 -0400
@@ -197,9 +197,11 @@
 
 
 def _pip_env() -> dict[str, str] | None:
+    env = os.environ.copy()
+    env['PYTHONPATH'] = ''
     if 'PIP_KEYRING_PROVIDER' not in os.environ and _has_keyring_cli():
-        return {**os.environ, 'PIP_KEYRING_PROVIDER': 'subprocess'}
-    return None
+        return {**env, 'PIP_KEYRING_PROVIDER': 'subprocess'}
+    return env
 
 
 class _PipBackend(_EnvBackend):

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions