Skip to content

在后台执行命令

https://www.ibm.com/developerworks/cn/linux/l-cn-nohup/

http://www.ruanyifeng.com/blog/2016/02/linux-daemon.html

如果不是后台进程,可按照以下步骤将进程变为作业:

  1. 按下Ctrl+Z挂起当前进程
  2. 使用jobs查看作业id
  3. 使用bg %id继续运行

下面这些方法使得在当前session断开后也能继续执行命令。

1. nohup 命令

nohup COMMAND [ARG]...

If standard input is a terminal, redirect it from /dev/null. If standard output is a terminal, append output to 'nohup.out' if possible, '$HOME/nohup.out' otherwise. If standard error is a terminal, redirect it to standard output. To save output to FILE, use 'nohup COMMAND > FILE'.

不支持 bash 内建的指令。

$ nohup ping baidu.com 2>&1 >ping.out &

2. setsid 命令

setsid [options] <program> [arguments ...]
[shark@linux ~]$ setsid ping baidu.com &
# 可以看到父id是1
[shark@linux ~]$ ps -ef | grep ping
shark     19124      1  0 15:05 ?        00:00:00 ping baidu.com

3. (\ &) 命令执行格式

[shark@linux ~]$ (ping baidu.com &)
# 与setsid原理相同
[shark@linux ~]$ ps -ef | grep ping
shark     19176      1  0 15:08 pts/0    00:00:00 ping baidu.com

4. disown 命令

适用于程序已经在执行的情况。这种方法的操作对象是作业。

 disown [-ar] [-h] [jobspec ...]
  • disown -h jobspec来使某个作业忽略HUP信号。
  • disown -ah来使所有的作业都忽略HUP信号。
  • disown -rh来使正在运行的作业忽略HUP信号。

使用过 disown 之后并且当前终端退出后,会将进程变为1进程的子进程,此时会将把目标作业从作业列表中移除,将不能再使用jobs来查看它,但是依然能够用ps -ef查找到它。

[shark@linux ~]$ ping baidu.com > ping.out &
[1] 19292
[shark@linux ~]$ jobs
[1]+  Running                 ping baidu.com > ping.out &
[shark@linux ~]$ ps -ef | grep ping
shark     19292  17782  0 15:26 pts/0    00:00:00 ping baidu.com
[shark@linux ~]$ disown -h %1
# 此时仍然是一个job
[shark@linux ~]$ jobs
[1]+  Running                 ping baidu.com > ping.out &
# 终端退出之后:
[shark@linux ~]$ ps -ef | grep ping
shark     19292      1  0 15:26 ?        00:00:00 ping baidu.com

5. screen 命令

适用于大批量操作。能够在一个真实终端下运行多个全屏的伪终端。

screen [ -options ] [ cmd [ args ] ]
screen -r [[pid.]tty[.host]]
screen -r sessionowner/[[pid.]tty[.host]]
  • screen -dmS session_name来建立一个处于断开模式下的会话(并指定其会话名)。
  • screen -list来列出所有会话。
  • screen -r session_name来重新连接指定会话。
  • 用快捷键CTRL-a d来暂时断开当前会话。

需要先安装:

$ yum install screen.x86_64