| 1 | """Utility functions for copying files and directory trees.
|
|---|
| 2 |
|
|---|
| 3 | XXX The functions here don't copy the resource fork or other metadata on Mac.
|
|---|
| 4 |
|
|---|
| 5 | """
|
|---|
| 6 |
|
|---|
| 7 | import os
|
|---|
| 8 | import sys
|
|---|
| 9 | import stat
|
|---|
| 10 | from os.path import abspath
|
|---|
| 11 |
|
|---|
| 12 | __all__ = ["copyfileobj","copyfile","copymode","copystat","copy","copy2",
|
|---|
| 13 | "copytree","move","rmtree","Error"]
|
|---|
| 14 |
|
|---|
| 15 | class Error(EnvironmentError):
|
|---|
| 16 | pass
|
|---|
| 17 |
|
|---|
| 18 | def copyfileobj(fsrc, fdst, length=16*1024):
|
|---|
| 19 | """copy data from file-like object fsrc to file-like object fdst"""
|
|---|
| 20 | while 1:
|
|---|
| 21 | buf = fsrc.read(length)
|
|---|
| 22 | if not buf:
|
|---|
| 23 | break
|
|---|
| 24 | fdst.write(buf)
|
|---|
| 25 |
|
|---|
| 26 | def _samefile(src, dst):
|
|---|
| 27 | # Macintosh, Unix.
|
|---|
| 28 | if hasattr(os.path,'samefile'):
|
|---|
| 29 | try:
|
|---|
| 30 | return os.path.samefile(src, dst)
|
|---|
| 31 | except OSError:
|
|---|
| 32 | return False
|
|---|
| 33 |
|
|---|
| 34 | # All other platforms: check for same pathname.
|
|---|
| 35 | return (os.path.normcase(os.path.abspath(src)) ==
|
|---|
| 36 | os.path.normcase(os.path.abspath(dst)))
|
|---|
| 37 |
|
|---|
| 38 | def copyfile(src, dst):
|
|---|
| 39 | """Copy data from src to dst"""
|
|---|
| 40 | if _samefile(src, dst):
|
|---|
| 41 | raise Error, "`%s` and `%s` are the same file" % (src, dst)
|
|---|
| 42 |
|
|---|
| 43 | fsrc = None
|
|---|
| 44 | fdst = None
|
|---|
| 45 | try:
|
|---|
| 46 | fsrc = open(src, 'rb')
|
|---|
| 47 | fdst = open(dst, 'wb')
|
|---|
| 48 | copyfileobj(fsrc, fdst)
|
|---|
| 49 | finally:
|
|---|
| 50 | if fdst:
|
|---|
| 51 | fdst.close()
|
|---|
| 52 | if fsrc:
|
|---|
| 53 | fsrc.close()
|
|---|
| 54 |
|
|---|
| 55 | def copymode(src, dst):
|
|---|
| 56 | """Copy mode bits from src to dst"""
|
|---|
| 57 | if hasattr(os, 'chmod'):
|
|---|
| 58 | st = os.stat(src)
|
|---|
| 59 | mode = stat.S_IMODE(st.st_mode)
|
|---|
| 60 | os.chmod(dst, mode)
|
|---|
|
|---|