Linux基础(53)之任务计划与周期性任务执行

Linux基础(53)之任务计划与周期性任务执行

微信搜索 zze_coding 或扫描 👉 二维码关注我的微信公众号获取更多资源推送:

在 Linux 中的任务计划的实现有两种:

  1. 未来的某时间点执行一次任务,可使用 atbatch 命令实现;
  2. 周期性运行某任务,可使用 cron 命令实现;

指定时间点执行计划-at

at 命令可以指定一个时间点来运行某任务。
常用格式如下:

at [option] [time]
    option:常用选项
        -l:列出等待执行的作业队列中的队列信息,相当于 atq;
        -d #:删除作业号为 # 的作业,作业号可通过 -l 查看,相当于 atrm #;
        -c:查看具体的作业信息;
        -f:从指定的文件中读取任务内容;
        
    time:指定方式有如下几种:
        1、指定任务执行的时间点,格式为:HH:MM [YYYY-mm-dd];
        2、还可模糊指定,如:
                noon 表示正午 12 点;
                midnight 表示夜里 12 点;
                teatime 表示下午 4 点;
                tomorrow 表示明天;
        3、now+#{minutes|hours|days|weeks} 指定多久之后执行,如 at now+3minutes 表示 3 分钟之后执行;

作业的执行结果会以邮件的方式发送给相关用户。

例:我要设置一个任务在 21:44 分执行,任务要执行的命令如下:

echo hello zze

那么我可以执行如下命令:

[root@zzehost ~]# at 21:44
at> echo hello zze     
at> <EOT>
job 2 at Tue Dec 10 21:44:00 2019

在进入到 at 的提示符下输入完要执行的命令后,可通过 CTRL + D 结束输入,任务则创建成功。
当时间到 21:44 时,所指定任务的执行结果会通过邮件的方式发送给用户。

查看邮件:

image.png

空闲时执行计划-batch

batch 命令的作用是让系统自行选择空闲时间去执行此处指定的任务,不可指定时间点。
直接看示例:

[~]: echo "echo hello from batch" | batch
job 3 at Wed Dec 11 15:49:00 2019

该种方式很少使用,简单了解即可。

周期性任务计划-cron

周期性任务计划指的是一个作业需要反反复复执行 n 遍的,只要时间点满足设定的情况计划就会运行。
对 Linux 来讲,周期性任务计划是通过 cron 来实现的,相关的程序包可通过 rpm -qa | grep cron 查看:

[~]: rpm -qa | grep cron
cronie-1.4.11-19.el7.x86_64
cronie-anacron-1.4.11-19.el7.x86_64
crontabs-1.11-6.20121102git.el7.noarch
  • cronie:主程序包,提供了 crond 守护进程及相关辅助工具;
  • cronie-anacroncronie 的补充程序,用于监控cronie 任务的执行状况,如果 cronie 中的任务在过去该运行的时间点未能运行,则 anacron 会随后启动一次此任务;
  • crontabs:包含 CentOS 提供的系统维护任务;

crond 守护进程必须正常运行,其它定义的任务才能在指定时间点正常运行。

  • CentOS 6 可通过 service crond status 查看 crond 守护进程的状态;
  • CentOS 7 可通过 systemctl status crond 查看 crond 守护进程的状态;

计划要周期性执行的任务提交给 crond,由其来实现到点运行。
Linux 系统中有两类周期性任务:

  1. 系统 cron 任务(系统维护作业):通过编辑 /etc/crontab 配置文件实现;
  2. 用户 cron 任务:使用 crontab 命令将任务提交给 crond 守护进程;

系统cron任务

系统 cron 任务最终所编写的作业需要保存在 /etc/crontab 文件中,这个文件需要遵循特定格式,查看该文件:

image.png

在该文件注释中已经做了明了的说明,定义一个任务需要 7 列,每列所表示的含义如下(序号与列顺序对应):

  1. 分钟;
  2. 小时;
  3. 日;
  4. 月;
  5. 周几;
  6. user-name 的身份执行;
  7. 要执行的命令;

即通过这 7 列能指定一个命令在几月几日(或周几)的几点几分以谁的身份执行指定命令

编写要执行的命令时最好使用绝对路径,在 /etc/crontab 的第 3 行可以看到该文件导入的环境变量其实是很少的,如果使用相对路径且使用的命令不在 path 指定的路径下,就会出现到执行时间点执行时找不到命令的情况。

这些时间的指定还有特殊的时间表示法:

  1. 特定值:仅指定时间点执行;
  2. *:所有时间点执行;
  3. 离散取值:使用 , 分割,如在小时位使用 2,4,6 则表示在 2 点、4 点、6 点时执行;
  4. 连续取值:使用 - 分割,如在小时位使用 2-6 则表示在 2 点到 6 点执行;
  5. 在指定时间单位上定义步长:格式为 */#* 为时间范围,# 就是步长,如在分钟位使用 */2 则表示每 2 分钟执行,也可在指定时间范围内定义步长,如在分钟位使用 20-50/3 则表示在 20 到 50 分时每 3 分钟执行,要注意的是,该方式的步长要能被指定的时间点所整除才会准时执行;

示例

例 1 :每天晚上 9 点 10 分以 root 用户的身份运行 echo hello

10 21 * * *  root /usr/bin/echo hello

例 2 :每 3 小时在整点以 root 用户的身份运行 echo hello

0 */3 * * *  root /usr/bin/echo hello

用户cron任务

用户 cron 任务是用户通过 crontab 命令定义的,每个用户都有专用的 cron 任务文件 /var/spool/cron/<username>,而 crontab 命令实际上就是编辑该文件,并且带有语法检查功能。
使用格式如下:

crontab [-u user] [-l | -r | -e] [-i]
    -e:打开任务编辑窗口;
    -l:查看任务列表;
    -r:移除所有任务,如果要删除某一个任务直接通过 -e 在编辑窗口删除一行即可;
    -i:同 -r 一起使用,以交互式模式有选择地移除指定任务;
    -u user:仅 root 可用,为指定用户创建 cron 任务;

因用户 cron 任务也是定义在文件中,所以实际上也可以通过编辑文件来定义任务,但是不建议这样做,因为 crontab 命令创建任务时带有语法检查的功能,而直接编辑任务文件出错也不自知。

用户通过 crontab 命令创建任务时这个任务默认就使用该用户的身份运行任务,不需要指定以哪个用户的身份运行,任务文件的规则及列顺序与系统 cron 任务的文件定义相同,去除第 6 列用户身份即可。

示例

例 1 :每天晚上 9 点 10 分运行 echo hello
执行 crontab -e 打开编辑窗口(操作与 VIM 一致),输入以下内容保存即可:

10 21 * * * /usr/bin/echo hello

注意

  • 不管是系统 cron 任务还是用户 cron 任务的执行结果默认都是以邮件方式发送给相关用户,如果不希望发送邮件,则可使用 COMMAND > /dev/nullCOMMAND &> /dev/null 将输出信息重定向;
  • 对于 cron 任务来讲,% 有特殊用途,如果要在命令中使用 %,则需要转义(\%),也可以将 % 放置在单引号中则不需要转移;

练习

1、每 4 小时备份一次 /etc 目录至 /backup 目录中,保存的文件名称格式为 etc-yyyy-mm-dd-HH.tar.xz

[~]:  cat scripts/cron-tar.sh 
#!/bin/bash
#
#

t=`date +%Y-%m-%d-%H`
mkdir /backup/etc-$t
cp /etc/* /backup/etc-$t 
tar -c -f /backup/etc-"$t".tar /backup/etc-$t
xz /backup/etc-"$t".tar
rm -df /backup/ect-$t

[~]:  crontab -l
20 */4 * * * /usr/bin/bash /root/scripts/cron-tar.sh

2、每周 2,4,7 备份/ var/log/messages 文件至 /logs 目录中,文件名形如 messages-yyyymmdd

* * * * 2,4,7 /usr/bin/cp /var/log/messages /logs/messages-`date +%Y%m%d`

3、每两小时取出当前系统 /proc/meminfo 文件中以 SM 开头的信息追加至 /tmp/meminfo.txt 文件中。

[~]: touch /tmp/meminfo.txt
[~]: crontab -l
20 */2 * * * /usr/bin/grep "^[SM]" /proc/meminfo >> /tmp/meminfo.txt

4、工作日时间内,每小执行一次 ip addr show 命令。

0 * * * 1-5 /usr/sbin/ip addr show

Copyright: 采用 知识共享署名4.0 国际许可协议进行许可

Links: https://www.zze.xyz/archives/linux-base-53.html

Buy me a cup of coffee ☕.