Skip to content

Commit a460f2c

Browse files
committed
Resolve more EncodingWarning not caught by Ruff
1 parent c749b49 commit a460f2c

20 files changed

+122
-61
lines changed

setuptools/_imp.py

+2-1
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88
import importlib.machinery
99

1010
from importlib.util import module_from_spec
11+
from .compat.encoding import encoding_for_open
1112

1213

1314
PY_SOURCE = 1
@@ -66,7 +67,7 @@ def find_module(module, paths=None):
6667
kind = C_EXTENSION
6768

6869
if kind in {PY_SOURCE, PY_COMPILED}:
69-
file = open(path, mode)
70+
file = open(path, mode, encoding=encoding_for_open)
7071
else:
7172
path = None
7273
suffix = mode = ''

setuptools/command/easy_install.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -872,7 +872,7 @@ def write_script(self, script_name, contents, mode="t", blockers=()):
872872
ensure_directory(target)
873873
if os.path.exists(target):
874874
os.unlink(target)
875-
with open(target, "w" + mode) as f:
875+
with open(target, "w" + mode, encoding=encoding_for_open) as f:
876876
f.write(contents)
877877
chmod(target, 0o777 - mask)
878878

setuptools/command/editable_wheel.py

+8-1
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,6 @@
3030
List,
3131
Mapping,
3232
Optional,
33-
Protocol,
3433
Tuple,
3534
TypeVar,
3635
Union,
@@ -43,6 +42,7 @@
4342
errors,
4443
namespaces,
4544
)
45+
from ..compat.encoding import encoding_for_pth
4646
from ..discovery import find_package_path
4747
from ..dist import Distribution
4848
from ..warnings import (
@@ -55,6 +55,13 @@
5555
if TYPE_CHECKING:
5656
from wheel.wheelfile import WheelFile # noqa
5757

58+
if sys.version_info >= (3, 8):
59+
from typing import Protocol
60+
elif TYPE_CHECKING:
61+
from typing_extensions import Protocol
62+
else:
63+
from abc import ABC as Protocol
64+
5865
_Path = Union[str, Path]
5966
_P = TypeVar("_P", bound=_Path)
6067
_logger = logging.getLogger(__name__)

setuptools/command/install_scripts.py

+2-1
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
import sys
55

66
from .._path import ensure_directory
7+
from ..compat.encoding import encoding_for_open
78

89

910
class install_scripts(orig.install_scripts):
@@ -60,7 +61,7 @@ def write_script(self, script_name, contents, mode="t", *ignored):
6061
mask = current_umask()
6162
if not self.dry_run:
6263
ensure_directory(target)
63-
f = open(target, "w" + mode)
64+
f = open(target, "w" + mode, encoding=encoding_for_open)
6465
f.write(contents)
6566
f.close()
6667
chmod(target, 0o777 - mask)

setuptools/command/setopt.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@ def edit_config(filename, settings, dry_run=False):
3838
log.debug("Reading configuration from %s", filename)
3939
opts = configparser.RawConfigParser()
4040
opts.optionxform = lambda x: x
41-
opts.read([filename])
41+
opts.read([filename], encoding=encoding_for_open)
4242
for section, options in settings.items():
4343
if options is None:
4444
log.info("Deleting section [%s] from %s", section, filename)

setuptools/package_index.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -1016,7 +1016,7 @@ def __init__(self):
10161016

10171017
rc = os.path.join(os.path.expanduser('~'), '.pypirc')
10181018
if os.path.exists(rc):
1019-
self.read(rc)
1019+
self.read(rc, encoding=encoding_for_open)
10201020

10211021
@property
10221022
def creds_by_repository(self):

setuptools/sandbox.py

+2-1
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@
1313
import pkg_resources
1414
from distutils.errors import DistutilsError
1515
from pkg_resources import working_set
16+
from .compat.encoding import encoding_for_open
1617

1718
if sys.platform.startswith('java'):
1819
import org.python.modules.posix.PosixModule as _os
@@ -450,7 +451,7 @@ def _file(self, path, mode='r', *args, **kw):
450451
def _open(self, path, mode='r', *args, **kw):
451452
if mode not in ('r', 'rt', 'rb', 'rU', 'U') and not self._ok(path):
452453
self._violation("open", path, mode, *args, **kw)
453-
return _open(path, mode, *args, **kw)
454+
return _open(path, mode, *args, **kw, encoding=encoding_for_open)
454455

455456
def tmpnam(self):
456457
self._violation("tmpnam")

setuptools/tests/config/test_apply_pyprojecttoml.py

+6-3
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919

2020
import setuptools # noqa ensure monkey patch to metadata
2121
from setuptools.dist import Distribution
22+
from setuptools.compat.encoding import encoding_for_open
2223
from setuptools.config import setupcfg, pyprojecttoml
2324
from setuptools.config import expand
2425
from setuptools.config._apply_pyprojecttoml import _MissingDynamic, _some_attrgetter
@@ -176,9 +177,11 @@ def _pep621_example_project(
176177
text = text.replace(orig, subst)
177178
pyproject.write_text(text, encoding="utf-8")
178179

179-
(tmp_path / readme).write_text("hello world")
180-
(tmp_path / "LICENSE.txt").write_text("--- LICENSE stub ---")
181-
(tmp_path / "spam.py").write_text(PEP621_EXAMPLE_SCRIPT)
180+
(tmp_path / readme).write_text("hello world", encoding=encoding_for_open)
181+
(tmp_path / "LICENSE.txt").write_text(
182+
"--- LICENSE stub ---", encoding=encoding_for_open
183+
)
184+
(tmp_path / "spam.py").write_text(PEP621_EXAMPLE_SCRIPT, encoding=encoding_for_open)
182185
return pyproject
183186

184187

setuptools/tests/config/test_expand.py

+2-1
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
import pytest
55

66
from distutils.errors import DistutilsOptionError
7+
from setuptools.compat.encoding import encoding_for_open
78
from setuptools.config import expand
89
from setuptools.discovery import find_package_path
910

@@ -12,7 +13,7 @@ def write_files(files, root_dir):
1213
for file, content in files.items():
1314
path = root_dir / file
1415
path.parent.mkdir(exist_ok=True, parents=True)
15-
path.write_text(content)
16+
path.write_text(content, encoding=encoding_for_open)
1617

1718

1819
def test_glob_relative(tmp_path, monkeypatch):

setuptools/tests/config/test_pyprojecttoml.py

+28-15
Original file line numberDiff line numberDiff line change
@@ -98,11 +98,17 @@ def create_example(path, pkg_root):
9898
(path / file).parent.mkdir(exist_ok=True, parents=True)
9999
(path / file).touch()
100100

101-
pyproject.write_text(EXAMPLE)
102-
(path / "README.md").write_text("hello world")
103-
(path / f"{pkg_root}/pkg/mod.py").write_text("class CustomSdist: pass")
104-
(path / f"{pkg_root}/pkg/__version__.py").write_text("VERSION = (3, 10)")
105-
(path / f"{pkg_root}/pkg/__main__.py").write_text("def exec(): print('hello')")
101+
pyproject.write_text(EXAMPLE, encoding=encoding_for_open)
102+
(path / "README.md").write_text("hello world", encoding=encoding_for_open)
103+
(path / f"{pkg_root}/pkg/mod.py").write_text(
104+
"class CustomSdist: pass", encoding=encoding_for_open
105+
)
106+
(path / f"{pkg_root}/pkg/__version__.py").write_text(
107+
"VERSION = (3, 10)", encoding=encoding_for_open
108+
)
109+
(path / f"{pkg_root}/pkg/__main__.py").write_text(
110+
"def exec(): print('hello')", encoding=encoding_for_open
111+
)
106112

107113

108114
def verify_example(config, path, pkg_root):
@@ -218,7 +224,9 @@ def test_dynamic(self, tmp_path):
218224
Framework :: Flask
219225
Programming Language :: Haskell
220226
"""
221-
(tmp_path / "classifiers.txt").write_text(cleandoc(classifiers))
227+
(tmp_path / "classifiers.txt").write_text(
228+
cleandoc(classifiers), encoding=encoding_for_open
229+
)
222230

223231
pyproject = tmp_path / "pyproject.toml"
224232
config = read_configuration(pyproject, expand=False)
@@ -246,7 +254,7 @@ def test_dynamic_without_config(self, tmp_path):
246254
"""
247255

248256
pyproject = tmp_path / "pyproject.toml"
249-
pyproject.write_text(cleandoc(config))
257+
pyproject.write_text(cleandoc(config), encoding=encoding_for_open)
250258
with pytest.raises(OptionError, match="No configuration .* .classifiers."):
251259
read_configuration(pyproject)
252260

@@ -258,7 +266,7 @@ def test_dynamic_readme_from_setup_script_args(self, tmp_path):
258266
dynamic = ["readme"]
259267
"""
260268
pyproject = tmp_path / "pyproject.toml"
261-
pyproject.write_text(cleandoc(config))
269+
pyproject.write_text(cleandoc(config), encoding=encoding_for_open)
262270
dist = Distribution(attrs={"long_description": "42"})
263271
# No error should occur because of missing `readme`
264272
dist = apply_configuration(dist, pyproject)
@@ -276,7 +284,7 @@ def test_dynamic_without_file(self, tmp_path):
276284
"""
277285

278286
pyproject = tmp_path / "pyproject.toml"
279-
pyproject.write_text(cleandoc(config))
287+
pyproject.write_text(cleandoc(config), encoding=encoding_for_open)
280288
with pytest.warns(UserWarning, match="File .*classifiers.txt. cannot be found"):
281289
expanded = read_configuration(pyproject)
282290
assert "classifiers" not in expanded["project"]
@@ -297,7 +305,7 @@ def test_dynamic_without_file(self, tmp_path):
297305
)
298306
def test_ignore_unrelated_config(tmp_path, example):
299307
pyproject = tmp_path / "pyproject.toml"
300-
pyproject.write_text(cleandoc(example))
308+
pyproject.write_text(cleandoc(example), encoding=encoding_for_open)
301309

302310
# Make sure no error is raised due to 3rd party configs in pyproject.toml
303311
assert read_configuration(pyproject) is not None
@@ -319,7 +327,7 @@ def test_ignore_unrelated_config(tmp_path, example):
319327
)
320328
def test_invalid_example(tmp_path, example, error_msg):
321329
pyproject = tmp_path / "pyproject.toml"
322-
pyproject.write_text(cleandoc(example))
330+
pyproject.write_text(cleandoc(example), encoding=encoding_for_open)
323331

324332
pattern = re.compile(f"invalid pyproject.toml.*{error_msg}.*", re.M | re.S)
325333
with pytest.raises(ValueError, match=pattern):
@@ -329,7 +337,7 @@ def test_invalid_example(tmp_path, example, error_msg):
329337
@pytest.mark.parametrize("config", ("", "[tool.something]\nvalue = 42"))
330338
def test_empty(tmp_path, config):
331339
pyproject = tmp_path / "pyproject.toml"
332-
pyproject.write_text(config)
340+
pyproject.write_text(config, encoding=encoding_for_open)
333341

334342
# Make sure no error is raised
335343
assert read_configuration(pyproject) == {}
@@ -341,7 +349,7 @@ def test_include_package_data_by_default(tmp_path, config):
341349
default.
342350
"""
343351
pyproject = tmp_path / "pyproject.toml"
344-
pyproject.write_text(config)
352+
pyproject.write_text(config, encoding=encoding_for_open)
345353

346354
config = read_configuration(pyproject)
347355
assert config["tool"]["setuptools"]["include-package-data"] is True
@@ -354,9 +362,14 @@ def test_include_package_data_in_setuppy(tmp_path):
354362
See https://github.com/pypa/setuptools/issues/3197#issuecomment-1079023889
355363
"""
356364
pyproject = tmp_path / "pyproject.toml"
357-
pyproject.write_text("[project]\nname = 'myproj'\nversion='42'\n")
365+
pyproject.write_text(
366+
"[project]\nname = 'myproj'\nversion='42'\n", encoding=encoding_for_open
367+
)
358368
setuppy = tmp_path / "setup.py"
359-
setuppy.write_text("__import__('setuptools').setup(include_package_data=False)")
369+
setuppy.write_text(
370+
"__import__('setuptools').setup(include_package_data=False)",
371+
encoding=encoding_for_open,
372+
)
360373

361374
with _Path(tmp_path):
362375
dist = distutils.core.run_setup("setup.py", {}, stop_after="config")

setuptools/tests/config/test_pyprojecttoml_dynamic_deps.py

+15-11
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import pytest
22

3+
from setuptools.compat.encoding import encoding_for_open
34
from setuptools.config.pyprojecttoml import apply_configuration
45
from setuptools.dist import Distribution
56
from setuptools.tests.textwrap import DALS
@@ -23,19 +24,21 @@ def test_dynamic_dependencies(tmp_path):
2324
[tool.setuptools.dynamic.dependencies]
2425
file = ["requirements.txt"]
2526
"""
26-
)
27+
),
28+
encoding=encoding_for_open,
2729
)
2830
dist = Distribution()
2931
dist = apply_configuration(dist, pyproject)
3032
assert dist.install_requires == ["six"]
3133

3234

3335
def test_dynamic_optional_dependencies(tmp_path):
34-
(tmp_path / "requirements-docs.txt").write_text("sphinx\n # comment\n")
36+
(tmp_path / "requirements-docs.txt").write_text(
37+
"sphinx\n # comment\n", encoding=encoding_for_open
38+
)
3539
pyproject = tmp_path / "pyproject.toml"
3640
pyproject.write_text(
37-
DALS(
38-
"""
41+
DALS("""
3942
[project]
4043
name = "myproj"
4144
version = "1.0"
@@ -47,8 +50,8 @@ def test_dynamic_optional_dependencies(tmp_path):
4750
[build-system]
4851
requires = ["setuptools", "wheel"]
4952
build-backend = "setuptools.build_meta"
50-
"""
51-
)
53+
"""),
54+
encoding=encoding_for_open,
5255
)
5356
dist = Distribution()
5457
dist = apply_configuration(dist, pyproject)
@@ -61,11 +64,12 @@ def test_mixed_dynamic_optional_dependencies(tmp_path):
6164
configurations in the case of fields containing sub-fields (groups),
6265
things would work out.
6366
"""
64-
(tmp_path / "requirements-images.txt").write_text("pillow~=42.0\n # comment\n")
67+
(tmp_path / "requirements-images.txt").write_text(
68+
"pillow~=42.0\n # comment\n", encoding=encoding_for_open
69+
)
6570
pyproject = tmp_path / "pyproject.toml"
6671
pyproject.write_text(
67-
DALS(
68-
"""
72+
DALS("""
6973
[project]
7074
name = "myproj"
7175
version = "1.0"
@@ -80,8 +84,8 @@ def test_mixed_dynamic_optional_dependencies(tmp_path):
8084
[build-system]
8185
requires = ["setuptools", "wheel"]
8286
build-backend = "setuptools.build_meta"
83-
"""
84-
)
87+
"""),
88+
encoding=encoding_for_open,
8589
)
8690
# Test that the mix-and-match doesn't currently validate.
8791
with pytest.raises(ValueError, match="project.optional-dependencies"):

setuptools/tests/config/test_setupcfg.py

+4-2
Original file line numberDiff line numberDiff line change
@@ -7,8 +7,9 @@
77
import pytest
88

99
from distutils.errors import DistutilsOptionError, DistutilsFileError
10-
from setuptools.dist import Distribution, _Distribution
10+
from setuptools.compat.encoding import encoding_for_open
1111
from setuptools.config.setupcfg import ConfigHandler, read_configuration
12+
from setuptools.dist import Distribution, _Distribution
1213
from setuptools.extern.packaging.requirements import InvalidRequirement
1314
from setuptools.warnings import SetuptoolsDeprecationWarning
1415
from ..textwrap import DALS
@@ -904,7 +905,8 @@ def test_cmdclass(self, tmpdir):
904905
module_path = Path(tmpdir, "src/custom_build.py") # auto discovery for src
905906
module_path.parent.mkdir(parents=True, exist_ok=True)
906907
module_path.write_text(
907-
"from distutils.core import Command\n" "class CustomCmd(Command): pass\n"
908+
"from distutils.core import Command\n" "class CustomCmd(Command): pass\n",
909+
encoding=encoding_for_open,
908910
)
909911

910912
setup_cfg = """

setuptools/tests/environment.py

+3
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
import subprocess
44
import unicodedata
55
from subprocess import Popen as _Popen, PIPE as _PIPE
6+
from ..compat.encoding import encoding_for_open
67

78
import jaraco.envs
89

@@ -31,6 +32,8 @@ def run(self, cmd, *args, **kwargs):
3132
if "PYTHONPATH" in env:
3233
del env["PYTHONPATH"]
3334
kwargs["env"] = env
35+
if "encoding" not in kwargs:
36+
kwargs["encoding"] = encoding_for_open
3437
return subprocess.check_output(cmd, *args, **kwargs)
3538

3639

setuptools/tests/integration/helpers.py

+2
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
import tarfile
1111
from zipfile import ZipFile
1212
from pathlib import Path
13+
from setuptools.compat.encoding import encoding_for_open
1314

1415

1516
def run(cmd, env=None):
@@ -19,6 +20,7 @@ def run(cmd, env=None):
1920
text=True,
2021
env={**os.environ, **(env or {})},
2122
# ^-- allow overwriting instead of discarding the current env
23+
encoding=encoding_for_open,
2224
)
2325

2426
out = r.stdout + "\n" + r.stderr

0 commit comments

Comments
 (0)