linux shell 脚本 历史文件清理脚本,按天,按月,清理前N天的历史文件,删除指定大小历史文件,历史文件归档清理
2017-05-05 16:18
603 查看
不知道大家那有没有要清理的这个事情。需要清理目录历史文件。可能后续也会有很多其他地方需要清理历史文件,可能会用到。
我这两天空闲写了个脚本,清理比较方便,有要进行清理的大量历史文件的话可以用。
脚本用到的命令只有linux才有,像solaris等就不支持,所以只能在linux上运行。如果是nas存储的话,可以挂载到一个linux主机上跑脚本清理。
另外,脚本查找文件用的是ls,但是ls也有最大文件的限度(大概10w以内),如果每天文件很多,每天都是10w+的,运行可能提示文件数过多无法ls。
还有,脚本内有个默认的限制,就是清理的文件的创建日期是跟文件名上的时间是相同的,如果是不同的话,是不会清理的,这是为了避免清理错了。
我写了两个版本的清理脚本,一个是直接清理文件的clearfile.sh,一个是把文件按天/月进行归档(归档成文件夹或压缩包形式)clearfile_ar.sh:
(一)单纯清理文件使用clearfile.sh
文件名是带有时间戳的文件,类似如下(或其他时间格式,后面描述)
按天/月清理:修改脚本内的CLEAR_TYPE参数,D是天,M是月
如果是按月的话,脚本按你输入的月份进行整月清理,不会看你输入的天的时间
清理指定期间内所有文件:
./clearfile.sh/wls/investop/tmp/
20170515 20170516
清理指定期间内固定大小文件(ls -l显示的大小):
./clearfile.sh
/wls/investop/tmp/ 20170515
20170516 40
其他文件日期格式清理:
脚本默认(TRUNC_DATE_FLAG参数为N)是清理上面截图这类格式的,没有任何间隔符的文件名。
如果文件名是有其他间隔符的,如*2017_05_16*这种的。
首先需要调整下脚本里的trunc()方法,把标黄的年月日之间的分隔符改成需要的分隔符(按天和按月两种哦)
然后再设置TRUNC_DATE_FLAG参数为Y,来让脚本使用你指定的日期格式清理
[b](二)归档方式清理历史文件,使用clearfile_ar.sh[/b]
使用方式与clearfile.sh相同,唯一不同的是要设置脚本里的DEL_FLAG参数。
按天/月清理同clearfile.sh
清理指定期间内所有文件同clearfile.sh
清理指定期间内固定大小文件 同clearfile.sh
其他文件日期格式清理 同clearfile.sh
模式1:DEL_FLAG=N
脚本只会把文件按天/按月归档到以时间命名的文件夹内,如
模式2:DEL_FLAG=Y
把文件归档成压缩文件*tar.gz,并删除归档的文件夹
PS,对于大量需要清理的目录,可以写一个非常简单的脚本来批量执行,类似
但是要去掉脚本里的是否确认执行这个反馈,否则脚本执行还是要你输入Y。
[b]~~~~~~~~~~~~~~~~~~脚本如下~~~~~~~~~~~~~~~~~~[/b]
clearfile.sh
clearfile_ar.sh
欢迎各位博友提出更新意见。
谢谢
我这两天空闲写了个脚本,清理比较方便,有要进行清理的大量历史文件的话可以用。
脚本用到的命令只有linux才有,像solaris等就不支持,所以只能在linux上运行。如果是nas存储的话,可以挂载到一个linux主机上跑脚本清理。
另外,脚本查找文件用的是ls,但是ls也有最大文件的限度(大概10w以内),如果每天文件很多,每天都是10w+的,运行可能提示文件数过多无法ls。
还有,脚本内有个默认的限制,就是清理的文件的创建日期是跟文件名上的时间是相同的,如果是不同的话,是不会清理的,这是为了避免清理错了。
我写了两个版本的清理脚本,一个是直接清理文件的clearfile.sh,一个是把文件按天/月进行归档(归档成文件夹或压缩包形式)clearfile_ar.sh:
(一)单纯清理文件使用clearfile.sh
文件名是带有时间戳的文件,类似如下(或其他时间格式,后面描述)
按天/月清理:修改脚本内的CLEAR_TYPE参数,D是天,M是月
如果是按月的话,脚本按你输入的月份进行整月清理,不会看你输入的天的时间
清理指定期间内所有文件:
./clearfile.sh/wls/investop/tmp/
20170515 20170516
清理指定期间内固定大小文件(ls -l显示的大小):
./clearfile.sh
/wls/investop/tmp/ 20170515
20170516 40
其他文件日期格式清理:
脚本默认(TRUNC_DATE_FLAG参数为N)是清理上面截图这类格式的,没有任何间隔符的文件名。
如果文件名是有其他间隔符的,如*2017_05_16*这种的。
首先需要调整下脚本里的trunc()方法,把标黄的年月日之间的分隔符改成需要的分隔符(按天和按月两种哦)
然后再设置TRUNC_DATE_FLAG参数为Y,来让脚本使用你指定的日期格式清理
[b](二)归档方式清理历史文件,使用clearfile_ar.sh[/b]
使用方式与clearfile.sh相同,唯一不同的是要设置脚本里的DEL_FLAG参数。
按天/月清理同clearfile.sh
清理指定期间内所有文件同clearfile.sh
清理指定期间内固定大小文件 同clearfile.sh
其他文件日期格式清理 同clearfile.sh
模式1:DEL_FLAG=N
脚本只会把文件按天/按月归档到以时间命名的文件夹内,如
模式2:DEL_FLAG=Y
把文件归档成压缩文件*tar.gz,并删除归档的文件夹
PS,对于大量需要清理的目录,可以写一个非常简单的脚本来批量执行,类似
但是要去掉脚本里的是否确认执行这个反馈,否则脚本执行还是要你输入Y。
[b]~~~~~~~~~~~~~~~~~~脚本如下~~~~~~~~~~~~~~~~~~[/b]
clearfile.sh
#!/bin/bash ################################ ##参数设置 ################################ TODAY=`date +%Y%m%d` DATE_BEGIN=`date +%Y%m%d` DATE_END=`date +%Y%m%d` DATE_FORMATION="%Y%m%d" FILESIZE="" COUNTING=0 #需要手工设置,按月清理不会根据输入日期的天清理,只能清理整个月。 CLEAR_TYPE=M #需要手工设置,是否需要转换日期格式,需要的话,要根据格式设置trunc()方法 TRUNC_DATE_FLAG=N if [ -f count.tmp ] then echo "" > count.tmp fi ################################ ##日期格式转换,eg:trunc 20170512 ################################ trunc() { if [ "D" = "$CLEAR_TYPE" ] then OPR_DATE=`echo $1 | sed -r 's/^(.{4})(.{2})(.{2})$/\1_\2_\3/g'` else OPR_DATE=`echo $1 | sed -r 's/^(.{4})(.{2})$/\1_\2/g'` fi } ################################ ##按日清理递归 ################################ dayclear() { echo "================================" echo "day clear working on $DATE_END" doclear $DATE_END priday $DATE_END if [ $DATE_END -lt $DATE_BEGIN ] then echo "================================" echo "Total cleard : $COUNTING " echo "dayclear end" return fi dayclear } ################################ ##按月清理递归 ################################ monthclear() { echo "================================" echo "clearfun working on $DATE_END" doclear $DATE_END primonth $DATE_END if [ $DATE_END -lt $DATE_BEGIN ] then echo "================================" echo "Total cleard : $COUNTING " echo "monthclear end" return fi monthclear } ################################ ##前一日日期,eg:priday 20170421 ################################ priday() { SEC=`date -d $1 +%s` PRI_SEC=$[${SEC}-86400] PRI_DAY=`date -d @${PRI_SEC} +%Y%m%d` DATE_END=$PRI_DAY } ################################ ##前一月日期,eg:primonth 201704 ################################ primonth() { #TMP_D=`echo $1 | cut -c 1-6` #TMP_D=${TMP_D}"01" TMP_D=`echo $1`"01" SEC=`date -d $TMP_D +%s` PRI_SEC=$[${SEC}-86400] PRI_MON=`date -d @${PRI_SEC} +%Y%m` DATE_END=$PRI_MON } ################################ ##清理文件 ################################ doclear() { #默认的日期格式,如20170512,201705 THE_DATE=$1 OPR_DATE=$1 #转换OPR_DATE的日期格式,如2017-05-12,2017-05 if [ "Y" = ${TRUNC_DATE_FLAG} ] ; then trunc $1 fi echo "clearing" if [ "" == "${FILESIZE}" ] then #ROW=`ls -l *${OPR_DATE}* | awk '{ print $9;output="ls -l "$9;system(output);}' | wc -l` ls -ld --time-style +${DATE_FORMATION} *${OPR_DATE}* | grep -v archive | awk -v date_str=${THE_DATE} 'BEGIN{count=0}{if (date_str==$6) {count+=1;output="rm "$7;system(output);}}END{oo="echo "count" > count.tmp";system(oo);}' ROW=`cat count.tmp` COUNTING=$[ $COUNTING + $ROW ] else #ROW=`ls -l *${OPR_DATE}* | awk -v the_size=${FILESIZE} '{if ($5==the_size) {output="ls -l "$9;system(output)}}' | wc -l` ls -ld --time-style +${DATE_FORMATION} *${OPR_DATE}* | awk -v the_size=${FILESIZE} -v date_str=${THE_DATE} 'BEGIN{count=0}{if (the_size==$5 && date_str==$6) {count+=1;output="rm "$7;system(output);}}END{oo="echo "count" > count.tmp";system(oo);}' ROW=`cat count.tmp` COUNTING=$[ $COUNTING + $ROW ] fi echo "clear $THE_DATE finished, clear file $ROW " } ####################################### ## main function ## 判断参数是否正确,可以输入如下: ## 清理所有文件:clear 20150601 20161231 ## 清理固定大小字节文件:clear 20150601 20161231 40 ## 清理固定大小字节文件:clear 20150601 20161231 40 ####################################### #清理所有文件, if [ $# -ne 3 ] && [ $# -ne 4 ] then echo "请输入正确的参数" echo "如清理/nfsc/hipo/bak目录下,从2015年4月1号到2016年12月31号的所有文件(默认按日清理):clearfile /nfsc/hipo/bak 20150401 20161231" echo "或清理清理/nfsc/hipo/bak目录下,从2015年4月1号到2016年12月31号的大小为40字节的文件(默认按日清理):clearfile /nfsc/hipo/bak 20150401 20161231 40" exit 1 else DATE_BEGIN=$2 DATE_END=$3 FILESIZE=$4 date -d $2 2>&- ERR1=$? date -d $3 2>&- ERR2=$? if [ $ERR1 -eq 1 ] || [ $ERR2 -eq 1 ]; then echo "date formation error, input the correct date string like 20170131." exit 1 elif [ $DATE_BEGIN -gt $DATE_END ]; then echo "BEGIN DATE is later than END DATE, please correct." exit 1 elif [ $TODAY -lt $DATE_END ]; then echo "END DATE is later than NOW DATE, please correct" elif [ ! -d $1 ]; then echo "DIR $1 does not exist." exit 0 fi fi cd $1 THEDIR=`pwd` echo ">>>>clear the DIR $THEDIR " echo ">>>>clear file between $DATE_BEGIN and $DATE_END." if [ "" == "${FILESIZE}" ]; then echo ">>>>every size of the files will be clear" else echo ">>>>clear filesize only is ${FILESIZE}" fi if [ "D" == "${CLEAR_TYPE}" ]; then echo ">>>>clear set by DAY" else echo ">>>>clear by MONTH" fi read -p "please confirm the information above,enter Y to continue, other to exit : " ANWSER #确认继续 if [ ! -n "$ANWSER" ] || [ $ANWSER != Y ] then echo "exit" exit 0 fi echo "[`date +%Y%m%d-%H%M%S`]==START==" if [ "D" = "$CLEAR_TYPE" ] then echo "DAY clear begin " DATE_FORMATION="%Y%m%d" dayclear else echo "MONTH clear begin " DATE_BEGIN=`echo $2 | cut -c 1-6` DATE_END=`echo $3 | cut -c 1-6` DATE_FORMATION="%Y%m" monthclear fi echo "[`date +%Y%m%d-%H%M%S`]==END=="
clearfile_ar.sh
#!/bin/bash ################################ ##参数设置 ################################ TODAY=`date +%Y%m%d` DATE_BEGIN=`date +%Y%m%d` DATE_END=`date +%Y%m%d` DATE_FORMATION="%Y%m%d" FILESIZE="" COUNTING=0 #需要手工设置,按月清理不会根据输入日期的天清理,只能清理整个月。 CLEAR_TYPE=M #需要手工设置,是否删除归档的文件,只保留压缩文件 DEL_FLAG=N #需要手工设置,是否需要转换日期格式,需要的话,要根据格式设置trunc()方法 TRUNC_DATE_FLAG=N if [ -f count.tmp ] then echo "" > count.tmp fi ################################ ##日期格式转换,eg:trunc 20170512 ################################ trunc() { if [ "D" = "$CLEAR_TYPE" ] then OPR_DATE=`echo $1 | sed -r 's/^(.{4})(.{2})(.{2})$/\1_\2_\3/g'` else OPR_DATE=`echo $1 | sed -r 's/^(.{4})(.{2})$/\1_\2/g'` fi } ################################ ##按日清理递归 ################################ dayclear() { echo "================================" echo "day clear working on $DATE_END" doclear $DATE_END priday $DATE_END if [ $DATE_END -lt $DATE_BEGIN ] then echo "================================" echo "Total cleard : $COUNTING " echo "dayclear end" return fi dayclear } ################################ ##按月清理递归 ################################ monthclear() { echo "================================" echo "clearfun working on $DATE_END" doclear $DATE_END primonth $DATE_END if [ $DATE_END -lt $DATE_BEGIN ] then echo "================================" echo "Total cleard : $COUNTING " echo "monthclear end" return fi monthclear } ################################ ##前一日日期,eg:priday 20170421 ################################ priday() { SEC=`date -d $1 +%s` PRI_SEC=$[${SEC}-86400] PRI_DAY=`date -d @${PRI_SEC} +%Y%m%d` DATE_END=$PRI_DAY } ################################ ##前一月日期,eg:primonth 201704 ################################ primonth() { #TMP_D=`echo $1 | cut -c 1-6` #TMP_D=${TMP_D}"01" TMP_D=`echo $1`"01" SEC=`date -d $TMP_D +%s` PRI_SEC=$[${SEC}-86400] PRI_MON=`date -d @${PRI_SEC} +%Y%m` DATE_END=$PRI_MON } ################################ ##清理文件 ################################ doclear() { #默认的日期格式,如20170512,201705 THE_DATE=$1 OPR_DATE=$1 #转换OPR_DATE的日期格式,如2017-05-12,2017-05 if [ "Y" = ${TRUNC_DATE_FLAG} ] ; then trunc $1 fi #创建归档文件夹 echo "clearing" if [ ! -d ${THE_DATE}"archive" ] ;then mkdir "${THE_DATE}"archive ERR=$? if [ 0 != ${ERR} ]; then echo "failed to create archive dir under "`pwd` exit 0 fi echo "created the archive directory ${THE_DATE}archive" chmod 777 ${THE_DATE}"archive" else echo "the archive directory already exist ${THE_DATE}archive" fi #如果要删除历史的归档文件,判断是否已经存在过历史文件的压缩包 if [ -f "${THE_DATE}archive.tar.gz" ] && [ "Y" = "${DEL_FLAG}" ] ;then echo "file ${THE_DATE}archive.tar.gz already exits, and again you choose to archive the file which had been archived ,this will cause the old tar.gz file tobe overwirted." echo "you should confirm the date parameter you input, or you can mv the exits *.tar.gz file to other directory." exit 0 fi if [ "" == "${FILESIZE}" ] then ls -ld --time-style +${DATE_FORMATION} *${OPR_DATE}* | grep -v archive | awk -v date_str=${THE_DATE} 'BEGIN{count=0;}{if (date_str==$6) {count+=1;output="mv "$7" "date_str"archive/";system(output);}}END{oo="echo "count" > count.tmp";system(oo);}' if [ "Y" = "${DEL_FLAG}" ] ; then tar -cf - ${THE_DATE}"archive/" | gzip > ${THE_DATE}"archive.tar.gz" rm -rf ${THE_DATE}"archive/" fi ROW=`cat count.tmp` COUNTING=$[ $COUNTING + $ROW ] else ls -ld --time-style +${DATE_FORMATION} *${OPR_DATE}* | grep -v archive | awk -v the_size=${FILESIZE} -v date_str=${THE_DATE} 'BEGIN{count=0;}{if (the_size==$5 && date_str==$6) {count+=1;output="mv "$7" "date_str"archive/";system(output);}}END{oo="echo "count" > count.tmp";system(oo);}' if [ "Y" = "${DEL_FLAG}" ] ; then tar -cf - ${THE_DATE}"archive/" | gzip > ${THE_DATE}"archive.tar.gz" rm -rf ${THE_DATE}"archive/" fi ROW=`cat count.tmp` COUNTING=$[ $COUNTING + $ROW ] fi echo "clear $THE_DATE finished, clear file $ROW " } ####################################### ## main function ## 判断参数是否正确,可以输入如下: ## 清理所有文件:clear 20150601 20161231 ## 清理固定大小字节文件:clear 20150601 20161231 40 ## 清理固定大小字节文件:clear 20150601 20161231 40 ####################################### #清理所有文件, if [ $# -ne 3 ] && [ $# -ne 4 ] then echo "请输入正确的参数" echo "如清理/nfsc/hipo/bak目录下,从2015年4月1号到2016年12月31号的所有文件(默认按日清理):clearfile /nfsc/hipo/bak 20150401 20161231" echo "或清理清理/nfsc/hipo/bak目录下,从2015年4月1号到2016年12月31号的大小为40字节的文件(默认按日清理):clearfile /nfsc/hipo/bak 20150401 20161231 40" exit 1 else DATE_BEGIN=$2 DATE_END=$3 FILESIZE=$4 date -d $2 2>&- ERR1=$? date -d $3 2>&- ERR2=$? if [ $ERR1 -eq 1 ] || [ $ERR2 -eq 1 ]; then echo "date formation error, input the correct date string like 20170131." exit 1 elif [ $DATE_BEGIN -gt $DATE_END ]; then echo "BEGIN DATE is later than END DATE, please correct." exit 1 elif [ $TODAY -lt $DATE_END ]; then echo "END DATE is later than NOW DATE, please correct" elif [ ! -d $1 ]; then echo "DIR $1 does not exist." exit 0 fi fi cd $1 THEDIR=`pwd` echo ">>>>clear the DIR $THEDIR " echo ">>>>clear file between $DATE_BEGIN and $DATE_END." if [ "" == "${FILESIZE}" ]; then echo ">>>>every size of the files will be clear" else echo ">>>>clear filesize only is ${FILESIZE}" fi if [ "D" == "${CLEAR_TYPE}" ]; then echo ">>>>clear set by DAY" else echo ">>>>clear by MONTH" fi read -p "please confirm the information above,enter Y to continue, other to exit : " ANWSER #确认继续 if [ ! -n "$ANWSER" ] || [ $ANWSER != Y ] then echo "exit" exit 0 fi echo "[`date +%Y%m%d-%H%M%S`]==START==" if [ "D" = "$CLEAR_TYPE" ] then echo "DAY clear begin " DATE_FORMATION="%Y%m%d" dayclear else echo "MONTH clear begin " DATE_BEGIN=`echo $2 | cut -c 1-6` DATE_END=`echo $3 | cut -c 1-6` DATE_FORMATION="%Y%m" monthclear fi echo "[`date +%Y%m%d-%H%M%S`]==END=="
欢迎各位博友提出更新意见。
谢谢
相关文章推荐
- Linux下自动清理超过指定大小的文件(shell脚本,通过du -sh或ls -l)
- Shell脚本自动删除指定大小以上的备份文件
- Linux 脚本删除大于指定大小的文件
- shell脚本自动清理超过指定大小的文件
- linux Shell: 定时清理指定目录下大于指定大小、指定文件名的文件?
- 一个关于打包和删除历史文件的小脚本
- 多匹配递归删除指定文件/文件夹,用以简便备份你的VS.NET解决方案 (1:清理垃圾文件)
- 用Batch删除当前目录下小于指定大小文件
- linux shell脚本_文件的批量删除_3.0_最终版
- 用shell脚本实现删除一定大小的文件
- 创建固定大小的文件 -- Linux shell 脚本编写实例
- shell脚本删除目录下的指定文件
- perl脚本之__分类统计某一目录下指定类型文件的大小
- Domino下通过vbs脚本删除指定主题邮件---脚本文件
- Linux删除指定目录文件脚本
- 创建固定大小的文件 -- Linux shell 脚本编写实例
- 快速批量删除指定类型文件脚本
- linux下使用shell编写的删除历史文件的脚本 find | xargs tar 有文件个数限制哦
- spec文件中写上一些脚本,使生成的rpm包在安装前删除系统中指定文件的方法
- shell脚本删除目录下的指定文件