본문 바로가기

CentOS/Study

[Study34]Linux Bash 셸 기술로 생산성 향상 - 변수(Variable)

반응형

변수(Variable)

변수는 하나의 값을 저장하기 위해 사용하는 것으로, 스크립트에서 가장 많이 사용되는 요소 중 하나입니다.

변수는 다음과 같이 종류가 있습니다.

 

- 지역변수(Local Variable): 변수가 선언된 스크립트 또는 함수에서만 사용 가능한 변수입니다. 지역 변수는 VAR=5와 같은 형식으로 선언됩니다.

- 환경변수(Environment Variable): 모든 프로세스에서 사용할 수 있는 변수입니다. export VAR=5와 같은 형식으로 선언합니다.

- 특수변수(Special Variable): 스크립트나 셸에서 미리 정의되어 있는 변수로, 사용할 때마다 특정한 의미를 가집니다. 예를 들어, $$는 현재 프로세스의 PID를 나타내고, $?는 최근에 실행된 명령어의 종료 코드를 나타냅니다.

 

따라서, 변수는 스크립트를 작성할 때 매우 중요한 부분이므로, 변수의 종류와 사용법에 대해 잘 알고 있어야 합니다.

 

지역 변수 선언

변수를 선언하는 방법은 VAR=5와 같이 변수명과 값을 할당해주는 것이다. 변수를 선언할 때 export 키워드를 사용하면 해당 변수가 현재 쉘에서 실행 중인 다른 프로세스에서도 사용 가능하다. 값이 할당된 변수를 출력하려면 $VAR와 같이 $ 기호를 변수명 앞에 붙여주면 된다. 변수를 제거하려면 unset VAR와 같이 사용한다.

지역 변수는 현재 사용하고 있는 쉘에만 적용되는 변수 값으로 선언하는 것이다. 서브 쉘에서 지역 변수 값을 확인하려고 할 경우 값이 나타나지 않는다.

var=5
echo $var (0)
----------+
          |
          | echo $var (X)
          +---------------+

위의 코드에서는 변수 var에 5라는 값을 할당하고, 이를 출력하면 0이 출력된다. 이는 다른 쉘에서는 해당 변수 값을 확인할 수 없기 때문이다.

var=5
echo $var
5
var=hello
echo $var
hello
bash
echo $var
exit
echo $var

위의 코드에서는 변수 var에 5라는 값을 할당하고, 출력하면 5가 출력된다. 이후 var에 hello라는 값을 할당하고, 출력하면 hello가 출력된다. 이어서 bash 명령어를 실행하면 새로운 쉘이 실행되는데, 이 상태에서 echo $var을 실행하면 값이 출력되지 않는다. 마지막으로 exit 명령어를 실행한 후 echo $var을 실행하면 이전에 할당된 hello가 출력된다.

 

환경변수 선언

환경변수란 현재 쉘과 서브쉘에 변수를 모두 적용되는 변수 값으로 선언해 주는 것을 의미합니다. 환경변수를 사용하는 이유는 이전 쉘에서 선언한 변수 값을 서브쉘에서도 동일하게 적용하기 위한 것입니다.

환경 변수는 'export' 명령어와 함께 선언됩니다. 예를 들어, 'export var = hello'라는 명령어를 입력하면 'var'라는 변수에 'hello'라는 값이 할당되며, 현재 쉘과 서브쉘에서 이 변수를 사용할 수 있습니다.

export var=hello
echo $var (0)

위 코드는 'var'라는 변수에 'hello'라는 값이 할당되며, 'echo $var' 명령어를 통해 변수의 값이 출력됩니다.

환경 변수는 다른 쉘에서도 사용할 수 있으며, 새로운 쉘에서 'export' 명령어를 입력하지 않아도 이전 쉘에서 선언된 환경 변수를 사용할 수 있습니다.

# var=hello
# export var
# echo $var
hello
# bash
# echo $var
hello
# exit

# echo $var
hello
export var=hello                   echo $var
                              +----------
                              |
                              | export var=centos
                              |
                          +---------------+
                          |
                          | echo $var
                          |
                          +---------------+

위의 코드는 이전 쉘에서 선언된 'var' 변수를 서브쉘에서도 사용할 수 있도록 하는 예시입니다. 'export var=centos'라는 명령어를 입력하면 'var' 변수에 'centos'라는 값이 할당되며, 이전 쉘에서 선언된 'hello' 값 대신 'centos' 값이 출력됩니다.

환경 변수는 유용하지만, 적절하게 사용해야 합니다. 환경 변수를 오용하면 시스템의 안정성이 저하되거나 보안 문제가 발생할 수 있습니다. 따라서, 환경 변수를 선언할 때는 신중하게 판단해야 합니다.

위의 코드는 Bash에서 환경 변수가 작동하는 방법을 보여줍니다. 환경 변수는 여러 쉘에 걸쳐 동일한 변수 값을 적용하는 데 도움이 되는 것에 유용합니다.

(결론) 환경 변수는 자신이 선언한 쉘의 서브쉘에서 적용되는 것이다. 상위의 쉘에는 적용되지 않는다.

[참고] env와 set의 차이점 (선언된 변수를 확인하는 명령어)

set 명령어는 모든 변수(지역변수 + 환경변수)에 대해 출력하는 명령어이며, env 명령어는 환경변수만 출력합니다. 이 둘의 차이를 살펴보면, 환경변수만 필요한 경우에는 env 명령어를 사용하는 것이 더 효율적일 수 있습니다.

아래는 set/env 명령어를 실습한 예시입니다.

먼저, var1 변수에 CentOS를 할당하고, var2 변수에는 Linux를 할당합니다.

# var1=CentOS
# export var2=Linux

그리고, set 명령어와 grep 명령어를 사용하여 var1 변수에 대한 정보를 출력합니다.

# set | grep var1
var1=CentOS

다음으로, set 명령어와 grep 명령어를 사용하여 var2 변수에 대한 정보를 출력합니다.

# set | grep var2

하지만, 출력되는 정보가 없습니다.

반면, env 명령어와 grep 명령어를 사용하여 var1 변수에 대한 정보를 출력합니다.

# env | grep var1

여전히, 출력되는 정보가 없습니다.

마지막으로, env 명령어와 grep 명령어를 사용하여 var2 변수에 대한 정보를 출력합니다.

# env | grep var2
var2=Linux

위와 같이, set/env 명령어를 사용하여 변수 정보를 확인할 수 있습니다.

 

시스템 지역변수

[3-1-1] PS1 명령어 프롬프트에 나타내는 시스템 환경 변수

시스템 지역변수는 사용자의 편의를 위해 시스템에서 제공하는 환경 변수입니다. 여기서 PS1은 명령어 프롬프트에서 시스템 환경 변수를 표시합니다.

보통 PS1의 기본값은 '[\u@\h \W]\$'입니다. 여기서 '\u'는 사용자 이름, '\h'는 호스트 이름, '\W'는 현재 작업 디렉토리의 이름입니다.

만약 경로를 출력하는 것이 더 유용하다면, PS1을 '\w>'로 설정할 수 있습니다. 이 경우에는 '[절대경로]>'가 출력됩니다.

PS1을 새로 설정하고자 한다면 명령어 프롬프트에서 'PS1=[원하는 값]'을 입력하면 됩니다. 이렇게 설정한 PS1은 현재 쉘에서만 유효합니다.

만약 PS1 설정을 영구적으로 변경하고자 한다면 '/etc/profile'에 PS1 값을 등록하면 됩니다. 이렇게 설정된 PS1은 모든 사용자와 쉘에서 유효합니다.

위와 같이 시스템 지역변수를 적절히 활용하면 명령어 프롬프트에서 유용한 정보를 신속하게 확인할 수 있습니다.

#: 현재 표시되는 이 문자에 대한 시스템 환경 변수를 표시한다.

echo $PS1
[\\\\u@\\\\h \\\\W]\\\\$

PS1 값이 기본값인 '[\u@\h \W]\$'로 설정되어 있습니다.

PS1='[\\\\u@\\\\h \\\\w]\\\\$ '

PS1 값을 '[\u@\h \w]\$ '로 설정합니다.

set | grep PS1
PS1='[\\\\u@\\\\h \\\\w]\\\\$ '

설정한 PS1 값을 확인합니다.

env | grep PS1

환경 변수에 설정한 PS1 값을 확인합니다.

PS1='\\\\w> '

PS1 값을 '\w> '로 설정합니다.

/root>

현재 경로만 표시합니다.

PS1='$PWD> '

PS1 값을 '$PWD> '로 설정합니다.

set | grep PS1
PS1='$PWD> '

설정한 PS1 값을 확인합니다.

env | grep PS1

환경 변수에 설정한 PS1 값을 확인합니다.

PS1='[$PWD]# '

PS1 값을 '[$PWD]# '로 설정합니다.

[/root]#

절대경로가 출력됩니다.

bash
PS1='[user@\\\\w]# '

PS1 값을 '[user@\w]# '로 설정합니다.

[root@linux200 ~]# PS1='[\\\\u@\\\\h \\\\w]\\\\$ '

PS1 값을 '[\u@\h \w]\$ '로 설정합니다.

[root@linux200 ~]# exit

 

PS1='[\u@\h \w]\$ '

# vi ~/.bashrc 
-------------------------------
.....
#
# Variable Definition
#
export PS1='[\\u@\\h \\w]\\$ '
-------------------------------

# .  ~/.bashrc   (# source ~/.bashrc)

PS1='[\\\\u@\\\\h \\\\w]\\\\$ ' 는 프롬프트(Prompt)에 표시되는 텍스트를 설정하는 것입니다.

PS1='[\\\\u@\\\\h \\\\w]\\\\$ ' 라는 값을 할당해줍니다.

할당된 값을 ~/.bashrc 파일에 저장합니다.

. ~/.bashrc 명령어를 실행하여 새로운 쉘에서도 설정된 값을 사용할 수 있도록 합니다.

 

디렉토리 이동시 경로 표시하기

디렉토리 이동을 하다 보면, 현재 위치한 디렉토리에서 다른 디렉토리로 이동할 때 어디로 이동했는지 모를 때가 있다. 이럴 때는 .bashrc 파일을 열어서 다음과 같이 코드를 추가하면 디렉토리 이동 후 경로가 표시된다.

# vi .bashrc
function cd { builtin cd $* && pwd ; }  # 디렉토리 이동후 경로 표시

위 코드를 추가한 후 저장한 뒤, 터미널을 다시 열게 되면 디렉토리 이동 후 경로가 표시되는 것을 확인할 수 있다. 이 방법을 통해 디렉토리 이동 시 어디에 위치해 있는지 한 눈에 알아볼 수 있어 편리하다. 또한, 이 기능은 파일 시스템 구조를 파악하는 데 도움이 된다. 따라서, 이 기능을 활용하여 보다 효율적인 디렉토리 이동을 할 수 있다.

 

PS1 시스템 환경 변수 설정하는 방법

쉘프롬프트에 보여지는 항목을 설정하는 것으로 아래와 같은 것들을 사용할 수 있다. 예를 들어, $ 표시 대신에 root 계정의 경우 # 표시를 사용할 수 있다.

  • \\\\t: 현재 시간을 HH:MM:SS 형식으로 표시
  • \\\\d: 날짜를 "요일 월 일" 형식으로 표시 (예, "Tue May 26")
  • \\\\n: 개행문자
  • \\\\s: 쉘의 이름, $0 의 베이스 이름 (마지막 슬래쉬 뒷 부분)
  • \\\\w: 현재 작업 디렉토리
  • \\\\W: 현재 작업 디렉토리의 베이스 이름
  • \\\\u: 현재 사용자의 사용자명
  • \\\\h: 호스트 이름
  • \\\\#: 이 명령의 명령 번호
  • \\\\!: 이 명령의 히스토리 번호
  • \\\\$: 유효 UID가 0 이면 '#' 표시, 그렇지 않으면 '$' 표시
  • \\\\nnn: 팔진수 nnn에 해당하는 문자
  • \\\\\\\\: 백슬래쉬
  • \\\\[: 비출력 문자의 시퀀스를 시작한다. 프롬프트에 터미널 제어시퀀스를 넣을때 사용한다.
  • \\\\]: 비출력 문자의 시퀀스를 마친다.

 

PS2 명령어가 아직 끝나지 않았음을 나타낼 때 사용

먼저, 다음과 같이 PS2 값을 설정해줍니다.

PS2='> '

그러면 터미널에서 다음과 같이 > 표시가 나타나게 됩니다.

>

이제, 명령어를 입력해보겠습니다.

ls -a -l

이 경우에는 명령어가 끝나기 때문에 > 표시가 나타나지 않습니다. 하지만, 명령어가 길어서 줄바꿈을 하고 싶을 때는 다음과 같이 \\\\를 입력하면 됩니다.

ls -a \\\\
> -l

그리고, 문자열을 입력할 때도 마찬가지입니다.

echo "hello linux
> "

이렇게 하면 입력이 끝나지 않았음을 나타내기 위해 > 표시가 나타납니다.

마지막으로, while 루프 안에서 명령어를 실행할 때도 > 표시가 나타납니다.

while true
do
CMD
sleep 5
done

이때, echo $PS2를 입력하면 다시 > 표시가 나타나게 됩니다.

 

시스템 환경변수

# echo $HOME
/root
# cd $HOME 
# pwd
/root
# echo $PWD
/root
# echo $LOGNAME
root
# echo $TERM
xterm
# echo $LANG
ko_KR.UTF-8
# echo $USER
root
# echo $UID
0

이 섹션에서는 시스템 환경변수에 대해 설명합니다. 환경변수는 프로그램이 실행되는 컴퓨터 환경의 설정을 나타냅니다. 시스템 환경변수는 운영 체제에서 정의하며, 모든 사용자에게 공통적으로 적용됩니다.

코드 블록은 여러 환경 변수와 그 값들을 보여줍니다. 예를 들어, $HOME 환경변수는 현재 사용자의 홈 디렉토리 경로를 나타냅니다. $PWD 환경변수는 현재 작업 중인 디렉토리의 경로를 나타냅니다. $LOGNAME 환경변수는 현재 사용자의 로그인 이름을 나타냅니다. 이러한 환경 변수들을 적절하게 설정하는 것이 프로그램의 실행과 관련된 문제를 해결하는 데 도움이 됩니다.

기타 환경변수에 대한 정보는 운영 체제 문서 또는 튜토리얼에서 찾을 수 있습니다. 예를 들어, $TERM 환경변수는 현재 터미널 타입을 나타냅니다. $LANG 환경변수는 현재 시스템 로케일을 나타냅니다. $USER 환경변수는 현재 사용자의 이름을 나타내며, $UID 환경변수는 현재 사용자의 UID를 나타냅니다.

환경변수는 시스템에서 매우 중요합니다. 다양한 프로그램에서 환경변수를 사용하여 다양한 기능을 수행하므로, 이를 이해하고 제대로 설정하는 것이 중요합니다. 예를 들어, 로그인 셸에서 PATH 환경변수를 올바르게 설정하지 않으면 실행 파일을 찾을 수 없습니다. 따라서, 환경 변수를 올바르게 설정하는 것이 프로그램을 성공적으로 실행하는 데 필수적입니다.

 

알아두면 좋은 특수 변수

① $ : 현재 쉘의 PID를 저장하고 있습니다. 이 PID는 쉘 스크립트 내에서 임시 파일의 이름을 지정할 때 주로 사용됩니다. 그러나 이 변수는 쉘 스크립트 내에서 다양한 용도로 활용될 수 있습니다. 예를 들어, 현재 쉘의 정보를 출력하거나, 쉘 스크립트가 실행 중인 호스트 이름을 출력하는 등의 용도로 사용될 수 있습니다.

# echo $$
11991

# ps
PID TTY          TIME CMD
11991 pts/1    00:00:00 bash

② ? : 바로 이전 명령어의 정상 실행 여부에 대한 결과값이 들어 있습니다. 이 변수는 쉘 스크립트 내에서 이전 명령어의 정상 수행 여부를 확인할 때 주로 사용됩니다. 그러나 이 변수는 쉘 스크립트 내에서 다양한 용도로 활용될 수 있습니다. 예를 들어, 이 변수를 이용하여 쉘 스크립트에서 조건문을 실행할 수 있습니다.

# ls /nodir
ls: /nodir: No such file or directory
# echo $?
2
# cd /nodir
-bash: cd: /nodir: No such file or directory
# echo $?
1
# no
-bash: no: command not found
# echo $?
127
# ls
Desktop          hash.tar.gz         mbox              top.seceret.mail.gpg
anaconda-ks.cfg  install.log         serv.pub
hash.md5         install.log.syslog  top.seceret.mail
# echo $?
0

 

백업 스크립트 작성

#!/usr/bin/bash
tar cvzf /backup/backup.tar.gz /home

위 코드는 '/home' 디렉토리를 '/backup/backup.tar.gz'로 압축하는 스크립트입니다.

스크립트 실행 결과 확인

if [ $? -eq 0 ] ; then
	echo "success"
else
	echo "error"
fi

스크립트 실행 결과에 따라서 'success' 또는 'error'를 출력하는 코드입니다. 위 코드에서는 '$?' 변수가 0이면 'success'를 출력하고, 그렇지 않으면 'error'를 출력합니다.

'$?'는 이전 명령어의 종료 코드를 나타내는 특수 변수입니다. 이 변수가 0이면 이전 명령어가 성공적으로 완료되었음을 나타내며, 그렇지 않으면 오류가 발생했음을 나타냅니다.

스크립트 실행 권한 부여

chmod +x backup.sh

위 코드를 실행하여 'backup.sh' 파일에 실행 권한을 부여합니다.

스크립트 실행

./backup.sh

위 코드를 실행하여 'backup.sh' 파일을 실행합니다.

만약 '/backup' 디렉토리가 존재하지 않으면 'No such file or directory' 오류가 발생합니다. 이 경우에는 '/backup' 디렉토리를 먼저 생성한 후에 스크립트를 실행해야 합니다.

 

/root/bin/script.sh 편하게 실행하기

/root/bin 디렉토리는 관리자가 생성한 쉘 스크립트(쉘 프로그램)들을 모아 놓은 디렉토리입니다. 이 디렉토리에는 다양한 쉘 스크립트 파일이 존재합니다.

또한, PATH는 명령어들이 위치한 디렉토리를 선언할 때 사용하는 변수입니다. PATH를 이용하면 /root/bin 디렉토리에 있는 쉘 스크립트 파일을 편하게 실행할 수 있습니다.

# echo $PATH
/usr/lib/qt-3.3/bin:/usr/kerberos/sbin:/usr/kerberos/bin:/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin:/root/bin

위 명령어를 입력하면 PATH 변수에 저장된 경로를 확인할 수 있습니다.

쉘 스크립트 파일을 실행할 때는 상대경로나 절대경로를 이용해서 실행할 수 있습니다. 예를 들어, ls 명령어를 실행할 때는 /bin/ls나 ./ls -al 같은 방식으로 실행할 수 있습니다.

또한, 아래와 같은 명령어를 이용해서 새로운 디렉토리를 생성할 수 있습니다.

# mkdir -p /backup
# mkdir -p /root/bin

만약 새로운 쉘 스크립트 파일을 작성하고 싶다면, 아래와 같은 명령어를 입력하세요.

# vi /root/bin/backup.sh

위 명령어를 입력하면 vi 에디터가 실행되며, backup.sh 파일을 작성할 수 있습니다. 아래는 backup.sh 파일의 내용입니다.

#!/bin/bash
tar cvzf /backup/back-date +%m%d.tar.gz --absolute-name /test

위 쉘 스크립트 파일은 /test 디렉토리의 모든 파일을 back-MMDD.tar.gz라는 이름으로 /backup 디렉토리에 백업하는 기능을 수행합니다.

쉘 스크립트 파일을 실행할 수 있도록 권한을 변경해야 합니다. 아래와 같은 명령어를 입력하세요.

# chmod 755 /root/bin/backup.sh

마지막으로, /root/bin 디렉토리를 PATH 변수에 추가해서 backup.sh 파일을 실행할 수 있게 만들어야 합니다. 아래와 같은 명령어를 입력하세요.

# export PATH=$PATH:/root/bin
# backup.sh
# cd /backup ; ls

위 명령어를 입력하면 /backup 디렉토리에 백업된 파일이 생성됩니다.

 

백업 스크립트 실패 유무 확인

아래는 백업 스크립트를 실행하면서 발생한 오류를 확인하는 예시입니다.

먼저, 아래와 같은 스크립트를 작성합니다.

#!/bin/bash

/root/bin/backup.sh
if [ $? -eq 0 ] ; then
    echo "Backup Success"
else
    echo "Backup Fail"
fi

위의 스크립트는 /root/bin/backup.sh 스크립트를 실행한 후, 실행 결과에 따라 "Backup Success" 또는 "Backup Fail"을 출력합니다.

다음으로, 스크립트에 실행 권한을 부여합니다.

chmod 755 /test/script.sh

이제 스크립트를 실행해봅니다.

./script.sh

위와 같이 스크립트를 실행하면, /root/bin/backup.sh 스크립트가 실행되고, 실행 결과에 따라 "Backup Success" 또는 "Backup Fail"이 출력됩니다.

그런데, /root/bin/backup.sh에서 오류가 발생할 경우에는 어떻게 될까요?

다음과 같이 /root/bin/backup.sh 스크립트를 작성합니다.

#!/bin/bash

tar cpvfz /backup/back-`date +'%m%d'`.tar.gz --absolute-name /nodir

위의 스크립트는 /nodir이라는 디렉토리를 아카이브로 묶어서 /backup/back-월일.tar.gz 파일로 저장합니다. 그런데, /nodir 디렉토리가 존재하지 않기 때문에 오류가 발생합니다.

이제 스크립트를 실행해봅니다.

./script.sh

위와 같이 스크립트를 실행하면, 오류 메시지가 출력됩니다.

tar: /nodir: Cannot stat: 그런 파일이나 디렉토리가 없음
tar: Error exit delayed from previous errors
Backup Fail

스크립트에서 오류가 발생하면 "Backup Fail"이 출력됩니다.

스크립트를 실행할 때 오류 메시지를 확인하기 위해서는, 스크립트를 실행하는 명령어 뒤에 > backup.log 2>&1을 추가하면 됩니다.

./script.sh > backup.log 2>&1

위와 같이 스크립트를 실행하면, 실행 결과가 backup.log 파일에 저장됩니다.

backup.log 파일을 열어보면, 아래와 같은 내용이 출력됩니다.

tar: /nodir: Cannot stat: 그런 파일이나 디렉토리가 없음
tar: Error exit delayed from previous errors
Backup Fail

따라서, 스크립트를 실행할 때 오류가 발생하면, backup.log 파일을 확인하여 오류 메시지를 확인할 수 있습니다.

(결론) 백업 스크립트를 실행할 때 발생한 오류를 확인하는 방법은, 스크립트를 실행할 때 오류 메시지를 출력하도록 스크립트를 작성하거나, 스크립트를 실행하는 명령어 뒤에 > 파일명을 추가하여 실행 결과를 파일에 저장하는 것입니다.

 

백그라운드에서 실행되는 프로세스의 PID 확인

!는 바로 이전에 실행한 백그라운드 프로세스의 PID를 나타내는 특수 변수입니다. 이전에 백그라운드로 실행한 프로세스의 PID를 확인하는 방법은 다음과 같습니다.

# sleep 300 &
[1] 25192
# echo $!
25192

위의 코드에서는 sleep 명령어를 백그라운드에서 실행하고, 이전에 실행한 백그라운드 프로세스의 PID인 25192를 확인합니다. $!는 이전에 실행한 백그라운드 프로세스의 PID를 나타내는 특수 변수입니다.

# ps
PID TTY          TIME CMD
24868 pts/1    00:00:00 bash
25101 pts/1    00:00:00 bash
25192 pts/1    00:00:00 sleep
25219 pts/1    00:00:00 ps
# sleep 400 &
[2] 25233
# ps
PID TTY          TIME CMD
24868 pts/1    00:00:00 bash
25101 pts/1    00:00:00 bash
25192 pts/1    00:00:00 sleep
25233 pts/1    00:00:00 sleep
25234 pts/1    00:00:00 ps
# echo $!
25233

위의 코드는 ps 명령어를 사용하여 현재 실행 중인 프로세스를 확인하고, sleep 명령어를 다시 백그라운드에서 실행합니다. $!를 사용하여 이전에 실행한 백그라운드 프로세스의 PID인 25233를 확인합니다.

 

인자변수(Argument Variable)

인자 변수(Argument Variable)는 스크립트나 함수에 전달되는 인자를 저장하기 위해 사용하는 변수입니다. $ 기호를 사용하여 인자 변수의 값을 나타낼 수 있습니다. 인자 변수는 $1, $2, $3과 같이 표현됩니다. $1은 첫 번째 인자를 나타내며, $2는 두 번째 인자를 나타냅니다.

아래는 인자 변수를 사용한 예제입니다.

$로 표시하여 인자변수의 값이 몇 번째인지 나타낼 수 있다.   인자변수1 | 인자변수2 | 인자변수3
		# ls -a
		# vi ls
		----------------------------------
		..... (중략) .....
		echo "$1"
		..... (중략) .....
		----------------------------------

위의 코드에서는 $1을 이용하여 첫 번째 인자 값을 출력합니다.

# cd /test
# vi test.sh
--------------------------------------
		#!/usr/bin/bash

		echo $1                     /* 첫번째 인자 */
		echo $2                     /* 두번째 인자 */
		echo $3                     /* 세번째 인자 */
--------------------------------------
# chmod 755 test.sh
# ls -l test.sh
-rwxr-xr-x 1 root root    38 Aug 19 14:22 test.sh
# ./test.sh test1 test2 test3
test1
test2
test3

위의 코드에서는 test.sh 파일을 작성하고, 이를 실행할 때 test1, test2, test3이라는 인자 값을 전달합니다. 실행 결과, 각 인자 값이 순서대로 출력됩니다.

# date
Thu Aug 19 14:24:33 KST 2010
# set $(date)
# echo $1
Thu
# echo $2
Aug
# echo $3
19
# echo $4
14:24:47
# echo $5
KST
# echo $6
2010

위의 코드에서는 date 명령어를 실행하고, 이를 set 명령어를 이용하여 인자 변수로 전달합니다. 실행 결과, $1부터 $6까지의 인자 값이 순서대로 출력됩니다.

인자 변수 예제의 코드를 각각 설명해드리겠습니다.

$로 표시하여 인자변수의 값이 몇 번째인지 나타낼 수 있다.   인자변수1 | 인자변수2 | 인자변수3
		# ls -a
		# vi ls
		----------------------------------
		..... (중략) .....
		echo "$1"
		..... (중략) .....
		----------------------------------

위 코드에서는 $1을 이용하여 첫 번째 인자 값을 출력합니다. 하지만 $1의 값이 지정되지 않아서 아무 것도 출력되지 않습니다.

# cd /test
# vi test.sh
--------------------------------------
		#!/usr/bin/bash

		echo $1                     /* 첫번째 인자 */
		echo $2                     /* 두번째 인자 */
		echo $3                     /* 세번째 인자 */
--------------------------------------
# chmod 755 test.sh
# ls -l test.sh
-rwxr-xr-x 1 root root    38 Aug 19 14:22 test.sh
# ./test.sh test1 test2 test3
test1
test2
test3

위 코드에서는 test.sh 파일을 작성하고, 이를 실행할 때 test1, test2, test3이라는 인자 값을 전달합니다. 실행 결과, 각 인자 값이 순서대로 출력됩니다.

# date
Thu Aug 19 14:24:33 KST 2010
# set $(date)
# echo $1
Thu
# echo $2
Aug
# echo $3
19
# echo $4
14:24:47
# echo $5
KST
# echo $6
2010

위 코드에서는 date 명령어를 실행하고, 이를 set 명령어를 이용하여 인자 변수로 전달합니다. 실행 결과, $1부터

 

PATH 변수

명령어를 검색할 디렉토리를 선언할 때 사용하여 절대 경로를 쓰지 않고 실행파일명만을 이용해서 사용할 수 있는 PATH 변수는 매우 유용합니다. which 명령어도 PATH에 설정되어 있는 디렉토리의 파일의 경로만을 알려줍니다. 이러한 기능을 이용하여 명령어를 더욱 효율적으로 사용할 수 있습니다.

아래는 PATH 변수를 이용하여 명령어를 실행하는 예시입니다.

# gedit &   # gedit 실행
# which gedit   # gedit이 설치된 위치 출력
/usr/bin/gedit
# echo $PATH   # PATH 변수에 등록된 디렉토리의 목록을 출력
/usr/lib/qt-3.3/bin:/usr/kerberos/sbin:/usr/kerberos/bin:/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin:/root/bin:/root/bin
# cd   # 홈 디렉토리로 이동
# ls -l /test/script.sh   # /test 디렉토리의 스크립트 파일 출력
-rwxrwxrwx 1 root root 109  5월 20 15:26 /test/script.sh

(필요하면 아래와 같이 /test/script.sh 스크립트를 생성합니다.)

# vi /test/script.sh
------------------------------
#!/bin/bash

echo "script.sh Excution"
------------------------------
# chmod 755 /test/script.sh

위에서 생성한 스크립트를 이용하여 명령어를 실행하는 예시입니다.

# script.sh   # 스크립트 파일 실행
-bash: script.sh: command not found
		(절대경로)# /test/script.sh   # 절대 경로를 이용하여 실행
		(상대경로) # cd /test   # /test 디렉토리로 이동
		# ./script.sh   # 상대 경로를 이용하여 실행
		# script.sh   # PATH 변수에 등록되어 있기 때문에 실행 가능

PATH 변수를 설정하는 방법은 다양합니다. 아래는 PATH 변수를 설정하는 방법 중 하나입니다.

  1. vi ~/.bash_profile 명령어를 이용하여 .bash_profile 파일을 엽니다.
  2. PATH=$PATH:/test 라인을 추가합니다.
  3. export PATH 명령어로 PATH 변수를 등록합니다.
  4. unset USERNAME으로 USERNAME 환경 변수를 제거합니다.
  5. . ~/.bash_profile 명령어로 변경사항을 적용합니다.
  6. echo $PATH 명령어로 PATH 변수를 출력합니다.

위와 같이 PATH 변수를 설정하면 새로운 디렉토리에서도 이전에 설정한 명령어들을 사용할 수 있습니다.

 

HISTTIMEFORMAT 변수

# export LANG=C
# man bash
------------------------------
/HISTTIMEFORMAT
       HISTTIMEFORMAT
              If this variable is set and not null,  its  value
              is  used  as  a  format string for strftime(3) to
              print the time stamp associated with each history
              entry  displayed by the history builtin.  If this
              variable is set, time stamps are written  to  the
              history  file  so  they  may  be preserved across
              shell sessions.
------------------------------
# man 3 strftime
------------------------------
/%F
       %F     Equivalent  to  %Y-%m-%d  (the ISO 8601 date for-
              mat). (C99)
/%T
       %T     The time in 24-hour notation (%H:%M:%S). (SU)
# vi /etc/profile
..... (중략) .....
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

#
# (1) Sfecific Configuration
#
export HISTTIMEFORMAT="%F %T     "

unset i
unset pathmunge
------------------------------
# telnet localhost
root 사용자로 로그인

# history
..... (중략) ....
  776  10:07:00     clear
  777  10:07:11     clear
  778  10:10:42     clear
  779  10:12:43     export LANG=C
  780  10:13:12     man bash
  781  10:15:13     clear
  782  10:15:16     man 3 strftime
  783  10:17:49     vi /etc/profile
  784  10:20:15     history
# exit
#

export LANG=C 명령어를 실행하여 LANG 환경 변수에 C 값을 할당합니다. 이러한 설정을 하면 언어 환경이 C로 설정되어 출력되는 메시지들이 영어로 출력됩니다.

man bash 명령어를 실행하여 bash 매뉴얼을 확인합니다. 매뉴얼에서 HISTTIMEFORMAT 환경 변수에 대한 설명을 찾습니다.

man 3 strftime 명령어를 실행하여 strftime 함수 매뉴얼을 확인합니다. strftime 함수는 시간을 문자열 형식으로 변환하는 함수입니다.

/etc/profile 파일을 편집합니다. 해당 파일은 모든 사용자에 대한 전역 설정 파일입니다. 파일 내부에는 HISTTIMEFORMAT 환경 변수에 값을 할당하는 과정이 있습니다.

telnet localhost 명령어를 실행하여 로컬 호스트에 로그인합니다.

history 명령어를 실행하여 이전에 실행한 명령어 목록을 확인합니다. 이때, 명령어 앞에는 실행한 시간이 출력됩니다.

HISTTIMEFORMAT 환경 변수는 history 명령어에서 실행한 명령어와 함께 실행한 시간을 함께 출력할 수 있도록 해주는 변수입니다. 위의 코드에서는 이러한 변수를 설정하기 위해 export HISTTIMEFORMAT="%F %T "와 같은 방식으로 변수를 설정하였습니다.

위의 과정에서 어떤 오류가 있었다면 추가로 알려주시면 수정하여 안내드리겠습니다.

 

메타캐릭터(Metacharacter)

메타캐릭터는 쉘에서 특별한 의미를 가지는 문자로, 스크립트를 작성할 때 자주 사용됩니다. 아래는 일반적으로 사용되는 메타캐릭터와 해당 메타캐릭터가 가지는 의미를 설명한 것입니다.

작은 따옴표(single quotation): 쉘이 해석할 수 없도록 막아 줍니다. 예를 들어, echo '$HOME'은 $HOME을 그대로 출력합니다.

# echo $HOME
/root
# echo '$HOME'
$HOME

큰 따옴표(double quotation): 쉘이 해석할 수 없도록 막아 줍니다. 다만, $, ```, \\\\\\\\와 같은 특수문자는 인식됩니다. 예를 들어, echo "$HOME is my directory."는 $HOME이 현재 사용자의 디렉토리로 대체된 문자열을 출력합니다.

# echo $HOME
/root
# echo "$HOME"
/root
# echo "$HOME is my    directory."
/root is my    directory.

역 따옴표(back quotation): 쉘이 명령어로 인식합니다. 예를 들어, echo date``와 echo $(date)는 같은 결과인 현재 날짜와 시간을 출력합니다.

# date
# echo `date`     (# echo $(date))
# echo `hostname` (# echo $(hostname))
# echo "`hostname` is my hostname."

# touch server_`date +%m%d`.log
# tar cvzf /backup/home_`date +%m%d`.tar.gz /home
# while true
> do
> echo "------------`date`---------"
......
> sleep 2
> done

역 슬래시(back slash): 뒤따라오는 문자를 쉘이 해석하지 않도록 막아 줍니다. 예를 들어, echo \\\\\\\\$HOME은 $HOME을 그대로 출력합니다.

# echo $HOME
# echo \\\\$HOME    (# echo '$HOME')

# find / -name core -type f -exec rm -f {} \\\\;
# find / \\\\( -perm -4000 -o -perm -2000 \\\\) -type f

		[참고] \\\\(역 슬래쉬)
		# \\\\CMD
		# CMD\\\\

		# ./configure --prefix=/usr/local/apache2 --options2=.... --options3=.... ....
		# ./configure —prefix=/usr/local/apache2 \\\\
		> --options2=.... \\\\
		> --options3=.... \\\\
		> --options4=....

세미콜론(semicolon): 한 줄에 여러 명령어를 입력할 때 사용됩니다. 예를 들어, ls ; date ; cal은 ls, date, cal을 순서대로 실행합니다.

# ls
# date
# cal

# ls ; date ; cal

# alias pps='ps -ef | head -1 ; ps -ef | grep $1'
# EDITOR=/usr/bin/vim ; export EDITOR    (# export EDITOR=/usr/bin/vim)

위의 코드 예시는 메타캐릭터가 어떻게 사용되는지 설명하고 있습니다. 메타캐릭터는 스크립트를 작성할 때 매우 유용하지만, 실수로 인한 오류가 발생할 수 있으므로 조심해야 합니다.

반응형