To find files older than the newest 8 I'm using:
find . -maxdepth 1 -type f -printf '%T@ %p\0' | sort -rz | sed -z 1,8d
The -printf '%T@ %p\0'
command applies a last modified timestamp (expressed as number of seconds since Jan. 1, 1970, 00:00 GMT, with fractional part) to the beginning of each zero-terminated filename matched, something like:
1597765267.7628475560 ./fileName2.txt1597765264.0267179360 ./fileName1.txt
In order to delete these oldest files by piping to xargs -0 gio trash
, I need to remove the timestamps. So I add another sed command to do this:
find . -maxdepth 1 -type f -printf '%T@ %p\0' | sort -rz | sed -z 1,8d | sed -z "s/^[0-9]*.[0-9]* //g"
Now I have the correct output, but is there a better more efficient way?
Based on @Quasímodo's answer, I tried to simplify further by using the sed delete pattern format (as I'm not actually substituting anything), but I got no output:
find . -maxdepth 1 -type f -printf '%T@ %p\0' | sort -rnz | sed -z "1,8d; /^[0-9]*\.[0-9]* /d"
Any suggestions appreciated.
Conclusion (from multiple responses):
find $targetPath -maxdepth 1 -type f -printf '%T@ %p\0' | sort -rnz | sed -z "1,${retain}d; s/^[^ ]* //"
Where:
$targetPath, Directory to find files, e.g. current directory '.'
${retain}, Number of newest files to retain, e.g. 8
-printf '%T@\t%p\0' | sort -rnz | tail -zn +9 | cut -zf2-
rm -- *(.Dom[8,-1])
(theD
is included for compatibility withfind
, which doesn't treat hidden files specially)