TMUX设置会话的环境变量

use*_*028 14 tmux

我工作的情况是我有多个项目,每个项目都有许多脚本,这些脚本使用设置为特定于该项目的值的环境变量.

我想要做的是为每个项目使用一个单独的tmux会话,并设置变量,以便为该会话中的所有窗口设置它们.

我尝试使用set-environment选项,该选项使用-g选项,但随后为连接到该服务器的所有会话设置变量.

如果没有-g选项,我在使用show-environment时会看到它的设置,但无法访问shell中的变量.

有没有人想出办法解决这个问题?

使用tmux 1.8和tcsh

Mic*_*rtl 7

我做了一个简单的

export MY_VAR="some value"
Run Code Online (Sandbox Code Playgroud)

在我开始 tmux 会话之前,它使我可以MY_VAR从该会话中的所有窗口访问。

  • 当您创建第一个会话并且“tmux”启动其服务器进程时,这将起作用。但是,如果您启动第二个会话,它将连接到同一个 tmux 服务器,因此它将获取您第一次启动服务器时设置的环境变量,而不是最新的环境变量。 (3认同)
  • @ghchoi,但是如果您有其他 tmux 会话已连接到该服务器,则在打开另一个会话之前导出变量将不起作用 (2认同)

gos*_*pes 6

您可以在会话中使用以下命令访问每个会话的tmux(本地)环境变量:

bash> tmux show-environment
Run Code Online (Sandbox Code Playgroud)

如果添加-g参数,则会获得所有会话的环境,即全局环境.本地环境与全球环境不同.上一个命令打印整个本地环境,但您也可以只查看一个变量:

bash> tmux show-environment variable_name
          variable_name=value
Run Code Online (Sandbox Code Playgroud)

要获得该值,您可以在单个变量上使用某些"sed"魔法或使用"export",或者甚至可以将整个环境"导出"到shell中.以下是3种方法.

bash> tmux show-environment variable_name | sed "s:^.*=::"
         value

bash> eval "export $(tmux show-environment variable_name)"
bash> echo $variable_name
         value    

bash> for var in $(tmux show-environment | grep -v "^-"); do eval "export $var"; done;
bash> echo $variable_name
         value    
Run Code Online (Sandbox Code Playgroud)

如果需要,您可以在show-environment命令后添加-g参数,以便访问全局环境.


Nik*_*ros 6

tmux 3.2 版本将支持直接更改本地环境的命令-e选项。new-session

同时,您可以使用它来运行一个新的 tmux 会话,该会话具有可用且最新的特定环境(或提到的其他解决方案之一):

tmux new-session 'export MY_VAR=value; exec bash'
Run Code Online (Sandbox Code Playgroud)

tmux 的问题是,当您第一次运行它时,会创建 tmux 服务器,并且它继承了创建时可用的环境。这就是所谓的全球环境。当您再次运行 tmux 并创建新会话时,tmux 服务器仍保留其环境副本。但这个副本是服务器在创建时了解到的“旧”环境,即全局环境。

关于适用于 tmux 环境的 tmux 命令:

  • set update-environment MY_VARMY_VAR:这将告诉 tmux从全局环境中获取变量并使其成为会话环境,即本地环境(由show-environment命令列出)。然后,会话将能够更改该变量的值而不影响全局环境。
  • set-environment MY_VAR value:这将在会话的本地环境中创建(或更改)一个变量。
  • set-environment -g MY_VAR value:这将在全局环境中创建(或更改)一个变量。

另请注意,当您运行 tmux 并且 tmux 调用 bash(或其他 shell)时,bash 将拥有服务器(全局)环境的副本。即使您在调用 tmux 之前更改了环境变量,创建新会话也会忽略这些更改。如果您在conf文件中添加tmux命令并运行tmux,例如使用tmux source-file tmux-session.conf,您在conf中提到的任何变量都将在tmux服务器知道的全局环境的上下文中进行评估,而不是在您运行tmux的上下文中进行评估命令。因此,为了使新会话看到变量的新值,您必须以将 env 变量的新值直接传递给它的方式调用 tmux。这就是这里的解决方案尝试做的事情。这也是新-e选项允许您执行的操作。


Rob*_*erd 5

我想出了一种方法。我正在使用tmux 2.5。

背景

在tmux手册页中,它指出了两组环境变量:全局变量和每个会话。创建新的tmux会话时,它将把两个组合并在一起,这将成为该会话中可用的环境变量集。如果将环境变量添加到全局组,则似乎在所有打开的会话之间共享它们。您要将它们添加到每个会话组。

做这个

第1步:创建一个tmux会话。

tmux new-session -s one
Run Code Online (Sandbox Code Playgroud)

步骤2:将环境变量添加到每个会话组。

tmux setenv FOO foo-one
Run Code Online (Sandbox Code Playgroud)

这会将环境变量添加到每个会话的环境变量集中。如果输入tmux showenv,您将在输出中看到它。但是,它不在当前会话的环境中。打字echo $FOO不会给你任何东西。可能有更好的方法来执行此操作,但是我发现手动导出它最简单:

export FOO='foo-one'
Run Code Online (Sandbox Code Playgroud)

步骤3:建立新的视窗/窗格

现在,每次在当前会话中创建新窗口或窗格时,tmux都会从每个会话组中获取FOO环境变量。

自动化

我使用bash脚本自动创建利用这些环境变量的tmux会话。这是我如何自动执行上述操作的示例:

#!/bin/bash
BAR='foo-one'
tmux new-session -s one \; \
  setenv FOO $BAR \; \
  send-keys -t 0 "export FOO="$BAR C-m \; \
  split-window -v \; \
  send-keys -t 0 'echo $FOO' C-m \; \
  send-keys -t 1 'echo $FOO' C-m
Run Code Online (Sandbox Code Playgroud)

  • 如果通过该命令设置的环境变量无法被“echo $foo”之类的东西访问,那么“setenv”的确切用途是什么? (2认同)
  • 当您创建会话时,它会自动创建窗口 0,该窗口会触发 shell。因此,对于该 shell,setenv 不起作用,您必须发送密钥。但是当您创建一个新窗口时,就像使用 split-window 一样,新窗口会从 setenv 获取环境。该示例显示两个窗口都具有通过导出或通过 setenv 显式设置的环境。 (2认同)