Skip to content

Commit 73b5c62

Browse files
committed
Overhaul for better visibility of warnings (#3849)
2 parents 000efbf + 54da8b6 commit 73b5c62

27 files changed

+660
-358
lines changed

setuptools/__init__.py

+11-9
Original file line numberDiff line numberDiff line change
@@ -3,15 +3,14 @@
33
import functools
44
import os
55
import re
6-
import warnings
76

87
import _distutils_hack.override # noqa: F401
98

109
import distutils.core
1110
from distutils.errors import DistutilsOptionError
1211
from distutils.util import convert_path as _convert_path
1312

14-
from ._deprecation_warning import SetuptoolsDeprecationWarning
13+
from .warnings import SetuptoolsDeprecationWarning
1514

1615
import setuptools.version
1716
from setuptools.extension import Extension
@@ -249,14 +248,17 @@ def findall(dir=os.curdir):
249248

250249
@functools.wraps(_convert_path)
251250
def convert_path(pathname):
252-
from inspect import cleandoc
251+
SetuptoolsDeprecationWarning.emit(
252+
"Access to implementation detail",
253+
"""
254+
The function `convert_path` is not provided by setuptools itself,
255+
and therefore not part of the public API.
253256
254-
msg = """
255-
The function `convert_path` is considered internal and not part of the public API.
256-
Its direct usage by 3rd-party packages is considered deprecated and the function
257-
may be removed in the future.
258-
"""
259-
warnings.warn(cleandoc(msg), SetuptoolsDeprecationWarning)
257+
Its direct usage by 3rd-party packages is considered improper and the function
258+
may be removed in the future.
259+
""",
260+
due_date=(2023, 12, 13) # initial deprecation 2022-03-25, see #3201
261+
)
260262
return _convert_path(pathname)
261263

262264

setuptools/_deprecation_warning.py

-7
This file was deleted.

setuptools/_importlib.py

+11-8
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,17 @@ def disable_importlib_metadata_finder(metadata):
1313
except ImportError:
1414
return
1515
except AttributeError:
16-
import warnings
17-
18-
msg = (
19-
"`importlib-metadata` version is incompatible with `setuptools`.\n"
20-
"This problem is likely to be solved by installing an updated version of "
21-
"`importlib-metadata`."
22-
)
23-
warnings.warn(msg) # Ensure a descriptive message is shown.
16+
from .warnings import SetuptoolsWarning
17+
18+
SetuptoolsWarning.emit(
19+
"Incompatibility problem.",
20+
"""
21+
`importlib-metadata` version is incompatible with `setuptools`.
22+
This problem is likely to be solved by installing an updated version of
23+
`importlib-metadata`.
24+
""",
25+
see_url="https://github.com/python/importlib_metadata/issues/396"
26+
) # Ensure a descriptive message is shown.
2427
raise # This exception can be suppressed by _distutils_hack
2528

2629
if importlib_metadata is metadata:

setuptools/_normalization.py

+14-17
Original file line numberDiff line numberDiff line change
@@ -3,14 +3,11 @@
33
and core metadata
44
"""
55
import re
6-
import warnings
7-
from inspect import cleandoc
86
from pathlib import Path
97
from typing import Union
108

11-
from setuptools.extern import packaging
12-
13-
from ._deprecation_warning import SetuptoolsDeprecationWarning
9+
from .extern import packaging
10+
from .warnings import SetuptoolsDeprecationWarning
1411

1512
_Path = Union[str, Path]
1613

@@ -79,18 +76,18 @@ def best_effort_version(version: str) -> str:
7976
try:
8077
return safe_version(version)
8178
except packaging.version.InvalidVersion:
82-
msg = f"""Invalid version: {version!r}.
83-
!!\n\n
84-
###################
85-
# Invalid version #
86-
###################
87-
{version!r} is not valid according to PEP 440.\n
88-
Please make sure specify a valid version for your package.
89-
Also note that future releases of setuptools may halt the build process
90-
if an invalid version is given.
91-
\n\n!!
92-
"""
93-
warnings.warn(cleandoc(msg), SetuptoolsDeprecationWarning)
79+
SetuptoolsDeprecationWarning.emit(
80+
f"Invalid version: {version!r}.",
81+
f"""
82+
Version {version!r} is not valid according to PEP 440.
83+
84+
Please make sure to specify a valid version for your package.
85+
Also note that future releases of setuptools may halt the build process
86+
if an invalid version is given.
87+
""",
88+
see_url="https://peps.python.org/pep-0440/",
89+
due_date=(2023, 9, 26), # See setuptools/dist _validate_version
90+
)
9491
v = version.replace(' ', '.')
9592
return safe_name(v)
9693

setuptools/build_meta.py

+10-7
Original file line numberDiff line numberDiff line change
@@ -43,7 +43,7 @@
4343
from . import errors
4444
from ._path import same_path
4545
from ._reqs import parse_strings
46-
from ._deprecation_warning import SetuptoolsDeprecationWarning
46+
from .warnings import SetuptoolsDeprecationWarning
4747
from distutils.util import strtobool
4848

4949

@@ -299,12 +299,15 @@ def _arbitrary_args(self, config_settings: _ConfigSettings) -> Iterator[str]:
299299
yield from self._get_config("--build-option", config_settings)
300300

301301
if bad_args:
302-
msg = f"""
303-
The arguments {bad_args!r} were given via `--global-option`.
304-
Please use `--build-option` instead,
305-
`--global-option` is reserved to flags like `--verbose` or `--quiet`.
306-
"""
307-
warnings.warn(msg, SetuptoolsDeprecationWarning)
302+
SetuptoolsDeprecationWarning.emit(
303+
"Incompatible `config_settings` passed to build backend.",
304+
f"""
305+
The arguments {bad_args!r} were given via `--global-option`.
306+
Please use `--build-option` instead,
307+
`--global-option` is reserved for flags like `--verbose` or `--quiet`.
308+
""",
309+
due_date=(2023, 9, 26), # Warning introduced in v64.0.1, 11/Aug/2022.
310+
)
308311

309312

310313
class _BuildMetaBackend(_ConfigSettingsTranslator):

setuptools/command/bdist_rpm.py

+9-6
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
import distutils.command.bdist_rpm as orig
2-
import warnings
32

4-
from setuptools import SetuptoolsDeprecationWarning
3+
from ..warnings import SetuptoolsDeprecationWarning
54

65

76
class bdist_rpm(orig.bdist_rpm):
@@ -14,10 +13,14 @@ class bdist_rpm(orig.bdist_rpm):
1413
"""
1514

1615
def run(self):
17-
warnings.warn(
18-
"bdist_rpm is deprecated and will be removed in a future "
19-
"version. Use bdist_wheel (wheel packages) instead.",
20-
SetuptoolsDeprecationWarning,
16+
SetuptoolsDeprecationWarning.emit(
17+
"Deprecated command",
18+
"""
19+
bdist_rpm is deprecated and will be removed in a future version.
20+
Use bdist_wheel (wheel packages) instead.
21+
""",
22+
see_url="https://github.com/pypa/setuptools/issues/1988",
23+
due_date=(2023, 10, 30) # Deprecation introduced in 22 Oct 2021.
2124
)
2225

2326
# ensure distro name is up-to-date

setuptools/command/build.py

+11-8
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,8 @@
11
import sys
2-
import warnings
32
from typing import TYPE_CHECKING, List, Dict
43
from distutils.command.build import build as _build
54

6-
from setuptools import SetuptoolsDeprecationWarning
5+
from ..warnings import SetuptoolsDeprecationWarning
76

87
if sys.version_info >= (3, 8):
98
from typing import Protocol
@@ -23,12 +22,16 @@ class build(_build):
2322
def get_sub_commands(self):
2423
subcommands = {cmd[0] for cmd in _build.sub_commands}
2524
if subcommands - _ORIGINAL_SUBCOMMANDS:
26-
msg = """
27-
It seems that you are using `distutils.command.build` to add
28-
new subcommands. Using `distutils` directly is considered deprecated,
29-
please use `setuptools.command.build`.
30-
"""
31-
warnings.warn(msg, SetuptoolsDeprecationWarning)
25+
SetuptoolsDeprecationWarning.emit(
26+
"Direct usage of `distutils` commands",
27+
"""
28+
It seems that you are using `distutils.command.build` to add
29+
new subcommands. Using `distutils` directly is considered deprecated,
30+
please use `setuptools.command.build`.
31+
""",
32+
due_date=(2023, 12, 13), # Warning introduced in 13 Jun 2022.
33+
see_url="https://peps.python.org/pep-0632/",
34+
)
3235
self.sub_commands = _build.sub_commands
3336
return super().get_sub_commands()
3437

setuptools/command/build_py.py

+45-27
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,11 @@
99
import distutils.errors
1010
import itertools
1111
import stat
12-
import warnings
1312
from pathlib import Path
1413
from typing import Dict, Iterable, Iterator, List, Optional, Tuple
1514

16-
from setuptools._deprecation_warning import SetuptoolsDeprecationWarning
17-
from setuptools.extern.more_itertools import unique_everseen
15+
from ..extern.more_itertools import unique_everseen
16+
from ..warnings import SetuptoolsDeprecationWarning
1817

1918

2019
def make_writable(target):
@@ -325,28 +324,48 @@ def assert_relative(path):
325324
class _IncludePackageDataAbuse:
326325
"""Inform users that package or module is included as 'data file'"""
327326

328-
MESSAGE = """\
329-
Installing {importable!r} as data is deprecated, please list it in `packages`.
330-
!!\n\n
331-
############################
332-
# Package would be ignored #
333-
############################
334-
Python recognizes {importable!r} as an importable package,
335-
but it is not listed in the `packages` configuration of setuptools.
336-
337-
{importable!r} has been automatically added to the distribution only
338-
because it may contain data files, but this behavior is likely to change
339-
in future versions of setuptools (and therefore is considered deprecated).
340-
341-
Please make sure that {importable!r} is included as a package by using
342-
the `packages` configuration field or the proper discovery methods
343-
(for example by using `find_namespace_packages(...)`/`find_namespace:`
344-
instead of `find_packages(...)`/`find:`).
345-
346-
You can read more about "package discovery" and "data files" on setuptools
347-
documentation page.
348-
\n\n!!
349-
"""
327+
class _Warning(SetuptoolsDeprecationWarning):
328+
_SUMMARY = """
329+
Package {importable!r} is absent from the `packages` configuration.
330+
"""
331+
332+
_DETAILS = """
333+
############################
334+
# Package would be ignored #
335+
############################
336+
Python recognizes {importable!r} as an importable package[^1],
337+
but it is absent from setuptools' `packages` configuration.
338+
339+
This leads to an ambiguous overall configuration. If you want to distribute this
340+
package, please make sure that {importable!r} is explicitly added
341+
to the `packages` configuration field.
342+
343+
Alternatively, you can also rely on setuptools' discovery methods
344+
(for example by using `find_namespace_packages(...)`/`find_namespace:`
345+
instead of `find_packages(...)`/`find:`).
346+
347+
You can read more about "package discovery" on setuptools documentation page:
348+
349+
- https://setuptools.pypa.io/en/latest/userguide/package_discovery.html
350+
351+
If you don't want {importable!r} to be distributed and are
352+
already explicitly excluding {importable!r} via
353+
`find_namespace_packages(...)/find_namespace` or `find_packages(...)/find`,
354+
you can try to use `exclude_package_data`, or `include-package-data=False` in
355+
combination with a more fine grained `package-data` configuration.
356+
357+
You can read more about "package data files" on setuptools documentation page:
358+
359+
- https://setuptools.pypa.io/en/latest/userguide/datafiles.html
360+
361+
362+
[^1]: For Python, any directory (with suitable naming) can be imported,
363+
even if it does not contain any `.py` files.
364+
On the other hand, currently there is no concept of package data
365+
directory, all directories are treated like packages.
366+
"""
367+
# _DUE_DATE: still not defined as this is particularly controversial.
368+
# Warning initially introduced in May 2022. See issue #3340 for discussion.
350369

351370
def __init__(self):
352371
self._already_warned = set()
@@ -363,6 +382,5 @@ def importable_subpackage(self, parent, file):
363382

364383
def warn(self, importable):
365384
if importable not in self._already_warned:
366-
msg = textwrap.dedent(self.MESSAGE).format(importable=importable)
367-
warnings.warn(msg, SetuptoolsDeprecationWarning, stacklevel=2)
385+
self._Warning.emit(importable=importable)
368386
self._already_warned.add(importable)

setuptools/command/dist_info.py

+4-3
Original file line numberDiff line numberDiff line change
@@ -6,14 +6,13 @@
66
import os
77
import shutil
88
import sys
9-
import warnings
109
from contextlib import contextmanager
1110
from distutils import log
1211
from distutils.core import Command
1312
from pathlib import Path
1413

1514
from .. import _normalization
16-
from .._deprecation_warning import SetuptoolsDeprecationWarning
15+
from ..warnings import SetuptoolsDeprecationWarning
1716

1817

1918
class dist_info(Command):
@@ -51,7 +50,9 @@ def initialize_options(self):
5150
def finalize_options(self):
5251
if self.egg_base:
5352
msg = "--egg-base is deprecated for dist_info command. Use --output-dir."
54-
warnings.warn(msg, SetuptoolsDeprecationWarning)
53+
SetuptoolsDeprecationWarning.emit(msg, due_date=(2023, 9, 26))
54+
# This command is internal to setuptools, therefore it should be safe
55+
# to remove the deprecated support soon.
5556
self.output_dir = self.egg_base or self.output_dir
5657

5758
dist = self.distribution

0 commit comments

Comments
 (0)