1. 程式人生 > >CentOS中環境變數和配置檔案

CentOS中環境變數和配置檔案

什麼是環境變數

bash shell用一個叫做 環境變數(environment variable) 的特性來儲存有關shell會話和工作環境的資訊。即允許在記憶體中儲存資料,使得在程式或shell中執行的指令碼能夠訪問它們。

在bash shell中,環境變數分為兩類:

  • 全域性變數
  • 區域性變數

全域性環境變數

全域性環境變數對於shell會話和所有生成的子shell都是可見的。區域性變數則只對建立它們的shell可見。

檢視全域性變數,可以使用envprintenv命令。

[[email protected] ~]# env
HOSTNAME=localhost
TERM=linux
SHELL=/bin/bash
HISTSIZE=1000
SSH_CLIENT=10.0.100.17 56344 22
SSH_TTY=/dev/pts/0
USER=root


[
[email protected]
~]# [[email protected] ~]# printenv HOSTNAME=localhost TERM=linux SHELL=/bin/bash HISTSIZE=1000 SSH_CLIENT=10.0.100.17 56344 22 SSH_TTY=/dev/pts/0 USER=root [[email protected] ~]# printenv TERM linux

使用環境變數,通過 $ +變數名。

[[email protected] ~]# echo $HOME
/root

系統環境變數基本上都是使用大寫字母,以區別於普通使用者的環境變數。

區域性環境變數

顧名思義,區域性環境變數只能在定義它們的程序中可見。set命令會顯示某個特定程序設定的所有環境變數,包括區域性變數、全域性變數以及使用者定義變數。

[[email protected] ~]# set
BASH=/bin/bash
BASHOPTS=checkwinsize:cmdhist:expand_aliases:extquote:force_fignore:hostcomplete:interactive_comments:login_shell:progcomp:promptvars:sourcepath
BASH_ALIASES=()
BASH_ARGC=()
BASH_ARGV=()
BASH_CMDS=()
BASH_LINENO=()
BASH_SOURCE=()
BASH_VERSINFO=([0]="4" [1]="1" [2]="2" [3]="1" [4]="release" [5]="x86_64-redhat-linux-gnu")
BASH_VERSION='4.1.2(1)-release'
COLORS=/etc/DIR_COLORS
COLUMNS=165

使用者定義變數

一旦啟動了bash shell,就能建立在這個shell程序內可見的區域性變數。該程序建立的子shell無法讀取父shell的區域性變數。

[[email protected] shell]# sh a.sh

2
22
2
[[email protected] shell]# cat a.sh
#!/bin/bash

a=1;
export b=2;

sh b.sh

echo $b;


[[email protected] shell]# cat b.sh
#!/bin/bash

echo $a;
echo $b;
b=22;
echo $b;
[[email protected] shell]# sh a.sh 

2
22
2

使用者可以通過export變數,使變數變為全域性變數,這樣子shell也可以讀取到。而子shell修改該變數,父shell中不受影響

如果在子shell中設定環境變數,想要在父shell中讀取呢?

一個使用場景是:多個執行指令碼依賴於共同的環境配置,這個配置寫在一個env.sh腳本里,如何使其他執行指令碼可以讀取到env.sh裡變數?在子shell中export變數,並不能影響到父shell。

source命令(從 C Shell 而來)是bash shell的內建命令。點命令,就是一個點符號,(從Bourne Shell而來)是source的另一名稱。這兩個命令都以一個指令碼為引數,該指令碼將作為當前shell的環境執行,即不會啟動一個新的子程序。所有在指令碼中設定的變數將成為當前Shell的一部分

[[email protected] shell]# cat c.sh
. ./env.sh
source ./profile.sh

echo $env;
echo $profile;
[[email protected] shell]# cat env.sh
env='test';
[[email protected] shell]# cat profile.sh 
profile="dev";
[[email protected] shell]# sh c.sh 
test
dev

如果想要刪除環境變數

unset var_name

設定全域性環境變數

上文中,可以知道,如果想要在本程序和子程序中使用共同的環境變數。通過source命令去讀取同一個環境變數指令碼可以實現。這是使用者自定義的方案。但很多時候,我們需要讀取的全域性環境變數並不知道source,所以需要一個預設的環境變數讀取檔案。

當你登入Linux系統時,bash shell會作為登入shell啟動。登入shell會從5個不同的啟動檔案裡讀取

  • /etc/profile
  • $HOME/.bash_profile
  • $HOME/.bashrc
  • $HOME/.bash_login
  • $HOME/.profile

/etc/profile

/etc/profile檔案是bash shell預設的主啟動檔案。只要你登入了Linux系統,bash就會執行/etc/profile啟動檔案的命令。

[[email protected] shell]# cat /etc/profile
# /etc/profile

# System wide environment and startup programs, for login setup
# Functions and aliases go in /etc/bashrc

# It's NOT a good idea to change this file unless you know what you
# are doing. It's much better to create a custom.sh shell script in
# /etc/profile.d/ to make custom changes to your environment, as this
# will prevent the need for merging in future updates.

pathmunge () {
    case ":${PATH}:" in
        *:"$1":*)
            ;;
        *)
            if [ "$2" = "after" ] ; then
                PATH=$PATH:$1
            else
                PATH=$1:$PATH
            fi
    esac
}


if [ -x /usr/bin/id ]; then
    if [ -z "$EUID" ]; then
        # ksh workaround
        EUID=`id -u`
        UID=`id -ru`
    fi
    USER="`id -un`"
    LOGNAME=$USER
    MAIL="/var/spool/mail/$USER"
fi

# Path manipulation
if [ "$EUID" = "0" ]; then
    pathmunge /sbin
    pathmunge /usr/sbin
    pathmunge /usr/local/sbin
else
    pathmunge /usr/local/sbin after
    pathmunge /usr/sbin after
    pathmunge /sbin after
fi

HOSTNAME=`/bin/hostname 2>/dev/null`
HISTSIZE=1000
if [ "$HISTCONTROL" = "ignorespace" ] ; then
    export HISTCONTROL=ignoreboth
else
    export HISTCONTROL=ignoredups
fi

export PATH USER LOGNAME MAIL HOSTNAME HISTSIZE HISTCONTROL

# By default, we want umask to get set. This sets it for login shell
# Current threshold for system reserved uid/gids is 200
# You could check uidgid reservation validity in
# /usr/share/doc/setup-*/uidgid file
if [ $UID -gt 199 ] && [ "`id -gn`" = "`id -un`" ]; then
    umask 002
else
    umask 022
fi

for i in /etc/profile.d/*.sh ; do
    if [ -r "$i" ]; then
        if [ "${-#*i}" != "$-" ]; then
            . "$i"
        else
            . "$i" >/dev/null 2>&1
        fi
    fi
done

unset i
unset -f pathmunge

該檔案會讀取/etc/profile.d/下所有的*.sh檔案,通過點命令(source)來載入變數。即在/etc/profile和/etc/profile.d/*.sh定義的變數,都是全域性的系統環境變數。

$HOME/.bash_profile

$HOME下的啟動檔案都是使用者專屬的啟動檔案,定義該使用者的環境變數。而/etc/profile則是系統的,所有使用者的環境變數。

shell會按照下列順序,執行第一個找到的檔案,餘下被忽略:

  • $HOME/.bash_profile
  • $HOME/.bash_login
  • $HOME/.profile

.bashrc通過.bash_profile來呼叫。

[[email protected] shell]# cat  ~/.bash_profile 
# .bash_profile

# Get the aliases and functions
if [ -f ~/.bashrc ]; then
        . ~/.bashrc
fi

# User specific environment and startup programs

PATH=$PATH:$HOME/bin

export PATH

總結

將要設定的系統全域性環境變數,比如JAVA_HOME,放在/etc/profile.d/目錄下, 以*.sh指令碼的形式定義。