Gnome-Terminal
gnome-terminal - 執行具有暫停功能的命令
我有一個應用程序啟動器,它使用 – 選項在 gnome-terminal 中執行命令,但是每當我進入終端並嘗試 crtl-z 嘗試掛起命令並將其移動到後台時,什麼都沒有發生。我的搜尋發現了一堆關於在 bash 中啟動互動式 shell 的文章,但我在那裡嘗試過的也沒有任何效果。有沒有辦法啟動 gnome-terminal 並執行一個命令,讓我能夠暫停命令並稍後顯示提示?
bash_in_gnome_terminal(){ local IFS printf -v cmd %q ". ~/.bashrc; set -m; $*" gnome-terminal -- bash -c "bash --rcfile <(echo $cmd)" } bash_in_gnome_terminal tail -f ~/.xsession-errors bash_in_gnome_terminal 'grep -r pattern dir | less'
由於該
gnome-terminal
命令實際上呼叫“終端伺服器”以生成終端實例,並且您無法將文件描述符傳遞給其中執行的程序,因此該解決方案很複雜(並且被削弱了!)。使用其他終端
xterm
或mlterm
解決方案更簡單,功能更強大:bash_in_xterm(){ local IFS xterm -e bash --rcfile <(printf '. ~/.bashrc; set -m; %s\n' "$*") }
此外,如果 bash 可以選擇在互動式 shell(如
vi +'cmd'
)之前執行一些命令,而無需像--rcfile <(...)
. 也許它甚至有 - 但我無法弄清楚;-)之所以需要,
set -m
是因為 bash 在監視模式關閉^Z
的情況下獲取初始化文件,即沒有作業控制和使用,fg
,bg
等的可能性。如果您希望在啟動命令退出時退出 shell 並關閉終端,可以像這樣修改函式
$$ assumes a recent version of bash $$:
bash_in_gnome_terminal(){ local IFS set -- 'sigchld(){ local j="\j"; ((${j@P})) || exit; }; trap sigchld CHLD;' "$@" printf -v cmd %q ". ~/.bashrc; set -m; $*" gnome-terminal -- bash -c "bash --rcfile <(echo $cmd)" }
該
${var@P}
表單擴展 中的任何提示轉義var
,並且\j
提示轉義擴展為作業數。因此,如果沒有更多作業,j="\j"; ((${j@P})) || exit
從陷阱呼叫的將退出 shell。CHLD
在不支持
${var@P}
擴展形式的舊版本 bash 中,必須使用更笨重的 kludge:set -- 'sigchld(){ trap - CHLD; test "$(jobs -p)" || exit; trap sigchld CHLD; }; trap sigchld CHLD;' "$@"
這裡
CHLD
必須禁用陷阱然後重新啟用,否則$(jobs -p)
命令替換將遞歸觸發它。這整個事情可以做成一個獨立的腳本而不是一個函式:
#! /bin/bash # uncomment and edit the following line accordingly # set -- <fixed command and arguments> "$@" # this only works in bash >= 4.4 # set -- 'sigchld(){ local j="\j"; ((${j@P})) || exit; }; trap sigchld CHLD;' "$@" set -- 'sigchld(){ trap - CHLD; test "$(jobs -p)" || exit; trap sigchld CHLD; }; trap sigchld CHLD;' "$@" printf -v cmd %q ". ~/.bashrc; set -m; $*" gnome-terminal -- bash -c "bash --rcfile <(echo $cmd)"