【问题标题】:Delete Old directories in Python删除 Python 中的旧目录
【发布时间】:2011-01-15 07:49:04
【问题描述】:

我有几个目录,我希望删除超过 7 天的目录。我已经实现了代码,但它似乎没有工作。谁能看出我哪里出错了?

def delete_sandbox():

    for directories in os.listdir(os.getcwd()): 

        if not os.path.isdir(directories) or not os.stat(directories).st_ctime < time.time()-(7*24*3600): 
            continue
        os.chdir(directories)
        drop_sandbox()
        os.chdir(rootDir)
        os.system("sudo rm -rf "+directories)
        print 'Folders older than 7 days old dropped and removed'

感谢您的帮助

文件夹沙盒删除但不删除。我希望程序进入这些文件夹中的每一个,放下沙箱,回到根目录并删除所有旧目录。当我这样做时,文件夹仍然存在。

当我通过存储在文件夹名称中的字符串日期删除目录时,此功能也起作用。但现在我正在尝试获取它已停止工作的时间戳。

我已经测试了'rm -rf'+directories,它不会删除旧文件夹。当我尝试shutil.rmtree 时,我收到错误消息:

Traceback (most recent call last):
  File "yep.py", line 21, in <module>
    delete_sandbox()
  File "yep.py", line 18, in delete_sandbox
    shutil.rmtree(directories)
  File "/home/build/workspace/downloads/Python-2.6.4/Lib/shutil.py", line 208, in rmtree
    onerror(os.listdir, path, sys.exc_info())
  File "/home/build/workspace/downloads/Python-2.6.4/Lib/shutil.py", line 206, in rmtree
    names = os.listdir(path)
OSError: [Errno 2] No such file or directory: 'Debug'

还有其他方法可以删除这些文件夹吗?

我成功了,我使用了shutil.rmtree,一切似乎都奏效了。谢谢你的帮助。修改后的代码是:

def delete_sandbox():

    for directories in os.listdir(os.getcwd()): 

        if not os.path.isdir(directories) or not os.stat(directories).st_ctime < time.time()-(sbox_age): 
            continue
        os.chdir(directories)
        drop_sandbox()
        os.chdir(rootDir)
        shutil.rmtree(directories)
        print 'Sandboxes older than 7 days old dropped and removed'

delete_sandbox()

【问题讨论】:

  • 这是什么意思似乎没有工作?您收到任何错误消息吗?
  • 如果某些目录名称包含空格(在 os.system 调用中)或者如果入口处的当前目录不是rootDir,这将失败。您是否遇到错误,如果是,是什么以及在哪里?或意外的行为,如果是这样,是什么,在哪里?一些prints 会给我们更多信息(你目前给我们大约0位;-)。
  • 一般建议/警告,在向系统调用时,尤其是在涉及“rm”时。为您的函数提供一个默认为 True 的空运行选项,以打印它将运行的系统命令。

标签: python time directory timestamp


【解决方案1】:

os.listdir 返回一个字符串列表,它们是相对路径。当您 chdir 到 rootdir 时,取决于 rootDir 是什么,这些路径可能不再有效。

【讨论】:

    【解决方案2】:
    • drop_sandbox() 有什么作用? (你给我们的函数是delete_sandbox())也许你的意思是这是一个递归函数并且使用了错误的函数名
    • rootDir 是全局变量吗?也许你的意思是os.chdir("..")
    • rootDir 包含什么? os.listdir给出相对路径。如果rootDir 是您搜索的基础,那么您列出的目录可能不起作用。更糟糕的是:如果他们这样做了,您可能会删除您仍然想要的内容。

    此外,shutil 包还有一个您可能想要研究的rmtree函数。

    【讨论】:

      【解决方案3】:
      import os
      import time
      import shutil
      numdays = 86400*7
      now = time.time()
      directory=os.path.join("/home","path")
      for r,d,f in os.walk(directory):
          for dir in d:
               timestamp = os.path.getmtime(os.path.join(r,dir))
               if now-numdays > timestamp:
                   try:
                        print "removing ",os.path.join(r,dir)
                        # shutil.rmtree(os.path.join(r,dir))  #uncomment to use
                   except Exception,e:
                        print e
                        pass
                   else: 
                        print "some message for success"
      

      【讨论】:

        【解决方案4】:

        虽然公认答案的总体思路是合理的,但实现有几点不是。

        1. 变量名不按角色收费。
        2. 请不要覆盖 dir() 等 python 方法

        因为我需要更多功能,所以我采纳了你的想法并构建了这个:

        class CompRM(object):
            exception_list = []
            path = None
            comparator = None
            comparator_target = None
            comparator_delete_condition = None
        
            delete_directories = False
            delete_files = False
        
            def __init__(self, target_path, comparator, comparator_target='st_mtime', comparator_delete_condition='>', delete_directories=False, delete_files=False):
                self.path = target_path
                self.comparator = comparator
                self.comparator_target = comparator_target
                self.comparator_delete_condition = comparator_delete_condition
        
                for directory_path, directory_names, file_names in os.walk(self.path):
                    if delete_directories is True:
                        self.walk_names(directory_path, directory_names)
                    if delete_files is True:
                        self.walk_names(directory_path, file_names)
        
                if len(self.exception_list) > 0:
                    raise Exception({'message': 'Encountered exceptions while deleting.', 'debug': self.exception_list})
        
            def walk_names(self, directory_path, names):
                for _name in names:
                    _path = os.path.join(directory_path, _name)
                    _stat = os.stat(_path)
                    _value = getattr(_stat, self.comparator_target)
                    if self.delete_condition_met(_value):
                        self.safe_remove(_path)
        
            def delete_condition_met(self, value):
                if self.comparator > value and self.comparator_delete_condition is '>':
                    return True
                if self.comparator < value and self.comparator_delete_condition is '<':
                    return True
                return False
        
            def safe_remove(self, remove_path):
                print 'remove', remove_path
                shutil.rmtree(remove_path, onerror=self.register_exception)
        
            def register_exception(self, function, path, exception_info):
                self.exception_list.append({
                    function: function,
                    path: path,
                    exception_info: exception_info,
                })
        

        你可以这样称呼它:

        comprm = CompRM('/tmp', time.time() - 60*60*24*7, comparator_target='st_ctime', delete_files=True)
        

        comparator_target 是 os.stat() 中用于比较的属性名。

        问候, 贾斯图斯

        【讨论】:

        • exception_list = [] 在类级别是一个错误。该列表在实例之间共享。始终需要在__init__ 中设置可变属性以避免这种情况(通常,最好对您总是要在实例上设置/使用的所有属性执行此操作,并且仅在您真正想要访问它们时才使用类级属性在班级层面上)
        • 另外,is 不适合比较。使用 == 来检查相同的对象,这纯属巧合,它适用于某些短字符串。
        猜你喜欢
        • 1970-01-01
        • 2018-03-19
        • 2015-12-03
        • 2011-04-06
        • 2021-06-21
        • 2016-11-17
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多