定期删除文件的 Python 脚本

定期手动清理文件系统并非上策,自动化才是王道!

不难想象,手动删除文件和文件夹并非令人愉悦的工作。 显然,将这些任务自动化是更明智的选择。

Python 的出现,让我们的生活变得轻松许多。 作为一种卓越的脚本语言,Python 可以帮助我们毫无障碍地完成任务。 在深入了解之前,让我们先来探讨一下为什么 Python 是如此理想的选择。

  • Python 是一种在自动化任务领域备受欢迎的编程语言。
  • 相较于其他编程语言,Python 编写的代码更为简洁。
  • Python 具有出色的跨平台兼容性,可以在 Windows、Linux 和 Mac 等多种操作系统中运行相同的代码。
  • Python 拥有一个名为 `os` 的模块,它能够协助我们与操作系统进行交互。 我们将利用此模块来实现文件删除的自动化。

我们可以借助 Python 来替代任何繁琐或重复的系统任务。 如果您对 Python 有所了解,编写脚本来执行特定的系统任务将变得轻而易举。 让我们来看一些具体的应用场景。

温馨提示:以下代码在 Python 3.6+ 版本中进行了测试。

删除早于 X 天的文件或文件夹

通常,我们不再需要旧的日志文件,并且需要定期清理它们以释放存储空间。 这项操作不仅限于日志文件,也适用于其他类型的文件。

在 `os` 模块中,有一个名为 `stat` 的方法,它可以提供关于上次访问 (st_atime)、修改 (st_mtime) 和元数据修改 (st_ctime) 时间的详细信息。 所有这些方法都会返回自纪元开始以来以秒为单位的时间。 您可以在这里找到有关纪元的更多信息。

我们将使用 `os.walk(path)` 方法来遍历文件夹的子文件夹。

按照以下步骤编写代码,根据天数来删除文件或文件夹。

  • 导入 `time`、`os` 和 `shutil` 模块。
  • 设置路径和天数的变量。
  • 使用 `time.time()` 方法将天数转换为秒。
  • 使用 `os.path.exists(path)` 模块检查路径是否存在。
  • 如果路径存在,获取路径中包含的文件和文件夹列表,包括子文件夹。 使用 `os.walk(path)` 方法,它会返回一个包含文件夹、文件和子文件夹的生成器。
  • 通过使用 `os.path.join()` 方法连接当前路径和文件或文件夹名称,获取文件或文件夹的路径。
  • 使用 `os.stat(path)` 方法获取 `st_ctime` 属性,即创建时间。
  • 将 `ctime` 与之前计算的时间进行比较。
  • 如果结果大于用户所需的天数,则检查它是文件还是文件夹。 如果是文件,则使用 `os.remove(path)` 方法删除;否则使用 `shutil.rmtree()` 方法删除文件夹。
  • 如果路径不存在,则打印未找到的消息。

接下来,让我们详细分析一下代码。

# 导入所需模块
import os
import shutil
import time

# 主函数
def main():

    # 初始化计数器
    deleted_folders_count = 0
    deleted_files_count = 0

    # 指定路径
    path = "/要删除的路径"

    # 指定天数
    days = 30

    # 将天数转换为秒
    # time.time() 返回当前时间的秒数
    seconds = time.time() - (days * 24 * 60 * 60)

    # 检查文件是否存在于路径中
    if os.path.exists(path):

        # 遍历路径中的每个文件夹和文件
        for root_folder, folders, files in os.walk(path):

            # 比较时间
            if seconds >= get_file_or_folder_age(root_folder):

                # 删除文件夹
                remove_folder(root_folder)
                deleted_folders_count += 1 # 计数器加一

                # 删除根文件夹后跳出循环
                break

            else:

                # 检查根文件夹中的文件夹
                for folder in folders:

                    # 文件夹路径
                    folder_path = os.path.join(root_folder, folder)

                    # 与时间比较
                    if seconds >= get_file_or_folder_age(folder_path):

                        # 调用 remove_folder 函数
                        remove_folder(folder_path)
                        deleted_folders_count += 1 # 计数器加一

                # 检查当前目录中的文件
                for file in files:

                    # 文件路径
                    file_path = os.path.join(root_folder, file)

                    # 与时间比较
                    if seconds >= get_file_or_folder_age(file_path):

                        # 调用 remove_file 函数
                        remove_file(file_path)
                        deleted_files_count += 1 # 计数器加一
    else:
            # 如果路径不是目录
            # 与时间比较
            if seconds >= get_file_or_folder_age(path):
                # 调用文件删除函数
                remove_file(path)
                deleted_files_count += 1 # 计数器加一
    else:
		# 文件/文件夹未找到
        print(f'"{path}" 未找到')
        deleted_files_count += 1 # 计数器加一

    print(f"总共删除的文件夹数:{deleted_folders_count}")
    print(f"总共删除的文件数:{deleted_files_count}")

def remove_folder(path):

	# 删除文件夹
	if not shutil.rmtree(path):

		# 成功消息
		print(f"{path} 已成功删除")

	else:

		# 失败消息
		print(f"无法删除 {path}")


def remove_file(path):

	# 删除文件
	if not os.remove(path):

		# 成功消息
		print(f"{path} 已成功删除")

	else:

		# 失败消息
		print(f"无法删除 {path}")


def get_file_or_folder_age(path):

	# 获取文件/文件夹的创建时间
	# 时间单位为秒
	ctime = os.stat(path).st_ctime

	# 返回时间
	return ctime


if __name__ == '__main__':
	main()

您需要根据实际需求调整上述代码中的以下两个变量。

days = 30 
path = "/要删除的路径"

删除大于 X GB 的文件

接下来,我们来搜索大于指定大小的文件并删除它们。 这与之前的脚本类似,只不过之前的脚本以“年龄”为参数,现在以“大小”为参数进行删除。

# 导入 os 模块
import os

# 返回文件大小的函数
def get_file_size(path):
	# 获取文件大小,单位为字节
	size = os.path.getsize(path)

	# 返回文件大小
	return size


# 删除文件的函数
def remove_file(path):

	# 删除文件
	if not os.remove(path):

		# 成功
		print(f"{path} 已成功删除")

	else:

		# 错误
		print(f"无法删除 {path}")

def main():
	# 指定路径
	path = "在此处输入路径"

	# 设置文件最大大小,单位为 MB
	size = 500

	# 检查路径是否存在
	if os.path.exists(path):

		# 将大小转换为字节
		size = size * 1024 * 1024

		# 遍历子文件夹
		for root_folder, folders, files in os.walk(path):

			# 遍历文件列表
			for file in files:
				
				# 获取文件路径
				file_path = os.path.join(root_folder, file)

				# 检查文件大小
				if get_file_size(file_path) >= size:
					# 调用 remove_file 函数
					remove_file(file_path)
        
		else:
            # 如果路径是文件
            if os.path.isfile(path):
                # 路径不是目录
                # 直接检查文件
                if get_file_size(path) >= size:
                    # 调用 remove_file 函数
                    remove_file(path)

	else:
		# 路径不存在
		print(f"{path} 不存在")

if __name__ == '__main__':
	main()

请调整以下两个变量。

path = "在此处输入路径"
size = 500

删除具有特定扩展名的文件

有时,您可能希望根据扩展名类型来删除文件,例如 `.log` 文件。 我们可以使用 `os.path.splitext(path)` 方法来找到文件的扩展名。 该方法会返回一个包含文件路径和扩展名的元组。

# 导入 os 模块
import os

# 主函数
def main():
    
    # 指定路径
    path = "要查找的路径"
    
    # 指定扩展名
    extension = ".log"
    
    # 检查路径是否存在
    if os.path.exists(path):
        
        # 检查路径是否为目录
        if os.path.isdir(path):
        
            # 遍历子文件夹
            for root_folder, folders, files in os.walk(path):
                
                # 检查文件
                for file in files:

                    # 文件路径
                    file_path = os.path.join(root_folder, file)

                    # 从文件名中提取扩展名
                    file_extension = os.path.splitext(file_path)[1]

                    # 检查文件扩展名
                    if extension == file_extension:
                        
                        # 删除文件
                        if not os.remove(file_path):
                            
                            # 成功消息
                            print(f"{file_path} 已成功删除")
                            
                        else:
                            
                            # 失败消息
                            print(f"无法删除 {file_path}")
        
        else:
            
            # 路径不是目录
            print(f"{path} 不是目录")
    
    else:
        
        # 路径不存在
        print(f"{path} 不存在")

if __name__ == '__main__':
    # 调用主函数
    main()

请务必更新上述代码中的路径和扩展名变量,以满足您的实际需求。

我建议您在非生产环境中测试这些脚本。 一旦您对结果感到满意,您就可以通过 cron(如果使用 Linux)来安排定期运行这些脚本,以执行维护任务。 Python 非常适合实现这些功能。 如果您有兴趣学习更多相关知识,请查看这个 Udemy 课程

喜欢这篇文章吗? 何不与大家分享呢?