Skip to content

Commit bdd76cd

Browse files
committed
Fix patching of Debian-specific tempfile
- Debian patches tempfile by importing shutil.rmtree as _rmtree (see https://salsa.debian.org/cpython-team/python3/-/blob/master/debian/patches/min-tempfile.diff) - this cached version of _rmtree was not patched, so we replace it with the original (patched) version from shutil
1 parent c7c0440 commit bdd76cd

File tree

3 files changed

+21
-6
lines changed

3 files changed

+21
-6
lines changed

CHANGES.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,11 @@ The released versions correspond to PyPI releases.
1313
the real filesystem behavior
1414
* remove support for Python versions before 3.10 (if needed, patches may be backported to the 5.x branch)
1515

16+
### Unreleased
17+
18+
## Fixes
19+
* fixes patching of Debian-specific `tempfile` in Python 3.13 (see [#1214](../../issues/1214))
20+
1621
## [Version 5.9.3](https://pypi.python.org/pypi/pyfakefs/5.9.3) (2025-08-28)
1722
Fixes a utility method.
1823

pyfakefs/fake_filesystem_unittest.py

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -98,6 +98,7 @@ class TempfilePatcher:
9898

9999
def __init__(self):
100100
self.tempfile_cleanup = None
101+
self.tempfile_rmtree = None
101102

102103
def start_patching(self):
103104
if self.tempfile_cleanup is not None:
@@ -109,6 +110,16 @@ def cleanup(self_, windows=(os.name == "nt"), unlink=None):
109110

110111
self.tempfile_cleanup = tempfile._TemporaryFileCloser.cleanup # type: ignore[module-attr]
111112
tempfile._TemporaryFileCloser.cleanup = cleanup # type: ignore[module-attr]
113+
114+
if sys.version_info >= (3, 13) and hasattr(tempfile, "_rmtree"):
115+
# Debian patches tempfile by importing or copying shutil.rmtree as _rmtree
116+
# we patch this to use the original (patched) version
117+
def _rmtree(*args, **kwargs):
118+
return tempfile._shutil.rmtree(*args, **kwargs)
119+
120+
self.tempfile_rmtree = tempfile._rmtree # type: ignore[module-attr]
121+
tempfile._rmtree = _rmtree # type: ignore[module-attr]
122+
112123
elif sys.platform != "win32":
113124

114125
def close(self_, unlink=None):
@@ -125,6 +136,9 @@ def stop_patching(self):
125136
else:
126137
tempfile._TemporaryFileCloser.cleanup = self.tempfile_cleanup # type: ignore[module-attr]
127138
self.tempfile_cleanup = None
139+
if self.tempfile_rmtree is not None:
140+
tempfile._rmtree = self.tempfile_rmtree # type: ignore[module-attr]
141+
self.tempfile_rmtree = None
128142
# reset the cached tempdir in tempfile
129143
tempfile.tempdir = None
130144

@@ -1063,12 +1077,13 @@ def start_patching(self) -> None:
10631077
self._paused = False
10641078

10651079
self.linecache_patcher.start_patching()
1066-
self.tempfile_patcher.start_patching()
10671080

10681081
self.patch_modules()
10691082
self.patch_functions()
10701083
self.patch_defaults()
1084+
10711085
self._set_glob_os_functions()
1086+
self.tempfile_patcher.start_patching()
10721087

10731088
self._dyn_patcher = DynamicPatcher(self)
10741089
sys.meta_path.insert(0, self._dyn_patcher)

pyfakefs/tests/fake_tempfile_test.py

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,6 @@
1818

1919
import os
2020
import stat
21-
import sys
2221
import tempfile
2322
import unittest
2423

@@ -89,10 +88,6 @@ def test_mkdtemp(self):
8988
self.assertTrue(self.fs.exists(dirname))
9089
self.assertEqual(self.fs.get_object(dirname).st_mode, stat.S_IFDIR | 0o700)
9190

92-
@unittest.skipIf(
93-
sys.version_info[:3] == (3, 13, 5),
94-
"Not working on Debian with this version, see #1214",
95-
)
9691
def test_temporary_directory(self):
9792
with tempfile.TemporaryDirectory() as tmpdir:
9893
self.assertTrue(tmpdir)

0 commit comments

Comments
 (0)