Skip to content

Commit f9ff1c6

Browse files
committed
Added support for path-like object argument in convenience methods
- concerns create_file(), create_dir(), create_symlink(), add_real_file() and add_real_directory() - closes #409
1 parent 297e362 commit f9ff1c6

File tree

3 files changed

+73
-2
lines changed

3 files changed

+73
-2
lines changed

Diff for: CHANGES.md

+4-1
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,10 @@ The release versions are PyPi releases.
44
## Version 3.5 (As yet unreleased)
55

66
#### New Features
7-
7+
* added support for path-like objects as arguments in `create_file()`,
8+
`create_dir()`, `create_symlink()`, `add_real_file()` and
9+
`add_real_directory()` (Python >= 3.6, see [#409](../../issues/409))
10+
811
#### Infrastructure
912
* moved tests into package
1013
* use README.md in pypi ([#358](../../issues/358))

Diff for: pyfakefs/fake_filesystem.py

+12
Original file line numberDiff line numberDiff line change
@@ -2176,6 +2176,12 @@ def remove_object(self, file_path):
21762176
except AttributeError:
21772177
self.raise_io_error(errno.ENOTDIR, file_path)
21782178

2179+
def make_string_path(self, path):
2180+
path = make_string_path(path)
2181+
os_sep = self._matching_string(path, os.sep)
2182+
fake_sep = self._matching_string(path, self.path_separator)
2183+
return path.replace(os_sep, fake_sep)
2184+
21792185
def create_dir(self, directory_path, perm_bits=PERM_DEF):
21802186
"""Create `directory_path`, and all the parent directories.
21812187
@@ -2191,6 +2197,7 @@ def create_dir(self, directory_path, perm_bits=PERM_DEF):
21912197
Raises:
21922198
OSError: if the directory already exists.
21932199
"""
2200+
directory_path = self.make_string_path(directory_path)
21942201
directory_path = self.absnormpath(directory_path)
21952202
self._auto_mount_drive_if_needed(directory_path)
21962203
if self.exists(directory_path, check_link=True):
@@ -2279,6 +2286,8 @@ def add_real_file(self, source_path, read_only=True, target_path=None):
22792286
that `pyfakefs` must not modify the real file system.
22802287
"""
22812288
target_path = target_path or source_path
2289+
source_path = make_string_path(source_path)
2290+
target_path = self.make_string_path(target_path)
22822291
real_stat = os.stat(source_path)
22832292
fake_file = self.create_file_internally(target_path,
22842293
read_from_real_fs=True)
@@ -2398,6 +2407,7 @@ def create_file_internally(self, file_path,
23982407
raw_io: `True` if called from low-level API (`os.open`)
23992408
"""
24002409
error_class = OSError if raw_io else IOError
2410+
file_path = self.make_string_path(file_path)
24012411
file_path = self.absnormpath(file_path)
24022412
if not is_int_type(st_mode):
24032413
raise TypeError(
@@ -2464,6 +2474,8 @@ def create_symlink(self, file_path, link_target, create_missing_dirs=True):
24642474
"on Windows before Python 3.2")
24652475

24662476
# the link path cannot end with a path separator
2477+
file_path = self.make_string_path(file_path)
2478+
link_target = self.make_string_path(link_target)
24672479
file_path = self.normcase(file_path)
24682480
if self.ends_with_path_separator(file_path):
24692481
if self.exists(file_path):

Diff for: pyfakefs/tests/fake_pathlib_test.py

+57-1
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@
2727
import sys
2828
import unittest
2929

30-
from pyfakefs import fake_pathlib
30+
from pyfakefs import fake_pathlib, fake_filesystem
3131
from pyfakefs.tests.test_utils import RealFsTestCase
3232

3333
is_windows = sys.platform == 'win32'
@@ -910,5 +910,61 @@ def use_real_fs(self):
910910
return True
911911

912912

913+
@unittest.skipIf(sys.version_info < (3, 6),
914+
'Path-like objects new in Python 3.6')
915+
class FakeFilesystemPathLikeObjectTest(unittest.TestCase):
916+
917+
def setUp(self):
918+
self.filesystem = fake_filesystem.FakeFilesystem(path_separator='/')
919+
self.pathlib = fake_pathlib.FakePathlibModule(self.filesystem)
920+
self.os = fake_filesystem.FakeOsModule(self.filesystem)
921+
922+
def test_create_dir_with_pathlib_path(self):
923+
dir_path_string = 'foo/bar/baz'
924+
dir_path = self.pathlib.Path(dir_path_string)
925+
self.filesystem.create_dir(dir_path)
926+
self.assertTrue(self.os.path.exists(dir_path_string))
927+
self.assertEqual(stat.S_IFDIR,
928+
self.os.stat(dir_path_string).st_mode & stat.S_IFDIR)
929+
930+
def test_create_file_with_pathlib_path(self):
931+
file_path_string = 'foo/bar/baz'
932+
file_path = self.pathlib.Path(file_path_string)
933+
self.filesystem.create_file(file_path)
934+
self.assertTrue(self.os.path.exists(file_path_string))
935+
self.assertEqual(stat.S_IFREG,
936+
self.os.stat(file_path_string).st_mode & stat.S_IFREG)
937+
938+
def test_create_symlink_with_pathlib_path(self):
939+
file_path = self.pathlib.Path('foo/bar/baz')
940+
link_path_string = 'foo/link'
941+
link_path = self.pathlib.Path(link_path_string)
942+
self.filesystem.create_symlink(link_path, file_path)
943+
self.assertTrue(self.os.path.lexists(link_path_string))
944+
self.assertEqual(stat.S_IFLNK,
945+
self.os.lstat(link_path_string).st_mode &
946+
stat.S_IFLNK)
947+
948+
def test_add_existing_real_file_with_pathlib_path(self):
949+
real_file_path_string = os.path.abspath(__file__)
950+
real_file_path = self.pathlib.Path(real_file_path_string)
951+
self.filesystem.add_real_file(real_file_path)
952+
fake_filepath_string = real_file_path_string.replace(
953+
os.sep, self.os.sep)
954+
self.assertTrue(self.os.path.exists(fake_filepath_string))
955+
self.assertEqual(stat.S_IFREG, self.os.stat(
956+
fake_filepath_string).st_mode & stat.S_IFREG)
957+
958+
def test_add_existing_real_directory_with_pathlib_path(self):
959+
real_dirpath_string = os.path.dirname(os.path.abspath(__file__))
960+
real_dir_path = self.pathlib.Path(real_dirpath_string)
961+
self.filesystem.add_real_directory(real_dir_path)
962+
fake_dirpath_string = real_dirpath_string.replace(
963+
os.sep, self.os.sep)
964+
self.assertTrue(self.os.path.exists(fake_dirpath_string))
965+
self.assertEqual(stat.S_IFDIR, self.os.stat(
966+
fake_dirpath_string).st_mode & stat.S_IFDIR)
967+
968+
913969
if __name__ == '__main__':
914970
unittest.main()

0 commit comments

Comments
 (0)