제  목 : 여러 서버의 load를 터미널에서 실시간 모니터링
작성자 : 좋은진호(truefeel, http://coffeenix.net/ )
작성일 : 2008.2.13(수)~15(금)

'리눅스 터미널(CLI모드)에서 보는 실시간 시계' ( http://coffeenix.net/bbs/viewtopic.php?t=2836 )에 대해 소개한 적이 있다. 이 시계 스크립트는 터미널의 오른쪽 상단에 실시간으로 시간을 표시한다. 

[ 터미널에서 시계 ] (1초단위로 시간이 바뀌면서 표시된다.)


1. 한화면 실시간 load 모니터링 개요

시계 스크립트를 응용하여, 여러 서버의 load를 한화면에서 볼 수 있도록 구현하였다. 스크립트는 다음과 같은 역할을 한다.

1) tput 명령과 ANSI코드를 이용하여 원하는 위치에 load를 표시한다.
2) 1~9초간격으로 새로운 데이터를 표시한다.
3) '로그 모니터링시 특정 문자를 highlight하기' ( http://coffeenix.net/board_view.php?bd_code=1562 , 글 좋은진호)에서 소개한 방법을 이용하여 load별로 다른 색을 표시한다.

   -------   --------
   load       색깔
   -------   --------
   0.0       하얀색
   0.1~0.39  녹  색
   0.4~0.79  파란색
   0.8~이상  빨간색
   -------   --------

4) 숫자 1~9까지 누르면 시간 간격을 변경할 수 있다. (단, foreground로 실행시)
5) q를 누르면 종료한다. (단, foreground 실행시)

참고로 서버는 10여대 정도만 샘플로 표시하였으며, 이미지상의 서버명은 실제 사용하지 않는 임의의 서버명이다.

[ load 모니터링 샘플 화면 ]


2. 미리 준비되어 있어야할 사항

통합 로그 서버와 각 서버에서 load를 보내주도록 처리해야 한다. 구축 방법에 대해서는 간략히 얘기하고, 시간이 될 때 추가 문서를 통해 설명하겠다.

1) 각 서버에서는 logger를 활용하여 서버의 load를 syslogd로 보내준다. 

  
 
   LOAD="`uptime|awk -F': '{print $2}'`"
   logger -p 로그의레빌 -t LOAD "호스트명 -> 현재시간 load $LOAD"
  
 


   syslogd 는 load부분에 대한 로그를 통합로그로 보내지도록 설정해야 한다. 이 때 서버의 load는 5~10초 간격, 또는 더 긴 간격으로 체크하여 syslogd로 보내주면 된다.

2) 통합 로그 서버에서는 각 서버의 syslog 결과를 받을 수 있도록 설정한다. 통합서버는 FreeBSD를 권장하지만, 리눅스 서버를 사용할 경우 syslog-ng를 통해서 로그 서버 구축한다. 각 서버에서 오는 load정보는 서버별로 별도 파일에 저장하도록 하는 것이 중요하다. 예를 들어 cnx10.log, cnx22.log, cnx25.log, ... 처럼. 통합로그 서버의 서버별 로그 파일에는 다음과 같이 형태로 로그가 저장된다.

 
Jan  6 00:00:04 192.168.123.140 LOAD: cnx10 -> 00:00:04 load 0.07, 0.03, 0.00
 


FreeBSD에서 실행할 때는 다음 2가지 사항을 체크해야 한다.
FreeBSD의 tput은 cursor 이동을 지원하지 않으므로 OpenBSD의 소스(ftp://ftp.openbsd.org/pub/OpenBSD/src/usr.bin/tput )를 가져다가 사용해야 한다. 또한 스크립트에서 사용한 read 옵션 -n, -s는 bash에 의존적으로 동작한다. /usr/ports/shells/bash ports 디렉토리에서 설치한다.

3. load 모니터링 스크립트

load_mon.sh 내려받기
 
#!/bin/bash
#
# system load를 실시간으로 모니터링
#
# by 좋은진호(truefeel, http://coffeenix.net/ )
# 2008.2.12~

# foreground로 실행할 때는 0으로, background로 할 때는 1로
fg=0

# 데이터를 실시간으로 보여줄 간격 (초단위)
sleep=2

# 오른쪽에서 몇번째 칸에 표시할 것인지 설정
cols=22

#
LOGDIR="/var/log/load"
TPUT="/usr/bin/tput"

# color
szColBk="^[[;30m";      szColBk1="^[[1;30m"     # black
szColRe="^[[;31m";      szColRe1="^[[1;31m"     # red
szColGr="^[[;32m";      szColGr1="^[[1;32m"     # green
szColYe="^[[;33m";      szColYe1="^[[1;33m"     # yellow
szColBl="^[[;34m";      szColBl1="^[[1;34m"     # blue
szColPu="^[[;35m";      szColPu1="^[[1;35m"     # magenta(purple)
szColCy="^[[;36m";      szColCy1="^[[1;36m"     # cyan
szColGy="^[[;37m";      szColWh="^[[1;37m"      # white
szInverse="^[[7m"
szInvOff="^[[27m"
szNormal="^[[;m"

#
szColLev1=$szColYe
szColLev2=$szColBl
szColLev3=$szColRe1

# ------------------------------------------------
#
keyinput () {
        stty -icanon
        read -t $sleep -n 1 -s time
        stty icanon

        case $time in
                [1-9])
                        sleep=$time
                        C=$((`$TPUT cols` - $cols))
                        $TPUT cup $row $C
                        echo "${szInverse} Delay time : $time sec   $szNormal"
                        ;;
                [qQ])
                        echo -n  "^[[u"
                        exit 0
                        ;;
        esac
}

# ------------------------------------------------
# 실시간 처리 시작
# ------------------------------------------------
# foreground면 화면 clear
if [ $fg -eq 0 ]; then
        clear
fi

cd $LOGDIR

while :
do

        # ------------------------------------------------
        # 결과값 추출
        # ------------------------------------------------
        cmd_local=`uptime | awk -F': ' '{print $2}'|awk -F', ' '{print $1 "|" $2 "|" $3 " "}'`
        cmd=`tail -1 *.log | grep : | awk '{print $6 "|" $10 "|" $11 "|" $12 " "}'`
        result="LOC_|$cmd_local $cmd"

        # highlight
        result_color=`echo "$result" \
        | sed \
                -e "s/,//g" \
                -e "s/\(0\.0\)/${szColGy}\\1/g" \
                -e "s/\(0\.[1-3]\)/${szColGr}\\1/g" \
                -e "s/\(0\.[4-7]\)/${szColBl1}\\1/g" \
                -e "s/\(0\.[8-9]\)/${szColLev3}\\1/g"  \
                -e "s/\([1-9]\.\)/${szColLev3}\\1/g"`

        # ------------------------------------------------
        # cursor 위치 저장
        echo -n "^[[s"

        $TPUT el         # cleans from position to end of line

        # ------------------------------------------------
        # 결과값을 출력
        # ------------------------------------------------
        col_width=`$TPUT cols`                  # column 길이

        #지정한 cols보다 좁으면 종료
        if [ $col_width -lt $cols ]; then
                echo "터미널의 폭이 너무 좁습니다."
                exit
        fi

        C=$(($col_width - $cols))               # data를 표시할 column 위치 계산
        row=0
        $TPUT civis                             # cursor 숨김
        for line in $result_color
        do
                $TPUT cup $row $C               # cursor 이동
                row=`expr $row + 1 `            # row 증가
                echo -n "$szColYe$szInverse$line$szNormal"
        done
        $TPUT cnorm                             # cursor 다시 표시

        # ------------------------------------------------
        if [ $fg -eq 0 ]; then
                keyinput
        else
                 # cursor 위치를 원래대로
                echo -n  "^[[u"

                sleep $sleep
        fi
done
 


foreground로 스크립트를 실행할 것이면 fg=0으로 하고, background로 실행할 때는 1로 해줘야 스크립트의 기능을 제대로 사용할 수 있다. sleep=2 는 실시간으로 조회할 데이터를 몇 초 간격으로 볼 것인가를 지정한다.

LOGDIR= : 서버 load가 저장되어 있는 로그 파일의 경로
TPUT=   : tput 명령의 경로. 기본 경로는 /usr/bin/tput

상단 부분의 'szCol' 로 시작하는 변수는 색깔을 정의한 ANSI 코드이다. ^[ 문자는 ESC키를 의미한다. 쉘에서 입력할 때 Ctrl+V를 누른 후 ESC키를 누르면 입력할 수 있다.

4. 스크립트 부분별 이해

 
keyinput () {
        stty -icanon
        read -t $sleep -n 1 -s time
        stty icanon

        case $time in
                [1-9])
                        sleep=$time
                        C=$((`$TPUT cols` - $cols))
                        $TPUT cup $row $C
                        echo "${szInverse} Delay time : $time sec   $szNormal"
                        ;;
                [qQ])
                        echo -n  "^[[u"
                        exit 0
                        ;;
        esac
}
 


keyinput() 함수는 foreground로 실행할 때 키입력을 받아들이는 부분이다.
read 의 -t 옵션은 입력 대기 시간이다. -t 5라면 5초동안 입력 대기를 하게 되는데, 결국 sleep 5 를 한 것과 같은 효과를 볼 수 있다. -n 1 은 1자만 입력 받는 것이고, -s는 입력한 키를 화면에 출력하지 말라는 뜻이다. 키 입력이 생기면 바로 그 다음줄이 실행되며, 입력되지 않더라도 대기시간이 지나면 넘어가게 된다. 결국 keyinput()함수는 프로그램의 실행에 방해를 주지 않으면서 원하는 키입력을 받아들이는 역할을 하게 된다.
1~9까지 입력(즉, 1~9초에 해당)하면 delay time을 변경하고, 화면 변경됐음을 보여준다. q를 누르면, 적당한 곳으로 커서를 옮기고 종료한다.

 
cmd_local=`uptime | awk -F': ' '{print $2}'|awk -F', ' '{print $1 "|" $2 "|" $3 " "}'`
cmd=`tail -1 *.log | grep : | awk '{print $6 "|" $10 "|" $11 "|" $12 " "}'`
 


원하는 데이터 값을 가져오는 부분이다.
$cmd_local : 스크립트를 실행중인 서버의 load가 저장된다. '0.03|0.01|0.00'
$cmd       : load가 저장된 각 서버별 로그파일의 맨 마지막 줄(가장 최근 load)를 읽어서 변수에 저장한다.
    'cnx10|1.00,|1.00,|0.95 cnx22|0.39,|0.38,|0.35 cnx25|0.31,|0.24,|0.18 ... 생략...'
    '서버명|1분load|5분load|15분load' 형태이며, 서버간의 구분은 반드시 1개 이상의 공백으로 해야 한다.

 
        C=$(($col_width  - $cols))              # data를 표시할 column 위치 계산
        row=0
   $TPUT civis            # cursor 숨김
        for line in $result_color
        do
                $TPUT cup $row $C               # cursor 이동
                row=`expr $row + 1 `            # row 증가
                echo -n "$szColYe$szInverse$line$szNormal"
        done
   $TPUT cnorm            # cursor 다시 표시
 


data를 표시할 위치를 오른쪽 상단, 오른쪽에서 $cols 번째칸으로 한다. 그런 후 서버마다 한줄에 한칸씩 보여준다. 화면에 표시될 때 커서는 안보이게 했다가(civis), 데이터가 다 뿌려지면 다시 보이도록 했다(cnorm).

다음은 실제 모니터링하는 화면이다. 3개의 화면을 연속으로 캡쳐한 것이다. 3초 간격, 3초 간격, 그리고 숫자 '5'를 누른 후 5초간격으로 보여주겠다는 화면이다.



highlight 처리 부분에 대한 설명은 참고문서로 대신한다. 그리고, 재미난 시계 스크립트를 소개한 'Sergio Gonzalez Duran'씨에게 감사드린다.

5. 참고자료

  * CLI Magic: Use ANSI escape sequences to display a clock in your terminal 
    http://www.linux.com/feature/124918
  * 로그 모니터링시 특정 문자를 highlight하기 (글 좋은진호, 2008.1)
    http://coffeenix.net/board_view.php?bd_code=1562 
  * bash 맨페이지 중에 'read' 부분
  * tput: Portable Terminal Control
    http://www.gnu.org/software/termutils/manual/termutils-2.0/html_chapter/tput_1.html


원본 자료 : http://coffeenix.net/board_view.php?bd_code=1571
Posted by 두장

도착방향

운행시간 / 도착터미널

김포공항

07:25

김포공항

08:25

김포공항

09:15

김포공항

10:15

김포공항

11:25

김포공항

12:35

김포공항

13:25

김포공항

14:25

김포공항

15:05

김포공항

16:05

김포공항

16:55

김포공항

18:25

김포공항

19:45

김포공항

 

김포공항

요금 : 12800

시간 : 150

동서울

06:25

동서울

06:45

동서울

07:05

동서울

07:25

동서울

07:45

동서울

08:05

동서울

08:25

동서울

08:45

동서울

09:05

동서울

09:15

동서울()

09:25

동서울

09:45

동서울

10:05

동서울

10:15

동서울()

10:30

동서울

10:55

동서울

11:15

동서울

11:35

동서울

11:55

동서울

12:15

동서울

12:35

동서울

12:55

동서울

13:15

동서울

13:35

동서울

13:55

동서울

14:15

동서울

14:35

동서울

14:55

동서울

15:15

동서울

15:25

동서울(,,)

15:35

동서울

15:45

동서울(,,)

15:55

동서울

16:15

동서울

16:35

동서울

16:55

동서울

17:05

동서울(,,)

17:15

동서울

17:35

동서울

17:55

동서울

18:15

동서울

18:35

동서울

18:55

동서울

19:15

동서울

19:25

동서울(,,)

19:35

동서울

20:00

동서울

20:25

동서울

20:50

동서울

21:15

동서울

동서울

요금 : 9700

시간 : 110

부천

07:55

부천

12:05

부천

15:05

부천

 

부천

요금 : 10600

시간 : 155

서울(남부)

16:15

서울(남부)

 

서울(남부)

요금 : 8800

시간 : 100

성남

06:30

성남

07:35

성남

08:10

성남

09:15

성남

10:05

성남

10:55

성남

11:45

성남

12:35

성남

13:25

성남

14:15

성남

15:15

성남

15:55

성남

16:45

성남

17:35

성남

18:25

성남

19:25

성남

20:25

성남

21:25

성남

성남

요금 : 8800

시간 : 110

수원

06:35

수원

06:45

수원

07:45

수원

08:45

수원

10:05

수원

10:15

수원

11:45

수원

13:05

수원

13:15

수원

14:15

수원

15:05

수원

15:15

수원

16:05

수원

16:15

수원

17:15

수원

18:15

수원

19:05

수원

19:15

수원

수원

요금 : 7000

시간 : 120

안산

18:50

안산

 

안산

요금 : 9100

시간 : 120

안양

07:35

안양

12:45

안양

18:45

안양

 

안양

요금 : 9200

시간 : 140

이천

10:15

이천

14:35

이천

19:45

이천

 

이천

요금 : 7200

시간 : 120

인천

06:15

인천

06:55

인천

07:45

인천

08:35

인천

09:25

인천

10:15

인천

10:55

인천

11:35

인천

12:15

인천

12:55

인천

13:35

인천

14:15

인천

14:55

인천

15:35

인천

16:15

인천

16:55

인천

17:35

인천

18:15

인천

18:55

인천

19:45

인천

20:25

인천

 

인천

요금 : 9900

시간 : 140

인천공항(일반),인천공항(우등)

03:30

인천공항(우등)

03:50

인천공항(우등)

04:15

인천공항(우등)

04:25

인천공항(우등)

04:35

인천공항(우등)

04:45

인천공항(일반)

04:55

인천공항(우등)

05:15

인천공항(우등)

05:25

인천공항(우등)

05:45

인천공항(우등)

05:55

인천공항(우등)

06:15

인천공항(우등)

06:45

인천공항(우등)

07:15

인천공항(우등)

07:45

인천공항(일반)

08:15

인천공항(우등)

08:35

인천공항(우등)

08:45

인천공항(우등)

08:55

인천공항(일반)

09:25

인천공항(우등)

10:05

인천공항(우등)

10:45

인천공항(우등)

11:15

인천공항(우등)

11:45

인천공항(우등)

12:15

인천공항(일반)

12:45

인천공항(우등)

13:15

인천공항(우등)

13:35

인천공항(우등)

13:55

인천공항(우등)

14:05

인천공항(우등)

14:15

인천공항(우등)

14:35

인천공항(우등)

14:55

인천공항(우등)

15:15

인천공항(우등)

15:55

인천공항(우등)

16:25

인천공항(우등)

16:45

인천공항(우등)

17:15

인천공항(일반)

17:45

인천공항(우등)

18:15

인천공항(우등)

19:25

인천공항(일반)

 

인천공항(일반)

요금 : 14800

시간 : 180

인천공항(우등)

요금 : 22200

시간 : 180

천안

07:15

천안

07:25

천안

14:40

천안

 

천안

요금 : 4100

시간 : 50

청주

07:45

청주

08:05

청주

11:00

청주

18:55

청주

 

청주

요금 : 3600

시간 : 40

 

 

 

Posted by 두장

도착방향

운행시간 / 도착터미널

강릉

10:20

강릉

12:20

강릉

18:00

강릉

 

강릉

요금 : 15000

시간 : 240

건양대,논산

07:50

건양대,논산

09:00

건양대,논산

10:00

건양대,논산

10:50

논산

12:00

건양대,논산

13:05

논산

14:10

건양대,논산

14:50

논산

15:35

논산

16:30

논산

17:35

논산

18:00

논산

18:30

논산

19:30

논산

20:20

논산

 

건양대

요금 : 3300

시간 : 40

논산

요금 : 3700

시간 : 50

공주

07:57

공주()

09:17

공주()

09:49

공주()

10:45

공주()

11:37

공주()

13:25

공주()

14:01

공주()

15:09

공주()

19:29

공주()

20:10

공주()

공주

요금 : 2700

시간 : 30

공주()

07:07

공주()

07:33

공주()

07:53

공주()

08:09

공주()

08:25

공주()

08:53

공주()

09:09

공주()

09:35

공주()

10:01

공주()

10:17

공주()

10:33

공주()

10:49

공주()

11:05

공주()

11:33

공주()

11:41

공주()

12:09

공주()

12:37

공주()

12:53

공주()

13:13

공주()

13:29

공주()

13:53

공주()

14:09

공주()

14:33

공주()

14:49

공주()

15:25

공주()

15:37

공주()

15:53

공주()

16:13

공주()

16:29

공주()

16:53

공주()

17:13

공주()

17:29

공주()

17:45

공주()

18:13

공주()

18:33

공주()

18:49

공주()

19:17

공주()

19:41

공주()

19:54

공주()

20:15

공주()

20:30

공주()

20:50

공주()

21:10

공주()

21:25

공주()

21:40

공주()

22:45

공주()

공주()

요금 : 2700

시간 : 40

공주,유구,예산,홍성

12:45

공주,유구,예산,홍성

17:33

공주,유구,예산,홍성

공주

요금 : 2700

시간 : 30

유구

요금 : 5500

시간 : 60

예산

요금 : 8300

시간 : 90

홍성

요금 : 9200

시간 : 120

광주

06:10

광주

07:10

광주

08:00

광주

08:50

광주

09:40

광주

10:30

광주

11:20

광주

12:10

광주

13:00

광주

13:50

광주

14:40

광주

15:30

광주

16:20

광주

17:10

광주

18:00

광주

18:50

광주

19:40

광주

20:50

광주

광주

요금 : 9400

시간 : 110

금산

07:50

마전,금산

08:50

마전,금산

10:20

마전,금산

11:40

마전,금산

14:50

마전,금산

17:00

마전,금산

금산

요금 : 3600

시간 : 50

대평리,공주

09:25

대평리,공주

22:20

대평리,공주

대평리

요금 : 1700

시간 : 20

공주

요금 : 2700

시간 : 50

동서울

06:10

동서울

06:30

동서울

06:50

동서울

07:10

동서울

07:30

동서울

07:50

동서울

08:10

동서울

08:30

동서울

08:50

동서울

09:00

동서울()

09:10

동서울

09:30

동서울

09:50

동서울

10:00

동서울()

10:15

동서울

10:40

동서울

11:00

동서울

11:20

동서울

11:40

동서울

12:00

동서울

12:20

동서울

12:40

동서울

13:00

동서울

13:20

동서울

13:40

동서울

14:00

동서울

14:20

동서울

14:40

동서울

15:00

동서울

15:10

동서울(,,)

15:20

동서울

15:30

동서울(,,)

15:40

동서울

16:00

동서울

16:20

동서울

16:40

동서울

16:50

동서울(,,)

17:00

동서울

17:20

동서울

17:40

동서울

18:00

동서울

18:20

동서울

18:40

동서울

19:00

동서울

19:10

동서울(,,)

19:20

동서울

19:45

동서울

20:10

동서울

20:35

동서울

21:00

동서울

동서울

요금 : 9700

시간 : 120

부천

07:40

부천

11:50

부천

14:50

부천

 

부천

요금 : 10600

시간 : 170

서울(남부)

16:00

서울(남부)

 

서울(남부)

요금 : 8800

시간 : 120

수원

06:30

수원

07:30

수원

08:30

수원

10:00

수원

11:30

수원

13:00

수원

14:00

수원

15:00

수원

16:00

수원

17:00

수원

18:00

수원

19:00

수원

수원

요금 : 7000

시간 : 140

예산

07:21

예산

08:13

예산

08:29

예산

08:45

예산

09:33

예산

09:57

예산

10:13

예산

10:29

예산

11:01

예산

11:21

예산

11:57

예산

12:45

예산

13:01

예산

13:17

예산

14:29

예산

14:57

예산

15:33

예산

16:05

예산

16:25

예산

17:01

예산

17:17

예산

17:33

예산

17:49

예산

18:05

예산

18:21

예산

18:45

예산

19:33

예산

 

예산

요금 : 8300

시간 : 120

예산,덕산,서산

08:29

예산,덕산,서산

 

예산

요금 : 8300

시간 : 120

덕산

요금 : 10000

시간 : 140

서산

요금 : 10000

시간 : 160

예산,홍성,서산

10:29

예산,홍성,서산

11:21

예산,홍성,서산

13:01

예산,홍성,서산

16:25

예산,홍성,서산

17:01

예산,홍성,서산

18:05

예산,홍성,서산

예산

요금 : 8300

시간 : 120

홍성

요금 : 9200

시간 : 150

서산

요금 : 10000

시간 : 190

예산,홍성,서산,태안

09:33

예산,홍성,서산,태안

 

예산

요금 : 8300

시간 : 120

홍성

요금 : 9200

시간 : 150

서산

요금 : 10000

시간 : 190

태안

요금 : 11000

시간 : 220

원주

15:15

원주

17:15

원주

원주

요금 : 10300

시간 : 140

원주,홍천,인제,원통,속초

10:15

원주,홍천,인제,원통,속초

12:15

원주,홍천,인제,원통,속초

원주

요금 : 10300

시간 : 140

홍천

요금 : 15200

시간 : 180

인제

요금 : 20700

시간 : 210

원통

요금 : 21600

시간 : 240

속초

요금 : 26000

시간 : 270

이천

10:00

이천

14:20

이천

19:30

이천

 

이천

요금 : 7200

시간 : 110

익산,군산

10:15

익산,군산

11:32

익산,군산

12:35

익산,군산

14:05

익산,군산

15:45

익산,군산

18:50

익산,군산

익산

요금 : 5300

시간 : 80

군산

요금 : 8000

시간 : 120

인천

06:00

인천

06:40

인천

07:30

인천

08:20

인천

09:10

인천

10:00

인천

10:40

인천

11:20

인천

12:00

인천

12:40

인천

13:20

인천

14:00

인천

14:40

인천

15:20

인천

16:00

인천

16:40

인천

17:20

인천

18:00

인천

18:40

인천

19:30

인천

20:10

인천

 

인천

요금 : 9900

시간 : 150

전주

08:15

전주

09:15

전주

10:00

전주

10:15

전주

10:50

전주

11:10

전주

11:30

전주

11:45

전주

12:20

전주

12:55

전주

13:10

전주

13:25

전주

13:30

전주

13:55

전주

14:25

전주

14:55

전주

15:00

전주

15:25

전주

16:00

전주

16:20

전주

16:30

전주

16:55

전주

17:40

전주

18:20

전주

18:30

전주

18:35

전주

18:50

전주

19:50

전주

20:00

전주

20:30

전주

21:00

전주

 

전주

요금 : 5100

시간 : 70