2嵔FDdZddlZddlZddlZddlZddlZddlZddlmZm Z ddl m Z ddl m Z ddlmZmZmZmZmZmZmZddlmZmZmZmZmZmZmZmZmZm Z m!Z!ddl"m#Z#m$Z$m%Z%m&Z&m'Z'm(Z(dd l)m*Z*m+Z+dd l,m-Z-m.Z.m/Z/m0Z0m1Z1m2Z2ej34d rd Z5nd Z5Gdde Z6e#j7Z7e#j8Z8e#j9Z9e#j:Z:e#j;Z;e#j<ZZ>e#j?Z?e$j@Z@e&jAZAe(jBZBe%jCZCej3dkre%jDZDe%jEZEe'jFZFe'jGZGe'jHZHe'jIZIe'jJZJe'jKZKe'jLZLe'jMZMe'jNZNe'jOZOe'jPZPe'jQZQGddZRde fdZSdZTeUdkr eSdSdS)a"A fake filesystem implementation for unit testing. :Usage: >>> from pyfakefs import fake_filesystem, fake_os >>> filesystem = fake_filesystem.FakeFilesystem() >>> os_module = fake_os.FakeOsModule(filesystem) >>> pathname = '/a/new/dir/new-file' Create a new file object, creating parent directory objects as needed: >>> os_module.path.exists(pathname) False >>> new_file = filesystem.create_file(pathname) File objects can't be overwritten: >>> os_module.path.exists(pathname) True >>> try: ... filesystem.create_file(pathname) ... except OSError as e: ... assert e.errno == errno.EEXIST, 'unexpected errno: %d' % e.errno ... assert e.strerror == 'File exists in the fake filesystem' Remove a file object: >>> filesystem.remove_object(pathname) >>> os_module.path.exists(pathname) False Create a new file object at the previous path: >>> beatles_file = filesystem.create_file(pathname, ... contents='Dear Prudence\nWon\'t you come out to play?\n') >>> os_module.path.exists(pathname) True Use the FakeFileOpen class to read fake file objects: >>> file_module = fake_filesystem.FakeFileOpen(filesystem) >>> for line in file_module(pathname): ... print(line.rstrip()) ... Dear Prudence Won't you come out to play? File objects cannot be treated like directory objects: >>> try: ... os_module.listdir(pathname) ... except OSError as e: ... assert e.errno == errno.ENOTDIR, 'unexpected errno: %d' % e.errno ... assert e.strerror == 'Not a directory in the fake filesystem' The FakeOsModule can list fake directory objects: >>> os_module.listdir(os_module.path.dirname(pathname)) ['new-file'] The FakeOsModule also supports stat operations: >>> import stat >>> stat.S_ISREG(os_module.stat(pathname).st_mode) True >>> stat.S_ISDIR(os_module.stat(os_module.path.dirname(pathname)).st_mode) True N) namedtuple OrderedDict) TestResults)Enum)S_IFREGS_IFDIRS_ISLNKS_IFMTS_ISDIRS_IFLNKS_ISREG) ListOptionalCallableUnionAnyDictTuplecastAnyStroverloadNoReturn) fake_file fake_pathfake_iofake_oshelpers fake_open)AnyFileWrapperAnyFile) is_int_typemake_string_path to_stringmatching_stringAnyPath AnyStringlinux( ceZdZdZdZdZdZdS)OSTypez?Defines the real or simulated OS of the underlying file system.r'macoswindowsN)__name__ __module__ __qualname____doc__LINUXMACOSWINDOWS/srv/buildsys-work-dir/castor/build_node/builder-2/WGSG1/unpkd_srcs/cloudlinux-venv-1.0.6/venv/lib/python3.11/site-packages/pyfakefs/fake_filesystem.pyr+r+s#II E EGGGr6r+win32c eZdZdZejjdddfdedee de de ddf d Z e de fd Ze de fd Zejd e ddfd Ze de fdZejd e ddfdZe defdZejd eddfdZe defdZe defdZe defdZejd eddfdZddee de fdZdZddZddZddZdefdZ dde deed ee defd!Zd"e de fd#Z!d"e dee fd$Z"d"e de fd%Z# dd"e dee d&e de$fd'Z%d(e&defd)Z'd"e dee$fd*Z(d"e de$fd+Z)defd,Z*d-e dee$fd.Z+dd"ee de,e e e ffd/Z-dde d"ee ddfd0Z.d1e d2e d3e ddfd4Z/dd5e d6e fd7Z0 dd5e d8e1d6e d9e ddf d:Z2 dd"e d;e d6e dd"e d?ee,e4e e5fe4e e5ffd@ee,e e fd6e ddf dAZ6e7d@ee,e e fd?ee,e4e e5fe4e e5fffdBZ8dCe9de fdDZ:dEe ddfdFZ;dEe de9fdGZd"e de fdJZ?d"e de fdKZ@d"e de fdLZAd"e de fdMZBd"e de,e e ffdNZCd"e de,e e ffdOZDd"e fdPZEdQe de fdRZFdSe de fdTZGeHd"edeIefdUZJeHd"eKdeIeKfdVZJd"e deIe fdWZJd2e de fdXZLd2e de fdYZMd"e de fdZZNd2e de fd[ZOd2e de fd\ZPd"e4e e&fde fd]ZQd"e de fd^ZRd_ed`ede,eeeeSffdaZTdd2e&dbe de fdcZUdd2e dde de fdeZVdfZWdgeIe deIefdhZXd2e de fdiZYdjeIedkeSdefdlZZ dd2e&dme dne deSfdoZ[e7dpZ\dd2e&dme de1fdqZ] dd2e d6e dde dme dne de1f drZ^d"e&de1fdsZ_d2e d8eSddfdtZ` ddue&dve&dwe ddfdxZadyZbd"e ddfdzZcdve due d{e ddfd|Zddwe dve due d}e1d{e dee f d~Zedwe dve de1d}e1d{e ddf dZfdve due dee fdZgd2e ddfdZhd"e&de fdZiejjkfd(e&de defdZlemejjnzdddddddfd2e&de dedee de de deedeedeeode1fdZp dde&de dee&de1fdZq dde&dee&de1fdZr dde&de de dee&def dZs ddeIe de de ddfdZtemejjnzddddddddf d2e&de dedee de de deedeede deeode1fdZu dd2e&de&de de1fdZv dde&de&d6e de de1f dZw dde&de&d6e de1fdZxde1de fdZyd"e&defdZzejjkfde&d;e ddfdZ{d"e de fdZ|ejjkdfde d;e de ddfdZ} dd"e&de d6e dme de f dZ~dd"e&d6e de fdZdd"e&d6e de fdZd"e&de fdZejdkrd"e&de fdZ dde dne defdZd"e ddfdZdde de ddfdZde deIe fdZdefdZddZdZdS)FakeFilesystemaProvides the appearance of a real directory tree for unit testing. Attributes: path_separator: The path separator, corresponds to `os.path.sep`. alternative_path_separator: Corresponds to `os.path.altsep`. is_windows_fs: `True` in a real or faked Windows file system. is_macos: `True` under MacOS, or if we are faking it. is_case_sensitive: `True` if a case-sensitive file system is assumed. root: The root :py:class:`FakeDirectory` entry of the file system. umask: The umask used for newly created files, see `os.umask`. patcher: Holds the Patcher object if created from it. Allows access to the patcher object if using the pytest fs fixture. patch_open_code: Defines how `io.open_code` will be patched; patching can be on, off, or in automatic mode. shuffle_listdir_results: If `True`, `os.listdir` will not sort the results to match the real file system behavior. NFpath_separator total_sizepatchercreate_temp_dirreturncF||_tjj|_||_||_|tjkrd|_tj dk|_ tj dk|_ |j p|j |_ |d|_tjd|_tj|jg|_g|_d|_d|_t)|_d|_||dt0j|_d|_dS) al Args: path_separator: optional substitute for os.path.sep total_size: if not None, the total size in bytes of the root filesystem. patcher: the Patcher instance if created from the Patcher create_temp_dir: If True, a temp directory is created on initialization. Under Posix, if the temp directory is not `/tmp`, a link to the temp path is additionally created at `/tmp`. Example usage to use the same path separator under all systems: >>> filesystem = FakeFilesystem(path_separator='/') Nr8darwinrF)r< init_pathlib)r;ospathaltsepalternative_path_separatorr=r>sepsysplatform_is_windows_fs _is_macos is_windows_fsis_case_sensitive_cwdumask open_files _free_fd_heaplast_inolast_devr mount_pointsdev_nullreset PatchModeOFFpatch_open_codeshuffle_listdir_results)selfr;r<r=r>s r7__init__zFakeFilesystem.__init__s,$29;' . RV # #.2D + "lg51-1,>,P$.'Q   (4..  AC(*  3>==!  ju === )}',$$$r6c"|j o|j SN)rNis_macosr]s r7is_linuxzFakeFilesystem.is_linuxs%%;dm*;;r6c|jSr`)rLrbs r7rNzFakeFilesystem.is_windows_fs s ""r6valuec|j|kr7||_|t|dSdSr`)rLrXFakePathModuler]res r7rNzFakeFilesystem.is_windows_fs sG  % ' '"'D  JJLLL   & & & & & ( 'r6c|jSr`)rMrbs r7razFakeFilesystem.is_macoss ~r6c|j|kr7||_|t|dSdSr`)rMrXrgrhs r7razFakeFilesystem.is_macossE >U " ""DN JJLLL   & & & & & # "r6c|jS)z||_||dS)zSet the current working directory of the fake filesystem. Make sure a new drive or share is auto-mounted under Windows. N)rP_auto_mount_drive_if_neededrhs r7rlzFakeFilesystem.cwd$s%   ((/////r6cF|jr|S|jS)ziReturn the root directory, which represents "/" under POSIX, and the current drive under Windows.)rN_mount_point_dir_for_cwdrootrbs r7root_dirzFakeFilesystem.root_dir,s)   30022 2yr6ct|jj}||js ||jzS|S)zwReturn the root directory name, which is "/" under POSIX, and the root path of the current drive under Windows.)r#rrnameendswithr;)r]rrs r7 root_dir_namezFakeFilesystem.root_dir_name4sBT]/00  !455 2d11 1r6cf|jr tjn|jr tjn tjS)z6Return the real or simulated type of operating system.)rNr+r4rar3r2rbs r7rEzFakeFilesystem.os=s1 ! FNN}  r6cD|tjk|_|tjk|_|tjk|_|tjkrdnd|_|tjkrdnd|_| t |dS)zSSet the simulated type of operating system underlying the fake file system.\/N) r+r4rLr3rMr2rOr;rHrXrgrhs r7rEzFakeFilesystem.osHs$v~5&,.!&&,!6&+v~&=&=dd316&.1H1H##d' T"""""r6TrDct|j||_t||_|j|jd|_d|_ |j | || |j r||rddlm}||dSdS)z3Remove all file system contents and reset the root. filesystemr) fake_pathlibN) FakeDirectoryr;rq FakeNullFilerWrRclearrSrTrUrV_add_root_mount_point_add_standard_streamsr>_create_temp_dirpyfakefsr~ init_module)r]r<rDr~s r7rXzFakeFilesystem.resetTs!$"5$GGG $T**     """   !!! "":... ""$$$   $  ! ! # # #  + - - - - - -  $ $T * * * * * + +r6c|jrdn|j}||_|j|js|xj|jz c_|||dS)NzC:)rNr;rPrlruadd_mount_point)r]r< mount_points r7rz$FakeFilesystem._add_root_mount_pointgsg"0Iddd6I  x  !455 - II, ,II [*55555r6cd|jtd|jdS)aPause the patching of the file system modules until `resume` is called. After that call, all file system calls are executed in the real file system. Calling pause() twice is silently ignored. Only allowed if the file system object was created by a Patcher object. This is also the case for the pytest `fs` fixture. Raises: RuntimeError: if the file system was not created by a Patcher. NzUpause() can only be called from a fake file system object created by a Patcher object)r= RuntimeErrorpauserbs r7rzFakeFilesystem.pausens? < <  r6cd|jtd|jdS)aGResume the patching of the file system modules if `pause` has been called before. After that call, all file system calls are executed in the fake file system. Does nothing if patching is not paused. Raises: RuntimeError: if the file system has not been created by `Patcher`. NzVresume() can only be called from a fake file system object created by a Patcher object)r=rresumerbs r7rzFakeFilesystem.resumes? < <  r6cJ|jr|jdSdS)z'Clear the cache of non-patched modules.N)r= clear_cacherbs r7rzFakeFilesystem.clear_caches0 < ' L $ $ & & & & & ' 'r6c|jrdndS)Nz  )rNrbs r7line_separatorzFakeFilesystem.line_separators+5vv5r6err_nofilenamewinerrorctj|dz}|)tjdkr|jrt ||||t |||)a+Raises OSError. The error message is constructed from the given error code and shall start with the error string issued in the real system. Note: this is not true under Windows if winerror is given - in this case a localized message specific to winerror will be shown in the real file system. Args: err_no: A numeric error code from the C variable errno. filename: The name of the affected file, if any. winerror: Windows only - the specific Windows error code. z in the fake filesystemNr8)rEstrerrorrJrKrNOSError)r]rrrmessages r7raise_os_errorzFakeFilesystem.raise_os_errorsY$+f%%(AA  CLG$;$;@R$;&'8X>> >fgx000r6rFc,t||jS)z2Return the path separator as the same type as path)r$r;r]rFs r7get_path_separatorz!FakeFilesystem.get_path_separatorstT%8999r6c,t||jS)z>Return the alternative path separator as the same type as path)r$rHrs r7_alternative_path_separatorz*FakeFilesystem._alternative_path_separatorstT%DEEEr6c||}||}||p|duo||S)z1Return True if path starts with a path separator.N)rr startswith)r]rFrIrGs r7starts_with_sepzFakeFilesystem.starts_with_sepsU%%d++11$77s##UvT'9'Udoof>U>UUr6 can_existc|||}|jD]}|jr|t ||ks?|jsi|t ||kr1|r|j|cS|tj||xj dz c_ |j |dd|j|<|t ||j j kr$|j }|xj dz c_ |j |_ n||}|j |_|j|S)aaAdd a new mount point for a filesystem device. The mount point gets a new unique device number. Args: path: The root path for the new mount path. total_size: The new total size of the added filesystem device in bytes. Defaults to infinite size. can_exist: If True, no error is raised if the mount point already exists Returns: The newly created mount point dict. Raises: OSError: if trying to mount an existing mount point again, and `can_exist` is False. r)idevr< used_size)normpathnormcaserVrOr$lowerrerrnoEEXISTrUrqrtrTst_ino_create_mount_point_dirst_dev)r]rFr<rrrrs r7rzFakeFilesystem.add_mount_pointsR2}}T]]40011, 8 8K& 8OD+>>>>-?JJLLOD+:K:K:M:M$N$NNN:,[9999##EL$777  M$# # $ ?488 8 8yH MMQ MM"mHOO33D99H- &&r6directory_pathc||}||}|j}g}d|DD]}||t |d}|s>t ||}|||||}ktt |}|D]}ttj z|_ |S)zA version of `create_dir` for the mount point directory creation, which avoids circular calls and unneeded checks. c,g|]}t|Sr5r#.0ps r7 z:FakeFilesystem._create_mount_point_dir..@@@1)A,,@@@r6rr|) r"_path_componentsrq_directory_contentr#rappend add_entryrrrPERM_DEFst_mode) r]rdir_pathpath_components current_dirnew_dirs component directorynew_dirs r7rz&FakeFilesystem._create_mount_point_dirs((88//99i @@@@@ = =I// Yy=Q=QRRSTUI =' dCCC(((%%g...% "=)<<  9 9G%(88GOOr6c||jr4||d}|r||dSdS)zWindows only: if `path` is located on an unmounted drive or UNC mount point, the drive/mount point is added to the mount points.rT)rFrN)rN splitdriver)r]rFdrives r7rnz*FakeFilesystem._auto_mount_drive_if_needed sM   HOOD))!,E H++$+GGGtr6cB|||}|jD]%}|t||kr|j|cS&t|d}||d}|jD]a}t||}|r||s*||r"t |t |kr|}b|r|jt|S||}|sJ|S)NrBr) absnormpath_original_pathrVr$rrlenr#rn)r]rF mount_pathr root_pathrs r7_mount_point_for_pathz$FakeFilesystem._mount_point_for_paths; 3 3D 9 9::+ 5 5JtZ8888(44449$T2.. %%a(* ' 'I'i88I Y11%88 y)) 'c)nns:.N.N&  <$Yz%:%:; ;66t<< {r6cdtffd }tj}jD]"}|t|kr ||cS#d}t|d}jD]`}t|}|r||s)||r"t |t |kr|}a||S)zjReturn the fake directory object of the mount point where the current working directory points to.r?c|}j}|D]*}tt||}+|Sr`)rrqrr get_entry) file_pathrtargetrr]s r7object_from_pathzAFakeFilesystem._mount_point_dir_for_cwd..object_from_path)sR"33I>>OYF, J J mV-=-=i-H-HIIMr6rBr)rr#rlrVrrr)r]rrFrrr str_root_paths` r7rpz'FakeFilesystem._mount_point_dir_for_cwd%s =      ""+ 4 4Jy,,,,'' 33333- $//$//233* ' 'I%i00M ]55e<< }-- '#m2D2Ds:2V2V&  +++r6rc^|jD]}|d|kr|cSdS)Nr)rVvalues)r]rrs r7_mount_point_for_devicez&FakeFilesystem._mount_point_for_device>sF,3355 # #K6"d**""""+tr6cTtdd}|4tt|j}n$t |}||}|r0|d(||d|d|d|dz S|dddS)aReturn the total, used and free disk space in bytes as named tuple, or placeholder values simulating unlimited space if not set. .. note:: This matches the return value of shutil.disk_usage(). Args: path: The disk space is returned for the file system device where `path` resides. Defaults to the root path (e.g. '/' on Unix systems). DiskUsageztotal, used, freeNr<rlr)rnextiterrVrr"r)r]rFrrrs r7get_disk_usagezFakeFilesystem.get_disk_usageDs{,?@@ <tD$5$<$<$>$>??@@KK(..I44Y??K  ;|4@9L)K(L)K ,DD  y2A7PQQQr6c||n|j}||}|d,|d|kr |tj|||d<dS)aChanges the total size of the file system, preserving the used space. Example usage: set the size of an auto-mounted Windows drive. Args: total_size: The new total size of the filesystem in bytes. path: The disk space is changed for the file system device where `path` resides. Defaults to the root path (e.g. '/' on Unix systems). Raises: OSError: if the new space is smaller than the used size. Nr<r)rvrrrENOSPC)r]r<rFrrs r7set_disk_usagezFakeFilesystem.set_disk_usage]sp $DD$*< 00;;  % 1K(:55    d 3 3 3$. L!!!r6 usage_changerrc||}|rK|d}|/||dz |kr |tj||dxx|z cc<dSdS)aChange the used disk space by the given amount. Args: usage_change: Number of bytes added to the used space. If negative, the used space will be decreased. file_path: The path of the object needing the disk space. st_dev: The device ID for the respective file system. Raises: OSError: if usage_change exceeds the free file system space r<Nr)rrrr)r]rrrrr<s r7change_disk_usagez FakeFilesystem.change_disk_usagews 226::  5$\2J% K 88<GG'' i@@@  $ $ $ 4 $ $ $ $ $  5 5r6 entry_pathfollow_symlinkscD |||dd}n%#t$r||}YnwxYwts#|j}|r||j|||||jS)aReturn the os.stat-like tuple for the FakeFile object of entry_path. Args: entry_path: Path to filesystem object to retrieve. follow_symlinks: If False and entry_path points to a symlink, the link itself is inspected instead of the linked object. Returns: The FakeStatResult object corresponding to entry_path. Raises: OSError: if the filesystem object doesn't exist. TF)allow_fdcheck_read_perm) resolve TypeErroris_root parent_dir get_objectrF(raise_for_filepath_ending_with_separator stat_resultcopy)r]rr file_objectrs r7statzFakeFilesystem.stats 3,, % 'KK  3 3 3,,z22KKK 3yy 1$/J 1 000 55  _   &++---s >>rmacos_handlingcz||r"t|jr ||}n\#t$rO}|jr|jt jkrYd}~dS|jr | t j |d}~wwxYw|r|js|jr|}|jrt|j}n4|jr|rt|j }nt|j }|r9|jr t j n t j }| ||dSdSdSr`)ends_with_path_separatorr rrrrarENOENTrNrEINVALr r ENOTDIR) r]rrrr link_objectexcis_errorerror_nrs r7rz7FakeFilesystem.raise_for_filepath_ending_with_separatorsu  ( ( 4 4 :{*++ ."&,,z":":KK}el)B)B)F++EL*EEE  '.$*<. ."-K! <";#677 <> <&{':;;;&{':;;; :+/+=P5<<5=##Hj99999) : :$ : :sA B B.(BBmodeforce_unix_modec,|||dd}|jr1|s/|tjzr|jdz|_n:|jdz|_n*|jtjz|tjzz|_tj|_dS)aChange the permissions of a file as encoded in integer mode. Args: path: (str) Path to the file. mode: (int) Permissions. follow_symlinks: If `False` and `path` points to a symlink, the link itself is affected instead of the linked object. force_unix_mode: if True and run under Windows, the mode is not adapted for Windows to allow making dirs unreadable T)r check_ownerimN)rrNr PERM_WRITErPERM_ALLnowst_ctime)r]rFrrrrs r7chmodzFakeFilesystem.chmods"ll /Dd#     o g(( E&1&9E&A ##&1&9H&D ###.#6':J9J#Jw''#K  '{}} r6)nsrtimesr c||||||d}|L|D]-}t|ttfst d.|d|_|d|_dS|E|D]&}t|tst d'|d|_|d|_ dStj }||_||_dS)aChange the access and modified times of a file. Args: path: (str) Path to the file. times: 2-tuple of int or float numbers, of the form (atime, mtime) which is used to set the access and modified times in seconds. If None, both times are set to the current time. ns: 2-tuple of int numbers, of the form (atime, mtime) which is used to set the access and modified times in nanoseconds. If `None`, both times are set to the current time. follow_symlinks: If `False` and entry_path points to a symlink, the link itself is queried instead of the linked object. Raises: TypeError: If anything other than the expected types is specified in the passed `times` or `ns` tuple, or if the tuple length is not equal to 2. ValueError: If both times and ns are specified. TrNzatime and mtime must be numbersrrzatime and mtime must be ints) _handle_utime_arg_errorsr isinstanceintfloatrst_atimest_mtime st_atime_ns st_mtime_nsrr)r]rFr r rr file_time current_times r7utimezFakeFilesystem.utimes6 %%b%000ll44lHH  " G G !)c5\::G#$EFFFG$)8K #(8K ^ D D !)S11D#$BCCCD')eK #&(eK # # #";==L#/K #/K r6c||td|"t|dkrtd|"t|dkrtddSdS)Nz:utime: you may specify either 'times' or 'ns' but not bothz9utime: 'times' must be either a tuple of two ints or Nonez'utime: 'ns' must be a tuple of two ints) ValueErrorrr)r r s r7r z'FakeFilesystem._handle_utime_arg_errors su  L   UqWXX X >c"ggllEFF F >llr6file_objc|jr&tj|j}|g|j|<|S|j|gt |jdz S)aXAdd file_obj to the list of open files on the filesystem. Used internally to manage open files. The position in the open_files array is the file descriptor number. Args: file_obj: File object to be added to open files list. Returns: File descriptor number for the file object. r)rSheapqheappoprRrr)r]ropen_fds r7_add_open_filezFakeFilesystem._add_open_file.sa   mD$677G(0zDOG $N z***4?##a''r6file_descNd|j|<tj|j|dS)zRemove file object with given descriptor from the list of open files. Sets the entry in open_files to None. Args: file_des: Descriptor of file object to be removed from open files list. N)rRrheappushrS)r]r!s r7_close_open_filezFakeFilesystem._close_open_fileBs+%)! t)844444r6ct|std|t|jk}|r|j|}||dS|t jt|dS)aReturn an open file. Args: file_des: File descriptor of the open file. Raises: OSError: an invalid file descriptor. TypeError: filedes is not an integer. Returns: Open file object. zan integer is requiredNr)r!rrrRrrEBADFstr)r]r!valid file_lists r7 get_open_filezFakeFilesystem.get_open_fileOs8$$ 6455 53t///  $1I$ |# EKX77777r6c(|d|jDvS)zReturn True if the given file object is in the list of open files. Args: file_object: The FakeFile object to be checked. Returns: `True` if the file is open. cFg|]}||dS)r)r)rwrapperss r7rz0FakeFilesystem.has_open_file..ns=   )1 QK " " $ $   r6)rR)r]rs r7 has_open_filezFakeFilesystem.has_open_filees/  59_     r6c||}|)||||S|Sr`)rreplacer)r]rFalt_seps r7_normalize_path_sepz"FakeFilesystem._normalize_path_seprsB22488  <<)@)@)F)FGG G r6cJt|}||S)aReplace all appearances of alternative path separator with path separator. Do nothing if no alternative separator is set. Args: path: The path to be normalized. Returns: The normalized path that will be used internally. )r"r2)r]rFrs r7rzFakeFilesystem.normcasexs%%T** '' 222r6c||}||\}}||}||}||}g}t |d}t |d} |D]L} | r| |kr | | kr&|r!|d| kr|4|r7|| M||} |r|| z} || zp|S)aMimic os.path.normpath using the specified path_separator. Mimics os.path.normpath using the path_separator that was specified for this FakeFilesystem. Normalizes the path, but unlike the method absnormpath, does not make it absolute. Eliminates dot components (. and ..) and combines repeated path separators (//). Initial .. components are left in place for relative paths. If the result is an empty path, '.' is returned instead. This also replaces alternative path separator with path separator. That is, it behaves like the real os.path.normpath on Windows if initialized with '\' as path separator and '/' as alternative separator. Args: path: (str) The path to normalize. Returns: (str) A copy of path with empty components and dot components removed. ...) rrrrsplitr$poprjoin) r]rFpath_strrrIis_absolute_pathrcollapsed_path_componentsdotdotdotrcollapsed_paths r7rzFakeFilesystem.normpathsG,==&&//(33x%%h//#..s33(0 ) )   "h,, 400( 8 8I 9#3#3F"", -b1V;;.11333% % , ,Y 7 7 7 7";<<  2 >1N~%,,r6cfd}jssSgj}D]}t |t s |cS|t|\}}|'t |t r|j|j dkr |cStt |} ||S)aDReturn a normalized case version of the given path for case-insensitive file systems. For case-sensitive file systems, return path unchanged. Args: path: the file path to be transformed Returns: A version of path matching the case of existing path elements. cttkr4dtdDj}|}r|s||z}t|dkr|r||z }|S)Nc34K|]}t|VdSr`rrs r7 zLFakeFilesystem._original_path..components_to_path..s9--%&IaLL------r6r)rextendr;r:rstarts_with_drive_letter)rInormalized_pathnormalized_componentsrFrr]s r7components_to_pathz9FakeFilesystem._original_path..components_to_paths?##c*?&@&@@@%,,--*9#>S:T:T:V:V*W---%C!hh'<==O##D)) 8$2F2F2W2W 8"%"7?##q((T-J-J..( 3&" "r6Nr) rOreplace_windows_rootrrqrrrr#_byte_contentsst_sizerr) r]rFrIrrdir_namerrHrs `` @@r7rzFakeFilesystem._original_pathsR # # # # # # # #  !  K((..//55 "i ( 3 3Ik=99 ,))+++++"&"9"9Yy11## Hi 9m44!,4%**))+++++}i88K ! ( ( 2 2 2 2!!###r6c||}t||j}|s||}|t|dkr|}n||s]t||jj}t|d}||||kr|p||f}n||}| |S)arAbsolutize and minimalize the given path. Forces all relative paths to be absolute, and normalizes the path to eliminate dot and empty components. Args: path: Path to normalize. Returns: The normalized path relative to the current working directory, or the root directory if path is empty. r5rB) rr$rlr_starts_with_root_pathrqrtr:rJr)r]rFrl root_nameemptys r7rzFakeFilesystem.absnormpaths}}T""dDH-- 1**400D ?4-- - -DD,,T22 3'din==I#D"--E**40055 !)c2UD9DD,,T22D}}T"""r6c~t|}||}||}||n||z}||\}}t |}|r!||dz |vr|dz}|r ||dz |v|d|||d}}||p|}||z|fS)aMimic os.path.split using the specified path_separator. Mimics os.path.split using the path_separator that was specified for this FakeFilesystem. Args: path: (str) The path to split. Returns: (str) A duple (pathname, basename) for which pathname does not end with a slash, and basename does not contain a slash. Nr)r"rrrrrstrip) r]rFrIr1sepsriheadtails r7 splitpathzFakeFilesystem.splitpath s %%%%d++22488oss3=ood++ t II DQKt++ FA DQKt++"1"XtABBxd{{4  (Dt|T!!r6c^t|}|jr t|dkr||}||}|dd|dzkr|dd|kr||d}|dkr |dd|fS|||dz}||dzkr |dd|fS|dkrt|}|d|||dfS|ddt |dkr|dd|ddfS|dd|fS)aSplits the path into the drive part and the rest of the path. Taken from Windows specific implementation in Python 3.5 and slightly adapted. Args: path: the full path to be splitpath. Returns: A tuple of the drive part and the rest of the path, or of an empty string and the full path if drive letters are not supported or no drive is present. rrr7Nr:)r"rNrrrfindr$)r]rFr;norm_strrI sep_index sep_index2s r7rzFakeFilesystem.splitdrive&sb$D))   68}}!!==22--h77QqSMS1W,,8AaC=C3G3G!) c1 5 5I B'|X55!)sIM!B!BJ!Y]22'|X55!R''%(]] #KZK0(:;;2GGGAaC=OHc$B$BBB#BQB<!""55|X%%r6ctj|}t|trB|j}d}|jr|j}d}d}d}n|j}|j}d}d}d}|jr*|r|||n|}|dd|kr|dd |kr|dd  |krd nd } | || } | d kr|||fS| || dz} | d kr|||fS|d| || | dz|| dzdfS||dd|ddfS|dd |kr@|d d |kr|dd |d d |d dfS|dd ||d dfS|||fS|dd|kr|||fS|dd |ks|d d |kr |||ddfS||dd |d dfS) zlSplit a pathname into drive, root and tail. Implementation taken from ntpath and posixpath. N:s\\?\UNC\r6r[z\\?\UNC\rBrrr7rZ) rEfspathrbytesr;encoderHrNr0upperr\) r]rFrrIrGcolon unc_prefixrQnormpstartindexindex2s r7 splitrootzFakeFilesystem.splitrootJs IdOO a   %,,..CF. B8??AAE(JEE%C4FE'JE  # +.4;AIIfc***!ERaRyC1:$$"'rr!2!2j!@!@AAaE!JJsE22E{{ %."ZZUQY77F|| %.WfW:q&1*)<'=q!NN!!BQB%122..qsu$$1:$$RaR5!AaC&!ABB%//RaR5%122..eQ&!u||eQ&1Q33!AaC&C--c1QRR5((aeQqrrU**r6 all_pathsc<|d}|dd}||}|||g}||\}}|D]}||\} } | r| dd|vr | s|s| }| }1| r>| |kr8|js*| |kr| }| }o| }|r|dd|vr||z}|| z}t |d} |r$|dd|vr|r|dd| kr||z|zS||zS)zSTaken from Python 3.5 os.path.join() code in ntpath.py and slightly adaptedrrNr7r[)rrrrOrr$) r]rn base_path paths_to_addrIrT result_drive result_pathrF drive_part path_partrgs r7_join_paths_with_drive_supportz-FakeFilesystem._join_paths_with_drive_supportsaL  } %%i00T55i@@A$(OOI$>$>! k  2 2D$(OOD$9$9 !J  *Yrr]d22.\.#-L'  * l : :)Z-=-=-?-?.s 888$bioo888r6rrr7rB) rrNrvrrOrurr$r:)r]rw file_pathsjoined_path_segmentsrI path_segments r7 joinpathszFakeFilesystem.joinpathss98%888 z??a  8O   D646 C C!%%jm44& > >L**<88 >(4~$$'50DR0H0Q0QRU0V0V5(//444>(// ===z!}b11667KLLLr6cdSr`r5rs r7rzFakeFilesystem._path_components r6cdSr`r5rs r7rzFakeFilesystem._path_componentsrr6c\|r|||krgS||\}}|||}|s|sJ|ds(t|dkr |dsg}n |dd}|r|d||S)a6Breaks the path into a list of component names. Does not include the root directory as a component, as all paths are considered relative to the root directory for the FakeFilesystem. Callers should basically follow this pattern: .. code:: python file_path = self.absnormpath(file_path) path_components = self._path_components(file_path) current_dir = self.root for component in path_components: if component not in current_dir.entries: raise OSError _do_stuff_with_component(current_dir, component) current_dir = current_dir.get_entry(component) Args: path: Path to tokenize. Returns: The list of names split from path. rrN)rrr8rinsert)r]rFrrs r7rzFakeFilesystem._path_componentss0 tt66t<<<<Iood++ t**T%<%>Q  9QqS>#9#9#;#;  !A#RW@W@W! tw$!11)<<<4!!! 55!us(A?? B  B c6t||jj}||}||pU|j o8||p||Sr`)r$rqrtr2rrOrrFr]rrPs r7rOz%FakeFilesystem._starts_with_root_path s#Ity~>> ,,Y77   + + 8))@!!,,Y__->->?? 8,,Y77  r6cX|r|jr|jr||}|dd|krvt|dks|dd|krU|jD]+}t ||}||r|cS,t ||j}||ddz}|S)zIn windows, if a path starts with a single separator, it points to the root dir of the current mount point, usually a drive - replace it with that mount point path to get the real path. rrrN)rNrrrrrVr$rrv)r]rFrIrrs r7rJz#FakeFilesystem.replace_windows_roots  .D& .4= .))$//CAaCyCSYY!^^tAaCyC7G7G!%!2$$I /i @ @Iy11$# $.dD4FGG "T!""X- r6clt||jj}||kp||Sr`)r$rqrtis_mount_pointrs r7 _is_root_pathzFakeFilesystem._is_root_path*s3#Ity~>> I%G)<)->-@-@@@ttur6ct|trdSt|}|sdS||}||}|||fvo-||p|duo||S)z>Return True if ``file_path`` ends with a valid path separator.FN)rrr"rrru)r]rFrrIrGs r7rz'FakeFilesystem.ends_with_path_separatorBs dC  5$T**  5%%i0011)<<f -   s # # XvT'9'Xi>P>PQW>X>X r6c||sdS|||SNF)risfile!_path_without_trailing_separatorsrs r7!is_filepath_ending_with_separatorz0FakeFilesystem.is_filepath_ending_with_separatorOs=,,T22 5{{4AA$GGHHHr6rrcttsdSjvrjfS|jsfdjD}|r|dSdS)NNNcg|];}|k,|j|f.\sM   <<>>Y__%6%666*623666r6r)rrrrO)r]rrmatching_contents `` r7rz!FakeFilesystem._directory_contentTs)]33 :  ) ) )i/ :: :% +     '/       +'**zr6 check_linkcZ|r||rdSt||}|t|sdS||jjkr|j ptjdkS | |rdS| |}n#t$rYdSwxYw| |rdS| |}|j}|D]E}||t|d}|dSt!t"|}FdS)aHReturn true if a path points to an existing file system object. Args: file_path: The path to examine. check_link: If True, links are not followed Returns: (bool) True if the corresponding object exists. Raises: TypeError: if file_path is None. TNF)rZrbr)islinkr#r"rrWrtrNrJ version_infor resolve_pathrrrrqrrr)r]rrrFrrrrs r7existszFakeFilesystem.existsfs`  $++i00 4..y99:: <O 5 4=% % %))GS-=-G G 55d;; u$$T**DD   55    d # # 4%)%:%:4%@%@i ( 9 9I// Yy=Q=QRRSTUI uu}i88KKts2B B B-,B-rc|rAt|tr,||jSt |}|t d|r||s |tj || | |}| |}||r|S|t||jjkr|S||}||}||}| |S)aFollow a path, resolving symlinks. ResolvePath traverses the filesystem along the specified file path, resolving file names and symbolic links until all elements of the path are exhausted, or we reach a file which does not exist. If all the elements are not consumed, they just get appended to the path resolved so far. This gives us the path which is as resolved as it can be, even if the file does not exist. This behavior mimics Unix semantics, and is best shown by example. Given a file system that looks like this: /a/b/ /a/b/c -> /a/b2 c is a symlink to /a/b2 /a/b2/x /a/c -> ../d /a/x -> y Then: /a/b/x => /a/b/x /a/c => /a/d /a/x => /a/y /a/b/c/d/e => /a/b2/d/e Args: file_path: The path to examine. allow_fd: If `True`, `file_path` may be open file descriptor. Returns: The resolved_path (str or byte). Raises: TypeError: if `file_path` is `None`. OSError: if `file_path` is '' or a part of the path doesn't exist. Nz/Expected file system path string, received None)rrr*rrFr"r_valid_relative_pathrrrrrrJrr$rWrtr_resolve_components_components_to_path)r]rrrFrresolved_componentss r7rzFakeFilesystem.resolve_pathsXL  C 9c22 C%%i00;;==B B ** <MNN N 4444T:: 4    d 3 3 3 3 3D 9 9::((..   d # # K ?4);<< < <K//55"66GG''(;<<((...r6c|r||dn|j}||}||s||z}|SNr)rr;r:rO)r]component_foldersrIrFs r7rz"FakeFilesystem._components_to_pathsh! %D # #$5a$8 9 9 9$ xx)****400 :D r6 componentscH|j}d}d|D}g}|r|d}|||||d}|||nt |jr}|tkr3|tj | || ||}| |} | |z}g}|j}|dz }ntt|}||S)Nrc,g|]}t|Sr5r)rcomps r7rz6FakeFilesystem._resolve_components..sBBBt9T??BBBr6r)rqr9rrrEr r_MAX_LINK_DEPTHrrELOOPr _follow_linkrrr) r]rr link_depthrrrr link_pathtarget_componentss r7rz"FakeFilesystem._resolve_componentssQi  BBzBBB)+! ='++A..I  & &y 1 1 1// YGGJI $**?;;;*++ =//'' 001DEE!--.A9MM %)$9$9)$D$D!"3o"E&(#"i a "=)<< C! =D#"r6c|jrdSt||jdz}|rQ||vrM|d||}|||sdS|r||vMdS)NTr6F)rNr$r;rfindrr)r]r slash_dotdots r7rz#FakeFilesystem._valid_relative_paths   4&y$2E2LMM  LI55!"AIOOL$A$A"ABI;;t// ::;; u LI55tr6link_path_componentslinkcd|j}||jr|dr |dd}||}||s4|dd}||||}||Std)a9Follow a link w.r.t. a path resolved so far. The component is either a real file, which is a no-op, or a symlink. In the case of a symlink, we have to modify the path as built up so far /a/b => ../c should yield /a/../c (which will normalize to /a/c) /a/b => x should yield /a/x /a/b => /x/y/z should yield /x/y/z The modified path may land us in a new spot which is itself a link, so we may repeat the process. Args: link_path_components: The resolved path built up to the link so far. link: The link object itself. Returns: (string) The updated path resolved after following the link. Raises: OSError: if there are too many levels of symbolic link Nz\\?\r7z Invalid link) contentsrNrrrOrr:rr)r]rrrrIrs r7rzFakeFilesystem._follow_links.M  ! *i&:&:9&E&E *%abbM )))44C..y99 1 2#2#6 !!),,,HHZ00 ==++ +(((r6rrct|}|t||jjkr|jS|t||jjkr|jS||}||}|j} |D]}t|jr4|j r-tt| |j }t|jsG|js |t j||t j|||}t)s?|r=|r;|||s%|t j|j n0#t0$r#|t j|YnwxYw|S)aSearch for the specified filesystem object within the fake filesystem. Args: file_path: Specifies target FakeFile object to retrieve, with a path that has already been normalized/resolved. check_read_perm: If True, raises OSError if a parent directory does not have read permission check_owner: If True, and check_read_perm is also True, only checks read permission if the current user id is different from the file object user id Returns: The FakeFile object corresponding to file_path. Raises: OSError: if the object is not found. )r"r$rqrtrWrrr rrrrrr rNrrrrrr _can_readEACCESrFKeyError)r]rrrrFrrrs r7rz'FakeFilesystem.get_object_from_normpath6s0 ** ?488 8 89  ?4);<< < <= ""4((//55 4, C C 6>**TT!%mT\\&/5R5R!S!Sv~..<-A++EM4@@@'' d;;;)))44 C'CC!NN6;?? C '' fkBBB C  4 4 4    d 3 3 3 3 3 4 s D F*GGc|jtjkr|s |jdzrdS|jt kr |jdzrdS|jdzS)NTr)r)st_uidrget_uidrst_gidget_gid)rowner_can_reads r7rzFakeFilesystem._can_readlsd =GO-- - - %!7 t =GII % %~% t~%%r6ct|}|||}|||S)aSearch for the specified filesystem object within the fake filesystem. Args: file_path: Specifies the target FakeFile object to retrieve. check_read_perm: If True, raises OSError if a parent directory does not have read permission Returns: The FakeFile object corresponding to `file_path`. Raises: OSError: if the object is not found. )r"rrr)r]rrrFs r7rzFakeFilesystem.get_objectvsH ** 3 3D 9 9::,,T?CCCr6c t|tr8|r'||St d|r+||||||S||S)a-Search for the specified filesystem object, resolving all links. Args: file_path: Specifies the target FakeFile object to retrieve. follow_symlinks: If `False`, the link itself is resolved, otherwise the object linked to. allow_fd: If `True`, `file_path` may be an open file descriptor check_read_perm: If True, raises OSError if a parent directory does not have read permission check_owner: If True, and check_read_perm is also True, only checks read permission if the current user id is different from the file object user id Returns: The FakeFile object corresponding to `file_path`. Raises: OSError: if the object is not found. z4path should be string, bytes or os.PathLike, not int)rrr*rrrrlresolve)r]rrrrrs r7rzFakeFilesystem.resolves6 i % % W B)))44??AAAUVV V  00!!)X66  }}Y'''r6ct|}|sttj||t ||jjkr|jS||}|t |dkrt ||j}| |}| |\}}|st ||j} | |}|sJt|ts\|js5t|tr |tj||tj||jt&jzs |tj||r"|t/|n|S#t0$rYnwxYwttj|)aSearch for the specified object, resolving only parent links. This is analogous to the stat/lstat difference. This resolves links *to* the object but not of the final object itself. Args: path: Specifies target FakeFile object to retrieve. Returns: The FakeFile object corresponding to path. Raises: OSError: if the object is not found. r5)r"rrrr$rqrtrrlrrXrrrrNFakeFilerrrr PERM_READrrr#r)r]rFr;parent_directory child_name parent_objs r7rzFakeFilesystem.lresolves$D)) 2%,11 1 x@@ @ @9 99(CC x55 5 5&x::H&&x00'+~~h'?'?$* C.xBB  &677J  :j-88 <)AjX.N.NA'' x@@@##EL(;;;%(99 D##EL2BCCC $$Yz%:%:;;;      D elH---sC#F88 GGc&|s|j}nqtt||}t |js5|jr tjn tj }| ||| |dS)a:Add a fake file or directory into the filesystem at file_path. Args: file_path: The path to the file to be added relative to self. file_object: File or directory to add. Raises: OSError: if file_path does not correspond to a directory. N) rrrrrr rrNrrrrr)r]rrtarget_directoryerrors r7 add_objectzFakeFilesystem.add_objects 6#}  #M4<< 3J3JKK +344 6(,(:M  ##E9555"";/////r6 old_file_path new_file_path force_replacect|}t|}||}||}||}||ds!|t j|d|r||||}|j s| |||||dr| |||||}|dS|}| |\} } | |\} } || s |t j| | | } | | }| j|jkr |t j|t!|js3||j r t jn t j|||r |t j||| | || dS)aRenames a FakeFile object at old_file_path to new_file_path, preserving all properties. Args: old_file_path: Path to filesystem object to rename. new_file_path: Path to where the filesystem object will live after this call. force_replace: If set and destination is an existing file, it will be replaced even under Windows if the user has permissions, otherwise replacement happens under Unix only. Raises: OSError: if old_file_path does not exist. OSError: if new_file_path is an existing directory (Windows, or Posix if old_file_path points to a regular file) OSError: if old_file_path is a directory and new_file_path a file OSError: if new_file_path is an existing file and force_replace not set (Windows only). OSError: if new_file_path is an existing file and could not be removed (Posix, or Windows with force_replace set). OSError: if dirname(new_file_path) does not exist. OSError: if the file would be moved to another filesystem (e.g. mount point). TrrN)r"rrrrrr%_handle_broken_link_with_trailing_seprrN_handle_posix_dir_link_errors_rename_to_existing_pathrXrrEXDEVr rrrhas_parent_objectr _do_rename)r]rrrold_pathnew_path ends_with_sep old_object renamed_pathold_dirold_namernew_nameold_dir_objectnew_dir_objects r7renamezFakeFilesystem.renamesV<$M22#M2255h?? ##H--##H--{{8{55 ;    h : : :  A  6 6x @ @ @]]8,, ! R  . .x= Q Q Q ;;xD; 1 1 (88x:}L#' NN844 NN844{{7## 7    g 6 6 6g..g..  N$9 9 9    X 6 6 6~-..     $ 2E  x     + +J 7 7 8    h 7 7 7 .(KKKKKr6c||}||d||_||}||jvr||nd} |r||||dS#t $r>|r||jvr||||_||wxYw)NF) recursive)r remove_entryrt_normalized_entrynamerrr)r]rrrrobject_to_rename old_entrys r7rzFakeFilesystem._do_rename=s)33H==##H#>>> (!77AA>111  $ $X . . .   6++H555  $ $%5 6 6 6 6 6    4X^-CCC((333$,  !  $ $%5 6 6 6   s *,BAC c||r_||sL|jr tjn|jr tjn tj}|||dSdSdSr`) rrrarrrNrrr)r]rFrs r7rz4FakeFilesystem._handle_broken_link_with_trailing_sepTs ;;t   1;;t$$ 1}'ELL)' ##E400000 1 1 1 1r6rc||dr5||r |tj|||drP||r;|r |jrdS|r tjn tj}||||rD||r1||kr-|js(|tj|dSdSdSdSdSNFr)isdirrrrrraEISDIRrN)r]rrrrs r7rz,FakeFilesystem._handle_posix_dir_link_errorsas8 ::mU: ; ; > A A  >    } = = = ::mU: ; ; 6 A A  6  %2DEMM E   } 5 5 5  > M** >..&/    } = = = = =  > > > >/...r6rc||}||krMt|js7|r5|jr tjn tj}|||dS||kr|||St|jst|jr| |||||nt|jr6|jr tj n tj}|||n?|jr#|s!|tj |n| ||Sr`) rr rrNrrrr_rename_same_objectr $_handle_rename_error_for_dir_or_linkr remove_object)r]rrrrr new_objectrs r7rz'FakeFilesystem._rename_to_existing_pathwsf__]33 M ) ):-.. := :(,(:M  ##E=9994  # #++M=II I :% & & .'*2D*E*E .  5 5     Z' ( ( .$($6IELLEME   } 5 5 5 5   .  .    m < < < <   } - - -r6rc|jrC|r!|tj|n |tj|t |jsz|jr=t |jr |r|js |tj |t|jr$|tj |dSdSdSr`) rNrrrrr rrra ENOTEMPTYr r)r]rrrrrs r7rz3FakeFilesystem._handle_rename_error_for_dir_or_links   A A##EL-@@@@##EL-@@@z)** A! H 233H(H =H ''GGGz)** A##EL-@@@@@ A A A Ar6c||k}|s> ||}||}||}||krz||k||kkrH||d}tj||jkp|j }n*||k}|rA| |\}} | ||| }n#t$rYnwxYw|sdS|Sr) rrrrrErFbasenamertrarXr}r) r]rr do_rename real_old_pathoriginal_old_path real_new_path real_objectparent file_names r7rz"FakeFilesystem._rename_same_objects"''))]-@-@-B-BB    $ 1 1- @ @ $($7$7 $F$F! $ 1 1- @ @  $555!]2#))++}/B/B/D/DD;F;F#',,}e,"T"TK((77;;KK-#},I !. 3 3 5 59L9L9N9N NI)-}(E(E%FI$(NN++F33Y%%M       4sD,E E)(E)c|||}||r |tj| ||\}}||d}||dS#t$r$|tj |YdSt$r$|tj |YdSwxYw)anRemove an existing file or directory. Args: file_path: The path to the file relative to self. Raises: OSError: if file_path does not correspond to an existing file, or if part of the path refers to something other than a directory. OSError: if the directory is in use (eg, if it is '/'). FrN) rrrrrEBUSYrXrrrrAttributeErrorr)r]rdirnamerrs r7rzFakeFilesystem.remove_objects $$T%8%8%C%CDD   i ( ( 8    Y 7 7 7 : $y 9 9 GX#||GU|KK   ) )( 3 3 3 3 3 9 9 9    i 8 8 8 8 8 8 : : :    y 9 9 9 9 9 9 :sAB%%*C?)C?>C?ct|}t|tj}||}|||Sr`)r"r$rErIrr0)r]rFr;os_sepfake_seps r7r"zFakeFilesystem.make_string_pathsI#D)) 2622**844111r6 perm_bitsc||}||}||||dr)||jvr |t j|||}|j }g}d|DD]}| |t|d}|sWt||} | | |jr||j kr|j}|| | }t#|jr'|jsJ||j}|sJt+t|}|jt,zt,kr%|t j|j|D]} t,|z| _|S)aCreate `directory_path`, and all the parent directories. Helper method to set up your test faster. Args: directory_path: The full directory path to create. perm_bits: The permission bits as set by `chmod`. Returns: The newly created FakeDirectory object. Raises: OSError: if the directory already exists. Trc,g|]}t|Sr5rrs r7rz-FakeFilesystem.create_dir.. rr6rr|)r"rrnrrVrrrrrqrr#rrrNrrrr rrrrrrrF) r]rr rrrrrrrs r7 create_dirzFakeFilesystem.create_dirs"((88##H-- ((222 ;;xD; 1 1 8hdFW6W6W    h 7 7 7//99i @@@@@ I II// Yy=Q=QRRSTUI I' dCCC(((%0+*B*B"&-K%%g...% 9,--%$---- $ Y-? @ @I$$$9"=)<< $w.'99'' {7GHHH  2 2G% 1GOOr6rBrrrLcreate_missing_dirs apply_umaskencodingerrors side_effectc >||||||||||  S)aGCreate `file_path`, including all the parent directories along the way. This helper method can be used to set up tests more easily. Args: file_path: The path to the file to create. st_mode: The stat constant representing the file type. contents: the contents of the file. If not given and st_size is None, an empty file is assumed. st_size: file size; only valid if contents not given. If given, the file is considered to be in "large file mode" and trying to read from or write to the file will result in an exception. create_missing_dirs: If `True`, auto create missing directories. apply_umask: `True` if the current umask must be applied on `st_mode`. encoding: If `contents` is a unicode string, the encoding used for serialization. errors: The error mode used for encoding/decoding errors. side_effect: function handle that is executed when file is written, must accept the file object as an argument. Returns: The newly created FakeFile object. Raises: OSError: if the file already exists. OSError: if the containing directory is required and missing. )r)create_file_internally) r]rrrrLrrrrrs r7 create_filezFakeFilesystem.create_file%s=R**        #+   r6 source_path read_only target_pathc4|p|}t|}tj|}||d}|j||r|xjdzc_||_||j |j |j |S)aDCreate `file_path`, including all the parent directories along the way, for an existing real file. The contents of the real file are read only on demand. Args: source_path: Path to an existing file in the real file system read_only: If `True` (the default), writing to the fake file raises an exception. Otherwise, writing to the file changes the fake file only. target_path: If given, the path of the target direction, otherwise it is equal to `source_path`. Returns: the newly created FakeFile object. Raises: OSError: if the file does not exist in the real file system. OSError: if the file already exists in the fake file system. .. note:: On most systems, accessing the fake file's contents may update both the real and fake files' `atime` (access time). In this particular case, `add_real_file()` violates the rule that `pyfakefs` must not modify the real file system. T)read_from_real_fsi$) r"rErrrset_from_stat_resultrrrsizertr)r]rrrsource_path_str real_statrs r7 add_real_filezFakeFilesystem.add_real_fileZs<"0[ *;77GO,, // t/TT  229===  *    )  -  y~y~y?OPPPr6ct|}||}tj|s?tj|s |tj|tj |}|r| ||S| ||S)a]Create a symlink at source_path (or target_path, if given). It will point to the same path as the symlink on the real filesystem. Relative symlinks will point relative to their new location. Absolute symlinks will point to the same, absolute path as on the real filesystem. Args: source_path: The path to the existing symlink. target_path: If given, the name of the symlink in the fake filesystem, otherwise, the same as `source_path`. Returns: the newly created FakeFile object. Raises: OSError: if the directory does not exist in the real file system. OSError: if the symlink could not be created (see :py:meth:`create_file`). OSError: if the directory already exists in the fake file system. ) r"rrErFrrrrrreadlinkcreate_symlink)r]rrrrs r7add_real_symlinkzFakeFilesystem.add_real_symlinks,+;77@@QQw~~o.. ?rw~~o7V7V ?    o > > >_--  @&&{F;; ;&&?? ?r6 lazy_readc ,t|}||}tj|s |t j|t|p|}|||rtj |d}||r| |}n| |}t||||} | | nz| |} tj|D]O\} } } tj| jtj| |} tj| D]v}tj| |}tj|sB||tj| |w| D]w}tj| |}tj|rB|||tj| |xQ| S)a;Create a fake directory corresponding to the real directory at the specified path. Add entries in the fake directory corresponding to the entries in the real directory. Symlinks are supported. Args: source_path: The path to the existing directory. read_only: If set, all files under the directory are treated as read-only, e.g. a write access raises an exception; otherwise, writing to the files changes the fake files only as usually. lazy_read: If set (default), directory contents are only read when accessed, and only until the needed subdirectory level. .. note:: This means that the file system size is only updated at the time the directory contents are read; set this to `False` only if you are dependent on accurate file system size in your test target_path: If given, the target directory, otherwise, the target directory is the same as `source_path`. Returns: the newly created FakeDirectory object. Raises: OSError: if the directory does not exist in the real file system. OSError: if the directory already exists in the fake file system. r)r"rrErFrrrrrnr8rrFakeDirectoryFromRealDirectoryrwalkr:relpathlistdirrr%r!)r]rrr&rrtarget_path_str parent_pathrrbase_filesnew_base fileEntry abs_fileEntryrFs r7add_real_directoryz!FakeFilesystem.add_real_directorysYD+;77@@QQw~~o.. ?    o > > >*;+I/JJ ((999  '--88;K{{;'' :!__[99 !__[99 4y/G   ) ) ) )ooo66G"$'/":":  a7<<LGOOD/::"$D!1!1I$&GLLy$A$AM7>>-88! ))%rw||Hi'H'H"'I7<<i88Dw~~d++! &&ih )J)J r6 path_list lazy_dir_readc|D]O}tj|r||||9|||PdS)aThis convenience method adds multiple files and/or directories from the real file system to the fake file system. See `add_real_file()` and `add_real_directory()`. Args: path_list: List of file and directory paths in the real file system. read_only: If set, all files and files under under the directories are treated as read-only, e.g. a write access raises an exception; otherwise, writing to the files changes the fake files only as usually. lazy_dir_read: Uses lazy reading of directory contents if set (see `add_real_directory`) Raises: OSError: if any of the files and directories in the list does not exist in the real file system. OSError: if any of the files and directories in the list already exists in the fake file system. N)rErFrr4r!)r]r5rr6rFs r7add_real_pathszFakeFilesystem.add_real_pathssg4 4 4Dw}}T"" 4''iGGGG""43333  4 4r6rc ||} || } t|std|| dr |t j| || \} } | st| |j } | | || sK|s |t j | t| | | j} n|| } |r ||jz}| r t#t%| || }nt'| ||||| }|| |||d}| sW||S |||n||n$#t.$r|| wxYw|S)aInternal fake file creator that supports both normal fake files and fake files based on real files. Args: file_path: path to the file to create. st_mode: the stat.S_IF constant representing the file type. contents: the contents of the file. If not given and st_size is None, an empty file is assumed. st_size: file size; only valid if contents not given. If given, the file is considered to be in "large file mode" and trying to read from or write to the file will result in an exception. create_missing_dirs: if True, auto create missing directories. apply_umask: whether or not the current umask must be applied on st_mode. encoding: if contents is a unicode string, the encoding used for serialization. errors: the error mode used for encoding/decoding errors read_from_real_fs: if True, the contents are read from the real file system on demand. side_effect: function handle that is executed when file is written, must accept the file object as an argument. z;st_mode must be of int type - did you mean to set contents?Tr)r}r)r}rrrNrB)r"rr!rrrrrrXr$rlrnrrrFrrQFakeFileFromRealFiler#rrset_large_file_sizeset_initial_contentsrr)r]rrrrLrrrrrrrFrnew_filers r7rz%FakeFilesystem.create_file_internally sQF$$Y//%%7## M  ;;t; - - 4    d 3 3 3%)^^D%9%9"( ?.tTX>>  (()9:::{{+,, E& D##EL2BCCC.doo&677<     $223CDD   #  { "G  .$DkKK#!' K (+666 ?x/H  h&:g>Q &33G<<<<44X>>>   ""4((( s -G!G/ link_targetc||}||}||}||r7||r |t j|||r(|js |t j|n|jr |t j ||| |ds |t j||j r-||dr| |n |t j|| |s||}||t t"jz||S)aCreate the specified symlink, pointed at the specified link target. Args: file_path: path to the symlink to create link_target: the target of the symlink create_missing_dirs: If `True`, any missing parent directories of file_path will be created Returns: The newly created FakeFile object. Raises: OSError: if the symlink could not be created (see :py:meth:`create_file`). Tr)rrr)r"rrrrrrrNrrrrarrrrr rr)r]rr>rrlink_target_paths r7r$zFakeFilesystem.create_symlinkl s*)))44 00==MM),,  ( ( 3 3 H{{9%% =##EL)<<<{{+,, H)A'' i@@@%H'' 6FGGG{{::9EE##H'' 6FGGG=H{{9{>>6**9555'' 6FGGG{{9%% 5)))44I** g..% 3 +   r6rrc.t|}t|}||}||dr |tj|||\}} |st||j}||s8|r| |n |tj || |r5|j r tj n tj} || ||j s5| |r |tj | |||} n0#t $r#|tj |YnwxYw| jt$zr3||j r tjn tj|| | _||| | S)aCreate a hard link at new_path, pointing at old_path. Args: old_path: An existing link to the target file. new_path: The destination path to create a new link at. follow_symlinks: If False and old_path is a symlink, link the symlink instead of the object it points to. create_missing_dirs: If `True`, any missing parent directories of file_path will be created Returns: The FakeFile object referred to by old_path. Raises: OSError: if something already exists at new_path. OSError: if old_path is a directory. OSError: if the parent directory doesn't exist. Trr)r"rrrrrrXr$rlrrrrNrrrrrrrEPERMrtr) r]rrrr old_path_str new_path_strnew_path_normalizednew_parent_directory new_basenamerold_files r7 create_linkzFakeFilesystem.create_link s2(11 '11 "..|<< ;;*t; < < <    l ; ; ;-1^^ ||||jzdS#t"$r} | jtjkr|r(t'||tsS|jr&| jtjkrtj| _|| j| jYd} ~ dSYd} ~ dSd} ~ wwxYw)azCreate a leaf Fake directory and create any non-existent parent dirs. Args: dir_name: (str) Name of directory to create. mode: (int) Mode to create directory (and any necessary parent directories) with. This argument defaults to 0o777. The umask is applied to this mode. exist_ok: (boolean) If exist_ok is False (the default), an OSError is raised if the target directory already exists. Raises: OSError: if the directory already exists and exist_ok=False, or as per :py:meth:`create_dir`. rBTrrN)rrrrrrarrr#rrrhasattrrrrrrQrrrrrNrr) r]rMrrVr dir_name_strrrres r7makedirszFakeFilesystem.makedirse s$ 2    b 1 1 155h?? ##H--  )  ) H 66 )KK))  )   x ( ( ( ** // ==m ( R RIK33 RK$777"=+2Ei2PQQ  9 OOHddj[&8 9 9 9 9 9 9 9 9w%,&& 9:dll8.D.Dm#T#T 9%+!'U]*B*B#lAG##AGQZ888888888 9 9 9 9 9 9  9sD$$ G .B GG st_flagc|tt|} ||||}|r1|||| t |j|kSn#t $rYdSwxYwdS)a Helper function to implement isdir(), islink(), etc. See the stat(2) man page for valid stat.S_I* flag values Args: path: Path to file to stat and test st_flag: The stat.S_I* flag checked for the file's st_mode check_read_perm: If True (default) False is returned for existing but unreadable file paths. Returns: (boolean) `True` if the st_flag is set in path's st_mode. Raises: TypeError: if path is None Nr)rF)rr"rrr rr)r]rFr\rrrobjs r7 _is_of_typezFakeFilesystem._is_of_type s. <O$T**  ,,?OC 6==s3F>ck**g55  6    55 usA A&& A43A4c:||t|S)aDetermine if path identifies a directory. Args: path: Path to filesystem object. Returns: `True` if path points to a directory (following symlinks). Raises: TypeError: if path is None. )r_rr]rFrs r7rzFakeFilesystem.isdir sg???r6c>||t|dS)aDetermine if path identifies a regular file. Args: path: Path to filesystem object. Returns: `True` if path points to a regular file (following symlinks). Raises: TypeError: if path is None. Fr)r_rras r7rzFakeFilesystem.isfile s"gPUVVVr6c<||tdS)aDetermine if path identifies a symbolic link. Args: path: Path to filesystem object. Returns: `True` if path points to a symlink (S_IFLNK set in st_mode) Raises: TypeError: if path is None. Fr)r_r rs r7rzFakeFilesystem.islink sguEEEr6)rZ cdS)z)Returns False. Junctions are never faked.Fr5rs r7 isjunctionzFakeFilesystem.isjunction s5r6rctt|||}|jtzs!|t j|d|S)aTest that the target is actually a directory, raising OSError if not. Args: target_directory: Path to the target directory within the fake filesystem. check_owner: If True, only checks read permission if the current user id is different from the file object user id Returns: The FakeDirectory object corresponding to target_directory. Raises: OSError: if the target is not a directory. ri )rrrrrrrr)r]rrrs r7 confirmdirzFakeFilesystem.confirmdir s^$  LL){L C C   7* F    /? E E Er6cjt|}||}||r||||r9||d}t |jtkr| |}t |jtkrJ|j r tj }n |jr tj}n tj}||||||rJ|j r tj }n |jr tj}n tj}|||n|||||dS)aRemove the FakeFile object at the specified file path. Args: path: Path to file to be removed. Raises: OSError: if path points to a directory. OSError: if path does not exist. OSError: if removal failed. FrN)r"rrrrrr rrrr rNrrrarBrrrurrrr)r]rF norm_pathr^rKrs r7removezFakeFilesystem.remove s%T** $$Y//  ( ( . . B  6 6y A A A ;;y ! ! I,,y%,@@Cck""g--==33(*++w66)- % - %  % ''y999==!8!8!>!>??:). % . %  % ''y999==dCHHH 9%%%%%r6 allow_symlinkcV|t|dkr5|jr tjn tj}|||||}||}||dr|jsB| |r-|rdS|r|j s |tj || |d}|j r |tj|||dSdS)aRemove a leaf Fake directory. Args: target_directory: (str) Name of directory to remove. allow_symlink: (bool) if `target_directory` is a symlink, the function just returns, otherwise it raises (Posix only) Raises: OSError: if target_directory does not exist. OSError: if target_directory does not point to a directory. OSError: if removal failed per FakeFilesystem.RemoveObject. Cannot remove '.'. r5TrhN)r$rNrrrrrrrirrarrrrr)r]rrmrr dir_objects r7rmdirzFakeFilesystem.rmdir7 sB /?EE E E'+'9Ku||u|H   *: ; ; ;556FGG ++,<== ??+? > > 1% I$++6F*G*G I F$IDMI'' 7GHHH&6DIIJ! G##EO5EFFF   / 0 0 0 0 0 1 1r6c||d}||}t|j}|jrt j||S)aReturn a list of file names in target_directory. Args: target_directory: Path to the target directory within the fake filesystem. Returns: A list of file names within the target directory in arbitrary order. If `shuffle_listdir_results` is set, the order is not the same in subsequent calls to avoid tests relying on any ordering. Raises: OSError: if the target is not a directory. Tr )rrilistrkeysr\randomshuffle)r]rrdirectory_contentss r7r+zFakeFilesystem.listdirV so ,,-=,MMOO$455 !)"3"8"8":":;;  ' / N- . . .!!r6c*t|jSr`)r'rrrbs r7__str__zFakeFilesystem.__str__l s4=!!!r6c|ttj|ttj|ttjdSr`)r StandardStreamWrapperrJstdinstdoutstderrrbs r7rz$FakeFilesystem._add_standard_streamso se 1#)<<=== 1#*==>>> 1#*==>>>>>r6cjtj}||s||tjdkrc|dsP|d|dtt|j d<dSdSdS)Nr8z/tmprr) tempfile gettempdirrrrJrKr$rrrVr)r]temp_dirs r7rzFakeFilesystem._create_temp_dirt s&(({{8$$ & OOH % % % <7 " "4;;v+>+> "    1 1 1CDDd'..0011 2 2; ? ? ? # " " "r6)NT)r?Nrrr`)T)TF)F)TFTF)TN)TTN)TT)r.r/r0r1rErFrIr'rrrboolr^propertyrcrNsetterrarlrrrrvr+rXrrrrrr&rrrrrrrrr%rrnrrprrrrrrrrrrrr staticmethodr rr r$r*r.r2rrrrrXrrmrvr}rrrrdrFrOrJrrrrr rrrrrrrrrrrrrrrrrrrrrr"rrrr PERM_DEF_FILErrr!r%r4r8rr$rIrrMr#rTrr[r_rrrrJrrfrirlrpr+rxrrr5r6r7r:r:s(!gk$( % ?-?-?-SM?- ?-  ?-  ?-?-?-?-B<$<<<X<#t###X#'4'D'''' $X_'d't'''_' SX Z00000Z0-XsX F   X Y # #4 # # #Y #++ +D++++&666$    '''' 66666 )-"& 1119%13- 1  1111.:v:&::::FF8F;KFFFFVFVtVVVV%) 3'3'3'SM3' 3'  3'3'3'3'jg-08D>&T&,-,,,,2CHTN RR8F#3RuS#s]?SRRRR2///HV4D/PT////455,25""""4"&v"&%*?"&"&"&"&H6+f6+6+6+6+p%*%*F%*%*%*%*NMM6MMMM8 S T#Y   X  U tE{   X %V%V %%%%N&T2  4    F&HvH$HHHH4(  U3<-@  T     IfIIIII &36 x}hw// 0$&&&T&d&&&&P:/:/f:/:/:/:/:/:/x   '#d6l'#tCy'#'#'#'#Rf,)c,)',)c,),),),)b!%! 4444 4  4444l&&\&DDGDdDhDDDD,!% $! &(&(&(&( &(  &(  &( &(&(&(&(P/.W/././././.b0F00T00000$ ELELELEL EL  ELELELELN. 1& 1T 1 1 1 1>#>4:>KO> >>>>,         &     DAAA A  A  A AAAA0"#"4:" & """"H:v:$::::.2W222229@8H11%1251 1111l!66 !%$(!"& $*.3 3 3 3  3 # 3 " 3 3 3-3  3 h'3  3 3 3 3 p)- ))))g& )  ))))XFJ @ @" @19'1B @  @ @ @ @J)- JJJJ J g& J  JJJJ^" 44<44 4  4444F!66 !%$(!"& $"'*.WWWW W # W " WW3-W W Wh'W WWWWz%) 7 7 7 7 " 7  7 7 7 7 z!%$( @@@@ @ " @  @@@@L!%            4(t%!W%!%!%!%!%!N6=5E. . . s. $. . . . `f -4,""4<"""","""""???? D D D D Dr6r:r?cFddl}ddl}||jSr)doctestrtestmodfake_filesystem)rrs r7 _run_doctestr s)NNNOOO ??83 4 44r6cp|dkr tjS|dkr tjStd|d)NUSER_IDGROUP_IDz No attribute r5)rrrr)rts r7 __getattr__r sC y z 2222 3 33r6__main__)Vr1rrrErtrJr collectionsrrrrenumrrrrr r r r r typingrrrrrrrrrrrrrrrrrrpyfakefs.fake_filerr pyfakefs.helpersr!r"r#r$r%r&rKrrr+rrr:rr(FakeFileWrapperrzFakeDirWrapperFakePipeWrapperrg FakeOsModule FakeFileOpen FakeIoModuleFakeFcntlModulerYrrset_uidrset_gid reset_idsrrPERM_EXErrrr:rrr.r5r6r7rsCCH ////////                          POOOOOOOOOOOOOOO66666666<7##OOOT  %  5' !*!I+!7)+)# % # <7-O   / / / / /          %  N+DN+DN+DN+DN+DN+DN+DN+DbV5k5555444 zLNNNNNr6