shell的一个不错的定期清理脚本
来源:互联网 发布:阿里云开通码 编辑:程序博客网 时间:2024/05/19 02:21
最近写了一个删除脚本,用于定期删除某些文件夹中的数据,该脚本需要如下参数:
①设置删除的目录
②该目录最少保留的时间,如3天
③该目录最多保留的时间,如30天
④该目录最大空间大小,如10G
⑤该目录所在磁盘分区的最大使用量,如80%
以上三个条件只要满足其中一条,便开始删除目录中30天前的数据,然后检查,若仍然满足,则继续删除29天前的数据,如此循环,直至磁盘分区使用量小于80%
改进:刚开始使用的是exit,但是这有个问题就是,如果要定期清理多个目录,就无法满足需求了,因为检查了第一个目录整个脚本就exit退出,而用return就ok,只会退出当前函数,会继续检查下一个目录
以下是脚本内容:粗略测试了一下,没什么问题,欢迎大家一起测试
最近做了个改版的,取消设置目录最大大小,触发条件仅为分区使用量,因为设置最大目录大小感觉很鸡肋
#!/bin/bash:<<block author:@michaelzeng date:2016-04-27blockloglevel=0 #debug:0; info:1; warn:2; error:3logdir=/data/logs/diskchklogfile=${logdir}/diskchk.logtest -d $logdir || mkdir -p $logdirfunction log { local msg;local logtype logtype=$1 msg=$2 datetime=`date +'%F %H:%M:%S'` logformat="[${logtype}]\t${datetime}\tfuncname: ${FUNCNAME[@]/log/} [line:`caller 0 | awk '{print$1}'`]\t${msg}" { case $logtype in debug) [[ $loglevel -le 0 ]] && echo -e "\033[30m${logformat}\033[0m" ;; info) [[ $loglevel -le 1 ]] && echo -e "\033[32m${logformat}\033[0m" ;; warn) [[ $loglevel -le 2 ]] && echo -e "\033[33m${logformat}\033[0m" ;; error) [[ $loglevel -le 3 ]] && echo -e "\033[31m${logformat}\033[0m" ;; esac } >> $logfile #} | tee -a $logfile}function check(){ #检查目录,确保目录不在以下目录,以免被误删 notdeldir='/ /boot /boot/ /var /var/ /lib/ /lib /etc /etc/ /bin /bin/ /lib64 /lib64/ /usr/ /usr /apps /apps/ /boot_ucloud /boot_ucloud/ /data /data/ /dev /dev/ /home /home/ /lost+found /lost+found/ /media /media/ /mnt /mnt/ /opt /opt/ /proc /proc/ /root /root/ /sbin /sbin/ /selinux /selinux/ /srv /srv/' local src_dir=$1 for blackdir in $notdeldir; do if [[ $src_dir == $blackdir ]];then log error "$src_dir:can't delete this directory" return 10 fi done return 0}function chkuse(){ local src_dir=$1 local partition;local par_size;local disk_ppc partition=`df -Ph $src_dir|awk '/dev/{print $6}'` par_size=`df -Ph $src_dir|awk '/dev/{print $2}'|tr -d G` disk_ppc=`df -Ph $src_dir|awk '/dev/{print $5}'|tr -d %` if [ ${disk_ppc} -le ${use} ]; then log info "partition:$partition; use:${disk_ppc}%,$src_dir dir is ok" return 1 else log info "partition:$partition; use:${disk_ppc}%,we will clean dir:$src_dir" return 0 fi}function clean(){ #满足删除条件时,删除文件直到分区用量小于$use paracount=3 if [ $# -eq $paracount ]; then local src_dir=$1 local min_tmd=$2 local max_tmd=$3 else return 1 fi local disk_ppc=0 #目录所在分区,分区大小,分区已用量 chkuse $src_dir if [ $? -eq 1 ]; then #log debug "disk:$partition; use:${disk_ppc}%,no need to clean" return 4 else local delfile delfile=$(find ${src_dir} -type f -mtime +${max_tmd}) if [[ -n $delfile ]];then log debug "delete file ${max_tmd} days ago;in dir:$src_dir;delete file : $delfile" for file in $delfile;do rm -f $file;done #for file in $delfile;do echo $file;done fi fi}# MIN_TMD 保留最短时间(天为单位)# MAX_TMD 保留最长时间(天为单位)function do_clean(){ PARACOUNT=3 if [ $# -eq $PARACOUNT ]; then local SRC_DIR=$1 local MIN_TMD=$2 local MAX_TMD=$3 else echo "Usage: ${FUNCNAME[@]} <SRC_DIR> <MIN_TMD> <MAX_TMD>" log debug "need $PARACOUNT parameters,but give:$#" return 1 fi if [ ${MAX_TMD} -lt ${MIN_TMD} ]; then log debug "para MAX_TMD should be biger than MIN_TMD" return 2 fi if [ ! -d "$SRC_DIR" ];then log debug "$SRC_DIR: No such directory" return 3 fi check $SRC_DIR if [ $? -eq 0 ];then #删除大于$MAX_TMD天的文件 local delfile delfile=$(find ${SRC_DIR} -type f -mtime +${MAX_TMD}) if [[ -n $delfile ]];then log debug "delete file that ${MAX_TMD} days ago,in dir:$SRC_DIR,file:${delfile}" for file in $delfile;do rm -f $file;done #for file in $delfile;do echo $file;done fi #开始循环检查 chkuse ${SRC_DIR} if [[ $? -eq 0 ]];then ((TM=MAX_TMD)) COUNT=$(( MAX_TMD-MIN_TMD )) for(( i=0; i<=COUNT;i++ )) do clean "$SRC_DIR" "$MIN_TMD" "$TM" if [ $? -eq 4 ]; then break fi if [ ${TM} -gt ${MIN_TMD} ]; then (( TM=TM-1 )) else #达到最少保留天数限制,则找出大于8G的大文件,清空 log warn "still not enough space,we will find the big file and clean it" bigfile=$(find ${SRC_DIR} -type f -size +${max_filesize}) if [[ -n $bigfile ]];then log debug "clean the filesize -gt ${max_filesize},bigfile is $bigfile" for f in $bigfile;do echo '' > $f;done chkuse ${SRC_DIR} break fi fi done fi fi}################## main ####################举个栗子:/var/spool/clientmqueue/目录,最少保留3天,最多保留30天use=75 #定义某分区最大使用量max_filesize=8G #定义最大文件大小,当达到最少保留天数限制时,清空该文件#do_clean /var/spool/clientmqueue/ 3 10do_clean /data/logs/ 3 10do_clean /data/backup/ 3 10
最初版本:
#!/bin/bash:<<block author:@michaelzeng date:2016-04-27blockuse=30 #定义某分区最大使用量loglevel=0 #debug:0; info:1; warn:2; error:3logfile=${0%.*}".log"function log { local msg;local logtype logtype=$1 msg=$2 datetime=`date +'%F %H:%M:%S'` #logformat="[${logtype}]\t${datetime}\tfuncname:${FUNCNAME[@]}\t[line:$LINENO]\t${msg}" logformat="[${logtype}]\t${datetime}\tfuncname: ${FUNCNAME[@]/log/} [line:`caller 0 | awk '{print$1}'`]\t${msg}" { case $logtype in debug) [[ $loglevel -le 0 ]] && echo -e "\033[30m${logformat}\033[0m" $logflag;; info) [[ $loglevel -le 1 ]] && echo -e "\033[32m${logformat}\033[0m" $logflag;; warn) [[ $loglevel -le 2 ]] && echo -e "\033[33m${logformat}\033[0m" $logflag;; error) [[ $loglevel -le 3 ]] && echo -e "\033[31m${logformat}\033[0m" $logflag;; esac #} >> $logfile } | tee -a $logfile}function check(){ #检查目录,确保目录不在以下目录,以免被误删 notdeldir='/ /boot /boot/ /var /var/ /lib/ /lib /etc /etc/ /bin /bin/ /lib64 /lib64/ /usr/ /usr /apps /apps/ /boot_ucloud /boot_ucloud/ /data /data/ /dev /dev/ /home /home/ /lost+found /lost+found/ /media /media/ /mnt /mnt/ /opt /opt/ /proc /proc/ /root /root/ /sbin /sbin/ /selinux /selinux/ /srv /srv/' local src_dir=$1 for blackdir in $notdeldir; do if [[ $src_dir == $blackdir ]];then log error "$src_dir:can't delete this directory" return 10 fi done return 0}function clean(){ #满足删除条件时,删除文件直到分区用量小于$use paracount=4 if [ $# -eq $paracount ]; then local src_dir=$1 local min_tmd=$2 local max_tmd=$3 local max_dsk=$4 else return 1 fi local disk_ppc=0 #目录所在分区,分区大小,分区已用量 partition=`df -Ph $src_dir|awk '/dev/{print $6}'` par_size=`df -Ph $src_dir|awk '/dev/{print $2}'|tr -d G` disk_ppc=`df -Ph $src_dir|awk '/dev/{print $5}'|tr -d %` if [ ${disk_ppc} -le ${use} ]; then log debug "disk:$partition; use:${disk_ppc}%,no need to clean" return 4 fi #检查设置的目录最大大小是否小于分区的$use% max_use=$((par_size*use/100)) if [ $max_dsk -gt $max_use ];then #echo "目录最大使用量设置错误,需小于所在分区大小的${use}%" #max_dsk改为分区大小的${use}% log warn "parameter MAX_GB:$max_dsk > ${par_size}*${use}/100,set default:par_size*use/100" max_dsk=$max_use fi #目录大小 local src_dir_sz=`du --summarize --block-size=1G ${src_dir} | awk '{print $1}'` if [ ${src_dir_sz} -gt ${max_dsk} ]; then #找出${src_dir}中${max_tmd}天前以日期命名的目录并删除直到,${src_dir}空间大小小于${max_dsk} local delfile delfile=$(find ${src_dir} -type f -mtime +${max_tmd} | egrep "`date +%Y`") log debug "in dir:$src_dir;delete file : $delfile" #find ${src_dir} -type f -mtime +${max_tmd} | egrep "`date +%Y`" |xargs -i rm -f {} else return 5 fi}# MIN_TMD 保留最短时间(天为单位)# MAX_TMD 保留最长时间(天为单位)# MAX_GB 目录最多存储空间(GB为单位)# 清理数据按1小时清理直到空间小于MAX_GBfunction do_clean(){ PARACOUNT=4 if [ $# -eq $PARACOUNT ]; then local SRC_DIR=$1 local MIN_TMD=$2 local MAX_TMD=$3 local MAX_GB=$4 else echo "Usage: ${FUNCNAME[@]} <SRC_DIR> <MIN_TMD> <MAX_TMD> <MAX_GB>" log debug "need $PARACOUNT parameters,but give:$#" return 1 fi if [ ${MAX_TMD} -lt ${MIN_TMD} ]; then log debug "para MAX_TMD should be biger than MIN_TMD" return 2 fi if [ ! -d "$SRC_DIR" ];then log debug "$SRC_DIR: No such directory" return 3 fi check $SRC_DIR if [ $? -eq 0 ];then #删除大于$MAX_TMD天的文件 local delfile delfile=$(find ${SRC_DIR} -type f -mtime +${MAX_TMD} | egrep "`date +%Y`") [[ -n $delfile ]] && log info "delete file that ${MAX_TMD} days ago,in dir:$SRC_DIR,file:${delfile}" #开始循环检查 (( TM=MAX_TMD )) for(( i=0; i<MAX_TMD; i++ )) do if [ ${TM} -gt ${MIN_TMD} ]; then (( TM=TM-1 )) else break fi log info "check dir:${SRC_DIR} that ${TM} days ago" clean "$SRC_DIR" "$MIN_TMD" "$TM" "$MAX_GB" if [ $? -eq 5 ]; then break fi done fi}################## main ####################举个栗子:/var/spool/clientmqueue/目录,最少保留3天,最多保留30天,最大1Gdo_clean /var/spool/clientmqueue/ 3 30 1do_clean /media 3 30 1 #禁止删除do_clean /media/ 3 30 1 #禁止删除#最大目录大小10G大于分区大小的最大使用量30%do_clean /media/CentOS 3 30 10 do_clean #参数错误
0 0
- shell的一个不错的定期清理脚本
- 定期清理服务器log的脚本
- 一个不错的shell 脚本教程
- 一个不错的shell 脚本教程
- 一个不错的shell 脚本教程
- 一个不错的shell 脚本教程
- 一个不错的shell 脚本教程
- 一个不错的shell 脚本教程
- 一个不错的shell 脚本教程 (国)
- 一个不错的shell 脚本教程
- 一个不错的shell脚本教程
- 一个不错的shell 脚本入门教程
- 一个不错的shell脚本入门教程
- 几个不错的Shell脚本
- 几个不错的Shell脚本
- 一个不错的shell 脚本教程 入门级
- 一个不错的shell 脚本教程 入门级
- 一个不错的shell 脚本教程 入门级
- validate
- 1319
- Python中if-else语句的多种写法
- 1043. Is It a Binary Search Tree (25)
- 关于使用hbase进行多维度条件实时查询的方案调研。
- shell的一个不错的定期清理脚本
- 【VR】NuFormer的虚拟现实系统
- 杭电部分题型
- EditText 的输入类型inputType
- Css框模型
- ubuntu 14.04 安装 Irrlicht
- php与redis扩展安装和使用-Redis学习笔记六
- 极客开源-如何使用Java来发送一封电子邮件?
- 计算机系统的数位与进制