如何调试涉及 netcat 的失败的 cron 作业?

如何调试涉及 netcat 的失败的 cron 作业?

使用 crontab 在两台机器上调度 netcat 命令的想法是在这个问题但受访者们都反驳了提问者并转而谈论scp

假设我好的考虑到这些影响,我该如何找到这个设置出了什么问题?出于测试目的,我在当地时间 13:45 同步了这两个作业。两台计算机都位于同一本地时区。

目标 crontab:

45 13 * * * nc -l -p 1234 > /path/to/backup-$(date +%F).tar.bz2

源crontab:

45 13 * * * /path/to/backup_script.sh

源备份脚本:

sleep 5  # to ensure the destination is already listening
tar -cvpj --exclude-vcs /path/to/source/files | nc -N dest 1234

就其本身而言(在 crontab 之外),listen 命令和备份脚本可以工作。据我了解,目标在收到 EOF 之前不会停止监听。但是,监听端似乎没有在应该监听的时候监听。我可以手动启动它监听,源的计划作业将发送文件,但我无法让目标在指定的时间监听。

答案1

crontab命令 ( man -a crontab) 不是bash。命令中不提供重定向和命令替换crontab

将所需的命令包装在bash脚本中,以 开头#!/bin/bash,然后从条目中调用该脚本crontab

答案2

如 中所述man 5 crontab,该%字符在 crontab 中很特殊,必须进行转义

                                         Percent-signs (%) in the command,
   unless escaped with backslash (\), will be changed into newline charac‐
   ters,  and  all  data  after the first % will be sent to the command as
   standard input. There is no way to split a  single  command  line  onto
   multiple lines, like the shell's trailing "\".

因此你的命令需要写成

45 13 * * * nc -l -p 1234 > /path/to/backup-$(date +\%F).tar.bz2

否则,%将被视为行尾字符,并且传递给 shell 的命令将被截断,nc -l -p 1234 > /path/to/backup-$(date +这显然是一个语法错误。


注意:由于问题是“如何调试”,您可以通过查看 cron 服务 ex 的日志条目来诊断。

journalctl -xeu cron | grep CMD

您可能会注意到命令被截断了。


尽管 crontab 文件本身不是 shell 脚本,但每个 crontab 条目的命令部分传递给 shell。再次来自man 5 crontab

   The  entire  command  portion  of the line, up to a newline or %
   character, will be executed by /bin/sh or by the shell specified in the
   SHELL  variable of the crontab file.  

因为默认值是/bin/sh,所以它将接受任何 POSIX shell 功能,包括重定向(例如)< > >>以及命令替换构造。除非您适当地更改 ,否则$(...)它将无法使用 bash 特定的重定向(例如)。因此,虽然将您的命令移到单独的 shell 脚本中可以修复失败,但这只是因为它将字符移到了crontab 之外。&>SHELL%

相关内容