我认为如果当前目录决定了一个人的 shell 环境,这将是有用/方便的。这意味着该命令
cd /my/projects/foo
...例如,不仅会设置当前工作目录(并更新、、、$PWD
等),而且还会在一个文件中调整许多其他环境元素(shell 选项、变量、函数、别名等)。方式与新的内容相适应。$OLDPWD
$dirstack
PWD
乍一看,这似乎是一个相对简单的实现方式,尤其是使用zsh
,因为它已经支持chpwd
钩子和$chpwd_functions
数组。但是,正如人们所说,细节决定成败1。
因此,在开始自己的实践之前,我想我应该问:有人知道这个想法的成熟实现吗?
或者,除了chpwd
等人之外,是否zsh
提供其他有助于实现这样的事情的工具?特别是,它是否为封装/保存/恢复环境提供任何支持? (我正在考虑R
环境对象的一些东西,但不仅包括变量,还包括例如别名、选项等)
FWIW,我知道 Python 的virtualenv
,它与本文中描述的想法共享一些功能,但当然,这仅限于与 Python 相关的设置。此外,它还会创建一个新的“状态变量”,如果您愿意的话,“当前虚拟环境”,正交(而不是包含在)“当前工作目录”状态变量。
1一旦人们更仔细地研究这一问题,很快就会遇到一些重要的问题。例如:如果cd
'ing to/my/projects/foo
激活自定义环境,那么之后会发生什么cd /my/projects/foo/modules/bar
?我们可以拥有由文件系统的树结构划分的嵌套自定义环境吗?符号链接怎么样?例如,如果/my/projects/foo/modules/bar
实际上是 的符号链接怎么办/my/shared/modules/bar
?或者,如果我执行/my/projects/foo/some_program
while $PWD
is /tmp
,那么结果进程的环境应该是什么?等等,等等,等等。我并不认为这些问题一定是棘手的,但我确实发现它们至少不是完全微不足道的。
答案1
有成熟的工具旨在为特定目录设置环境变量。
与为此设计的其他工具相比,direnv
是其中最好的。主要好处之一是它支持卸下当您退出该目录时,更改环境变量。
direnv
是 shell 的环境切换器。它知道如何挂钩 bash、zsh、tcsh、fish shell 和 elvish 来加载或卸下环境变量取决于当前目录。这允许项目特定环境变量而不会使~/.profile
文件混乱。
direnv
与其他类似工具的区别是什么:
direnv
是用 Go 编写的,快点与用 Python 编写的对应版本相比direnv
支持卸下当您从特定目录退出时使用环境变量direnv
覆盖许多贝壳
类似项目
- 环境模块- 最古老(以一种好的方式)的环境加载系统之一
- 自动环境- 轻的;不支持卸载;用Python写的很慢
- zsh-autoenv- autoenv 和的功能丰富的混合物智能CD:进入/离开事件、嵌套、隐藏(仅限 Zsh)。
- 阿斯达夫- 具有插件系统的纯 bash 解决方案