【问题标题】:Bash Script Not Executing in Cron CorrectlyBash 脚本未在 Cron 中正确执行
【发布时间】:2025-12-21 16:55:11
【问题描述】:

所以,我有一个 bash 脚本,它应该每小时将 ifconfig 的输出通过管道传输到一个文本文件。很多人似乎都遇到过,这个脚本在被 cron 使用时不能正常运行。但是,我看到的大多数修复方法似乎不适用于我的情况。我已经明确说明了所有路径,脚本具有执行权限,并且 cron 文件末尾有一个换行符。

创意十足,我的脚本 ip.sh 包含:

ifconfig > /home/drake/Dropbox/maintenance_scripts/ip.txt

cron 条目是:

0 * * * *   /home/drake/Dropbox/maintenance_scripts/ip.sh

(我让它每分钟运行一次以进行调试)

这里的大问题是,当它运行并且确实运行时,它会清除 ip.txt 中可能包含的任何内容。另外,我还有另一个脚本,它在正常运行时间上做同样的事情,而且它没有任何问题,只是被混淆了。我也试过>>,这似乎产生了相同的结果

那么,有没有人知道为什么一个脚本可以按预期运行,而另一个脚本会像这样运行?

这是在我的 Ubuntu 服务器上运行的。我正在使用 Dropbox 来同步文本文件

【问题讨论】:

    标签: bash ubuntu cron execution


    【解决方案1】:

    ip.sh 脚本应该在每次运行时删除ip.txt 文件;然后由ifconfig 程序重新填充它。所以,你的问题是 ifconfig 没有这样做。

    cron 运行的常见问题是环境。请注意,当cron 运行命令时,不会使用配置文件。

    在这种情况下,我认为cron 下的 PATH 设置不包括 ifconfig 所在的目录(所以 /sbin 不在 PATH 上)。明显的解决方法:

    • /sbin/ifconfig ...
    • export PATH=$PATH:/sbin; ifconfig ...

    我认为简单地从crontab 文件运行脚本通常是开展业务的最佳方式。在不更改crontab 设置的情况下,您可以添加调试代码、更改环境设置,或者随意修改。在crontab 文件中摆弄复杂的命令行迟早会在某些系统或其他系统上遇到麻烦。所以我认为你的系统是明智的——我在自己的cron-run 脚本中使用了一个更复杂的系统,但是有很多共性。关键是 crontab 条目很简单,而运行的脚本隐藏了复杂性。

    【讨论】:

      【解决方案2】:

      您的脚本顶部应该有一个“shebang”行:

      #!/bin/sh
      

      虽然这不是绝对必需的。

      脚本会覆盖ip.txt,因为您告诉它这样做。这就是> 重定向操作符所做的。如果要附加到文件末尾,请使用>>。 (你说你试过了,结果相同。我怀疑这是真的。我怀疑 cron 作业没有产生任何输出,所以它没有向文件附加任何内容。)

      但是你不需要一个单独的脚本来做重定向;您可以在 cron 作业本身中使用 >>>

      0 * * * *    ifconfig >> /home/drake/Dropbox/maintenance_scripts/ip.txt
      

      至少在我的系统上,cron 作业的默认$PATH/usr/bin:/bin,但ifconfig/sbin/ifconfig。尝试which ifconfigtype ifconfig 来查看ifconfig 在您的系统上的位置(我们都使用Ubuntu,所以可能相同),并在cron 作业中使用完整路径;例如:

      0 * * * *    /sbin/ifconfig >> /home/drake/Dropbox/maintenance_scripts/ip.txt
      

      如果您想查看何时输出更改(我想这就是您要检查的内容),添加时间戳很容易:

      0 * * * *    ( date ; /sbin/ifconfig ) >> /home/drake/Dropbox/maintenance_scripts/ip.txt
      

      【讨论】:

      • 啊,我知道它必须是这样的。它实际上驻留在 /sbin/ 中,并将其更改为 /sbin/ifconfig 设置正确。
      • 您可以通过单击旁边的复选标记图标将答案视为正确答案。一旦您获得 15 个声望点(应该不会花很长时间),如果您愿意,也可以对一个或多个答案进行投票。
      【解决方案3】:

      试试这个,它对我来说是从 cron 开始的。 请注意,ifconfig 输出可能会因 Linux 发行版而异,因此您可能需要调整 awk 选择。

      # Cron ifconfig piping is broken
      eth0ipIC=`/sbin/ifconfig eth0`
      eth0ip=`echo $eth0ipIC|awk '{print $7}'|awk -F: '{print $2}'`
      

      【讨论】: