【问题标题】:Execute bash script from url via cron通过 cron 从 url 执行 bash 脚本
【发布时间】:2023-03-06 20:51:01
【问题描述】:

我正在尝试让云服务器(从我保存的图像构建)在启动时从 URL 执行脚本,但该脚本未正确执行。

我使用来自Execute bash script from URL 的答案之一来配置 curl 脚本,并通过 crontab (Ubuntu 14.04) 中的 @reboot 指令执行该脚本。我的设置如下所示:

脚本包含以下命令:

user@cloud-server-01:~$ cat startup.sh
#! /bin/sh
/usr/bin/curl -s http://192.168.100.59/user/startup.sh.txt | bash /dev/stdin

我通过 crontab 调用脚本:

user@cloud-server-01:~$ crontab -l
@reboot /home/user/startup.sh > startup.log 2>&1 &

如果我使用完全相同的命令从命令行手动执行脚本,它工作正常。但是,在启动时由 crontab 执行,它似乎挂起,我看到以下进程正在运行:

user@cloud-server-01:~$ ps ux
USER       PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
user      1287  0.0  0.1   4444   632 ?        S    19:17   0:00 /bin/sh /home/user/startup.sh
user      1290  0.0  0.7  89536  3536 ?        S    19:17   0:00 /usr/bin/curl -s http://192.168.100.59/user/startup.sh.txt
user      1291  0.0  0.2  12632  1196 ?        S    19:17   0:00 bash /dev/stdin

我是否遗漏了一些明显的东西,为什么 cron 执行没有给我与命令行相同的结果?

编辑:

感谢 Olof 重定向我的故障排除。事实上,curl 正在执行,如果我等待足够长的时间(几分钟),它似乎可以按需要运行。我怀疑问题是最初调用 curl 时网络接口和/或 URL 不可用,虽然它可能会轮询连接,但它可能会退回其轮询间隔。所以现在的问题变成了,“我如何在调用 curl 之前检查我是否与这个 URL 建立了连接?”

【问题讨论】:

    标签: bash curl cron


    【解决方案1】:

    这不是 bash 问题;您的 curl 命令仍在运行,因此 bash 仍在运行,等待 curl 关闭 bash shell 正在读取的管道。

    为了解决你的 curl 调用问题,我会先运行它而不用管道连接到 bash 来检查我是否得到了预期的输出。

    【讨论】:

    • 类似bash <(/usr/bin/curl -s http://192.168.100.59/user/startup.sh.txt) ???
    • @Jord,这相当于问题中使用不同(仅限现代外壳)语法的调用。 OP 使用 /bin/sh 来调用 curl 并且可能无法处理该语法。
    • @Olof,感谢您提供有关查看位置的提示。我通过将 60 秒的睡眠时间放入脚本中,让网络有机会进行设置,从而使其正常工作。仍在寻找更好的方法来在我自己的脚本中轮询网络连接。
    • 我的荣幸,@DanielWiddis。检查是否有响应是一个不错的主意。我不会为 check_online 设置全局变量和打印字符串而烦恼。类似:while ! nc -z $HOST 80 > /dev/null 2>&1; do sleep 5; done 就足够了,恕我直言。
    • 甜蜜。我会试试的。我对 bash 语法不是很熟悉,所以我从互联网上的其他地方大量窃取!
    【解决方案2】:

    Olof's answer 中的提示让我到达了那里,但为了完整起见,我将完整的结果发布在这里:

    由于云提供商的脚本在重新启动后需要 20-40 秒,当我第一次执行 cron 时,我想要的连接 IP 不可用。它要么超时,要么在显着延迟后连接。我已经修改了我的连接脚本以轮询连接,直到它在调用 curl 之前可用:

    #! /bin/bash
    PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
    HOST_IP=192.168.100.59
    
    check_online() {
        IS_ONLINE=$(netcat -z -w 5 $HOST_IP 80 && echo 1 || echo 0)
    }
    
    # Initial check to see if we're online
    check_online
    
    # Loop while we're not online.
    while [ $IS_ONLINE -eq 0 ];do
        # We're offline. Sleep for a bit, then check again
        sleep 5;
        check_online
    done
    
    # Run remote script
    bash <(curl -s http://${HOST_IP}/user/startup.sh.txt)
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-08-09
      • 2016-10-01
      • 2020-08-16
      • 2020-05-12
      • 1970-01-01
      • 2018-08-23
      相关资源
      最近更新 更多