0 前言
自己在学习linux的时候遇到了这个问题,老师讲解说,使用export指令可以创捷一个环境变量,让其他的shell脚本访问到。但是自己去实验的时候,却根本访问不到,经过一段时间的研究,我根据自己浅薄的知识,对这种问题做出了一个解释,可能不正确,欢迎各位大佬指正
1 了解几个命令和配置文件
在解决这个问题之前,我们先来了解几个简单的指令
1.1 cat 命令
使用这个命令可以查看到当前shell环境中的环境变量
cat
# 直接输入即可
1.2 echo 指令
使用这个指令我们可以查看到当前的环境变量的值,可以辅助我们判断当前环境中是否存在这个环境变量(如果没有,那么就不会显示值)
echo $环境变量名
1.3 /etc/profile 配置文件
新的终端在启动的时候,会读取这个配置文件中配置的环境变量,将其加载到我们的shell环境中,
我们通过配置这个文件来给我们的环境添加环境变量
同时我们使用下面的指令
cat /etc/profile | grep export
可以看到我们配置的环境变量
1.4 source 指令
让配置文件中的配置,或则是shell脚本中的环境变量等,在当前shell环境中生效
#比如我们下面这行代码的含义就是,让hello.sh 中配置的环境变量在当前环境中生效
source hello.sh
#这行代码的意思就是,让/etc/profile中的配置在当前的shell环境中生效
source /etc/profile
2 shell进程与环境
当我们打开一个终端的时候,linux就会创建一个交互式的shell进程,这个进程有它自己的一套环境(别名,环境变量等)
当我们去执行一个shell脚本的时候,这个进程就会创建一个子进程来执行这个shell脚本,同时这个子进程也会继承父进程的环境(本文中所说的当前环境,指的就是这个交互shell的环境)
3 解释问题
3.1 shell脚本配置环境变量
有了前面的知识,那么我们在来解释这个问题就很容易了。
现在假设我们有一个叫做 test.shell 的脚本,它里面的代码是这样写的
#!/bin/bash
export TEST=1
这行代码的作用是,将TEST这个环境变量配置到子进程的shell环境中,所以,我们在其他的shell进程中,是无法访问到这个环境变量的。
那怎样才能将这个环境变量配置到当前环境(也就是父进程的环境)呢?
这时候就要请出我们的source指令了
source test.sh
执行上述代码,我们就能将这个环境变量,配置到父进程的环境了,在当前这个终端(交互shell进程)下的所有子进程,也都可以访问到这个环境变量了(因为继承了父进程的环境),我们再写一个新的shell脚本,也能访问到这个环境变量了。
那么,假如我们再打开一个终端,在这个新的终端中,还能不能访问到这个环境变量呢?
答案当然是不能的,因为这个环境变量只存在于当前的父进程环境中,也就是仅局限于这个终端。
那么,怎么才能配置一个所有的终端都可以访问的环境变量呢?
3.2 通过/etc/profile配置环境变量
我们还通过配置/etc/profile这个配置文件来配置环境变量
#我们可以使用下述的格式来创捷新的环境变量
export JAVA_HOME=/opt/jdk/jdk1.8.0_202
系统在建立新的终端的时候,会读取这个文件,然后将其中的环境变量加入到自己的shell环境中。
所以假如再我们在修改这个配置文件之后没有重启终端,我们就不能访问到我们新添加的环境变量了。
当然,我们也可以使用source指令
source /etc/profile
这个指令可以立即将我们修改的配置加入到当前环境中,这样我们就可以访问到了
3.3 两种方法的比较
通过上面的解释,我们可以得到下面的一些结论(可能有误,个人理解)
使用shell指令方式配置的环境变量,仅能在当前这个终端环境中使用,更换终端,再次登录,都无法再找到了(同时也不会写入/etc/profile这个配置文件中)
使用更改配置文件方式配置的环境变量,可以在其他的所有终端中使用到,是真正的全局配置
这两种方法,各有各的优势所在,功能强大,作用范围大的不一定更好,合适的才是最好的
3.4 一些实验
下面是一些有趣的实验,可以加深对环境变量的理解
1 使用shell命令方式添加环境变量,使用cat指令可以找到吗,在配置文件中呢
2 使用shell命令方式添加环境变量,然后切换用户,是否可以找得到,使用配置文件方式呢
3 使用shell命令方式添加环境变量,然后建立新的连接或者终端,是否可以找到到,使用配置文件方式呢
4 使用cat指令查到的环境变量的数目是不是比使用配置文件查到的数目多,为什么呢
欢迎大家在评论区留下对问题结果的讨论,和对我的指正