博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
python:OS模块
阅读量:5058 次
发布时间:2019-06-12

本文共 41871 字,大约阅读时间需要 139 分钟。

1 r"""OS routines for NT or Posix depending on what system we're on.   2    3 This exports:   4   - all functions from posix or nt, e.g. unlink, stat, etc.   5   - os.path is either posixpath or ntpath   6   - os.name is either 'posix' or 'nt'   7   - os.curdir is a string representing the current directory (always '.')   8   - os.pardir is a string representing the parent directory (always '..')   9   - os.sep is the (or a most common) pathname separator ('/' or '\\')  10   - os.extsep is the extension separator (always '.')  11   - os.altsep is the alternate pathname separator (None or '/')  12   - os.pathsep is the component separator used in $PATH etc  13   - os.linesep is the line separator in text files ('\r' or '\n' or '\r\n')  14   - os.defpath is the default search path for executables  15   - os.devnull is the file path of the null device ('/dev/null', etc.)  16   17 Programs that import and use 'os' stand a better chance of being  18 portable between different platforms.  Of course, they must then  19 only use functions that are defined by all platforms (e.g., unlink  20 and opendir), and leave all pathname manipulation to os.path  21 (e.g., split and join).  22 """  23   24 #'  25 import abc  26 import sys, errno  27 import stat as st  28   29 _names = sys.builtin_module_names  30   31 # Note:  more names are added to __all__ later.  32 __all__ = ["altsep", "curdir", "pardir", "sep", "pathsep", "linesep",  33            "defpath", "name", "path", "devnull", "SEEK_SET", "SEEK_CUR",  34            "SEEK_END", "fsencode", "fsdecode", "get_exec_path", "fdopen",  35            "popen", "extsep"]  36   37 def _exists(name):  38     return name in globals()  39   40 def _get_exports_list(module):  41     try:  42         return list(module.__all__)  43     except AttributeError:  44         return [n for n in dir(module) if n[0] != '_']  45   46 # Any new dependencies of the os module and/or changes in path separator  47 # requires updating importlib as well.  48 if 'posix' in _names:  49     name = 'posix'  50     linesep = '\n'  51     from posix import *  52     try:  53         from posix import _exit  54         __all__.append('_exit')  55     except ImportError:  56         pass  57     import posixpath as path  58   59     try:  60         from posix import _have_functions  61     except ImportError:  62         pass  63   64     import posix  65     __all__.extend(_get_exports_list(posix))  66     del posix  67   68 elif 'nt' in _names:  69     name = 'nt'  70     linesep = '\r\n'  71     from nt import *  72     try:  73         from nt import _exit  74         __all__.append('_exit')  75     except ImportError:  76         pass  77     import ntpath as path  78   79     import nt  80     __all__.extend(_get_exports_list(nt))  81     del nt  82   83     try:  84         from nt import _have_functions  85     except ImportError:  86         pass  87   88 else:  89     raise ImportError('no os specific module found')  90   91 sys.modules['os.path'] = path  92 from os.path import (curdir, pardir, sep, pathsep, defpath, extsep, altsep,  93     devnull)  94   95 del _names  96   97   98 if _exists("_have_functions"):  99     _globals = globals() 100     def _add(str, fn): 101         if (fn in _globals) and (str in _have_functions): 102             _set.add(_globals[fn]) 103  104     _set = set() 105     _add("HAVE_FACCESSAT",  "access") 106     _add("HAVE_FCHMODAT",   "chmod") 107     _add("HAVE_FCHOWNAT",   "chown") 108     _add("HAVE_FSTATAT",    "stat") 109     _add("HAVE_FUTIMESAT",  "utime") 110     _add("HAVE_LINKAT",     "link") 111     _add("HAVE_MKDIRAT",    "mkdir") 112     _add("HAVE_MKFIFOAT",   "mkfifo") 113     _add("HAVE_MKNODAT",    "mknod") 114     _add("HAVE_OPENAT",     "open") 115     _add("HAVE_READLINKAT", "readlink") 116     _add("HAVE_RENAMEAT",   "rename") 117     _add("HAVE_SYMLINKAT",  "symlink") 118     _add("HAVE_UNLINKAT",   "unlink") 119     _add("HAVE_UNLINKAT",   "rmdir") 120     _add("HAVE_UTIMENSAT",  "utime") 121     supports_dir_fd = _set 122  123     _set = set() 124     _add("HAVE_FACCESSAT",  "access") 125     supports_effective_ids = _set 126  127     _set = set() 128     _add("HAVE_FCHDIR",     "chdir") 129     _add("HAVE_FCHMOD",     "chmod") 130     _add("HAVE_FCHOWN",     "chown") 131     _add("HAVE_FDOPENDIR",  "listdir") 132     _add("HAVE_FEXECVE",    "execve") 133     _set.add(stat) # fstat always works 134     _add("HAVE_FTRUNCATE",  "truncate") 135     _add("HAVE_FUTIMENS",   "utime") 136     _add("HAVE_FUTIMES",    "utime") 137     _add("HAVE_FPATHCONF",  "pathconf") 138     if _exists("statvfs") and _exists("fstatvfs"): # mac os x10.3 139         _add("HAVE_FSTATVFS", "statvfs") 140     supports_fd = _set 141  142     _set = set() 143     _add("HAVE_FACCESSAT",  "access") 144     # Some platforms don't support lchmod().  Often the function exists 145     # anyway, as a stub that always returns ENOSUP or perhaps EOPNOTSUPP. 146     # (No, I don't know why that's a good design.)  ./configure will detect 147     # this and reject it--so HAVE_LCHMOD still won't be defined on such 148     # platforms.  This is Very Helpful. 149     # 150     # However, sometimes platforms without a working lchmod() *do* have 151     # fchmodat().  (Examples: Linux kernel 3.2 with glibc 2.15, 152     # OpenIndiana 3.x.)  And fchmodat() has a flag that theoretically makes 153     # it behave like lchmod().  So in theory it would be a suitable 154     # replacement for lchmod().  But when lchmod() doesn't work, fchmodat()'s 155     # flag doesn't work *either*.  Sadly ./configure isn't sophisticated 156     # enough to detect this condition--it only determines whether or not 157     # fchmodat() minimally works. 158     # 159     # Therefore we simply ignore fchmodat() when deciding whether or not 160     # os.chmod supports follow_symlinks.  Just checking lchmod() is 161     # sufficient.  After all--if you have a working fchmodat(), your 162     # lchmod() almost certainly works too. 163     # 164     # _add("HAVE_FCHMODAT",   "chmod") 165     _add("HAVE_FCHOWNAT",   "chown") 166     _add("HAVE_FSTATAT",    "stat") 167     _add("HAVE_LCHFLAGS",   "chflags") 168     _add("HAVE_LCHMOD",     "chmod") 169     if _exists("lchown"): # mac os x10.3 170         _add("HAVE_LCHOWN", "chown") 171     _add("HAVE_LINKAT",     "link") 172     _add("HAVE_LUTIMES",    "utime") 173     _add("HAVE_LSTAT",      "stat") 174     _add("HAVE_FSTATAT",    "stat") 175     _add("HAVE_UTIMENSAT",  "utime") 176     _add("MS_WINDOWS",      "stat") 177     supports_follow_symlinks = _set 178  179     del _set 180     del _have_functions 181     del _globals 182     del _add 183  184  185 # Python uses fixed values for the SEEK_ constants; they are mapped 186 # to native constants if necessary in posixmodule.c 187 # Other possible SEEK values are directly imported from posixmodule.c 188 SEEK_SET = 0 189 SEEK_CUR = 1 190 SEEK_END = 2 191  192 # Super directory utilities. 193 # (Inspired by Eric Raymond; the doc strings are mostly his) 194  195 def makedirs(name, mode=0o777, exist_ok=False): 196     """makedirs(name [, mode=0o777][, exist_ok=False]) 197  198     Super-mkdir; create a leaf directory and all intermediate ones.  Works like 199     mkdir, except that any intermediate path segment (not just the rightmost) 200     will be created if it does not exist. If the target directory already 201     exists, raise an OSError if exist_ok is False. Otherwise no exception is 202     raised.  This is recursive. 203  204     """ 205     head, tail = path.split(name) 206     if not tail: 207         head, tail = path.split(head) 208     if head and tail and not path.exists(head): 209         try: 210             makedirs(head, mode, exist_ok) 211         except FileExistsError: 212             # Defeats race condition when another thread created the path 213             pass 214         cdir = curdir 215         if isinstance(tail, bytes): 216             cdir = bytes(curdir, 'ASCII') 217         if tail == cdir:           # xxx/newdir/. exists if xxx/newdir exists 218             return 219     try: 220         mkdir(name, mode) 221     except OSError: 222         # Cannot rely on checking for EEXIST, since the operating system 223         # could give priority to other errors like EACCES or EROFS 224         if not exist_ok or not path.isdir(name): 225             raise 226  227 def removedirs(name): 228     """removedirs(name) 229  230     Super-rmdir; remove a leaf directory and all empty intermediate 231     ones.  Works like rmdir except that, if the leaf directory is 232     successfully removed, directories corresponding to rightmost path 233     segments will be pruned away until either the whole path is 234     consumed or an error occurs.  Errors during this latter phase are 235     ignored -- they generally mean that a directory was not empty. 236  237     """ 238     rmdir(name) 239     head, tail = path.split(name) 240     if not tail: 241         head, tail = path.split(head) 242     while head and tail: 243         try: 244             rmdir(head) 245         except OSError: 246             break 247         head, tail = path.split(head) 248  249 def renames(old, new): 250     """renames(old, new) 251  252     Super-rename; create directories as necessary and delete any left 253     empty.  Works like rename, except creation of any intermediate 254     directories needed to make the new pathname good is attempted 255     first.  After the rename, directories corresponding to rightmost 256     path segments of the old name will be pruned until either the 257     whole path is consumed or a nonempty directory is found. 258  259     Note: this function can fail with the new directory structure made 260     if you lack permissions needed to unlink the leaf directory or 261     file. 262  263     """ 264     head, tail = path.split(new) 265     if head and tail and not path.exists(head): 266         makedirs(head) 267     rename(old, new) 268     head, tail = path.split(old) 269     if head and tail: 270         try: 271             removedirs(head) 272         except OSError: 273             pass 274  275 __all__.extend(["makedirs", "removedirs", "renames"]) 276  277 def walk(top, topdown=True, οnerrοr=None, followlinks=False): 278     """Directory tree generator. 279  280     For each directory in the directory tree rooted at top (including top 281     itself, but excluding '.' and '..'), yields a 3-tuple 282  283         dirpath, dirnames, filenames 284  285     dirpath is a string, the path to the directory.  dirnames is a list of 286     the names of the subdirectories in dirpath (excluding '.' and '..'). 287     filenames is a list of the names of the non-directory files in dirpath. 288     Note that the names in the lists are just names, with no path components. 289     To get a full path (which begins with top) to a file or directory in 290     dirpath, do os.path.join(dirpath, name). 291  292     If optional arg 'topdown' is true or not specified, the triple for a 293     directory is generated before the triples for any of its subdirectories 294     (directories are generated top down).  If topdown is false, the triple 295     for a directory is generated after the triples for all of its 296     subdirectories (directories are generated bottom up). 297  298     When topdown is true, the caller can modify the dirnames list in-place 299     (e.g., via del or slice assignment), and walk will only recurse into the 300     subdirectories whose names remain in dirnames; this can be used to prune the 301     search, or to impose a specific order of visiting.  Modifying dirnames when 302     topdown is false is ineffective, since the directories in dirnames have 303     already been generated by the time dirnames itself is generated. No matter 304     the value of topdown, the list of subdirectories is retrieved before the 305     tuples for the directory and its subdirectories are generated. 306  307     By default errors from the os.scandir() call are ignored.  If 308     optional arg 'onerror' is specified, it should be a function; it 309     will be called with one argument, an OSError instance.  It can 310     report the error to continue with the walk, or raise the exception 311     to abort the walk.  Note that the filename is available as the 312     filename attribute of the exception object. 313  314     By default, os.walk does not follow symbolic links to subdirectories on 315     systems that support them.  In order to get this functionality, set the 316     optional argument 'followlinks' to true. 317  318     Caution:  if you pass a relative pathname for top, don't change the 319     current working directory between resumptions of walk.  walk never 320     changes the current directory, and assumes that the client doesn't 321     either. 322  323     Example: 324  325     import os 326     from os.path import join, getsize 327     for root, dirs, files in os.walk('python/Lib/email'): 328         print(root, "consumes", end="") 329         print(sum([getsize(join(root, name)) for name in files]), end="") 330         print("bytes in", len(files), "non-directory files") 331         if 'CVS' in dirs: 332             dirs.remove('CVS')  # don't visit CVS directories 333  334     """ 335     top = fspath(top) 336     dirs = [] 337     nondirs = [] 338     walk_dirs = [] 339  340     # We may not have read permission for top, in which case we can't 341     # get a list of the files the directory contains.  os.walk 342     # always suppressed the exception then, rather than blow up for a 343     # minor reason when (say) a thousand readable directories are still 344     # left to visit.  That logic is copied here. 345     try: 346         # Note that scandir is global in this module due 347         # to earlier import-*. 348         scandir_it = scandir(top) 349     except OSError as error: 350         if onerror is not None: 351             onerror(error) 352         return 353  354     with scandir_it: 355         while True: 356             try: 357                 try: 358                     entry = next(scandir_it) 359                 except StopIteration: 360                     break 361             except OSError as error: 362                 if onerror is not None: 363                     onerror(error) 364                 return 365  366             try: 367                 is_dir = entry.is_dir() 368             except OSError: 369                 # If is_dir() raises an OSError, consider that the entry is not 370                 # a directory, same behaviour than os.path.isdir(). 371                 is_dir = False 372  373             if is_dir: 374                 dirs.append(entry.name) 375             else: 376                 nondirs.append(entry.name) 377  378             if not topdown and is_dir: 379                 # Bottom-up: recurse into sub-directory, but exclude symlinks to 380                 # directories if followlinks is False 381                 if followlinks: 382                     walk_into = True 383                 else: 384                     try: 385                         is_symlink = entry.is_symlink() 386                     except OSError: 387                         # If is_symlink() raises an OSError, consider that the 388                         # entry is not a symbolic link, same behaviour than 389                         # os.path.islink(). 390                         is_symlink = False 391                     walk_into = not is_symlink 392  393                 if walk_into: 394                     walk_dirs.append(entry.path) 395  396     # Yield before recursion if going top down 397     if topdown: 398         yield top, dirs, nondirs 399  400         # Recurse into sub-directories 401         islink, join = path.islink, path.join 402         for dirname in dirs: 403             new_path = join(top, dirname) 404             # Issue #23605: os.path.islink() is used instead of caching 405             # entry.is_symlink() result during the loop on os.scandir() because 406             # the caller can replace the directory entry during the "yield" 407             # above. 408             if followlinks or not islink(new_path): 409                 yield from walk(new_path, topdown, onerror, followlinks) 410     else: 411         # Recurse into sub-directories 412         for new_path in walk_dirs: 413             yield from walk(new_path, topdown, onerror, followlinks) 414         # Yield after recursion if going bottom up 415         yield top, dirs, nondirs 416  417 __all__.append("walk") 418  419 if {open, stat} <= supports_dir_fd and {listdir, stat} <= supports_fd: 420  421     def fwalk(top=".", topdown=True, οnerrοr=None, *, follow_symlinks=False, dir_fd=None): 422         """Directory tree generator. 423  424         This behaves exactly like walk(), except that it yields a 4-tuple 425  426             dirpath, dirnames, filenames, dirfd 427  428         `dirpath`, `dirnames` and `filenames` are identical to walk() output, 429         and `dirfd` is a file descriptor referring to the directory `dirpath`. 430  431         The advantage of fwalk() over walk() is that it's safe against symlink 432         races (when follow_symlinks is False). 433  434         If dir_fd is not None, it should be a file descriptor open to a directory, 435           and top should be relative; top will then be relative to that directory. 436           (dir_fd is always supported for fwalk.) 437  438         Caution: 439         Since fwalk() yields file descriptors, those are only valid until the 440         next iteration step, so you should dup() them if you want to keep them 441         for a longer period. 442  443         Example: 444  445         import os 446         for root, dirs, files, rootfd in os.fwalk('python/Lib/email'): 447             print(root, "consumes", end="") 448             print(sum([os.stat(name, dir_fd=rootfd).st_size for name in files]), 449                   end="") 450             print("bytes in", len(files), "non-directory files") 451             if 'CVS' in dirs: 452                 dirs.remove('CVS')  # don't visit CVS directories 453         """ 454         if not isinstance(top, int) or not hasattr(top, '__index__'): 455             top = fspath(top) 456         # Note: To guard against symlink races, we use the standard 457         # lstat()/open()/fstat() trick. 458         orig_st = stat(top, follow_symlinks=False, dir_fd=dir_fd) 459         topfd = open(top, O_RDONLY, dir_fd=dir_fd) 460         try: 461             if (follow_symlinks or (st.S_ISDIR(orig_st.st_mode) and 462                                     path.samestat(orig_st, stat(topfd)))): 463                 yield from _fwalk(topfd, top, topdown, onerror, follow_symlinks) 464         finally: 465             close(topfd) 466  467     def _fwalk(topfd, toppath, topdown, onerror, follow_symlinks): 468         # Note: This uses O(depth of the directory tree) file descriptors: if 469         # necessary, it can be adapted to only require O(1) FDs, see issue 470         # #13734. 471  472         names = listdir(topfd) 473         dirs, nondirs = [], [] 474         for name in names: 475             try: 476                 # Here, we don't use AT_SYMLINK_NOFOLLOW to be consistent with 477                 # walk() which reports symlinks to directories as directories. 478                 # We do however check for symlinks before recursing into 479                 # a subdirectory. 480                 if st.S_ISDIR(stat(name, dir_fd=topfd).st_mode): 481                     dirs.append(name) 482                 else: 483                     nondirs.append(name) 484             except OSError: 485                 try: 486                     # Add dangling symlinks, ignore disappeared files 487                     if st.S_ISLNK(stat(name, dir_fd=topfd, follow_symlinks=False) 488                                 .st_mode): 489                         nondirs.append(name) 490                 except OSError: 491                     continue 492  493         if topdown: 494             yield toppath, dirs, nondirs, topfd 495  496         for name in dirs: 497             try: 498                 orig_st = stat(name, dir_fd=topfd, follow_symlinks=follow_symlinks) 499                 dirfd = open(name, O_RDONLY, dir_fd=topfd) 500             except OSError as err: 501                 if onerror is not None: 502                     onerror(err) 503                 continue 504             try: 505                 if follow_symlinks or path.samestat(orig_st, stat(dirfd)): 506                     dirpath = path.join(toppath, name) 507                     yield from _fwalk(dirfd, dirpath, topdown, onerror, follow_symlinks) 508             finally: 509                 close(dirfd) 510  511         if not topdown: 512             yield toppath, dirs, nondirs, topfd 513  514     __all__.append("fwalk") 515  516 # Make sure os.environ exists, at least 517 try: 518     environ 519 except NameError: 520     environ = {} 521  522 def execl(file, *args): 523     """execl(file, *args) 524  525     Execute the executable file with argument list args, replacing the 526     current process. """ 527     execv(file, args) 528  529 def execle(file, *args): 530     """execle(file, *args, env) 531  532     Execute the executable file with argument list args and 533     environment env, replacing the current process. """ 534     env = args[-1] 535     execve(file, args[:-1], env) 536  537 def execlp(file, *args): 538     """execlp(file, *args) 539  540     Execute the executable file (which is searched for along $PATH) 541     with argument list args, replacing the current process. """ 542     execvp(file, args) 543  544 def execlpe(file, *args): 545     """execlpe(file, *args, env) 546  547     Execute the executable file (which is searched for along $PATH) 548     with argument list args and environment env, replacing the current 549     process. """ 550     env = args[-1] 551     execvpe(file, args[:-1], env) 552  553 def execvp(file, args): 554     """execvp(file, args) 555  556     Execute the executable file (which is searched for along $PATH) 557     with argument list args, replacing the current process. 558     args may be a list or tuple of strings. """ 559     _execvpe(file, args) 560  561 def execvpe(file, args, env): 562     """execvpe(file, args, env) 563  564     Execute the executable file (which is searched for along $PATH) 565     with argument list args and environment env , replacing the 566     current process. 567     args may be a list or tuple of strings. """ 568     _execvpe(file, args, env) 569  570 __all__.extend(["execl","execle","execlp","execlpe","execvp","execvpe"]) 571  572 def _execvpe(file, args, env=None): 573     if env is not None: 574         exec_func = execve 575         argrest = (args, env) 576     else: 577         exec_func = execv 578         argrest = (args,) 579         env = environ 580  581     head, tail = path.split(file) 582     if head: 583         exec_func(file, *argrest) 584         return 585     last_exc = saved_exc = None 586     saved_tb = None 587     path_list = get_exec_path(env) 588     if name != 'nt': 589         file = fsencode(file) 590         path_list = map(fsencode, path_list) 591     for dir in path_list: 592         fullname = path.join(dir, file) 593         try: 594             exec_func(fullname, *argrest) 595         except OSError as e: 596             last_exc = e 597             tb = sys.exc_info()[2] 598             if (e.errno != errno.ENOENT and e.errno != errno.ENOTDIR 599                 and saved_exc is None): 600                 saved_exc = e 601                 saved_tb = tb 602     if saved_exc: 603         raise saved_exc.with_traceback(saved_tb) 604     raise last_exc.with_traceback(tb) 605  606  607 def get_exec_path(env=None): 608     """Returns the sequence of directories that will be searched for the 609     named executable (similar to a shell) when launching a process. 610  611     *env* must be an environment variable dict or None.  If *env* is None, 612     os.environ will be used. 613     """ 614     # Use a local import instead of a global import to limit the number of 615     # modules loaded at startup: the os module is always loaded at startup by 616     # Python. It may also avoid a bootstrap issue. 617     import warnings 618  619     if env is None: 620         env = environ 621  622     # {b'PATH': ...}.get('PATH') and {'PATH': ...}.get(b'PATH') emit a 623     # BytesWarning when using python -b or python -bb: ignore the warning 624     with warnings.catch_warnings(): 625         warnings.simplefilter("ignore", BytesWarning) 626  627         try: 628             path_list = env.get('PATH') 629         except TypeError: 630             path_list = None 631  632         if supports_bytes_environ: 633             try: 634                 path_listb = env[b'PATH'] 635             except (KeyError, TypeError): 636                 pass 637             else: 638                 if path_list is not None: 639                     raise ValueError( 640                         "env cannot contain 'PATH' and b'PATH' keys") 641                 path_list = path_listb 642  643             if path_list is not None and isinstance(path_list, bytes): 644                 path_list = fsdecode(path_list) 645  646     if path_list is None: 647         path_list = defpath 648     return path_list.split(pathsep) 649  650  651 # Change environ to automatically call putenv(), unsetenv if they exist. 652 from _collections_abc import MutableMapping 653  654 class _Environ(MutableMapping): 655     def __init__(self, data, encodekey, decodekey, encodevalue, decodevalue, putenv, unsetenv): 656         self.encodekey = encodekey 657         self.decodekey = decodekey 658         self.encodevalue = encodevalue 659         self.decodevalue = decodevalue 660         self.putenv = putenv 661         self.unsetenv = unsetenv 662         self._data = data 663  664     def __getitem__(self, key): 665         try: 666             value = self._data[self.encodekey(key)] 667         except KeyError: 668             # raise KeyError with the original key value 669             raise KeyError(key) from None 670         return self.decodevalue(value) 671  672     def __setitem__(self, key, value): 673         key = self.encodekey(key) 674         value = self.encodevalue(value) 675         self.putenv(key, value) 676         self._data[key] = value 677  678     def __delitem__(self, key): 679         encodedkey = self.encodekey(key) 680         self.unsetenv(encodedkey) 681         try: 682             del self._data[encodedkey] 683         except KeyError: 684             # raise KeyError with the original key value 685             raise KeyError(key) from None 686  687     def __iter__(self): 688         # list() from dict object is an atomic operation 689         keys = list(self._data) 690         for key in keys: 691             yield self.decodekey(key) 692  693     def __len__(self): 694         return len(self._data) 695  696     def __repr__(self): 697         return 'environ({
{
{}}})'.format(', '.join( 698 ('{!r}: {!r}'.format(self.decodekey(key), self.decodevalue(value)) 699 for key, value in self._data.items()))) 700 701 def copy(self): 702 return dict(self) 703 704 def setdefault(self, key, value): 705 if key not in self: 706 self[key] = value 707 return self[key] 708 709 try: 710 _putenv = putenv 711 except NameError: 712 _putenv = lambda key, value: None 713 else: 714 if "putenv" not in __all__: 715 __all__.append("putenv") 716 717 try: 718 _unsetenv = unsetenv 719 except NameError: 720 _unsetenv = lambda key: _putenv(key, "") 721 else: 722 if "unsetenv" not in __all__: 723 __all__.append("unsetenv") 724 725 def _createenviron(): 726 if name == 'nt': 727 # Where Env Var Names Must Be UPPERCASE 728 def check_str(value): 729 if not isinstance(value, str): 730 raise TypeError("str expected, not %s" % type(value).__name__) 731 return value 732 encode = check_str 733 decode = str 734 def encodekey(key): 735 return encode(key).upper() 736 data = {} 737 for key, value in environ.items(): 738 data[encodekey(key)] = value 739 else: 740 # Where Env Var Names Can Be Mixed Case 741 encoding = sys.getfilesystemencoding() 742 def encode(value): 743 if not isinstance(value, str): 744 raise TypeError("str expected, not %s" % type(value).__name__) 745 return value.encode(encoding, 'surrogateescape') 746 def decode(value): 747 return value.decode(encoding, 'surrogateescape') 748 encodekey = encode 749 data = environ 750 return _Environ(data, 751 encodekey, decode, 752 encode, decode, 753 _putenv, _unsetenv) 754 755 # unicode environ 756 environ = _createenviron() 757 del _createenviron 758 759 760 def getenv(key, default=None): 761 """Get an environment variable, return None if it doesn't exist. 762 The optional second argument can specify an alternate default. 763 key, default and the result are str.""" 764 return environ.get(key, default) 765 766 supports_bytes_environ = (name != 'nt') 767 __all__.extend(("getenv", "supports_bytes_environ")) 768 769 if supports_bytes_environ: 770 def _check_bytes(value): 771 if not isinstance(value, bytes): 772 raise TypeError("bytes expected, not %s" % type(value).__name__) 773 return value 774 775 # bytes environ 776 environb = _Environ(environ._data, 777 _check_bytes, bytes, 778 _check_bytes, bytes, 779 _putenv, _unsetenv) 780 del _check_bytes 781 782 def getenvb(key, default=None): 783 """Get an environment variable, return None if it doesn't exist. 784 The optional second argument can specify an alternate default. 785 key, default and the result are bytes.""" 786 return environb.get(key, default) 787 788 __all__.extend(("environb", "getenvb")) 789 790 def _fscodec(): 791 encoding = sys.getfilesystemencoding() 792 errors = sys.getfilesystemencodeerrors() 793 794 def fsencode(filename): 795 """Encode filename (an os.PathLike, bytes, or str) to the filesystem 796 encoding with 'surrogateescape' error handler, return bytes unchanged. 797 On Windows, use 'strict' error handler if the file system encoding is 798 'mbcs' (which is the default encoding). 799 """ 800 filename = fspath(filename) # Does type-checking of `filename`. 801 if isinstance(filename, str): 802 return filename.encode(encoding, errors) 803 else: 804 return filename 805 806 def fsdecode(filename): 807 """Decode filename (an os.PathLike, bytes, or str) from the filesystem 808 encoding with 'surrogateescape' error handler, return str unchanged. On 809 Windows, use 'strict' error handler if the file system encoding is 810 'mbcs' (which is the default encoding). 811 """ 812 filename = fspath(filename) # Does type-checking of `filename`. 813 if isinstance(filename, bytes): 814 return filename.decode(encoding, errors) 815 else: 816 return filename 817 818 return fsencode, fsdecode 819 820 fsencode, fsdecode = _fscodec() 821 del _fscodec 822 823 # Supply spawn*() (probably only for Unix) 824 if _exists("fork") and not _exists("spawnv") and _exists("execv"): 825 826 P_WAIT = 0 827 P_NOWAIT = P_NOWAITO = 1 828 829 __all__.extend(["P_WAIT", "P_NOWAIT", "P_NOWAITO"]) 830 831 # XXX Should we support P_DETACH? I suppose it could fork()**2 832 # and close the std I/O streams. Also, P_OVERLAY is the same 833 # as execv*()? 834 835 def _spawnvef(mode, file, args, env, func): 836 # Internal helper; func is the exec*() function to use 837 if not isinstance(args, (tuple, list)): 838 raise TypeError('argv must be a tuple or a list') 839 if not args or not args[0]: 840 raise ValueError('argv first element cannot be empty') 841 pid = fork() 842 if not pid: 843 # Child 844 try: 845 if env is None: 846 func(file, args) 847 else: 848 func(file, args, env) 849 except: 850 _exit(127) 851 else: 852 # Parent 853 if mode == P_NOWAIT: 854 return pid # Caller is responsible for waiting! 855 while 1: 856 wpid, sts = waitpid(pid, 0) 857 if WIFSTOPPED(sts): 858 continue 859 elif WIFSIGNALED(sts): 860 return -WTERMSIG(sts) 861 elif WIFEXITED(sts): 862 return WEXITSTATUS(sts) 863 else: 864 raise OSError("Not stopped, signaled or exited???") 865 866 def spawnv(mode, file, args): 867 """spawnv(mode, file, args) -> integer 868 869 Execute file with arguments from args in a subprocess. 870 If mode == P_NOWAIT return the pid of the process. 871 If mode == P_WAIT return the process's exit code if it exits normally; 872 otherwise return -SIG, where SIG is the signal that killed it. """ 873 return _spawnvef(mode, file, args, None, execv) 874 875 def spawnve(mode, file, args, env): 876 """spawnve(mode, file, args, env) -> integer 877 878 Execute file with arguments from args in a subprocess with the 879 specified environment. 880 If mode == P_NOWAIT return the pid of the process. 881 If mode == P_WAIT return the process's exit code if it exits normally; 882 otherwise return -SIG, where SIG is the signal that killed it. """ 883 return _spawnvef(mode, file, args, env, execve) 884 885 # Note: spawnvp[e] is't currently supported on Windows 886 887 def spawnvp(mode, file, args): 888 """spawnvp(mode, file, args) -> integer 889 890 Execute file (which is looked for along $PATH) with arguments from 891 args in a subprocess. 892 If mode == P_NOWAIT return the pid of the process. 893 If mode == P_WAIT return the process's exit code if it exits normally; 894 otherwise return -SIG, where SIG is the signal that killed it. """ 895 return _spawnvef(mode, file, args, None, execvp) 896 897 def spawnvpe(mode, file, args, env): 898 """spawnvpe(mode, file, args, env) -> integer 899 900 Execute file (which is looked for along $PATH) with arguments from 901 args in a subprocess with the supplied environment. 902 If mode == P_NOWAIT return the pid of the process. 903 If mode == P_WAIT return the process's exit code if it exits normally; 904 otherwise return -SIG, where SIG is the signal that killed it. """ 905 return _spawnvef(mode, file, args, env, execvpe) 906 907 908 __all__.extend(["spawnv", "spawnve", "spawnvp", "spawnvpe"]) 909 910 911 if _exists("spawnv"): 912 # These aren't supplied by the basic Windows code 913 # but can be easily implemented in Python 914 915 def spawnl(mode, file, *args): 916 """spawnl(mode, file, *args) -> integer 917 918 Execute file with arguments from args in a subprocess. 919 If mode == P_NOWAIT return the pid of the process. 920 If mode == P_WAIT return the process's exit code if it exits normally; 921 otherwise return -SIG, where SIG is the signal that killed it. """ 922 return spawnv(mode, file, args) 923 924 def spawnle(mode, file, *args): 925 """spawnle(mode, file, *args, env) -> integer 926 927 Execute file with arguments from args in a subprocess with the 928 supplied environment. 929 If mode == P_NOWAIT return the pid of the process. 930 If mode == P_WAIT return the process's exit code if it exits normally; 931 otherwise return -SIG, where SIG is the signal that killed it. """ 932 env = args[-1] 933 return spawnve(mode, file, args[:-1], env) 934 935 936 __all__.extend(["spawnl", "spawnle"]) 937 938 939 if _exists("spawnvp"): 940 # At the moment, Windows doesn't implement spawnvp[e], 941 # so it won't have spawnlp[e] either. 942 def spawnlp(mode, file, *args): 943 """spawnlp(mode, file, *args) -> integer 944 945 Execute file (which is looked for along $PATH) with arguments from 946 args in a subprocess with the supplied environment. 947 If mode == P_NOWAIT return the pid of the process. 948 If mode == P_WAIT return the process's exit code if it exits normally; 949 otherwise return -SIG, where SIG is the signal that killed it. """ 950 return spawnvp(mode, file, args) 951 952 def spawnlpe(mode, file, *args): 953 """spawnlpe(mode, file, *args, env) -> integer 954 955 Execute file (which is looked for along $PATH) with arguments from 956 args in a subprocess with the supplied environment. 957 If mode == P_NOWAIT return the pid of the process. 958 If mode == P_WAIT return the process's exit code if it exits normally; 959 otherwise return -SIG, where SIG is the signal that killed it. """ 960 env = args[-1] 961 return spawnvpe(mode, file, args[:-1], env) 962 963 964 __all__.extend(["spawnlp", "spawnlpe"]) 965 966 967 # Supply os.popen() 968 def popen(cmd, mode="r", buffering=-1): 969 if not isinstance(cmd, str): 970 raise TypeError("invalid cmd type (%s, expected string)" % type(cmd)) 971 if mode not in ("r", "w"): 972 raise ValueError("invalid mode %r" % mode) 973 if buffering == 0 or buffering is None: 974 raise ValueError("popen() does not support unbuffered streams") 975 import subprocess, io 976 if mode == "r": 977 proc = subprocess.Popen(cmd, 978 shell=True, 979 stdout=subprocess.PIPE, 980 bufsize=buffering) 981 return _wrap_close(io.TextIOWrapper(proc.stdout), proc) 982 else: 983 proc = subprocess.Popen(cmd, 984 shell=True, 985 stdin=subprocess.PIPE, 986 bufsize=buffering) 987 return _wrap_close(io.TextIOWrapper(proc.stdin), proc) 988 989 # Helper for popen() -- a proxy for a file whose close waits for the process 990 class _wrap_close: 991 def __init__(self, stream, proc): 992 self._stream = stream 993 self._proc = proc 994 def close(self): 995 self._stream.close() 996 returncode = self._proc.wait() 997 if returncode == 0: 998 return None 999 if name == 'nt':1000 return returncode1001 else:1002 return returncode << 8 # Shift left to match old behavior1003 def __enter__(self):1004 return self1005 def __exit__(self, *args):1006 self.close()1007 def __getattr__(self, name):1008 return getattr(self._stream, name)1009 def __iter__(self):1010 return iter(self._stream)1011 1012 # Supply os.fdopen()1013 def fdopen(fd, *args, **kwargs):1014 if not isinstance(fd, int):1015 raise TypeError("invalid fd type (%s, expected integer)" % type(fd))1016 import io1017 return io.open(fd, *args, **kwargs)1018 1019 1020 # For testing purposes, make sure the function is available when the C1021 # implementation exists.1022 def _fspath(path):1023 """Return the path representation of a path-like object.1024 1025 If str or bytes is passed in, it is returned unchanged. Otherwise the1026 os.PathLike interface is used to get the path representation. If the1027 path representation is not str or bytes, TypeError is raised. If the1028 provided path is not str, bytes, or os.PathLike, TypeError is raised.1029 """1030 if isinstance(path, (str, bytes)):1031 return path1032 1033 # Work from the object's type to match method resolution of other magic1034 # methods.1035 path_type = type(path)1036 try:1037 path_repr = path_type.__fspath__(path)1038 except AttributeError:1039 if hasattr(path_type, '__fspath__'):1040 raise1041 else:1042 raise TypeError("expected str, bytes or os.PathLike object, "1043 "not " + path_type.__name__)1044 if isinstance(path_repr, (str, bytes)):1045 return path_repr1046 else:1047 raise TypeError("expected {}.__fspath__() to return str or bytes, "1048 "not {}".format(path_type.__name__,1049 type(path_repr).__name__))1050 1051 # If there is no C implementation, make the pure Python version the1052 # implementation as transparently as possible.1053 if not _exists('fspath'):1054 fspath = _fspath1055 fspath.__name__ = "fspath"1056 1057 1058 class PathLike(abc.ABC):1059 1060 """Abstract base class for implementing the file system path protocol."""1061 1062 @abc.abstractmethod1063 def __fspath__(self):1064 """Return the file system path representation of the object."""1065 raise NotImplementedError1066 1067 @classmethod1068 def __subclasshook__(cls, subclass):1069 return hasattr(subclass, '__fspath__')
python:os

 

转载于:https://www.cnblogs.com/lmgsanm/p/8349451.html

你可能感兴趣的文章
64位内核开发第十讲,IRQL中断级别了解
查看>>
ASP.NET WebAPi(selfhost)之文件同步或异步上传
查看>>
列表的操作
查看>>
老徐杂谈:作为一个测试人员,思维比技术重要!
查看>>
如何配置 struts2 可以受理的请求的扩展名
查看>>
读Zepto源码之fx_methods模块
查看>>
elasticsearch Suggester实现搜索建议(八)
查看>>
全国电子设计竞赛集训记录
查看>>
kendo grid 点击更新没有反映
查看>>
读构建之法第四章第十七章有感
查看>>
C#中的IEnumerable<T>知识点
查看>>
android访问链接时候报java.net.MalformedURLException: Protocol not found
查看>>
拓扑排序/DP【洛谷P2883】 [USACO07MAR]牛交通Cow Traffic
查看>>
dwz ie10一直提示数据加载中
查看>>
Windows Phone开发(4):框架和页 转:http://blog.csdn.net/tcjiaan/article/details/7263146
查看>>
Windows Phone Marketplace 发布软件全攻略
查看>>
Unity3D研究院之打开Activity与调用JAVA代码传递参数(十八)【转】
查看>>
语义web基础知识学习
查看>>
hexo个人博客添加宠物/鼠标点击效果/博客管理
查看>>
python asyncio 异步实现mongodb数据转xls文件
查看>>