Skip to content

Python 3.12 compatibility: export.py imports distutils.util.strtobool which was removed in Python 3.12 #7571

@Odilhao

Description

@Odilhao

Version
pulpcore 3.85.15 (and likely all current versions — confirmed on main branch as of 2026-04-09)

Describe the bug
pulpcore/app/tasks/export.py imports strtobool from distutils.util:

# pulpcore/app/tasks/export.py, line 7
from distutils.util import strtobool

distutils was deprecated in Python 3.10 and removed entirely from the Python 3.12 stdlib (PEP 632). On Python 3.12 installs where setuptools is not present at runtime (it is only a build dependency in many packaging configurations), this causes pulpcore-manager to crash on startup with:

ModuleNotFoundError: No module named 'distutils'

The full import chain:

pulpcore/app/viewsets/base.py
  → pulpcore/app/tasks/__init__.py
    → pulpcore/app/tasks/export.py:7
        from distutils.util import strtobool
ModuleNotFoundError: No module named 'distutils'

This breaks pulpcore-manager migrate, pulpcore-manager collectstatic, and any other management commands that trigger this import path, making pulpcore completely non-functional on Python 3.12 systems where setuptools is not installed as a runtime dependency.

To Reproduce

  1. Install pulpcore on a Python 3.12 system without setuptools as a runtime dependency
  2. Run pulpcore-manager migrate --noinput or pulpcore-manager collectstatic --noinput
  3. Observe: ModuleNotFoundError: No module named 'distutils'

Expected behavior
pulpcore-manager should start without errors on Python 3.12. distutils.util.strtobool should be replaced with an inline implementation or with packaging's equivalent, since distutils is no longer available in Python 3.12.

Suggested fix
Replace the distutils import and usage in export.py:

# Remove this:
from distutils.util import strtobool

# Replace line 353:
full = bool(strtobool(full))

# With (inline, no import needed):
full = str(full).lower() in ('y', 'yes', 't', 'true', 'on', '1')

Additional context

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions