0%

Linux ssh 远程执行命令环境切换问题


  • 今天将公司之前的shell脚本处理一下,放到Jenkins中执行,方便大家部署,结果出现了一个奇怪的问题,通过ssh 远程执行命令的时候发现找不到java命令。
  • 直接用ssh切换到那台机器是没有问题的,java命令存在。远程执行 ssh -t user@host ‘java -version’ 提示java命令找不到。
  • 查了一堆资料,定位了问题:
    • 使用这种方式执行命令,不会执行/etc/profile文件,而我的java_home,java path都是在/etc/profile文件中配置的
  • 解决也不太复杂:
    • 方法1:ssh -t user@host ‘source /etc/profile && java -version’ 久违的jdk1.8终于出来了(嗯。。我就用这个解决的)
    • 方法2: 修改 ~/.bashrc 加入java_home,java path (这个没敢动。。因为机器是公用的。。。)
  • 补充知识点:
  1. 通过SSH登录后再执行命令和脚本
    这种方式会使用Bash的interactive + login shell模式,这里面有两个概念需要解释:interactive和login。

    • login故名思义,即登陆,login shell是指用户以非图形化界面或者以ssh登陆到机器上时获得的第一个shell,简单些说就是需要输入用户名和密码的shell。因此通常不管以何种方式登陆机器后用户获得的第一个shell就是login shell。
    • interactive意为交互式,这也很好理解,interactive shell会有一个输入提示符,并且它的标准输入、输出和错误输出都会显示在控制台上。所以一般来说只要是需要用户交互的,即一个命令一个命令的输入的shell都是interactive shell。而如果无需用户交互,它便是non-interactive shell。通常来说如bash script.sh此类执行脚本的命令就会启动一个non-interactive shell,它不需要与用户进行交互,执行完后它便会退出创建的Shell。
    • 在interactive + login shell模式中,Shell首先会加载/etc/profile文件,然后再尝试依次去加载下列三个配置文件之一,一旦找到其中一个便不再接着寻找:
    1
    2
    3
    ~/.bash_profile
    ~/.bash_login
    ~/.profile
  2. 通过SSH直接执行远程命令和脚本
    这种方式会使用Bash的non-interactive + non-login shell模式,它会创建一个shell,执行完脚本之后便退出,不再需要与用户交互。

    • no-login shell,顾名思义就是不是在登录Linux系统时启动的(比如你在命令行提示符上输入bash启动)。它不会去执行/etc/profile文件,而会去用户的HOME目录检查.bashrc并加载。
    • 系统执行Shell脚本的时候,就是属于这种non-interactive shell。Bash通过BASH_ENV环境变量来记录要加载的文件,默认情况下这个环境变量并没有设置。如果有指定文件,那么Shell会先去加载这个文件里面的内容,然后再开始执行Shell脚本。

引用: https://www.cnblogs.com/zhenyuyaodidiao/p/9287497.html