noc*_*rea 2 command-line bash login environment-variables 22.04
操作系统:Ubuntu桌面22.04
我最初以用户 carl 身份登录。我打开一个 shell 并 echo $0,我得到确认,我处于非登录 shell 中。(“bash”,没有破折号)但是当我 echo $PATH 时,我看到 $HOME/.local/bin 和 $HOME/bin 都是来源的,它既没有在 ~/.bashrc 中也没有在 /etc/environment 中声明。
该线程的答案表明从登录用户继承。
所以我测试了一些东西:
$ su - root
$ echo $0
> -bash
$ echo $PATH
> /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin
$ su carl
$ echo $0
> bash
$ echo $PATH
> /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin
$ su - carl
$ echo $0
> -bash
$ echo $PATH
> /home/carl/.local/bin:/home/carl/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin
$ su carl
$ echo $0
> bash
$ echo $PATH
> /usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin
Run Code Online (Sandbox Code Playgroud)
在此示例中,以 root 身份登录后,然后切换到非登录用户 shell,PATH 变量就如其应有的那样。然后我检查是否以 carl 身份登录,然后切换到非登录 shell,因为 carl 继承了登录的 shell 变量,但事实并非如此。
其他注意事项:
我正式不再猜测,非常感谢企鹅大师来启发我,以便我可以再次入睡。
.local/bin默认情况下添加(~/.profile复制自/etc/skel/.profile):
# set PATH so it includes user's private bin if it exists
if [ -d "$HOME/.local/bin" ] ; then
PATH="$HOME/.local/bin:$PATH"
fi
Run Code Online (Sandbox Code Playgroud)
.profile是改的地方正确PATH,不是.bashrc。
不,情况恰恰相反。.profile来源.bashrc:
# if running bash
if [ -n "$BASH_VERSION" ]; then
# include .bashrc if it exists
if [ -f "$HOME/.bashrc" ]; then
. "$HOME/.bashrc"
fi
fi
Run Code Online (Sandbox Code Playgroud)
让我们看一下你的例子:
$ su - root
$ echo $0
-bash # This is a root login shell. It sources /root/.profile
$ echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin
$ su carl
$ echo $0
bash # This is a user non-login shell. It sources .bashrc not .profile
$ echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin
$ su - carl
$ echo $0
-bash # This is a user login shell. It sources .profile not .bashrc
$ echo $PATH
/home/carl/.local/bin:/home/carl/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin
$ su carl
$ echo $0
bash # This is a user non-login shell. It sources .bashrc not .profile
$ echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin
Run Code Online (Sandbox Code Playgroud)
如果我强行(不推荐)使用su登录而不通过登录外壳,我不会得到我$PATH想要的正常结果:
home@daniel-desktop3:~$ su home
Password:
home@daniel-desktop3:~$ echo $0 # Non-login shell. Didn't get .profile
bash
home@daniel-desktop3:~$ echo $PATH # Missing what I want
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin
home@daniel-desktop3:~$ bash # Start nested shell
home@daniel-desktop3:~$ echo $0
bash
home@daniel-desktop3:~$ echo $PATH
/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin
home@daniel-desktop3:~$ exit # Exit nested shell
exit
home@daniel-desktop3:~$ exit # Exit su shell
exit
Run Code Online (Sandbox Code Playgroud)
但是,如果我正常登录,$PATH应该会被export编辑到子 shell。su - username当您通过GUI登录时,它应该.profile设置$PATH. 然后这个变量将从桌面环境的进程继承,然后是终端模拟器,然后是在其中运行的 bash。
home@daniel-desktop3:~$ su - home
Password:
home@daniel-desktop3:~$ echo $0 # Login shell sources .profile
-bash
home@daniel-desktop3:~$ echo $PATH # I get the path I want
/home/home/.elan/bin:/home/home/bin:/home/home/.cargo/bin:/home/home/kde/src/kdesrc-build:/home/home/.cabal/bin:/home/home/.ghcup/bin:/home/home/.local/bin:/opt/rocm-6.0.0/bin:/home/home/.go/bin:/home/home/.nvm/versions/node/v21.6.1/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin:/home/home/.local/share/JetBrains/Toolbox/scripts
home@daniel-desktop3:~$ bash # Start a subshell
home@daniel-desktop3:~$ echo $0 # .bashrc is sourced again. .profile is NOT sourced. $PATH is INHERITED
bash
home@daniel-desktop3:~$ echo $PATH # I inherit $PATH like I want
/home/home/.elan/bin:/home/home/bin:/home/home/.cargo/bin:/home/home/kde/src/kdesrc-build:/home/home/.cabal/bin:/home/home/.ghcup/bin:/home/home/.local/bin:/opt/rocm-6.0.0/bin:/home/home/.go/bin:/home/home/.nvm/versions/node/v21.6.1/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games:/snap/bin:/home/home/.local/share/JetBrains/Toolbox/scripts
home@daniel-desktop3:~$ exit # Exit nested non-login subshell
exit
home@daniel-desktop3:~$ exit # Exit login shell
logout
Run Code Online (Sandbox Code Playgroud)
因此,在 GUI 登录中,以下是简化视图(忽略systemd中间的细节和其他过程):
gdm3作为根用户
gnome-session或另一个DE。这个来源.profile
gnome-terminal。不来源任何东西。继承$PATH
bash。这是您的非登录子 shell。其来源.bashrc并非如此.profile。它$PATH通过 gnome-terminal 继承自 gnome-session
bash。如果您再次输入,这是一个子 shell bash。与上面做同样的事情对于 SSH/su - username登录(也忽略 PAM 详细信息):
sshd作为根用户
-bash这是您的登录 shell。这来源 .profile。除非告诉它
.bashrc,否则它不会直接获取.profilebash如果您再次键入,这是一个非登录子 shell bash。其来源.bashrc并非如此.profile。它直接继承$PATH自-bash
bashbash如果您再次键入,这是另一个嵌套的非登录子 shell 。它的作用与其他非登录子 shell 相同。它继承$PATH自-bashviabash这是预期的行为。尝试更改它可能会导致出现重复条目$PATH并且变得太长的错误。
$PATH如果您确实希望在非登录 shell 中使用原始较短的内容,您可以添加一些代码~/.bashrc来检测这种情况,并解析并删除$PATH.
| 归档时间: |
|
| 查看次数: |
399 次 |
| 最近记录: |