Skip to content

Commit b41d5a5

Browse files
authored
Merge pull request #12412 from pytest-dev/backport-12408-to-8.2.x
[8.2.x] cacheprovider: fix "Directory not empty" crash from cache directory creation
2 parents 4569a01 + 9bb73d7 commit b41d5a5

File tree

2 files changed

+20
-8
lines changed

2 files changed

+20
-8
lines changed

Diff for: changelog/12381.bugfix.rst

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
Fix possible "Directory not empty" crashes arising from concurent cache dir (``.pytest_cache``) creation. Regressed in pytest 8.2.0.

Diff for: src/_pytest/cacheprovider.py

+19-8
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
# This plugin was not named "cache" to avoid conflicts with the external
55
# pytest-cache version.
66
import dataclasses
7+
import errno
78
import json
89
import os
910
from pathlib import Path
@@ -227,14 +228,24 @@ def _ensure_cache_dir_and_supporting_files(self) -> None:
227228
with open(path.joinpath("CACHEDIR.TAG"), "xb") as f:
228229
f.write(CACHEDIR_TAG_CONTENT)
229230

230-
path.rename(self._cachedir)
231-
# Create a directory in place of the one we just moved so that `TemporaryDirectory`'s
232-
# cleanup doesn't complain.
233-
#
234-
# TODO: pass ignore_cleanup_errors=True when we no longer support python < 3.10. See
235-
# https://github.com/python/cpython/issues/74168. Note that passing delete=False would
236-
# do the wrong thing in case of errors and isn't supported until python 3.12.
237-
path.mkdir()
231+
try:
232+
path.rename(self._cachedir)
233+
except OSError as e:
234+
# If 2 concurrent pytests both race to the rename, the loser
235+
# gets "Directory not empty" from the rename. In this case,
236+
# everything is handled so just continue (while letting the
237+
# temporary directory be cleaned up).
238+
if e.errno != errno.ENOTEMPTY:
239+
raise
240+
else:
241+
# Create a directory in place of the one we just moved so that
242+
# `TemporaryDirectory`'s cleanup doesn't complain.
243+
#
244+
# TODO: pass ignore_cleanup_errors=True when we no longer support python < 3.10.
245+
# See https://github.com/python/cpython/issues/74168. Note that passing
246+
# delete=False would do the wrong thing in case of errors and isn't supported
247+
# until python 3.12.
248+
path.mkdir()
238249

239250

240251
class LFPluginCollWrapper:

0 commit comments

Comments
 (0)