Reputation: 45
I am new to bash and im struggling with it. I have an assignment which the question is
Try to find that top 5 larger files in the entire file system ordered by size and move the file to /tmp folder and rename the file with current datetime format
I tried with the following code
du -a /sample/ | sort -n -r | head -n 5
Im getting the list, but i cannot able to move..
Suggestions please
Upvotes: 0
Views: 174
Reputation: 141145
Looks like a simple case of xargs:
du -a /sample/ | sort -n -r | head -n 5 | xargs -I{} mv {} /tmp
xargs
here simply reads lines from standard input and appends them as arguments to the command, mv
in this case. Because the -I{}
is specified, the {}
string is replaced for the argument by xargs
. So mv {} /tmp
is executed as mv <the first file> /tmp
and mv <the second file> /tmp
and so on. You can ex. add -t
option to xargs
or ex. add echo
to see what's happenning: xargs -I{} -t echo mv {} /tmp
.
Instead of running 5 processes, we could add /tmp on the end of the stream and run only one mv
command:
{ du -a /sample/ | sort -n -r | head -n 5; echo /tmp; } | xargs mv
or like:
du -a . | sort -n -r | head -n 5 | { tee; echo /tmp; } | xargs mv
Note that using du -a
will most probably not work with filenames with special characters, spaces, tabs and newlines. It will also include directories in it's output. If you want to filter the files only, move to much safer find
:
find /sample/ -type f -printf '%s\t%p\n' | sort -n -r | cut -f2- | head -n5 | xargs -I{} mv {} /tmp
First we print each filename with it's size in bytes. Then we numerically sort the stream. Then we remove the size, ie. cut the stream on first '\t'
tabulation. Then we get the head -n5
lines. Lastly, we copy with xargs
. It will work for filenames not having special characters in filenames, like unreadable bytes, spaces, newlines and tabs.
For such corner cases it's preferred to use find
and handle zero terminated strings, like this (note simply just -z
and -0
options added):
find /sample/ -type f -printf '%s\t%p\0' | sort -z -n -r | cut -z -f2- | head -z -n5 | xargs -0 -I{} mv {} /tmp
Upvotes: 1