How to find and delete all files with specific name
ProgrammingThis forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.
Notices
Welcome to LinuxQuestions.org, a friendly and active Linux Community.
You are currently viewing LQ as a guest. By joining our community you will have the ability to post topics, receive our newsletter, use the advanced search, subscribe to threads and access many other special features. Registration is quick, simple and absolutely free. Join our community today!
Note that registered members see fewer ads, and ContentLink is completely disabled once you log in.
If you have any problems with the registration process or your account login, please contact us. If you need to reset your password, click here.
Having a problem logging in? Please visit this page to clear all LQ-related cookies.
Get a virtual cloud desktop with the Linux distro that you want in less than five minutes with Shells! With over 10 pre-installed distros to choose from, the worry-free installation life is here! Whether you are a digital nomad or just looking for flexibility, Shells can put your Linux machine on the device that you want to use.
Exclusive for LQ members, get up to 45% off per month. Click here for more info.
What do you mean -mtime won't work? I don't understand what you mean capture via the filename. Typically the find command would look like this...
Code:
#test
find /location -type f -mtime +365
#remove the files
find /location -type f -mtime +365 -exec rm {} \;
Did something happen to the files where you can't use the timestamp? If you need to do it based off of the date in the filename then you would need to use a more advanced loop like the following... Note, this assumes *all* files end with [0-9]{8}.gz.
Code:
find . -type f -name '*[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9].gz' | while read x;do
filedate="$(echo $x | sed 's/.*\.\([0-9]\{8\}\).gz/\1/')"
if [ "$(date -d "$filedate" +%s)" -lt "$(date -d -1year +%s)" ];then
echo "$x is older than 1 year from now. Created on $(date -d "$filedate")"
fi
done
It's best to explicitly state the format you expect the files to be otherwise this method would likely fail. You should check the date in the file name against the output of the date -d "$filedate" command. On my system, date command automatically interprets the date format to be YYYYMMDD.
What do you mean -mtime won't work? I don't understand what you mean capture via the filename. Typically the find command would look like this...
Code:
#test
find /location -type f -mtime +365
#remove the files
find /location -type f -mtime +365 -exec rm {} \;
Did something happen to the files where you can't use the timestamp? If you need to do it based off of the date in the filename then you would need to use a more advanced loop like the following... Note, this assumes *all* files end with [0-9]{8}.gz.
Code:
find . -type f -name '*[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9].gz' | while read x;do
filedate="$(echo $x | sed 's/.*\.\([0-9]\{8\}\).gz/\1/')"
if [ "$(date -d "$filedate" +%s)" -lt "$(date -d -1year +%s)" ];then
echo "$x is older than 1 year from now. Created on $(date -d "$filedate")"
fi
done
It's best to explicitly state the format you expect the files to be otherwise this method would likely fail. You should check the date in the file name against the output of the date -d "$filedate" command. On my system, date command automatically interprets the date format to be YYYYMMDD.
Yeah the modify timestamp is screwed up
actually format is this (modified first post).. sorry had given the wrong format earlier
Quote:
filename.date-*.gz
the "date" is in format "YYYYMMDD" and that is what we want to act on to delete all files older than one year
I realise that it is due to the | symbol opening a subshell..
But basically want to store all results in a array which then I can
1) email via mailx command in one email like a report (if i currently will put it in loop it will send 100 emails individually for each find)and
2) delete using -exec rm command
Perhaps, you should step back from the problem and figure out what it is you actually want. Currently your last post is entirely different from your original request. Please organize your thoughts and properly express what you're trying to do from start to finish.
The original answer I gave you seemed sufficient in that it could have been lightly modified by you to accomplish removing files older than a year when the date timestamp is part of the file name. One could update the expression or change how they're obtaining the date from the file name with a small modification. If that's not what you want then see my former statement in this post.
If you need to email the output before removing then don't mess with an array. Simply pipe stdout from the while loop in my original posted program to stdin of the mail program of your choosing.
Your format for time does not make sense and is not a standard time format. Since you only care about things older than a year then the day should be precise enough (i.e. we don't care about the time).
Quote:
Originally Posted by khandu
Also modified timestamp is not proper for these files so cannot rely on that
Understood.
Quote:
Originally Posted by khandu
I want to
1) Find all the files for the DATE more than a year old from today
2) Delete all those found files
3) Send a report email of all the files matched above and deleted.
Okay then you can lightly modify my original program. You should break it down into two steps. The first is a for loop which will mail you what *would* be deleted. Then execute the same program slightly modified to actually delete it. Here is my last post pretty much literal. Considering you don't seem to understand the original program I wrote I highly recommend against you running any code on your system until you fully understand what it does. Use at your own risk.
Here's what I talked about breaking it into two steps.
Code:
find . -type f -name '*.gz' | while read x;do
filedate="$(echo $x | sed 's/.*\.\([0-9]\{8\}\)-[0-9]\+.gz/\1/')"
if [ "$(date -d "$filedate" +%s)" -lt "$(date -d -1year +%s)" ];then
echo "$x is older than 1 year from now. Created on $(date -d "$filedate")"
fi
done | mail -s "files to be deleted" user@email.example
Code:
find . -type f -name '*.gz' | while read x;do
filedate="$(echo $x | sed 's/.*\.\([0-9]\{8\}\)-[0-9]\+.gz/\1/')"
if [ "$(date -d "$filedate" +%s)" -lt "$(date -d -1year +%s)" ];then
\rm "$x"
fi
done
You should learn bash, read the date man page to understand what I'm doing, and backup any files before you attempt this yourself.
I did understand your first code.. i just didn't realise that i can pipe the mail after the done..
I have a similar script running for another use where I am doing two step (one for mail and one for actual delete) but the difference was that it was in a single line command and thus mailx command was working at the end of it.. this had loop and therefore I didn't realize the mailx had to be outside the done with a |
LinuxQuestions.org is looking for people interested in writing
Editorials, Articles, Reviews, and more. If you'd like to contribute
content, let us know.