linux下定时任务计划的使用

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了linux下定时任务计划的使用相关的知识,希望对你有一定的参考价值。

一、定时任务之at实现;


PS本次操作以CentOS 7.5为实验环境;


1.1、at软件包说明

最小化安装,可能没有at或atq这个命令,at来自于软件包at,如果yum能用,直接:
yum -y install at

[[email protected] ~]# rpm -ql at
/etc/at.deny
/etc/pam.d/atd
/etc/sysconfig/atd
/usr/bin/at
/usr/bin/atq
/usr/bin/atrm
/usr/bin/batch
/usr/lib/systemd/system/atd.service
/usr/sbin/atd
/usr/sbin/atrun
/usr/share/doc/at-3.1.13
/usr/share/doc/at-3.1.13/ChangeLog
/usr/share/doc/at-3.1.13/Copyright
/usr/share/doc/at-3.1.13/Problems
/usr/share/doc/at-3.1.13/README
/usr/share/doc/at-3.1.13/timespec
/usr/share/man/man1/at.1.gz
/usr/share/man/man1/atq.1.gz
/usr/share/man/man1/atrm.1.gz
/usr/share/man/man1/batch.1.gz
/usr/share/man/man5/at.allow.5.gz
/usr/share/man/man5/at.deny.5.gz
/usr/share/man/man8/atd.8.gz
/usr/share/man/man8/atrun.8.gz
/var/spool/at
/var/spool/at/.SEQ
/var/spool/at/spool

要想运行at任务,必须要启动atd.service服务:
systemctl status atd.service   查看状态
systemctl start atd.service 启动atd服务;
systemctl enable atd.service 让atd服务器开机自动启动;

1.2、at和其他几个关联组件

at      executes commands at a specified time.
在指定的时刻执行命令;

atq     lists the user‘s pending jobs, unless the user is the superuser; in that case, everybody‘s jobs are listed.
          The format of the output lines (one for each job) is: Job number, date, hour, queue, and username.
atq用来操作用户追加的任务列表。如果是管理员查看,普通用户的任务列表也会被列出来。

atrm   deletes jobs, identified by their job number.
通过任务的编号来删除任务;

batch   executes commands when system load levels permit; in other words, when the load average 
            drops below 0.8,or the value specified in the invocation of atd.
batch会让系统自行选择在系统资源较空闲的时间去执行指定的任务;
用法和at一样,这里不介绍了,工作中一般at的用的比较少,我们的重心放在
后面要讲的cron上。

1.3、at的选项和介绍

常见的选项有:
-l:查看作业队列,相当于atq
-f /PATH/FROM/SOMEFILE:从指定文件中读取作业任务,而不用再交互式输入;
-d:删除指定的作业,相当于atrm;
-c:查看指定作业的具体内容;
-q QUEUE:指明队列;

注意:作业执行结果是以邮件发送给提交作业的用户;
at的作业有队列,用单个字母表示,默认都使用a队列;

at的语法结构为:
at  [OPTION]... TIME

TIME可以设定为以下的形式,非常灵活多变:
HH:MM [YYYY-mm-dd]
noon,midnight, teatime
tomorrow
now+#
    UNIT:minutes, hours, days, OR weeks
比如:
now +5minutes 表示任务将在5分钟后执行;
now +1hours 表示任务将在1小时候执行;
now + 31days 表示任务将在1个月后执行;
now +1weeks表示任务将在1周后执行;
12:32 表示任务将在今天的12:32分的时候执行;

[[email protected] ~]# at now+5minutes
at> cat /etc/fstab
at> <EOT>
job 2 at Sat Oct 27 06:21:00 2018
[[email protected] ~]# date
Sat Oct 27 06:17:03 CST 2018

<EOT> 部分是通过Ctrl +D来保存的;可以等5分钟后去查看邮件;
具体用法参见mail。

[[email protected] ~]# at now+5minutes
at> cat /etc/fstab
at> <EOT> 
job 3 at Sat Oct 27 06:25:00 2018
[[email protected] ~]# at -l
3   Sat Oct 27 06:25:00 2018 a root
[[email protected] ~]# at now+1weeks
at> mkdir -p /data/backup 
at> tar -zcvf /data/backup/var1.tar.gz /var/log &>/dev/null
at> <EOT>
job 4 at Sat Nov  3 06:20:00 2018
[[email protected] ~]# at -l
3   Sat Oct 27 06:25:00 2018 a root
4   Sat Nov  3 06:20:00 2018 a root
任务队列有两个,如果要查看详细内容,可以使用
at -c 任务编号
[[email protected] ~]# at -c 4
#!/bin/sh
...... 处理省略非常多的内容
${SHELL:-/bin/sh} << ‘marcinDELIMITER2d55ee54‘
mkdir -p /data/backup
tar -zcvf /data/backup/var1.tar.gz /var/log &>/dev/null

marcinDELIMITER2d55ee54
[[email protected] ~]# 
中间省略的部分,都是一些与环境有关的东西。
时间内容就是上边的部分;
[[email protected] ~]# at -d 4
[[email protected] ~]# at -l
3   Sat Oct 27 06:25:00 2018 a root
删除了任务编号4的任务。

二、定时任务之cron实现;

2.1、cron的软件包cronie

/etc/cron.d
/etc/cron.d/0hourly
/etc/cron.deny
/etc/pam.d/crond
/etc/sysconfig/crond
/usr/bin/crontab
/usr/lib/systemd/system/crond.service
/usr/sbin/crond
/usr/share/doc/cronie-1.4.11
/usr/share/doc/cronie-1.4.11/AUTHORS
/usr/share/doc/cronie-1.4.11/COPYING
/usr/share/doc/cronie-1.4.11/ChangeLog
/usr/share/doc/cronie-1.4.11/INSTALL
/usr/share/doc/cronie-1.4.11/README
/usr/share/man/man1/crontab.1.gz
/usr/share/man/man5/crontab.5.gz
/usr/share/man/man8/cron.8.gz
/usr/share/man/man8/crond.8.gz
/var/spool/cron

[[email protected] cron]# rpm -ql crontabs
/etc/cron.daily
/etc/cron.hourly
/etc/cron.monthly
/etc/cron.weekly
/etc/crontab
/etc/sysconfig/run-parts
/usr/bin/run-parts
/usr/share/man/man4/crontabs.4.gz
/usr/share/man/man4/run-parts.4.gz

最关键的是一个叫做crontab的命令,我们要书写的非系统定时任务就是通过此程序来编写的;
要保证crond.service服务有启动,cron定时任务才会生效:
systemctl status crond.service  查看crond服务状态;
systemctl enable crond.service  开机自动启动crond服务;
systemctl disable crond.service 开机禁止启动crond服务;
systemctl start crond.service   启动crond服务;
systemctl stop crond.service  停止crond服务;
 systemctl restart crond.service   重启crond服务;

 crontabs软件包提供了系统级别的定时任务的配置文件和一些初始状态的脚本,正常情况,我们不应该
 去动这些脚本。特别是系统默认自带的东西,不要去修改他们,如果一定要用系统的定时任务,无非
 是我们自己去按照规定去添加。

2.2、提交cron定时任务说明

向crond提交作业的方式不同于at,它需要使用专用的配置文件,此文件有固定格式,
不建议使用文本编辑器直接编辑此文件;要使用crontab命令;

cron任务分为两类:
1、系统cron任务
主要用来实现系统自身的维护;可以手动编辑修改/etc/crontab文件

2、用户cron任务
通过crontab命令(一个带有SUID权限的工具)增删改查;

2.3、系统定时任务配置文件

查看配置文件/etc/crontab
[[email protected] ~]# cat /etc/crontab
SHELL=/bin/bash
PATH=/sbin:/bin:/usr/sbin:/usr/bin
MAILTO=root

# For details see man 4 crontabs

# Example of job definition:
# .---------------- minute (0 - 59)
# |  .------------- hour (0 - 23)
# |  |  .---------- day of month (1 - 31)
# |  |  |  .------- month (1 - 12) OR jan,feb,mar,apr ...
# |  |  |  |  .---- day of week (0 - 6) (Sunday=0 or 7) OR sun,mon,tue,wed,thu,fri,sat
# |  |  |  |  |
# *  *  *  *  * user-name  command to be executed

说明:
1. 如果定义的cron任务有多个,每行写一个,共7个字段;字段分别为,
分 时 日 月 周 user-name表示用户名, 后边表示要执行的命令或脚本;
2. 由于这里的环境变量PATH定义的可选值与系统bash接口略有差别,这里范围更小,
所以建议,定义定时任务中用到的命令建议使用绝对路径,或者自定义PATH环境变量;
3. 执行结果邮件发送给MAILTO指定的用户

2.4、非系统(用户)定时任务配置文件

系统的cron配置为/var/spool/cron/USERNAME
其中USERNAME表示谁的定时任务,它的配置文件语法和系统配置文件语法差别不大,
SHELL=/bin/bash
PATH=/sbin:/bin:/usr/sbin:/usr/bin
MAILTO=root

# For details see man 4 crontabs

# Example of job definition:
# .---------------- minute (0 - 59)
# |  .------------- hour (0 - 23)
# |  |  .---------- day of month (1 - 31)
# |  |  |  .------- month (1 - 12) OR jan,feb,mar,apr ...
# |  |  |  |  .---- day of week (0 - 6) (Sunday=0 or 7) OR sun,mon,tue,wed,thu,fri,sat
# |  |  |  |  |
# *  *  *  *  *   command to be executed    

和系统配置文件查看不多,写定时任务的时候不必要指定用户了;
注意点:
1.每行定义一个cron任务,共6个字段;
2.此处的环境变量不同于用户登录后获得的环境,因此,建议命令使用绝对路径,或者自定义PATH环境变量;
3.邮件发送给当前用户;

2.5、crontab命令选项和说明

crontab的常建语法结构和选项:
crontab [-u user] [-l | -r | -e] [-i]

-e:编辑当前用户的或者指定用户的crontab,如果没有定时任务,会作为一个新的文件编辑,编辑默认是以vi编辑
器来编辑,可以通过显式设定VISUAL或EDITOR环境变量来修改使用指定的编辑器来编辑。一但编辑的crontab保
存退出后,crontab会自动被安装成定时任务计划。
比如:
export EDITOR="/usr/bin/nano" 或 export EDITOR="/usr/bin/emasc",然后再去crontab -e
nano和emacs都是文本编辑器,默认都是没有安装的,需要自己手动指定安装。
-l:列出当前用户或者指定用户的crontab到标准输出。
-r:移除当前用户或者指定用户的所有定时任务,即删除/var/spool/cron/USERNAME文件;(危险,没有交互式
操作提示)
-i:在使用-r选项移除所有任务时提示用户确认信息;
-u user:指定管理给定用户的crontab,只有超级管理员用户才能管理,普通用户不能使用此选项;

小技巧和注意事项:
1、如果不想把定时任务运行结果通知给指定用户
COMMAND > /dev/null  标准错误信息还是会以邮件的形式通知给用户;
COMMAND &> /dev/null 所有输出信息都不会以邮件的形式通知用户;
2.定义COMMAND时,如果命令需要用到%,需要对其转义;但放置于单引号中的%不用转义亦可;
3.某任务在指定的时间因关机未能执行,下次开机不会自动执行;
4.如果期望某时间因故未能按时执行,下次开机后无论是否到了相应时间点都要执行一次,可使用anacron实现;

2.6、crontab配置定时任务时候的时间表示

时间格式一共5位,分别对应:

* * * * *
分 时 日 月 周
分钟有效值:0 - 59;
时的有效值:0 - 23;
日的有效值: 1 - 31;
月的有效值:1 - 12 或 jan,feb,mar,apr,may,jun,jul,aug,sep,oct,nov,dec;
周的有效值:0 - 6 ,星期天可以用0或7表示,这个是个特例,也可以用周的英文缩写,
sun,mon,tue,wed,thu,fri,sat
  • 指定特定值
给定时间点有效取值范围内的值;
注意:day of week和day of month一般不同时使用;

例如:
3 * * * *:执行频率为 每小时执行一次;每小时的第3分钟执行;
3 4 * * 5:执行频率为 每周执行一次;每周5的4点3分执行;
5 6 7 * *:执行频率为 每月执行一次;每月的7号的6点5分执行;
7 8 9 10 *:执行频率为 每年执行一次;每年的10月9号8点7分执行;
  • 取所有值
给定时间点上有效取值范围内的所有值;表示"每xxx"的含义;
  • 离散取值
在时间点上使用逗号分隔的多个值;
x,y,z
例如:
0 8,20 * * 3,7:这种不建议;(出现了20号,又出现了每周3,周天);
9 8 * * 3,7:每周三和周日执行的8点9分执行;
  • 连续取值
在时间点上使用符号短破折号"-"连接开头和结束
x-y
例如:
0 9-18 * * 1-5:周1到周5,每天的9点到18点,执行;(假设上午9点上班,下午18点下班,双休,这就是
工作日执行要执行的任务)
  • 步长取值
在指定时间点上,定义步长:
/number :其中number表示步长;
指定的时间点不能被步长整除时,其意义将不复存在;
最小时间单位为"分钟",想要完成"秒"级别任务,需要额外借助于其他机制,例如
可以定义每分钟定时计划任务,再利用脚本实现在每分钟之内,循环执行多次;

例如:
*/5 * * * *:每5分钟执行一次;
* */1 * * *:每1小时执行一次;
* * */5 * *:每5天执行一次;
*/7 * * * *:这个并不完全是每7分钟执行一次,这种不整除的现象,不建议使用。

2.7、crontab权限控制相关

[[email protected] ~]# ls -ld /
dr-xr-xr-x. 17 root root 4096 Oct 16 18:53 /
[[email protected] ~]# ls -ld /var/spool/
drwxr-xr-x. 9 root root 90 Oct 27 05:55 /var/spool/
[[email protected] ~]# ls -ld /var/spool/cron
drwx------. 2 root root 19 Oct 27 10:59 /var/spool/cron
[[email protected] ~]# ls -l /var/spool/cron/
total 8
-rw------- 1 root   root   45 Oct 27 11:18 root
-rw------- 1 yanhui yanhui 15 Oct 27 10:21 yanhui
[[email protected] ~]# id yanhui
uid=1000(yanhui) gid=1000(yanhui) groups=1000(yanhui)
[[email protected] ~]# which crontab
/usr/bin/crontab
[[email protected] ~]# ls -l /usr/bin/crontab
-rwsr-xr-x. 1 root root 57536 Jul 30  2014 /usr/bin/crontab

1、首先"/"目录,普通用户有读和执行权限,所以普通用户能够查看"/"目录本身以及"/"目录下的展开(ls -l /);
2、/var 和/var/spool 目录,普通用户有读和执行权限,所以普通用户能查看目录本身以及其他的展开列表;
3、/var/spool/cron 这个目录,普通用户是没有任何权限的,所以普通用户无法查看和直接编辑;
4、为什么crontab,普通用户也可以在/var/spool/cron目录下写,是因为crontab命令有SUID权限;

如何对普通用户使用cron做限制?
 1、如果cron.allow存在
普通用户想要使用cron,必须配置用户名在配置文件/etc/cron.allow中(一行一个用户名);
/etc/cron.allow会影响/etc/cron.deny的因为,如果一个普通用户的用户名出现/etc/cron.allow和
/etc/cron.deny中,以/etc/cron.allow为主;
 2、如果cron.allow不存在且cron.deny文件存在
  普通用户想要使用cron,用户名不能出现在配置文件/etc/cron.allow中;
 3、cron.allow文件和cron.deny文件都存在
 如果两个配置文件都为空,表示只有管理员用户可以使用。其他情况,请参见第1种情形;

说明: 默认情况是cron.deny存在,你可以理解为黑名单(上边的第二种情况),/etc/cron.allow存在,你可以
理解为白名单,普通想要使用cron,就必须在/etc/cron.allow配置文件中添加用户名;管理员用户不受到
/etc/cron.allow以及/etc/cron.deny的影响。

提示不能使用:(crontab 不能用)
[[email protected] ~]$ crontab -e
You (yanhui) are not allowed to use this program (crontab)
See crontab(1) for more information
[[email protected] ~]$ crontab -l
You (yanhui) are not allowed to use this program (crontab)
See crontab(1) for more information

2.8、cron定时任务示例(以用户定时任务为主)

1、每12小时备份一次/etc目录至/backups目录中,保存文件 名称格式为“etc-yyyy-mm-dd-hh.tar.xz”
要添加的任务计划为:

* */12 * * *  /usr/bin/mkdir -p /backups  >/dev/null && /usr/bin/tar -JPcvf /backups/etc-`date ‘+%Y-%m-%d-%H‘`.tar.xz /etc >/dev/null
* 

2、每周2、4、7备份/var/log/secure文件至/logs目录中,文件名格式为“secure-yyyymmdd”;

要添加的任务计划为:

* * * * 2,4,7 /usr/bin/mkdir -p /logs >/dev/null && tar -JcvfP /logs/secure-`date +%Y%m%d`.tar.xz /var/log/secure >/dev/null

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

* */2 * * *  /usr/bin/grep -E ‘^(S|M)‘ /proc/meminfo >> /tmp/meminfo.txt

4、制定每周三凌晨三、五点10分执行某个脚本,输出当前时间,时间格式为 2017-12-28 10:00:00;

我的脚本内容为:
[[email protected] ~]# cat /var/tmp/print_dtime.sh
#! /bin/bash

PATH=$PATH:/bin:/sbin:/usr/bin:/usr/sbin:/usr/local/bin:/usr/local/sbin
LANG="en_US.UTF-8"
export PATH LANG
source /etc/profile
shopt -u expand_aliases  #关闭 bash alias 扩展

echo `date +‘%Y-%m-%d %H:%M:%S‘`
[[email protected] ~]# 

定时任务计划为:
10 3,5 * * 3 bash /var/tmp/print_dtime.sh

技术分享图片

技术分享图片

技术分享图片

以上是关于linux下定时任务计划的使用的主要内容,如果未能解决你的问题,请参考以下文章

Linux定时任务Crontab命令详解

[Linux之crond计划任务定时任务]

Linux定时任务Crontab命令

Linux定时任务之crontab

Linux定时任务Crontab命令详解

linux中的crondtab定时计划任务