执行一个 shell 的时候分成login shell和non-login shell。logshell
login shell 和no-login shell?
login-shell 通俗的说就是 需要输入账密且分配一个终端的shell.
- ssh 远程执行指令也是 login shell,也就是伴随登录的意思
- su:交互式非登录式
- su --login(su -):交互式登录式
第一点在有的地方说法不一,因为ssh 远程并没有分配一个终端,但是可以通过参数强制分配终端。
如果ssh没加tt参数(表示不为这个连接分配TTY,这里非得用两个tt才不会报错),可能会报Pseudo-terminal will not be allocated because stdin is not a terminal的错
另外可以通过shopt login_shell查看login shell是否开启. 开启与否就是加载的坏境变量不同,这点容易采坑。例如切换gpadmin 用户时,不带-时,gpadmin 用户的环境变量没有加载,因此gp的相关指令就找不到.
~]# shopt login_shell login_shell on
login shell 会触发很多文件执行,路径如下:
/etc/profile
- ~/.bash_profile
- ~/.bashrc
- /etc/bashrc
- /etc/profile.d/*.sh
如果以当前用户身份正常执行一个shell脚本,比如说./a.sh,就是一个non-login的模式。 这时候不会触发上述的完整逻辑。
另外shell还有另一种分法,就是
- interactive
- non-interactive。
interactive 是交互式的意思,当用户打开一个终端命令行工具后,会进入一个输入命令得到结果的交互界面,这个时候,就是interactive shell。
两种方式辨别是否为交互式shell?
可以通过PS1返回值,如果返回代表是interactive shell,为空则为no-interactive shell,可参考
1. ~]# echo $PS1 2. [\u@\h \W]\$
带 i 字符的就是interactive,没有带i字符就不是。
1. ~]# echo $- 2. himBHs
bashrc文件通常只在interactive模式下才会执行,这是因为~/.bashrc文件中通常有这样的语句,如下图所示:
因此, 如果你需要通过 ssh 远程 shell 执行一个文件,你就不是在 interactive 模式下,bashrc 不会触发。但是因为登录的原因,login shell 都会触发,也就是说 profile 文件依然会执行。
另外可以明确使用--login指定交互式登录.
- bash命令:交互式非登录式
- bash --login:交互式登录式
总结时刻
常见的bash启动方式
shell脚本:非交互非登录。 这点在脚本中调用其他脚本时要特别注意开启的bash是什么类型? 是否有环境变量?