[shall script] 명령어 정리

김탁형·2025년 1월 1일

1. 쉘 스크립트

(1) 정의

쉘 스크립트란 간단히 말하자면 Unix 커맨드 등을 나열해서 실행하는 것이다. 언제 어떤 조건으로 어떠한 명령을 실행시킬 것인가, 파일을 컨텐츠를 읽어 들일 것인가, 로그 파일을 작성하는 것 등을 할 수 있다.
또 다른 뜻으로 운영체제의 shell 을 이용하여 한줄씩 순차적으로 읽으면서 명령어들을 실행 시켜주는 인터프리터 방식 의 프로그램 이다.

(2) 기본 설정

1) 작성

예시로 다음과 같이 test.sh 파일을 작성한다.

#!/bin/sh
echo "Hello, World!"
  • 쉘 스크립트 파일은 기본적으로 .sh 확장자로 작성한다.
  • 실제 코드를 작성하기 전에 맨 처음의 행에는 #!/bin/sh 를 쓴다. 시스템에 지금부터 쉘 스크립트를 쓴다는 사실을 알려주기 위함이다.
#!bin/sh

# 는 hash, ! 는 bang 이므로 #!를 shebang 이라고 부르기도 한다.
그러나 bash의 독자적인 기능을 사용하는 경우 다르게 작성한다. (#!/usr/bin/env bash).

2) 실행

쉘 스크립트 파일(test.sh) 를 실행하기 위해서는, 터미널에서 파일이 저장된 장소에 가서 아래 커맨드 중 하나를 선택해서 실행해야한다

<입력>

chmod 755 test.sh
./test.sh
sh test.sh
bash test.sh

<출력>

Hello, World!

2. 쉘 스크립트 명령어

(1) 코멘트

1) 예시

#!/bin/sh

# 여기는 코멘트이다.
# 코멘트처리된 구문은 실행되지 않는다.

echo "Hello, World!"

(2) 입력/출력

1) 설명

echo 로 출력, read 로 입력할 수 있다.

2) 예시

<작성>

#!/bin/sh

read NAME
echo "Hello, $NAME!"

<실행>

$ ./test.sh
Tensai
Hello, Tensai!

입력을 대기 하고 있는 경우, 스크립트는 실행되지 않는다.
또한 Bash 에서는 -e 플래그로 특수 텍스트를 이스케이프할 수 있다.

#!/bin/bash
echo -e "Hello\n$NAME!" #개행된다.

(3) 변수

1) 설명

  • 변수의 이름으로써 영문자, 숫자 그리고 언더바가 사용된다.
  • 변수에 값을 전달할 때는 = 의 앞,뒤 공백 없이 작성한다. 문자열인 경우 "(쌍따옴표)로 감싼다.
  • 변수에 엑세스할 때 변수명의 앞에 $를 넣는다. 혹은 $ 넣어서 변수를 {} 로 감싼다.
  • 하나의 변수에 한 개의 값만 보존된다.
  • 변수의 값이 덮어 쓰기 되는 것을 방지하기 위해서는 readonly를 사용한다.
  • 변수를 unset으로 삭제할 수 있다. 그러나 readonly 변수를 삭제하는 것을 불가능 하다.

2) 예시

<작성>

#!/bin/sh
var = "변수1"
VaR_2 = "변수2"
echo "Var_2=$VaR_2"

VaR_2="VaR_2가 변경됐다"
echo ${VaR_2}

readonly var
var="readonly var를 바꿔보자"

<실행>

$ ./test.sh
Var_2=변수2
VaR_2가 변경됐다.
shell.sh: line 11: var: readonly variable

(4) 특별한 변수

1) 설명

쉘 스크립트에서는 아래와 같은 특별한 변수가 있다.

변수기능
$0스크립트명
$1~ $9인수, 첫 번째의 인수는 $1, 2번째의 인수는 $2 로 엑세스
$#스크립트에 전달된 인수의 수
$*모든 인수를 모아 하나로 처리
$@모든 인수를 각각 처리
$?직전에 실행한 커맨드의 종료값(0은 성공, 1은 실패)
$$이 쉘 스크립트의 프로세스 ID
$!마지막으로 실행한 백그라운드 프로세스 ID

2) 예시

<작성>

#!/bin/sh

echo "\$0(스크립트 명): $0"
echo "\$1(1번째 인수): $1"
echo "\$2(2번째 인수): $2"
echo "\$#(인수의 수): $#"
echo "\"\$*\": \"$*\""
echo "\"\$@\": \"$@\""
VAR="exit값은0이 될 것이다."
echo $?

<실행>

$ ./test.sh first second 3rd
$0(스크립트 명): test.sh
$1(1번째 인수): first
$2(2번째 인수): second
$3(3번째 인수): 3rd
$#(인수의 수): 3
"$*": "first second third"
"$@": "first second third"
0

(5) 특수문자

1) 설명

* ? [ ' " \ $ ; & ( ) | ~ < > # % = 스페이트 탭 개행 는 쉘 스크립트의 특수 문자 이다. 문자열로써 사용할 때는 \ 를 앞에 쓴 다음에 쓴다.

(6) 배열

1) 설명

2) 예시

<작성>

#!/bin/bash

#bash shell로 배열을 작성하는 방법
ARRAY=(item1 item2 item3 item4)
ARRAY[0]="ITEM1"
ARRAY[2]="ITEM3"

echo "ARRAY[0]: ${ARRAY[0]}"
echo "ARRAY[1]: ${ARRAY[1]}"

#모든 아이템에 액세스
echo "ARRAY[*]: ${ARRAY[*]}"
echo "ARRAY[@]: ${ARRAY[@]}"

<실행>

$ ./test.sh
ARRAY[0]: ITEM1
ARRAY[1]: item2
ARRAY[*]: ITEM1 item2 ITEM3 item4
ARRAY[@]: ITEM1 item2 ITEM3 item4

(5) 오퍼레이터

1) 산수 연산자

shell 에서는 산수연산자로 expr 숫자 연산자 숫자 를 이용한다.

연산자의미
+덧셈echo ` expr 10+20` =>30
-뺄셈echo ` expr 20-10` =>10
\*echo ` expr 11\*11` =>121
/나눗셈echo ` expr 10/2 ` =>5
%나머지echo ` expr 10%4` =>2
=저장a=$b b의 값은 a에 저장된다
==동일["$a" ==" $b"] $a 과 $b가 동일하는 경우 true 가 반환된다.
!=다름["$a" != " $b"] $a 과 $b가 동일하지 않을 경우 true 가 반환된다.

2) 비교 연산자

연산자의미
-eq동일["$a" -eq " $b"] $a 과 $b가 동일하는 경우 true 가 반환된다.
-ne다름["$a" -ne " $b"] $a 과 $b가 동일하지 않을 경우 true 가 반환된다.
-gt보다 큼["a"gt"a" -gt "b"] $a 가 $b보다 큰 경우 true 가 반환된다.
-lt보다 작음["$a" -lt " $b"] $a 가 $b보다 작은 경우 true 가 반환된다.
-ge보다 크거나 같거나["$a" -ge " $b"] $a 가 $b보다 크거나 같은 경우 true 가 반환된다.
-le보다 작거나 같거나["$a" -le " $b"] $a 가 $b보다 작거나 같은 경우 경우 true 가 반환된다.
!(이)가 아니다[!"$a" -gt " $b"] $a 가 $b보다 크지 않은 경우 true 가 반환된다.
-oOR["$a" -gt " $b" -o " $a" -lt " $b"] $a 가 $b보다 크거나 작은 경우 true 가 반환된다. (Bash 확장 / POSIX 폐지 예정)
-aAND["$a" -gt 90 -a " $a" -lt 100 ] $a 가 90보다 크고 100보다 작은 경우 true 가 반환된다.
-z문자열 null 여부[-z "$a"] $a에 어떤 것도 지정되지 않은 경우 true 가 반환된다.
-n문자열 null 여부[-z "$a"] $a에 어떤 것도 지정되어 있다면 true 가 반환된다.

3) if 조건

  • 위 비교 연산자를 근거로 if 조건을 작성 할 수 있다.
  • 기본 작성법은 if[조건] then 커맨드 fi 이다.
  • 조건 과 일치하는 경우 then 뒤의 커맨드가 실행된다.
  • 조건과 다른 경우 차례로 elif[조건] 에 적힌 내용을 확인한다.
  • 일치하는 조건이 없는 경우 else 다음의 커맨드가 실행된 후 종료된다.
  • else 가 존재하지 않은 경우, 그대로 종료된다.
    <작성>
#!/bin/sh

if["$1" -gt "$2"]
then
echo"1번째 인수가 2번째 보다 크다"
elif["$1" -eq "$2"]
then
echo"1번째 인수와 2번째 인수가 동일하다"
else
echo"1번째 인수가 2번째 인수가 작다"
fi

<실행>

 ./test.sh 2 7
1번째 인수가 2번째 인수보다 작다
$ ./test.sh 10 5
1번째 인수가 2번째 인수보다 크다
$ ./test.sh 9 9
1번째 인수와 2번째 인수가 동일하다

(6) 루프(반복문)

  • break 키워드로 종료
  • continue 키워드로 현재의 루프를 건너 뛸 수 있다.

1)while

조건과 일치할 때 반복된다.
<작성>

#!/bin/sh

a=0
while [ $a -lt 5 ]
do
    echo $a
    a=`expr $a + 1`
done

<실행결과>

$ ./test.sh
0
1
2
3
4

2)until

while과 반대로, 조건과 일치할 때까지 반복된다.
<작성>

#!/bin/sh

a=0
until [ ! $a -lt 5 ]
do
    echo $a
    a=`expr $a + 1`
done

<실행결과>

$ ./test.sh
0
1
2
3
4

3) for

  • for의 기본 작성법은 for 변수 in [여러개의값] [변수] [범위] do 커맨드 done 이다.
  • 조건 값이 변수와 일치하는 경우 커맨드가 실행된다.
    <작성>
#!/bin/sh

for var in 0 1 2 3 4  #범위의 작성법(Bash독자) => {0..4}
do
    echo $var
done

<실행결과>

$ ./test.sh
0
1
2
3
4

(7) 함수

1) 설명

  • 쉘 스크립트에서는 함수를 작성하여 인용하는 것이 가능하다

2) 예시

<작성>

#!/bin/sh

#함수를 작성한다
MyFunction () { 
    echo "함수의 echo이다."
}
MyParamFunc() {
    echo "인수1:$1 인수2:$2"
}

#함수를 호출한다
MyFunction
MyParamFunc param1 param2

<실행결과>

$ ./test.sh
함수의 echo입니다.
인수1:param1 인수2:param2

(8) awk

1) 설명

  • 입력을 주어진 분리자(field seperator)로 분리하여 명령을 처리한다.
  • 기본작성법으론 awk [주요옵션] [내장함수]

2) 주요 옵션

연산자의미
-F문자열을 분리할 기준이 되는 분리문자 입력
-v파라미터 전달

3) 내장 함수

  • awk는 지정한 처리를 실행할 떄 내장 함수를 이용할 수 있다.
함수의미
sub지정한 문자열 치환
gsub문자열 일괄 치환
index주어진 문자열과 일치하는 문자의 인덱스를 반환
length문자열의 길이를 반환
substr시작위치에서 주어진 길이 만큼의 문자열 반환
split문자열을 분리하여 배열로 반환
print문자열 출력
printf지정한 포맷에 따라 함수 출력
system명령 실행

4) 예시

  • print : 문자열 출력
$echo "Hello World" | awk '{print $0}'
> ello World

$echo "Hello World" | awk '{print $1}'
> Hello

$echo "Hello World" | awk '{print $2}'
> World

$echo "Hello,World" | awk -F "," '{print $2}'
> World
  • sub : 지정한 문자열 치환
$echo "i have a water." | awk -F " " '{sub("a","b",$4); print $4}'
> wbter
  • gsub : 문자열 일괄 치환
$echo "i have a water." | awk -F " " '{gsub("a","b"); print $1""$2""$3""$4}'
> i hbve b wbter.
  • index : 주어진 문자열과 일치하는 문자의 인덱스를 반환
$echo "i have a water." | awk -F ""'{print index($4, "a")}'
> 2
  • length : 문자열의 길이를 반환
$echo "i have a water." | awk -F ""'{print length($4)}'
> 6
  • substr : 시작위치에서 주어진 길이 만큼의 문자열 반환
$echo "i have a water." | awk -F ""'{print substr($1,3,2)}'
> 34
  • split : 문자열을 분리하여 배열로 반환
$echo "A/B/C/D/E/F/G" | awk -F ""'{print split($1,array,"/"); print array[1];print array[3];}'
> 7
> A
> C
  • printf :지정한 포맷에 따라 함수 출력
$echo | awk '{printf("%.1f+%.2f = %.3f\n", 40.1, 20.2, 40.1 + 20.2);}'
> 40.1 + 20.20 = 60.300
  • system : 명령 실행
# system 으로 추가 명령어 실행
$ echo "Hello World" | awk '{system("echo "$1)}'
> Hello

5) 사용 예제

  • 그룹의 합 구하기
    그룹의 합을 구하는 것은 배열을 이용한다. 배열의 인덱스를 키로 사용하여 값을 모두 더하여 마지막에 출력하면 된다.
$ cat sample.txt
a 1
b 2
a 4 
c 1
c 2

$cat sample.txt | awk '{arr[$1] += $2} END { for (i in arr) { print i, arr[i]}}'
a 5
b 2
c 3
  • 합계 구하기
    합계는 지정한 인덱스의 값을 모두 더하여 구할 수 있다.
$ cat sample.txt
a 1
b 2
a 4 
c 1
c 2

$ cat sample.txt | awk '{sum+=$2} END {print sum}'
> 10
  • 문자열 자르기
    문자열을 자를 때는 내장 함수 substr 을 이용
$echo "1234567890" | awk -F ""'{print substr($1,3,2)}'
> 34
  • 파라미터 전달
    awk에 파라미터를 전달 할 때는 v 옵션을 이용한다. v옵션과 함께 이름=값 형태로 전달하고 내장함수에서 사용하면 된다.
root = "/webroot"
$ echo | awk -v r = $root'{print "shell root value - "r}'
shell root value - /webroot

출처
https://engineer-mole.tistory.com/200

profile
김탁형/성남/31

0개의 댓글