cornsnake.util_file
File operations including copying, reading, and writing text to files.
1""" 2File operations including copying, reading, and writing text to files. 3 4[Documentation](http://docs.mrseanryan.cornsnake.s3-website-eu-west-1.amazonaws.com/cornsnake/util_file.html) 5""" 6 7import os 8import shutil 9 10from . import util_os 11from . import util_pdf 12from . import util_text 13 14 15def backup_file_by_copying(path_to_file, backup_dir, backup_filename): 16 """ 17 Backup the given file by copying it to a new uniquely named file. 18 """ 19 path_to_backup = os.path.join(backup_dir, backup_filename) 20 path_to_backup = get_unique_filepath(path_to_backup) 21 copy_file(path_to_file, path_to_backup) 22 return path_to_backup 23 24 25def copy_file(from_path, to_path): 26 """ 27 Copy a file from one path to another. 28 29 Args: 30 from_path (str): The path of the file to copy. 31 to_path (str): The destination path to copy the file to. 32 """ 33 shutil.copyfile(from_path, to_path) 34 35 36def delete_file(path_to_file): 37 """ 38 Delete a file from the disk. 39 """ 40 os.remove(path_to_file) 41 42 43def get_unique_filepath(path_to_file): 44 """ 45 Get a unique new filepath, similar to the given path. 46 """ 47 filename_no_extension, extension = os.path.splitext(path_to_file) 48 49 suffix = 2 50 while os.path.exists(path_to_file): 51 path_to_file = f"{filename_no_extension}-{suffix:02}{extension}" 52 suffix += 1 53 return path_to_file 54 55 56def get_this_script_dir(this_file): 57 """ 58 Get the directory of the current script file. 59 60 Args: 61 this_file (str): The path of the current script file (__file__). 62 63 Returns: 64 str: The directory of the current script file. 65 """ 66 return os.path.dirname(os.path.realpath(this_file)) 67 68 69def is_file_under_dir(path_to_file, path_to_dir): 70 """ 71 Does that file exist under that directory or a sub-directory. 72 """ 73 path_to_file = os.path.normpath(path_to_file) 74 path_to_dir = os.path.normpath(path_to_dir) + os.sep 75 return path_to_file.startswith(path_to_dir) 76 77 78def _get_long_file_path(path_to_file): 79 """ 80 Get the long file path for Windows. 81 82 Args: 83 path_to_file (str): The original file path. 84 85 Returns: 86 str: The long file path for Windows. 87 """ 88 return "\\\\?\\" + path_to_file if util_os.is_windows() else path_to_file 89 90 91def is_empty_directory_only_subdirectories(path_to_file): 92 """ 93 Check if a directory is empty (only subdirectories are empty). 94 95 Args: 96 path_to_file (str): The path to the directory to check. 97 98 Returns: 99 bool: True if the directory is empty, False otherwise. 100 """ 101 if os.path.isfile(path_to_file): 102 return is_empty_file(path_to_file) 103 contents = os.listdir(path_to_file) 104 for content in contents: 105 path_to_sub = os.path.join(path_to_file, content) 106 if os.path.isfile(path_to_sub): 107 return is_empty_file(path_to_sub) 108 if not os.path.isfile(path_to_sub): 109 is_empty = is_empty_directory_only_subdirectories(path_to_sub) 110 if not is_empty: 111 return False 112 return True 113 114 115def is_empty_file(path_to_file): 116 """ 117 Check if a file is empty. 118 119 Args: 120 path_to_file (str): The path to the file to check. 121 122 Returns: 123 bool: True if the file is empty, False otherwise. 124 """ 125 if not os.path.isfile(path_to_file): 126 return False 127 if os.path.islink(path_to_file): 128 return False 129 fp_allow_long_path = _get_long_file_path(path_to_file) 130 size = os.path.getsize(fp_allow_long_path) 131 return size == 0 132 133 134def move_file(from_filepath, to_filepath): 135 """ 136 Recursively move a file or directory to another location. This is similar to the Unix "mv" command. Return the file or directory's destination. 137 138 If the destination is a directory or a symlink to a directory, the source is moved inside the directory. The destination path must not already exist. 139 """ 140 shutil.move(from_filepath, to_filepath) 141 142 143def read_lines_from_file(filepath, skip_comments=False): 144 """ 145 Read lines from a text file. 146 147 Args: 148 filepath (str): The path to the text file. 149 skip_comments (bool): Whether to skip lines starting with '#'. Default is False. 150 151 Returns: 152 list: A list of lines read from the file. 153 """ 154 lines = [] 155 with open(filepath, encoding="utf-8") as file: 156 lines = [line.strip() for line in file] 157 if skip_comments: 158 lines = _remove_comments(lines) 159 return lines 160 161 162def read_text_from_file(filepath): 163 """ 164 Read text from a text file. 165 166 Args: 167 filepath (str): The path to the text file. 168 169 Returns: 170 str: The text read from the file. 171 """ 172 with open(filepath, encoding="utf-8") as file: 173 return file.read() 174 175 176def _remove_comments(lines): 177 """ 178 Remove lines starting with '#' from a list of lines. 179 180 Args: 181 lines (list): List of lines to filter. 182 183 Returns: 184 list: Filtered list of lines without comments. 185 """ 186 filtered_lines = [] 187 for line in lines: 188 if not line.startswith("#"): 189 filtered_lines.append(line) 190 return filtered_lines 191 192 193def read_text_from_text_or_pdf_file_skipping_comments(filepath): 194 """ 195 Read text from a text or PDF file, skipping comments. 196 197 Args: 198 filepath (str): The path to the text or PDF file. 199 200 Returns: 201 str: The text read from the file without comments. 202 """ 203 if util_pdf.is_pdf(filepath): 204 return util_pdf.extract_text_from_pdf(filepath) 205 lines = read_lines_from_file(filepath) 206 filtered_lines = _remove_comments(lines) 207 return util_text.LINE_END.join(filtered_lines) 208 209 210def write_text_lines_to_file(lines, filepath): 211 """ 212 Write lines of text to a text file. 213 214 Args: 215 lines (list): List of lines to write to the file. 216 filepath (str): The path to the output text file. 217 """ 218 with open(filepath, encoding="utf-8", mode="w") as file: 219 for line in lines: 220 file.write(line + util_text.LINE_END) 221 222 223def write_array_to_file_skipping_empty(PATH_TO_OUTPUT_TEXT_FILE, lines): 224 """ 225 Write non-empty lines from an array to a file, skipping empty lines. 226 227 Args: 228 PATH_TO_OUTPUT_TEXT_FILE (str): The path to the output text file. 229 lines (list): List of lines to write to the file. 230 """ 231 with open(PATH_TO_OUTPUT_TEXT_FILE, "w") as f: 232 for line in lines: 233 if line is not None and len(line) > 0: 234 f.write(line + "\n") 235 236 237def write_text_to_file(text, filepath): 238 """ 239 Write text to a text file. 240 241 Args: 242 text (str): The text to write to the file. 243 filepath (str): The path to the output text file. 244 """ 245 with open(filepath, "w", encoding="utf-8") as f: 246 f.write(text) 247 248 249def get_last_part_of_path(file_path): 250 """ 251 Get the last part of a file path (filename). 252 253 Args: 254 file_path (str): The full file path. 255 256 Returns: 257 str: The last part of the file path (filename). 258 """ 259 return file_path.split(os.sep)[-1]
16def backup_file_by_copying(path_to_file, backup_dir, backup_filename): 17 """ 18 Backup the given file by copying it to a new uniquely named file. 19 """ 20 path_to_backup = os.path.join(backup_dir, backup_filename) 21 path_to_backup = get_unique_filepath(path_to_backup) 22 copy_file(path_to_file, path_to_backup) 23 return path_to_backup
Backup the given file by copying it to a new uniquely named file.
26def copy_file(from_path, to_path): 27 """ 28 Copy a file from one path to another. 29 30 Args: 31 from_path (str): The path of the file to copy. 32 to_path (str): The destination path to copy the file to. 33 """ 34 shutil.copyfile(from_path, to_path)
Copy a file from one path to another.
Args: from_path (str): The path of the file to copy. to_path (str): The destination path to copy the file to.
37def delete_file(path_to_file): 38 """ 39 Delete a file from the disk. 40 """ 41 os.remove(path_to_file)
Delete a file from the disk.
44def get_unique_filepath(path_to_file): 45 """ 46 Get a unique new filepath, similar to the given path. 47 """ 48 filename_no_extension, extension = os.path.splitext(path_to_file) 49 50 suffix = 2 51 while os.path.exists(path_to_file): 52 path_to_file = f"{filename_no_extension}-{suffix:02}{extension}" 53 suffix += 1 54 return path_to_file
Get a unique new filepath, similar to the given path.
57def get_this_script_dir(this_file): 58 """ 59 Get the directory of the current script file. 60 61 Args: 62 this_file (str): The path of the current script file (__file__). 63 64 Returns: 65 str: The directory of the current script file. 66 """ 67 return os.path.dirname(os.path.realpath(this_file))
Get the directory of the current script file.
Args: this_file (str): The path of the current script file (__file__).
Returns: str: The directory of the current script file.
70def is_file_under_dir(path_to_file, path_to_dir): 71 """ 72 Does that file exist under that directory or a sub-directory. 73 """ 74 path_to_file = os.path.normpath(path_to_file) 75 path_to_dir = os.path.normpath(path_to_dir) + os.sep 76 return path_to_file.startswith(path_to_dir)
Does that file exist under that directory or a sub-directory.
92def is_empty_directory_only_subdirectories(path_to_file): 93 """ 94 Check if a directory is empty (only subdirectories are empty). 95 96 Args: 97 path_to_file (str): The path to the directory to check. 98 99 Returns: 100 bool: True if the directory is empty, False otherwise. 101 """ 102 if os.path.isfile(path_to_file): 103 return is_empty_file(path_to_file) 104 contents = os.listdir(path_to_file) 105 for content in contents: 106 path_to_sub = os.path.join(path_to_file, content) 107 if os.path.isfile(path_to_sub): 108 return is_empty_file(path_to_sub) 109 if not os.path.isfile(path_to_sub): 110 is_empty = is_empty_directory_only_subdirectories(path_to_sub) 111 if not is_empty: 112 return False 113 return True
Check if a directory is empty (only subdirectories are empty).
Args: path_to_file (str): The path to the directory to check.
Returns: bool: True if the directory is empty, False otherwise.
116def is_empty_file(path_to_file): 117 """ 118 Check if a file is empty. 119 120 Args: 121 path_to_file (str): The path to the file to check. 122 123 Returns: 124 bool: True if the file is empty, False otherwise. 125 """ 126 if not os.path.isfile(path_to_file): 127 return False 128 if os.path.islink(path_to_file): 129 return False 130 fp_allow_long_path = _get_long_file_path(path_to_file) 131 size = os.path.getsize(fp_allow_long_path) 132 return size == 0
Check if a file is empty.
Args: path_to_file (str): The path to the file to check.
Returns: bool: True if the file is empty, False otherwise.
135def move_file(from_filepath, to_filepath): 136 """ 137 Recursively move a file or directory to another location. This is similar to the Unix "mv" command. Return the file or directory's destination. 138 139 If the destination is a directory or a symlink to a directory, the source is moved inside the directory. The destination path must not already exist. 140 """ 141 shutil.move(from_filepath, to_filepath)
Recursively move a file or directory to another location. This is similar to the Unix "mv" command. Return the file or directory's destination.
If the destination is a directory or a symlink to a directory, the source is moved inside the directory. The destination path must not already exist.
144def read_lines_from_file(filepath, skip_comments=False): 145 """ 146 Read lines from a text file. 147 148 Args: 149 filepath (str): The path to the text file. 150 skip_comments (bool): Whether to skip lines starting with '#'. Default is False. 151 152 Returns: 153 list: A list of lines read from the file. 154 """ 155 lines = [] 156 with open(filepath, encoding="utf-8") as file: 157 lines = [line.strip() for line in file] 158 if skip_comments: 159 lines = _remove_comments(lines) 160 return lines
Read lines from a text file.
Args: filepath (str): The path to the text file. skip_comments (bool): Whether to skip lines starting with '#'. Default is False.
Returns: list: A list of lines read from the file.
163def read_text_from_file(filepath): 164 """ 165 Read text from a text file. 166 167 Args: 168 filepath (str): The path to the text file. 169 170 Returns: 171 str: The text read from the file. 172 """ 173 with open(filepath, encoding="utf-8") as file: 174 return file.read()
Read text from a text file.
Args: filepath (str): The path to the text file.
Returns: str: The text read from the file.
194def read_text_from_text_or_pdf_file_skipping_comments(filepath): 195 """ 196 Read text from a text or PDF file, skipping comments. 197 198 Args: 199 filepath (str): The path to the text or PDF file. 200 201 Returns: 202 str: The text read from the file without comments. 203 """ 204 if util_pdf.is_pdf(filepath): 205 return util_pdf.extract_text_from_pdf(filepath) 206 lines = read_lines_from_file(filepath) 207 filtered_lines = _remove_comments(lines) 208 return util_text.LINE_END.join(filtered_lines)
Read text from a text or PDF file, skipping comments.
Args: filepath (str): The path to the text or PDF file.
Returns: str: The text read from the file without comments.
211def write_text_lines_to_file(lines, filepath): 212 """ 213 Write lines of text to a text file. 214 215 Args: 216 lines (list): List of lines to write to the file. 217 filepath (str): The path to the output text file. 218 """ 219 with open(filepath, encoding="utf-8", mode="w") as file: 220 for line in lines: 221 file.write(line + util_text.LINE_END)
Write lines of text to a text file.
Args: lines (list): List of lines to write to the file. filepath (str): The path to the output text file.
224def write_array_to_file_skipping_empty(PATH_TO_OUTPUT_TEXT_FILE, lines): 225 """ 226 Write non-empty lines from an array to a file, skipping empty lines. 227 228 Args: 229 PATH_TO_OUTPUT_TEXT_FILE (str): The path to the output text file. 230 lines (list): List of lines to write to the file. 231 """ 232 with open(PATH_TO_OUTPUT_TEXT_FILE, "w") as f: 233 for line in lines: 234 if line is not None and len(line) > 0: 235 f.write(line + "\n")
Write non-empty lines from an array to a file, skipping empty lines.
Args: PATH_TO_OUTPUT_TEXT_FILE (str): The path to the output text file. lines (list): List of lines to write to the file.
238def write_text_to_file(text, filepath): 239 """ 240 Write text to a text file. 241 242 Args: 243 text (str): The text to write to the file. 244 filepath (str): The path to the output text file. 245 """ 246 with open(filepath, "w", encoding="utf-8") as f: 247 f.write(text)
Write text to a text file.
Args: text (str): The text to write to the file. filepath (str): The path to the output text file.
250def get_last_part_of_path(file_path): 251 """ 252 Get the last part of a file path (filename). 253 254 Args: 255 file_path (str): The full file path. 256 257 Returns: 258 str: The last part of the file path (filename). 259 """ 260 return file_path.split(os.sep)[-1]
Get the last part of a file path (filename).
Args: file_path (str): The full file path.
Returns: str: The last part of the file path (filename).