把脚本运行于后台 linux,linux – Bash:如何让脚本重新运行作为后台任务?

我正在编写一个旨在用作守护进程的Bash脚本.如果我的脚本的用户没有向脚本传递–sync选项,我希望脚本使用该选项将其自身重新运行为后台任务.这是我的代码(最后一部分是从this SO post被盗):

#!/usr/bin/env bash

args=("$@") # capture them here so we can use them if --sync's not passed

async=true

while [ $# -gt 0 ]

do

case "$1" in

--sync)

async=false

;;

# other options

esac

shift

done

# if --sync isn't passed, rerun the script as a background task

$async && exec nohup "${BASH_SOURCE[0]}" --sync "${args[@]}" 0 /dev/null &

出于某种原因,它似乎没有起作用.当我执行bash -x myscript(这有助于调试脚本)时,即使$async为true,它似乎仍然继续运行,我认为这不会发生,因为exec通常会停止执行.

同样,如果我从终端运行此命令:

exec nohup true 0 /dev/null &

尽管使用了exec,它也无法退出shell.为什么会这样,我该怎么做才能解决这个问题? (加分点:如果不创建子shell,有没有办法做到这一点?)

谢谢.

解决方法:

&正在应用于exec命令本身,所以exec foo&分叉一个新的异步子shell(或其等价物,见下文).子shell立即用foo替换自己.如果您希望父(也就是您的脚本)也终止,您需要使用exit命令显式地执行此操作.

这位高管可能不会在这里给你买任何东西. Bash非常聪明,实际上并没有为简单的后台命令启动子shell.所以它应该足够:

if $async; then

nohup "${BASH_SOURCE[0]}" --sync "${args[@]}" 0 /dev/null &

exit 0

fi

我不知道没有子shell的方法.但是当你编写shell脚本时,你会得到子shell.就个人而言,我只是使用一个简单的变量并使用if [[$async]]等测试它;而不是执行true或false,但由于这些也是bash内置的,它非常相同.在其他炮弹中,它们可以在子炮弹中运行.

现在我想到了,因为你无论如何都在重新处理异步执行中的所有选项,你可能只是在case语句中fork和exit,所以你根本不需要第二次检查:

case "$1" in

--sync)

nohup "${BASH_SOURCE[0]}" --sync "${args[@]}" 0 /dev/null &

exit 0

;;

标签:bash,shell,unix,linux,sh

来源: https://codeday.me/bug/20190623/1270145.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值