def _get_approx_size(path: Path) -> int: count = 0 if not path.is_symlink() and path.is_file(): count += path.size() elif not path.is_symlink() and path.is_dir(): for subdir in path.iterdir(): count += _get_approx_size(subdir) return count
def _copy(source_path: Path, target_path: Path, overwrite: str, copy_permissions: bool, context: Optional[Path], callback: Optional[CopyCallback], already_written: int, size: int ) -> int: """Copy a file or directory from one path to another. See the documentation of copy() for the required behaviour. The context path is guaranteed to be a prefix of source_path, on \ the same file system. Args: source_path: The path to the source file. target_path: A path to copy it to. overwrite: Selects behaviour when the target exists. copy_permissions: Whether to copy permissions along. context: Root of the tree we are copying, or None. callback: A callback function to call. already_written: Starting count of bytes written. size: Approximate total size of data to copy. Returns: The approximate total number of bytes written. """ logging.debug('Copying {} to {}'.format(source_path, target_path)) target_path_exists = target_path.exists() or target_path.is_symlink() if source_path.is_symlink(): if _copy_symlink(source_path, target_path, overwrite, context): return already_written if source_path.is_file(): already_written = _copy_file(source_path, target_path, overwrite, copy_permissions, callback, already_written, size) elif source_path.is_dir(): already_written = _copy_dir(source_path, target_path, overwrite, copy_permissions, context, callback, already_written, size) elif source_path.exists() or source_path.is_symlink(): # We don't copy special entries or broken links logging.debug( 'Skipping special entry or broken link {}'.format(source_path)) else: raise FileNotFoundError(('Source path {} does not exist, cannot' ' copy').format(source_path)) return already_written