Skip to content

Commit 7dc540f

Browse files
authored
Merge pull request #10115 from pytest-dev/atomicwrites-windows
replace atomicwrites with os.replace
2 parents 966d4fb + 4cd0322 commit 7dc540f

File tree

5 files changed

+26
-70
lines changed

5 files changed

+26
-70
lines changed

.pre-commit-config.yaml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,6 @@ repos:
6767
- attrs>=19.2.0
6868
- packaging
6969
- tomli
70-
- types-atomicwrites
7170
- types-pkg_resources
7271
- repo: local
7372
hooks:

changelog/10114.trivial.rst

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Replace `atomicwrites <https://github.com/untitaker/python-atomicwrites>`__ dependency on windows with `os.replace`.

setup.cfg

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,6 @@ install_requires =
4646
packaging
4747
pluggy>=0.12,<2.0
4848
py>=1.8.2
49-
atomicwrites>=1.0;sys_platform=="win32"
5049
colorama;sys_platform=="win32"
5150
importlib-metadata>=0.12;python_version<"3.8"
5251
tomli>=1.0.0;python_version<"3.11"

src/_pytest/assertion/rewrite.py

Lines changed: 22 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -302,53 +302,29 @@ def _write_pyc_fp(
302302
fp.write(marshal.dumps(co))
303303

304304

305-
if sys.platform == "win32":
306-
from atomicwrites import atomic_write
307-
308-
def _write_pyc(
309-
state: "AssertionState",
310-
co: types.CodeType,
311-
source_stat: os.stat_result,
312-
pyc: Path,
313-
) -> bool:
314-
try:
315-
with atomic_write(os.fspath(pyc), mode="wb", overwrite=True) as fp:
316-
_write_pyc_fp(fp, source_stat, co)
317-
except OSError as e:
318-
state.trace(f"error writing pyc file at {pyc}: {e}")
319-
# we ignore any failure to write the cache file
320-
# there are many reasons, permission-denied, pycache dir being a
321-
# file etc.
322-
return False
323-
return True
324-
325-
else:
326-
327-
def _write_pyc(
328-
state: "AssertionState",
329-
co: types.CodeType,
330-
source_stat: os.stat_result,
331-
pyc: Path,
332-
) -> bool:
333-
proc_pyc = f"{pyc}.{os.getpid()}"
334-
try:
335-
fp = open(proc_pyc, "wb")
336-
except OSError as e:
337-
state.trace(f"error writing pyc file at {proc_pyc}: errno={e.errno}")
338-
return False
339-
340-
try:
305+
def _write_pyc(
306+
state: "AssertionState",
307+
co: types.CodeType,
308+
source_stat: os.stat_result,
309+
pyc: Path,
310+
) -> bool:
311+
proc_pyc = f"{pyc}.{os.getpid()}"
312+
try:
313+
with open(proc_pyc, "wb") as fp:
341314
_write_pyc_fp(fp, source_stat, co)
342-
os.rename(proc_pyc, pyc)
343-
except OSError as e:
344-
state.trace(f"error writing pyc file at {pyc}: {e}")
345-
# we ignore any failure to write the cache file
346-
# there are many reasons, permission-denied, pycache dir being a
347-
# file etc.
348-
return False
349-
finally:
350-
fp.close()
351-
return True
315+
except OSError as e:
316+
state.trace(f"error writing pyc file at {proc_pyc}: errno={e.errno}")
317+
return False
318+
319+
try:
320+
os.replace(proc_pyc, pyc)
321+
except OSError as e:
322+
state.trace(f"error writing pyc file at {pyc}: {e}")
323+
# we ignore any failure to write the cache file
324+
# there are many reasons, permission-denied, pycache dir being a
325+
# file etc.
326+
return False
327+
return True
352328

353329

354330
def _rewrite_test(fn: Path, config: Config) -> Tuple[os.stat_result, types.CodeType]:

testing/test_assertrewrite.py

Lines changed: 3 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -1009,7 +1009,7 @@ def test_meta_path():
10091009
)
10101010
assert pytester.runpytest().ret == 0
10111011

1012-
def test_write_pyc(self, pytester: Pytester, tmp_path, monkeypatch) -> None:
1012+
def test_write_pyc(self, pytester: Pytester, tmp_path) -> None:
10131013
from _pytest.assertion.rewrite import _write_pyc
10141014
from _pytest.assertion import AssertionState
10151015

@@ -1021,27 +1021,8 @@ def test_write_pyc(self, pytester: Pytester, tmp_path, monkeypatch) -> None:
10211021
co = compile("1", "f.py", "single")
10221022
assert _write_pyc(state, co, os.stat(source_path), pycpath)
10231023

1024-
if sys.platform == "win32":
1025-
from contextlib import contextmanager
1026-
1027-
@contextmanager
1028-
def atomic_write_failed(fn, mode="r", overwrite=False):
1029-
e = OSError()
1030-
e.errno = 10
1031-
raise e
1032-
yield # type:ignore[unreachable]
1033-
1034-
monkeypatch.setattr(
1035-
_pytest.assertion.rewrite, "atomic_write", atomic_write_failed
1036-
)
1037-
else:
1038-
1039-
def raise_oserror(*args):
1040-
raise OSError()
1041-
1042-
monkeypatch.setattr("os.rename", raise_oserror)
1043-
1044-
assert not _write_pyc(state, co, os.stat(source_path), pycpath)
1024+
with mock.patch.object(os, "replace", side_effect=OSError):
1025+
assert not _write_pyc(state, co, os.stat(source_path), pycpath)
10451026

10461027
def test_resources_provider_for_loader(self, pytester: Pytester) -> None:
10471028
"""

0 commit comments

Comments
 (0)