日常工作中,经常需要跑一个很重要的程序,在有些时候有的程序要跑好几个小时,甚至几天,乃至需要一直需要运行下去,这个时候,如果我们关闭终端(xshell、SecureCRT等),或者网络连接不好或者其他原因,那么这个程序就会中断了。这种情况肯定不愿意看到,我们希望即使终端关闭了,程序依然可以跑。那么这时候就要用到 nohup 命令了。
nohup命令是no hangup 的缩写,这里指的是程序不退出。这个命令会让程序忽略hup信号,保证程序能够正常运行。
hup信号是什么呢?
在 Unix 的早期版本中,每个终端都会通过 modem 和系统通讯。当用户 logout 时,modem 就会挂断(hang up)电话。同理,当 modem 断开连接时,就会给终端发送 hangup 信号来通知其关闭所有子进程。
那怎么解决呢?
我们知道,当用户注销(logout)或者网络断开时,终端会收到Linux HUP信号(hangup)信号从而关闭其所有子进程。因此,我们的解决办法就有两种途径:要么让进程忽略Linux HUP信号,要么让进程运行在新的会话里从而成为不属于此终端的子进程。
这时候 本文的主角 nohup就出现了。
nohup命令基本语法
nohup 命令的基本语法如下:
# nohup command
或者:
# nohup command &
当这个程序进行起来之后,这个程序对应的 log 输出及其错误日志都将被记录在 nohup.out 文件里,这个文件一般位于当前目录
重定向程序的输出
如果你不想把程序的输出保存当前目录,我想保存在我指定的路径,并且自定义文件名,要怎么操作?这时我们就可以使用重定向操作 > 。
现在我有一个监控服务的脚本 monitor_service.sh 我想把它的输出日志保存在/www/logs 目录下 文件名就用脚本的名字monitor_service.log 可以如下运行脚本:
# nohup ./monitor_service.sh > /www/logs/monitor_service.log
使用nohup命令后台启动一个程序
如果想让程序在后台运行,可以加上 & 符号。但这样运行之后,程序就无影无踪了。想要让程序重新回到终端,可以使用 fg 命令。
这个命令的输出 log 将保存在 nohup.out 文件里,你可以使用 cat 或其它命令查看。第二行里 31031 这个数字代表这个命令对应的进程号,也就是 pid 。我们可以使用 ps 命令来找到这个进程。
使用nohup同时运行多个程序
如果你需要同时跑多个程序,没必要一个个运行,直接使用 && 符号即可。比如,你想同时跑 mkdir ,ls 三个命令,可以这样运行:
# nohup bash -c 'mkdir shell && ls'
终止跑在后台的进程
上面有提到,nohup 命令结合 & 符号可以使进程在后台运行,即使关闭了终端依然不受影响。这时,如果想要终止这个进程,要怎么操作呢?
最简单的当属 kill 命令,相信大家用过很多次了
# kill -9 PID
那要如何找到进程对应的 pid 呢?我们可以使用 ps 命令。
# ps -ef | grep monitor_service.sh
或者:
# ps aux | grep monitor_service.sh
或者使用pgrep命令也是可以的。
下边就直接使用 kill 命令就可以终止该进程了。
# kill -9 3381
如果想要得到更多关于nohup的用法介绍,可以查看他的帮助页面
# nohup --help
如果想要查看nohup的版本
# nohup --version