云网牛站
所在位置:首页 > Linux教程 > 在Linux系统下使用Systemd定时器的基础,附示例操作

在Linux系统下使用Systemd定时器的基础,附示例操作

2021-06-22 09:22:57作者:戴均力稿源:云网牛站

本文介绍用于调度任务的Systemd定时器(Systemd Timer),也是一篇在Linux系统下使用Systemd定时器的基础文章。将展示如何在Systemd中使用定时器在系统启动后并在此后重复运行任务。当前Systemd已经提供了一段时间的定时器,作为cron的替代品,该功能值得一看。

 

Cron vs anacron vs systemd

Cron可以安排任务以从几分钟到几个月或更长时间的运行。设置相对简单,只需要一个配置文件。虽然配置行有点深奥,不过一般用户也可以使用。

但是,如果您的系统在适当的执行时间发生时没有运行,则Cron会失败。

Anacron,克服了“系统未运行”的问题。它确保当您的系统再次处于活动状态时将执行任务。虽然它旨在供管理员使用,但某些系统为一般用户提供访问权限。

但是,执行的anacron频率可以不少于每天。

cron和anacron都存在执行上下文的一致性问题。必须注意任务运行时有效的环境与测试时使用的环境完全相同。必须提供相同的shell、环境变量和路径。这意味着测试和调试有时会很困难。

Systemd定时器提供了cron和anacron的最佳功能。允许调度到分钟粒度。确保任务将在系统再次运行时执行,即使它在预期的执行时间内关闭。可供所有用户使用。您可以在它将运行的环境中测试和调试执行。

但是配置比较复杂,至少需要两个配置文件。

如果您的cron和anacron配置很好地为您服务,那么可能没有理由改变。但systemd至少值得研究,因为它可以简化任何当前的cron /anacron解决方法。

参考: 在Linux系统下使用Crontab UI安全管理Cron定时任务

 

配置

Systemd定时器执行的函数至少需要两个文件。它们是“timer unit”和“service unit”。操作不仅仅是一个简单的命令,您还需要一个“job”文件或脚本来执行必要的功能。

定时器单元文件定义调度,而服务单元文件定义执行的任务。有关.timer单元的更多详细信息,请参阅“man systemd.timer”。有关服务单元的详细信息,请参见“man systemd.service”。

单元文件存在于多个位置(在手册页中列出)。然而,对于一般用户来说,最简单的位置可能是“~/.config/systemd/user”。请注意,此处的“user”是文字字符串“user”。

 

示例

这个示例是一个简单的例子,创建一个用户计划作业而不是系统计划作业(它将以root身份运行)。它将消息、日期和时间打印到文件中。

1、首先创建一个将执行任务的shell脚本。在本地“bin”目录中创建它,例如,在“~/bin/schedule-test.sh”。

要创建文件:

touch  ~/bin/schedule-test.sh

然后将以下内容添加到您刚刚创建的文件中:

#!/bin/sh

echo "This is only a test: $(date)" >> "$HOME/schedule-test-output.txt"

请记住使您的 shell 脚本可执行。

2、创建将调用上述脚本的.service单元。在“~/.config/systemd/user/schedule-test.service”位置创建目录和文件:

[Unit]

Description=A job to test the systemd scheduler

[Service]

Type=simple

ExecStart=/home/<user>/bin/schedule-test.sh

[Install]

WantedBy=default.target

请注意,<user>应该是您的@HOME地址,但单元文件路径名中的“user”实际上是字符串“user”。

ExecStart行应该提供一个没有变量的绝对地址。一个例外是,对于用户单位,您可以将“%h”替换为$HOME。换句话说,您可以使用:

ExecStart=%h/bin/schedule-test.sh

这仅用于用户单元文件使用。这对系统单元不利,因为“%h”在系统环境中运行时将始终返回“/root”。其他替换在“man systemd.unit”中的“SPECIFIERS”标题下找到。由于它超出了本文的范围,这就是我们现在需要了解的有关SPECIFIERS的全部内容。

3、创建一个.timer单元文件,它实际调度您刚刚创建的.service单元。在与.service文件“~/.config/systemd/user/schedule-test.timer”相同的位置创建它。请注意,文件名仅在扩展名上有所不同,即“.service”与“.timer”:

[Unit]

Description=Schedule a message every 1 minute

RefuseManualStart=no  # Allow manual starts

RefuseManualStop=no   # Allow manual stops

[Timer]

#Execute job if it missed a run due to machine being off

Persistent=true

#Run 120 seconds after boot for the first time

OnBootSec=120

#Run every 1 minute thereafter

OnUnitActiveSec=60

#File describing job to execute

Unit=schedule-test.service

[Install]

WantedBy=timers.target

请注意,.timer文件已使用“OnUnitActiveSec”来指定时间表。“OnCalendar”选项更加灵活。例如:

# run on the minute of every minute every hour of every day

 OnCalendar=*-*-* *:*:00

# run on the hour of every hour of every day

 OnCalendar=*-*-* *:00:00

# run every day

 OnCalendar=*-*-* 00:00:00

# run 11:12:13 of the first or fifth day of any month of the year

# 2012, but only if that day is a Thursday or Friday

 OnCalendar=Thu,Fri 2012-*-1,5 11:12:13

以下截图提供了有关“OnCalendar”的更多信息:

在Linux系统下使用Systemd定时器的基础,附示例操作

4、所有部分都已就位,但您应该进行测试以确保一切正常。首先,启用用户服务:

$ systemctl --user enable schedule-test.service

这应该会产生类似于以下内容的输出:

Created symlink /home/<user>/.config/systemd/user/default.target.wants/schedule-test.service → /home/<user>/.config/systemd/user/schedule-test.service.

现在对作业进行测试运行:

$ systemctl --user start schedule-test.service

检查您的输出文件($HOME/schedule-test-output.txt)以确保您的脚本是正确执行。因为我们还没有启动定时器,所以应该有一个条目。根据需要进行调试。如果您需要更改.service文件而不是它调用的shell脚本,请不要忘记再次启用该服务。

5、作业正常工作后,通过为您的服务启用和启动用户定时器来实时安排它:

$ systemctl --user enable schedule-test.timer

$ systemctl --user start schedule-test.timer

请注意,您已经在上面的步骤4中启动并启用了该服务,因此只需为其启用和启动定时器即可。

“enable”命令将导致类似以下的输出:

Created symlink /home/<user>/.config/systemd/user/timers.target.wants/schedule-test.timer → /home/<user>/.config/systemd/user/schedule-test.timer.

并且“start”只会让您返回到CLI提示符。

 

其他操作

您可以检查和监控服务。如果您收到来自服务单元的错误,下面的第一个命令特别有用:

$ systemctl --user status schedule-test

$ systemctl --user list-unit-files

手动停止服务:

$ systemctl --user stop schedule-test.service

永久停止和禁用定时器和服务,重新加载守护程序配置并重置任何失败通知:

$ systemctl --user stop schedule-test.timer

$ systemctl --user disable schedule-test.timer

$ systemctl --user stop schedule-test.service

$ systemctl --user disable schedule-test.service

$ systemctl --user daemon-reload

$ systemctl --user reset-failed

 

概括

本文引导您使用Systemd定时器,但是,Systemd的内容远不止此处介绍的内容,它仅为您提供构建的基础。

 

相关主题

在Linux系统上使用Cron调度系统命令

精选文章
热门文章