【问题标题】:Automator - find and move most recent file in filtered listAutomator - 在过滤列表中查找和移动最近的文件
【发布时间】:2020-05-05 11:42:00
【问题描述】:

我正在尝试使用 Automator 来

  1. 获取文件夹中超过 30 天 (ok) 的过滤文件列表
  2. 将最新的(如果有的话)移动到现有的子文件夹
  3. 把其他人扔掉。

第 1 步很简单,但我无法找到执行第 2 步的方法 - 选择并移动最新的过滤集。

结果将是:如果工作流程安排为每月一次,则子文件夹将每月包含一个文件,而父文件夹将仅包含 31 天以内的文件

有没有办法做到这一点?

更新 我尝试将 shell 脚本添加到自动化工作流程

fn=$(ls -t | head -n1)
mv -f -- "$fn" ./<subdirectory>/

但是第二行的路径有问题。

【问题讨论】:

    标签: bash automator


    【解决方案1】:

    ls -t | head -n1 不错,但要小心;如果子目录是最近修改的,它将占用第一个插槽,不仅会导致尝试将该目录移动到自身中(不允许,这可能是您的问题“第二行中的路径”),但可能会删除其余文件,包括您要保留的文件。有很多方法可以过滤掉任何目录;在我的脑海中,你可以ls -tp | grep -v '/$' | head -n1。请注意,将文件添加到目录会影响 posix 上的目录 mtime(上次修改时间)。

    删除所有文件很容易,一旦您将要保留的文件移出,只需rm *。请注意,这不会删除目录(只要您不放 -r),我认为这是您想要的,因为您似乎正在将要保留的文件移动到它所在的子目录。

    您可能还想添加一些错误捕获,因此如果某个步骤失败,以后的步骤不要删除您不想删除的文件。我不使用自动机,但只要您使用真正的 bash,这应该可以工作:(包括其他调度程序,如 cron,只要您首先进入正确的工作目录)

    mv -- "$(ls -tp | grep -v '/$' | head -n1)" subdirectory/ && rm *
    

    && 意味着只有在前面的事情成功时才做后面的事情。将./ 添加到目标文件的开头没有任何作用,但在末尾保留/ 可以防止创建一个名为“子目录”的新文件(如果它不存在)。另外,我很确定您发送的代码 sn-p 中的“”是将其标记为与您的实际代码不同,但以防万一:请注意,无论调用什么子目录,都可能需要特殊处理如果它确实包含这些字符。

    编辑:

    我刚刚在问题中注意到约束“获取超过 30 天的文件夹中的过滤文件列表”。所以,稍作改动:(用find比较时间)

    mv -- "$(find -maxdepth 1 -type f -mtime +30 -printf '%T@ %f\n' | sort -rn | head -n1 | cut -d\  -f2-)" subdirectory/ && find -maxdepth 1 -type f -mtime +30 -delete
    

    解释:在当前目录(不是子目录,所以 maxdepth 1)中查找 mtime 至少为过去 30 天(-mtime +30)的文件(不是目录,类型 f)并打印修改和名称 (%T@ %f);像倒序(-r)中的数字(-n)一样排序;只取第一个(head -n1);提取文件名(第二个+空格分隔的字段)并将其移动到子目录。如果成功,请删除任何符合与以前相同的查找条件的内容。

    我不会将文件放在环境变量中,除非磁盘 /very/ 很慢且未缓存。过滤掉你移动的文件名所花费的时间可能比重新查询磁盘要花费更多的精力,除非你有大量的文件,在这种情况下它们可能不适合环境部分。

    编辑 2: KamilCuk 是对的。使用 null 终止,因为 null 是文件名中不允许的(唯一字符):

    find -maxdepth 1 -type f -mtime +30 -printf '%T %f\0' | sort -z -t' ' -r -n -s -k1 | head -z -n1 | cut -z -d' ' -f2- | xargs -0 -I{} mv {} subdirectory/ && find -maxdepth 1 -type f -mtime +30 -delete
    

    【讨论】:

    • @KamilCuk 是的,显然有一些奇怪的潜在文件名可能会导致问题。实际测试这个(使用-print 而不是-delete),我看到 find 用 ? 替换了每个换行符。 除非输出到非tty,所以是的,在这种情况下移动可能会中断(处于失败状态,因此不会发生删除)。如果要支持包含换行符的文件名,则需要更健壮的过滤程序,在这种情况下,应该使用可以更好地处理原始字符代码的语言创建一些东西 (C)。
    • 只需使用零分隔流。喜欢find -maxdepth 1 -type f -mtime +30 -printf '%T %f\0' | sort -z -t' ' -r -n -s -k1 | head -z -n1 | cut -z -d' ' -f2- | xargs -0 -I{} mv {} subdirectory/
    • 我不知道 sort 有这个选项,但是是的,这很棒。总有一天我会使用它。
    • 太棒了,非常感谢。我一直在努力通过它并且有点让它工作,但这要好得多。非常感谢。
    猜你喜欢
    • 1970-01-01
    • 2017-06-25
    • 2020-05-23
    • 1970-01-01
    • 2012-12-31
    • 2015-07-26
    • 1970-01-01
    • 1970-01-01
    • 2019-08-12
    相关资源
    最近更新 更多