GNU屏幕:在会话中启动命令而不更改窗口

时间:2012-06-23 22:06:07

标签: bash sh sysadmin gnu-screen

我们有一个有人值守的升级脚本,可以在我们管理的所有系统上同时启动apt-get update && apt-get upgrade。理想情况下,我们希望在屏幕会话中全部启动它们。当我这样做时:

文件:upgrade.sh


for host in $ALLHOSTS
do
    some_commands_which_take_considerable_time
    screen -X screen sh -c "ssh $host \"apt-get update && apt-get upgrade\""
done

$ screen ./upgrade.sh

,它可以工作,但是当会话中有新窗口到达时,它们会自动切换到。相反,我宁愿有一个固定活动窗口的版本,除非包含进程退出或我使用^A n手动切换。

如果有可能使用已退出的进程保留窗口,但将它们与具有活动进程的窗口分开,则获得积分。

3 个答案:

答案 0 :(得分:2)

您可以使用tmux执行此操作。例如:

# Start a session named "apt-get" and leave it running in the background.
tmux session-new -d -s apt-get

# Preserve windows with inactive processes.
tmux set-option -t apt-get set-remain-on-exit on

# Start a new window without switching to it. You can also do this from
# within a running tmux session, not just outside of it.
tmux new-window -d -t apt-get -n upgrade-$host \
     "ssh $host 'apt-get update && apt-get upgrade'"

请注意,您可以拥有多个具有相同名称的窗口,或者将-n标志的参数修改为唯一名称。 tmux应用程序不关心。

例如,您可以将每个窗口命名为“升级”,但这样会很难一目了然地识别您的SSH会话。相反,此示例将 host 变量的值(由for循环填充)附加到每个窗口名称。这样可以更轻松地导航或以编程方式关闭不再感兴趣的窗口。当您有大量未关闭的窗口显示已终止的进程时,这尤其有用。

总的来说,对于这类任务,语法比GNU屏幕更清晰,更直观,但您的里程可能会有所不同。

答案 1 :(得分:0)

W / r / t在子进程退出后保留窗口,一种可能是调用屏幕配置文件中的zombie命令,这要求您指定两个键盘字符来杀死或复活窗口, 分别。 E.g:

zombie KR

然后,K将终止其子进程已终止的窗口,而R将尝试在同一窗口中重新启动子进程。请注意,在僵尸窗口中,这些键是在顶层捕获的(即,不要在它们之前使用正常的屏幕控制字符前缀序列)。

为了防止自动切换到新创建的窗口,请尝试将您的屏幕调用更改为以下内容:

screen -X eval 'screen sh -c "ssh $host \"apt-get update && apt-get upgrade\""' 'other'

答案 2 :(得分:0)

感谢CodeGnome,我可能会选择tmux,因为我相信没有办法用屏幕做(这很不幸,真的!)。

更好地描述如何使用它:

#!/bin/sh

tmux new-session -d -s active
tmux new-session -d -s inactive
tmux set-option -t active set-remain-on-exit on

for host in $ALLHOSTS
do
    tmux new-window -d -t active: -n upgrade-$host "
        ./do_upgrade_stuff.sh $host
        tmux move-window -s active:upgrade-$host -t inactive:
    "
done