Abhijeet Viswam Asked: 2022-03-07 23:51:54 +0800 CST2022-03-07 23:51:54 +0800 CST 2022-03-07 23:51:54 +0800 CST 如何自动将 tmux 窗口重命名为别名命令 772 我已经设置了多个别名来 ssh 到不同的服务器 alias sa="ssh user1@server1" alias sb="ssh user2@server2" alias sc="ssh user3@server3" 当我从 tmux 运行这些命令时,所有窗口都重命名为ssh, 而不是sa, sb, sc。如何让别名显示为窗口名称而不是实际的进程名称? 编辑:使用 macOS 12.2.1、tmux 3.2a、zsh 5.8 zsh tmux 1 个回答 Voted Best Answer Kamil Maciorowski 2022-03-08T03:40:46+08:002022-03-08T03:40:46+08:00 初步说明 分析的某些部分(如下)主要适用于 Linux。 该解决方案已在 Kubuntu 21.10 中测试并发布。直到那时 OP 才透露他们正在使用 macOS;事实证明,该解决方案在 macOS 中不起作用。 我决定不删除答案(还),但请注意它可能会或可能不会在非 Linux 操作系统中工作。 tl;博士 alias sa='bash -c '\''exec -a "$0" ssh user1@server1 "$@"'\'' sa' 或者更好(?)(unalias sa首先,如果需要): sa() { bash -c 'exec -a "$0" ssh user1@server1 "$@"' sa "$@" } 分析——你可以做什么tmux tmux默认情况下,根据在活动窗格中运行的可执行文件更改窗口的名称。这由automatic-rename选项控制: automatic-rename [on | off] 控制自动窗口重命名。启用此设置后,tmux将使用指定的格式自动重命名窗口automatic-rename-format。new-window如果在创建时使用或指定名称new-session,或稍后使用rename-window或使用终端转义序列指定名称,则此标志会自动为单个窗口禁用。[…] 我假设您希望此设置保持启用状态。 您可以按需重命名窗口 ( ) 并在调用之前或之后tmux rename-window sa重新启用设置 ( ) 。但:tmux set-option -w automatic-rename onssh 如果之前ssh是 ,则在同一个窗口中选择另一个窗格将automatic-rename完成它的工作(您可能期望这样做),但选择返回窗格ssh会将窗口重命名为ssh,而不是sa; 如果 after ssh,则在同一窗口中选择另一个窗格(在ssh完成之前)不会重命名窗口。 可能还有其他缺点;两种方法都不是完美的。另请注意,如果您set-option -w automatic-rename在多个窗格中使用,则一个窗格中的命令可能会以tmux不同于另一窗格尝试强加的方式配置窗口。来回更改设置不是一个好的解决方案。 一个好的解决方案会自动tmux设置sa为标题。我们需要一种方法来告诉tmux使用字符串sa而不是ssh. 为此,我们需要了解如何tmux知道ssh您正在运行。 分析——tmux知道的 tmux为你的 shell 提供一个终端。当 shell 生成时,shell 通过将进程组设置为前台进程组ssh,将自己置于后台。ssh退出时ssh,作为父进程的 shell 做出反应,通过将其进程组设置为前台,将自己置于前台。这种“杂耍”的主要目的是使作业控制工作(带有stdin的后台进程仍然连接到终端,以防万一fg他们;但在他们的进程组成为前台进程组之前无法“窃取”输入)。 (或另一个进程)知道前台可执行文件名称的能力tmux只是这种机制的一个有用的副作用。知道它提供的终端的前台进程组,tmux可以找到作为组长的进程并自动调整标题。 shell 不会直接通知tmux正在执行的命令。如果是这种情况,一个足够聪明的 shell 可以通过sa而不是ssh. 您的 shell 决定哪个进程组(以及何时)成为与终端关联的前台进程组(在tmux上下文中:窗格)。通过监视这一点,tmux可以在窗格中找到前台进程。 别名不是进程。您的每个别名都运行一个名为ssh. tmux无法知道您使用的别名。这就是为什么您的窗口被重命名为ssh,无论您使用哪个别名。 解决方案 事实证明,真正重要的并不是前台可执行文件的名称tmux。重要的是您可以看到的字符串作为/proc/PID/cmdline. 通常(按照惯例)它是可执行文件的路径或其名称;但它几乎可以是任何东西。 有多种方法可以运行ssh(或其他)并指定自定义字符串。请参阅设置线程/proc/PID/cmdline。在 Bashexec -a …中可以做到这一点。但是不要直接从您的交互式 shell 调用它,因为exec它将用您想要运行的任何内容替换shell。bash因此,您需要一个将被替换的额外内容。例子: bash -c 'exec -a "foo" sleep 300' 上面在 shell 中调用的命令tmux会将tmux窗口重命名为foo(如果automatic-rename是on; 你可能需要等待几秒钟)。 使用此方法的基本别名是: alias sa='bash -c "exec -a sa ssh user1@server1"' 我注意到您的别名与其他参数配合得很好。我的意思是,例如,您的sa sleep 30扩展是在服务器上ssh user1@server1 sleep 30运行的理智命令。sleep 30我们的别名还不支持这一点。这是修复: alias sa='bash -c '\''exec -a sa ssh user1@server1 "$@"'\'' whatever' 哪里whatever像第二个sh什么是第二个 sh in sh -c 'some shell code' sh?我个人更喜欢传递所需的名称而不是whatever: alias sa='bash -c '\''exec -a sa ssh user1@server1 "$@"'\'' sa' 或者也许(见DRY): alias sa='bash -c '\''exec -a "$0" ssh user1@server1 "$@"'\'' sa' 注意sa结尾附近的别名不需要匹配名称。在这里它匹配,因为你想要这个。 别名有些复杂。它有效,但它超出了别名的用途。等效函数可能被认为更优雅。这是功能(unalias sa首先,如果需要): sa() { bash -c 'exec -a "$0" ssh user1@server1 "$@"' sa "$@" } 笔记 exec -a不可移植,它在 Bash 中有效,在 pure 中无效sh。别名本身(或函数本身)在任何类似 POSIX 的 shell 中仍然有效。bash无论您的主 shell 是什么,它都会显式调用。 还有其他工具可以读取/proc/PID/cmdline或等效信息。我们的解决方案可能会误导他们或使用它们的用户。例如将在列中ps -eo pid,comm,command打印,但在列中。sshcommsacommand
初步说明
tl;博士
或者更好(?)(
unalias sa
首先,如果需要):分析——你可以做什么
tmux
tmux
默认情况下,根据在活动窗格中运行的可执行文件更改窗口的名称。这由automatic-rename
选项控制:我假设您希望此设置保持启用状态。
您可以按需重命名窗口 ( ) 并在调用之前或之后
tmux rename-window sa
重新启用设置 ( ) 。但:tmux set-option -w automatic-rename on
ssh
ssh
是 ,则在同一个窗口中选择另一个窗格将automatic-rename
完成它的工作(您可能期望这样做),但选择返回窗格ssh
会将窗口重命名为ssh
,而不是sa
;ssh
,则在同一窗口中选择另一个窗格(在ssh
完成之前)不会重命名窗口。可能还有其他缺点;两种方法都不是完美的。另请注意,如果您
set-option -w automatic-rename
在多个窗格中使用,则一个窗格中的命令可能会以tmux
不同于另一窗格尝试强加的方式配置窗口。来回更改设置不是一个好的解决方案。一个好的解决方案会自动
tmux
设置sa
为标题。我们需要一种方法来告诉tmux
使用字符串sa
而不是ssh
. 为此,我们需要了解如何tmux
知道ssh
您正在运行。分析——
tmux
知道的tmux
为你的 shell 提供一个终端。当 shell 生成时,shell 通过将进程组设置为前台进程组ssh
,将自己置于后台。ssh
退出时ssh
,作为父进程的 shell 做出反应,通过将其进程组设置为前台,将自己置于前台。这种“杂耍”的主要目的是使作业控制工作(带有stdin的后台进程仍然连接到终端,以防万一fg
他们;但在他们的进程组成为前台进程组之前无法“窃取”输入)。(或另一个进程)知道前台可执行文件名称的能力
tmux
只是这种机制的一个有用的副作用。知道它提供的终端的前台进程组,tmux
可以找到作为组长的进程并自动调整标题。shell 不会直接通知
tmux
正在执行的命令。如果是这种情况,一个足够聪明的 shell 可以通过sa
而不是ssh
. 您的 shell 决定哪个进程组(以及何时)成为与终端关联的前台进程组(在tmux
上下文中:窗格)。通过监视这一点,tmux
可以在窗格中找到前台进程。别名不是进程。您的每个别名都运行一个名为
ssh
.tmux
无法知道您使用的别名。这就是为什么您的窗口被重命名为ssh
,无论您使用哪个别名。解决方案
事实证明,真正重要的并不是前台可执行文件的名称
tmux
。重要的是您可以看到的字符串作为/proc/PID/cmdline
. 通常(按照惯例)它是可执行文件的路径或其名称;但它几乎可以是任何东西。有多种方法可以运行
ssh
(或其他)并指定自定义字符串。请参阅设置线程/proc/PID/cmdline
。在 Bashexec -a …
中可以做到这一点。但是不要直接从您的交互式 shell 调用它,因为exec
它将用您想要运行的任何内容替换shell。bash
因此,您需要一个将被替换的额外内容。例子:上面在 shell 中调用的命令
tmux
会将tmux
窗口重命名为foo
(如果automatic-rename
是on
; 你可能需要等待几秒钟)。使用此方法的基本别名是:
我注意到您的别名与其他参数配合得很好。我的意思是,例如,您的
sa sleep 30
扩展是在服务器上ssh user1@server1 sleep 30
运行的理智命令。sleep 30
我们的别名还不支持这一点。这是修复:哪里
whatever
像第二个sh
什么是第二个 sh insh -c 'some shell code' sh
?我个人更喜欢传递所需的名称而不是whatever
:或者也许(见DRY):
注意
sa
结尾附近的别名不需要匹配名称。在这里它匹配,因为你想要这个。别名有些复杂。它有效,但它超出了别名的用途。等效函数可能被认为更优雅。这是功能(
unalias sa
首先,如果需要):笔记
exec -a
不可移植,它在 Bash 中有效,在 pure 中无效sh
。别名本身(或函数本身)在任何类似 POSIX 的 shell 中仍然有效。bash
无论您的主 shell 是什么,它都会显式调用。/proc/PID/cmdline
或等效信息。我们的解决方案可能会误导他们或使用它们的用户。例如将在列中ps -eo pid,comm,command
打印,但在列中。ssh
comm
sa
command