Profile picture

[Shell Script] 최근 리붓(reboot) 횟수 디스코드(Discord) 알림 전송 스크립트

JaehyoJJAng2024년 05월 05일

개요

  • 비정상적인 서버 리부팅 모니터링 점검을 위해 서버에서 발생하는 리부팅 횟수 확인
  • 스크립트 구조
    • last 명령어로 down (reboot)된 로그를 이용한 모니터링 진행
    • 생성한 스크립트를 rc.local에 등록하여 서버 부팅 시 스크립트 실행
    • 알람 전송 (디스코드, 텔레그램 ..)

스크립트 작성

reboot_check.sh

#!/usr/bin/bash

DISCORD_WEBHOOK_URI=""
host=$(hostname)

send_discord_notification() {
    payload=$(cat << EOF
    {
      "embeds": [{
          "title": "Alarm",
          "description": "$1",
          "color": "$2"
      }]
    }
EOF
    )
    curl -H "Content-Type: application/json" -X POST -d "$payload" "$DISCORD_WEBHOOK_URI"
}

b=$(last reboot | grep 'reboot' | wc -l)
up_time=$(cat /proc/uptime | awk '{print $1}' | cut -d . -f 1)

reboot_date=""
for i in $(seq $b)
do
    if [[ "$i" == 4 ]]; then
        break
    fi
    time=$(last -f /var/log/wtmp --fulltime |grep "system boot"| awk '{print $5, $6, $7, $8, $9}' | sed -n "${i}p")
    time_convert=$(date -d "$time" "+%Y-%m-%d %H:%M")
    reboot_date+="$time_convert\n"
    reboot_date_final=$(echo $reboot_date | sed 's/ /, /g')
done
echo $reboot_date
output="$host에서 총 $b회 리붓 되었습니다.\n\n**최근 리붓 시기**\n$reboot_date"

# 디스코드로 알림 전송
send_discord_notification "$output" "45973"
코드 설명
send_discord_notification() { ... } 이 함수는 디스코드로 메시지를 전송하는 역할을 합니다. 입력 매개변수로 메시지 내용과 색상을 받아서 디스코드 웹훅을 통해 해당 내용을 보냅니다.
b=$(last reboot | grep 'reboot' | wc -l) last reboot 명령어를 통해 시스템의 리부팅 로그를 확인하고, 이 중에서 'reboot'이라는 문자열을 가진 줄만 선택하여 총 리부팅 횟수를 세어 변수 b에 저장합니다.
up_time=$(cat /proc/uptime | awk '{print $1}' | cut -d . -f 1) /proc/uptime 파일을 통해 시스템의 켜진 시간(업타임)을 초 단위로 가져옵니다.
reboot_date="" 빈 문자열을 초기화하여 리부트 시간을 저장할 변수를 만듭니다.
for i in $(seq $b) 리부트 횟수만큼 반복하는 루프를 설정합니다.
time=$(last -f /var/log/wtmp --fulltime | grep "system boot" | awk '{print $5, $6, $7, $8, $9}' | sed -n "${i}p") /var/log/wtmp 파일에서 시스템 부팅 로그를 찾고, 각각의 부팅 시간을 저장합니다.
time_convert=$(date -d "$time" "+%Y-%m-%d %H:%M") 부팅 시간을 원하는 형식(년-월-일 시:분)으로 변환합니다.
reboot_date="$reboot_date $time_convert" 부팅 날짜를 변수 reboot_date에 추가합니다.
reboot_date_final=$(echo $reboot_date | sed 's/ /, /g') 부팅 날짜 사이에 쉼표를 추가하여 최종 부팅 날짜를 만듭니다.

실행 결과

해당 스크립트 실행

bash reboot_check.sh

image


rc.local 등록: Debian/Ubuntu 환경인 경우

스크립트 등록

sudo vim /etc/rc.local

/etc/rc.local

#!/bin/bash

bash /home/dev/serverChecking/02_reboot_check.sh
exit 0

systemd 서비스 유닛 등록: Arch 환경인 경우

아치 리눅스는 rc.local을 기본적으로 지원하지 않기 때문에, rc.local 방식은 권장되지 않고, 동작하지도 않습니다.


아치 환경에서는 systemd 서비스 유닛을 이용해 부팅 시 스크립트를 실행하는 것이 표준입니다.


스크립트를 부팅 시 실행하려면 다음과 같이 처리해주세요.


1. 스크립트 위치 이동

sudo mv reboot_check.sh /usr/local/bin/reboot_check.sh
sudo chmod +x /usr/local/bin/reboot_check.sh

2. systemd 서비스 유닛 파일 생성

/etc/systemd/system/reboot_check.service 파일을 만들어서 다음과 같이 작성해줍시다.

[Unit]
Description=Show recent reboot count
After=network.target

[Service]
Type=oneshot
ExecStart=/usr/local/bin/reboot_check.sh

[Install]
WantedBy=multi-user.target

3. 서비스 활성화 및 테스트

sudo systemctl daemon-reexec
sudo systemctl enable reboot_check.service
    Tag -

Loading script...