Linux 命令的後臺執行

weixin_33724059發表於2017-04-08

先來寫一個需要一直執行的程式,比如 Flask 版的 Hello World

$ vi hello.py
from flask import Flask

app = Flask(__name__)

@app.route('/')
def index():
    return '<h1>hello world<h1>'

if __name__ == '__main__':
    app.run(host='0.0.0.0')
$ pip install flask
$ python hello.py

啟動成功控制檯提示:

* Running on http://0.0.0.0:5000/ (Press CTRL+C to quit)

此時開啟瀏覽器訪問 http://你的伺服器ip:5000 即可看到 Hello World

CTRL+C 退出,如果想讓程式一直執行又想同時做其他事怎麼辦?

CTRL+Z 暫停程式

程式在前臺執行時,按下 CRTL+Z, 程式進入暫停狀態

[1]  + 74237 suspended  python hello.py

此時你又可以在終端下敲其他命令了。但重新整理瀏覽器,長時間沒有響應,因為程式進入暫停狀態了。

jobs 列出後臺執行的命令

$ jobs
[1]  - suspended  python hello.py

再來啟動一個命令,比如

$ tail -f hello.py

然後 CTRL+Z 暫停,再執行下 jobs 命令

$ jobs
[1]  - suspended  python hello.py
[2]  + suspended  tail -f hello.py

前面的[1] [2] 是任務編號,+ - 和接下來要說的 fgbg 命令有關,suspended 那一欄表示狀態,剩下的就是命令了

bg 將程式執行在後臺

直接打 bg 命令不加引數,執行的將是 jobs 列出的 第二列是 + 的那個程式

$ jobs
[1]  - suspended  python hello.py
[2]  + suspended  tail -f hello.py
$ bg
[2]  - 74616 continued  tail -f hello.py
$ jobs
[1]  + suspended  python hello.py
[2]  - running    tail -f hello.py

打了一次 bg 命令之後,原本是 + 的那個命令變成 running 了,同時 + 也移到了其他命令前面

$ bg
[1]  - 74237 continued  python hello.py
$ jobs
[1]  - running    python hello.py
[2]  + running    tail -f hello.py

此時看到 python hello.py 處於執行狀態,瀏覽器訪問 http://你的伺服器ip:5000 正常看到 hello world,但儘管程式已經在後臺執行了,終端還是有日誌輸出:

127.0.0.1 - - [08/Apr/2017 14:34:52] "GET / HTTP/1.1" 200 -

這對我們的其他工作造成了干擾,下面再討論怎麼解決這個問題。

bg 命令還可以新增引數任務

$ bg %1

% 號後面跟著的是 jobs 命令輸出的標號

fg 將後臺執行的程式調到前臺

fgbg 命令一樣,可以直接打 fg 將前面有 + 號的程式調到前臺,也可以以 %標號的形式指定哪個程式

$ fg %2

然後 CTRL+C 退出,或者 CTRL+Z 暫停,然後 bg %2 在後臺執行

使用 & 將程式放到後臺

要把一個程式放在後臺執行,照上面的做法,得先執行,然後 CTRL+Z 暫停,再用 bg 命令放到後臺執行。使用 & 來簡化這一過程,並且使用 > 來重定向後臺執行的程式在終端上的輸出。要繼續下面的操作,先用 fg 命令將

python hello.py

調到前臺,然後 CTRL+C 退出執行。

重新執行

$ python hello.py > hello.log 2>&1 &

上面這條命令,> hello.log 表示將 python hello.py 在螢幕上標準的輸出重定向到了 hello.log 這個檔案,2>&1 表示將錯誤資訊重定向到標準輸出,& 號表示在後臺執行。重新整理瀏覽器,正常看到 'hello word',終端沒有輸出。可以使用 tail 命令加上 -f 引數追蹤 hello.log 檔案的輸出

$ tail -f hello.log

多重新整理幾次瀏覽器,可以看到和之前那樣的日誌輸出。
要退出執行,同樣可以使用 fg 命令,然後 CTRL+C 退出。

nohup 命令的使用

使用 bg 命令和 & 後臺執行程式還有個缺點,你退出當前終端,程式也結束了。解決這一辦法的是使用 nohup 命令,例如

$ nohup python hello.py &

nohup 命令預設將輸出重定向到 nohup.out 這個檔案,可以使用 tail 命令跟蹤 nohup.out 這個檔案觀察程式的輸出

$ tail -f nohup.out

多重新整理幾次瀏覽器,可以看到和之前螢幕上一樣的輸出。退出當前終端,重新整理瀏覽器,還是能看到 'hello world'。
沒退出終端之前,可以使用 fg 命令將程式調到前臺,然後 CTRL+C 結束。如果已經退出當前終端,下次再登入進來,可以使用 ps aux 命令找出程式的 pid, 然後用 kill 命令結束。

相關文章