Rupesh
Rupesh

Reputation: 1748

Keep the recent 3 folders and delete the rest in bash script?

I am new in shell script. Can you please suggest me some code for following requirement?

I have following formatted folders

example: /home/backup/store_id/datewisefolder/some.zip

like: /home/backup/44/22032014/some_file.zip

  /home/backup/44/23032014/some_file.zip 

  /home/backup/44/24032014/some_file.zip 

   /home/backup/44/25032014/some_file.zip

many more..

I want to go to each store id folders & keep only recent 3 date wise folder rest of deleted. Here 44 store id folder 23032014,24032014,25032014 these three are recent one so keep as it is. 22032014 older so delete one.

I wrote shell code which find out recent three file but I don't know how to delete rest off using store_ID folder loop.

below code find out most recent folder date wise

cd /home/backup/44/ ls -1 | sort -n -k1.8 -k1.4 -k 1 | tail -3

Upvotes: 1

Views: 2862

Answers (4)

dave sines
dave sines

Reputation: 1

cd into each store_id directory in turn. Create a list of directories with eight-digit names sorted in reverse order (most recent first); finally pass a part of the list, omitting the first $retain elements, to rm.

basedir=/home/backup
# How many directories to keep:
retain=3

shopt -s nullglob

# Assuming that anything beginning with a digit is a store_id directory.
for workdir in "$basedir"/[0-9]*/ ; do
  (
    cd "$workdir" || exit 1
    # Create the list.  The nullglob option ensures that if there are no
    # suitable directories, rmlist will be empty.
    rmlist=(
        $(
          printf '%s\n' [0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]/ |
          sort -nr -k1.5,1.8 -k1.3,1.4 -k1.1,1.2
        )
      )
    # If there are fewer than $retain entries in ${rmlist[@]}, rm will be
    # given no names and so do nothing.
    rm -rf -- "${rmlist[@]:$retain}"
  )
done

Upvotes: 0

Hema
Hema

Reputation: 167

ls /home/backup | while read store_id
do
  count=0
  ls -t /home/backup/$store_id | while read dir_to_remove
  do
    count=$((count + 1))
    if [ $count -gt 3 ]; then
      rm -rf /home/backup/$store_id/$dir_to_remove
    fi
  done
done

Upvotes: 2

Vishal R
Vishal R

Reputation: 1074

Below script can work.

declare -a axe
axe=`ls -l /home/backup/* | sort -n -k1.8 -k1.4 -k 1|head -n -3`

for i in $axe
do
  rm -rf $i;
done

Upvotes: 0

Jayesh Bhoi
Jayesh Bhoi

Reputation: 25875

find is the common tool for this kind of task :

find ./my_dir -mtime +3 -delete

explaination:

./my_dir your directory (replace with your own)
-mtime +3 older than 3 days
-delete delete it.

Or as per your script code

files=(`ls -1 /my_dir | sort -n -k1.8 -k1.4 -k 1 | tail -3`)

for i in *; do 
 keep=0; 
 #Check whether this file is in files array:
 for a in ${files[@]}; do 
  if [ $i == $a ]; then 
   keep=1; 
  fi; 
 done; 
 # If it wasn't, delete it
 if [ $keep == 0 ]; then 
  rm -rf $i;
 fi;
done

Upvotes: 0

Related Questions