为什么.profile(而不是.bashrc)将~/bin添加到路径中?

由于`.bashrc`更加“通用”(在这个意义上,`.profile`会引用它),为什么“将`~/bin`包含到路径中”的步骤不在`.bashrc`中呢?为什么用户不希望在非登录shell中使用它呢?(尤其是现在,非登录shell更加常见*。)
我知道我可以手动进行这样的更改,但我想知道是否有原因。
*无法证明,但我认为情况是如此。
2个回答

~/.bashrc/etc/bash.bashrc在每次启动交互式bash shell时运行。

相比之下,~/.profile/etc/profile在每次启动任何登录 shell时运行。因此它不必是一个bash shell,但它必须是一个登录 shell(而许多bash shell实例并非登录 shell)。

  • bash shell是指提供该shell的程序是bash,而不是其他程序,比如dash
  • 登录 shell是指作为登录后自动启动的shell,用于提供登录的用户界面(图形或命令行)。当退出登录 shell时,登录终止。
因此,在 bashrc 文件中放置一个附加条目到 PATH 的注释将会有以下效果:
  1. 当 shell 不是 bash 时(这种情况很常见),什么也不会发生。例如,当你处于图形登录会话时, PATH 不会被修改。请记住,PATH 不仅仅被命令行程序使用。

  2. 在存在嵌套的 bash shell 时,它会一次又一次地追加。所以,如果你在一个 shell 中启动另一个 shell——这是非常常见的,出于各种原因——那么你的 PATH 将会有多个 ~/bin 条目。这使得 PATH 环境变量难以阅读,并且有时还会降低性能。

这些都是不希望发生的。因此,在 bashrc 文件中放置这个内容是错误的;它真正应该放在 ~/.profile 中。对于这样的设置来说,~/.profile正确的位置

# set PATH so it includes user's private bin if it exists
if [ -d "$HOME/bin" ] ; then
    PATH="$HOME/bin:$PATH"
fi

非登录Shell的父进程是登录Shell(或者行为类似于登录Shell),非登录Shell会继承大部分环境变量,包括PATH,来自于它的父进程。因此,在~/.profile中放置修改路径的命令需要您退出并重新登录以使其生效,但这也会影响非登录Shell的环境(以及那些不是Shell的程序的环境,因为每个程序都会从其父进程继承一组环境变量,称为"环境")。

我明白。但是这个决定对我来说还是没有意义。如果我现在打开一个终端,它只会加载.bashrc文件,那么我就看不到我的私人bin目录了。 - borges
@borges 如果默认配置对您来说不起作用,您应该随意更改它。(毕竟这是您的计算机,或者至少是您的帐户。)但这听起来像是一次性的事情。也就是说,听起来像是您登录时不存在您的私有“bin”目录,并且您在此登录会话期间创建了它。如果您退出并重新登录,它将出现在您的“PATH”中。由于创建您的私有“bin”目录只需要进行一次,所以这只是一次性的不便。 - Eliah Kagan

“这是因为传统上环境变量只放在 /etc/profile 或者 .profile 文件中。bashrc 文件则用于别名、提示设置、shell 选项等 (即与 shell 直接相关的内容)。”