Skip to content

Commit f78b56a

Browse files
graingertbluetech
authored andcommitted
use tempfile.TemporaryDirectory to cleanup garbage- dir
Python has a very nice rm_rf hidden in tempfile.TemporaryDirectory._rmtree we can use it to cleanup our "garbage-" dir https://github.com/python/cpython/blob/3d43f1dce3e9aaded38f9a2c73e3c66acf85505c/Lib/tempfile.py#L784-L812
1 parent 1bed1d7 commit f78b56a

File tree

3 files changed

+24
-6
lines changed

3 files changed

+24
-6
lines changed

changelog/8940.bugfix.rst

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Fixed an issue where dirs without S_IXUSR prevented pytest from cleaning up the temp dir

src/_pytest/pathlib.py

Lines changed: 3 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -26,11 +26,11 @@
2626
from posixpath import sep as posix_sep
2727
import shutil
2828
import sys
29+
import tempfile
2930
import types
3031
from types import ModuleType
3132
from typing import Any
3233
from typing import TypeVar
33-
import uuid
3434
import warnings
3535

3636
from _pytest.compat import assert_never
@@ -286,11 +286,8 @@ def maybe_delete_a_numbered_dir(path: Path) -> None:
286286
lock_path = None
287287
try:
288288
lock_path = create_cleanup_lock(path)
289-
parent = path.parent
290-
291-
garbage = parent.joinpath(f"garbage-{uuid.uuid4()}")
292-
path.rename(garbage)
293-
rm_rf(garbage)
289+
with tempfile.TemporaryDirectory(prefix="garbage-", dir=path.parent) as garbage:
290+
path.replace(garbage)
294291
except OSError:
295292
# known races:
296293
# * other process did a cleanup at the same time

testing/test_pathlib.py

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -486,6 +486,26 @@ def test_long_path_during_cleanup(tmp_path: Path) -> None:
486486
assert not os.path.isdir(extended_path)
487487

488488

489+
def test_permission_denied_during_cleanup(tmp_path: Path) -> None:
490+
"""
491+
Ensure that deleting a numbered dir does not fail because of missing file
492+
permission bits (#7940).
493+
"""
494+
path = tmp_path / "temp-1"
495+
p = path / "ham" / "spam" / "eggs"
496+
p.parent.mkdir(parents=True)
497+
p.touch(mode=0)
498+
for parent in p.parents:
499+
if parent == path:
500+
break
501+
parent.chmod(mode=0)
502+
503+
lock_path = get_lock_path(path)
504+
maybe_delete_a_numbered_dir(path)
505+
assert not path.exists()
506+
assert not lock_path.is_file()
507+
508+
489509
def test_get_extended_length_path_str() -> None:
490510
assert get_extended_length_path_str(r"c:\foo") == r"\\?\c:\foo"
491511
assert get_extended_length_path_str(r"\\share\foo") == r"\\?\UNC\share\foo"

0 commit comments

Comments
 (0)