Skip to content

Remove pkg_resources #5007

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft
wants to merge 6 commits into
base: main
Choose a base branch
from
Draft

Remove pkg_resources #5007

wants to merge 6 commits into from

Conversation

jaraco
Copy link
Member

@jaraco jaraco commented May 21, 2025

  • Remove pkg_resources
  • Remove assertion that 'import pkg_resources' works; it's no longer an invariant.
  • Mark pbr integration test as xfail.
  • Mark namespace tests as xfail. Support for pkg_resources-style namespaces is dropped.
  • Add news fragment.

Summary of changes

Closes #3085

Pull Request Checklist

@jaraco
Copy link
Member Author

jaraco commented May 21, 2025

To be sure, this change is a big deal. It's been decades in the making to provide replacements for this functionality. There are known open issues and efforts to remove the dependence on pkg_resources and probably other use-cases that haven't migrated. My hope is that these cases can pin to Setuptools<81.

I don't have any plans to rush this out or force it on the community, but I'd like to start thinking about what it would take to get committed.

@jaraco jaraco force-pushed the feature/remove-more-pkg_resources branch from 35e39e7 to b3f9277 Compare May 21, 2025 22:22
@jaraco jaraco requested a review from abravalheri May 22, 2025 00:01
Copy link
Contributor

@abravalheri abravalheri left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you very much Jason for the effort in untangling the 2 code bases.
I agree that it is time to start thinking about the removal of pkg_resources.

I propose we do it in 2 stages:

  1. Explicitly mention a "due date" to the warning message
  2. Removal once the "due date" arrives.

I have 2 doubts:

@jaraco
Copy link
Member Author

jaraco commented May 25, 2025

  • Does the namespace_packages (deprecated) keyword for setup.py works without pkg_resources.declare_namespace?

It's a mixed bag.

If I recall correctly, when pip-installed, a declared namespace gets its __init__.py omitted, so ends up acting like a PEP 420 namespace. I also seem to recall that there's a .pth file that gets installed under certain circumstances (although maybe not any more after the removal of easy_install).

Looking at zope.interface as an example:

 🐚 py -3.13 -m pip-run git+https://github.com/zopefoundation/zope.interface -- -c "import zope, pathlib; print('files in zope:', list(pathlib.Path(zope.__path__[0]).iterdir())); print('nspkg.pth file:', next(pathlib.Path(zope.__path__[0]).parent.glob('*-nspkg.pth')).read_text())"
files in zope: [PosixPath('/var/folders/f2/2plv6q2n7l932m2x004jlw340000gn/T/pip-run-r43zfapw/zope/interface')]
nspkg.pth file: import sys, types, os;p = os.path.join(sys._getframe(1).f_locals['sitedir'], *('zope',));importlib = __import__('importlib.util');__import__('importlib.machinery');m = sys.modules.setdefault('zope', importlib.util.module_from_spec(importlib.machinery.PathFinder.find_spec('zope', [os.path.dirname(p)])));m = m or sys.modules.setdefault('zope', types.ModuleType('zope'));mp = (m or []) and m.__dict__.setdefault('__path__',[]);(p not in mp) and mp.append(p)

The same is true for the wheel.

These results confirm that, at least for the pip-installed packages, the use of pkg_resources is completely absent.

This confirmation gives me higher confidence that this removal is at least safer than I'd previously thought.

In fact, I wonder if declare_namespace is in use anywhere at all.

  If I understood correctly previously these worked in tandem, but I don't know what is the situation now after the latest changes in https://github.com/pypa/setuptools/blob/v80.8.0/setuptools/namespaces.py#L47-L63.

There was a time where even the -nspkg.pth file did nothing and fell back to PEP 420 on Python 3.3+. In 27b7d4e, however, I limited the PEP 420 fallback to Python 3.3 and 3.4. I didn't leave any good justification for making that change (no linked issue, no mention in changelog). Maybe it had something to do with #1214. I wonder if that change was a mistake and could have been allowed to simply fall back to PEP 420.

In fact, I wonder if declare_namespace is in use anywhere at all.

I guess it has to still be used for the editable case... at least where setup.py develop was used.

Confirmed - it's still used even for the modern editable case:

 zope.interface master 🐚 py -3.13 -m pip-run -e .
Python 3.13.3 (main, Apr  8 2025, 13:54:08) [Clang 16.0.0 (clang-1600.0.26.6)] on darwin
Type "help", "copyright", "credits" or "license" for more information.
>>> import zope
>>> zope.__file__
'/Users/jaraco/draft/zope.interface/src/zope/__init__.py'
>>> zope.__path__
['/Users/jaraco/draft/zope.interface/src/zope']

I'm less worried about the editable case, because it's outside the typical integration and production workflows and the developer has a lot more control to implement workarounds, such as to pin setuptools.

  • Is the idea of https://github.com/pypa/pkg_resources to also publish something to PyPI? Even if the package is born deprecated it may be a "last-resort" alternative for users that rely on packages that have not received updates for a long time, or that are still working on the migration...

As you've observed, I was considering this option, but I'm still not confident it's the right thing to do. It would require getting the name opened up for use, which I'm fairly confident the maintainers would do for this purpose.

But it would still require the users to install it. It wouldn't be installed implicitly as Setuptools is in some environments. And if they have the ability to install a custom pkg_resources package, they probably also have the ability to pin to an older Setuptools... so maybe "pin setuptools" is the universal workaround.

I propose we do it in 2 stages:

1. Explicitly mention a "due date" to the [warning message](https://github.com/pypa/setuptools/blob/v80.8.0/pkg_resources/__init__.py#L98-L103)

2. Removal once the "due date" arrives.

I'm good with that plan. I'll set the due date for 6 months and mark this PR as draft in the meantime.

@jaraco jaraco marked this pull request as draft May 25, 2025 13:56
@jaraco
Copy link
Member Author

jaraco commented May 25, 2025

I propose we do it in 2 stages:

1. Explicitly mention a "due date" to the [warning message](https://github.com/pypa/setuptools/blob/v80.8.0/pkg_resources/__init__.py#L98-L103)

2. Removal once the "due date" arrives.

I started looking into this plan, but it seems that pkg_resources doesn't have any of the due date functionality of setuptools.warnings, so I'm just going to apply some changes to the messaging.

@abravalheri
Copy link
Contributor

Thank you very much Jason for adding the due date and providing the review about the namespaces.

But it would still require the users to install it. It wouldn't be installed implicitly as Setuptools is in some environments. And if they have the ability to install a custom pkg_resources package, they probably also have the ability to pin to an older Setuptools... so maybe "pin setuptools" is the universal workaround.

As a brainstorm: there is one possibility to make it "installed implicitly" in build environments.

I mentioned in #3085 (comment) that we could return pkg_resources in setuptools.build_meta:__legacy__.get_requires_for_build_sdist/wheel.

But I am not sure this direction is worth pursuing specially because pip (and posibly uv?) don't fully1 fallback by default yet to setuptools.build_meta:__legacy__ when pyproject.toml is absent (instead they run python setup.py ...).

Footnotes

  1. This behaviour is meant to be the default, but the pip team has-postponed/never-manage-to-implement this change to avoid backwards incompatibility. So what we have right now is an heuristic that sometimes uses python setup.py and sometimes setuptools.build_meta:__legacy__.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Setuptools should not rely on pkg_resources
2 participants