본문 바로가기

OS/Linux

Linux - SSL 인증서 만료 체크 스크립트

728x90

서버 운영 시 SSL 인증서의 만료 여부를 주기적으로 체크하는 것은 중요합니다.

SSL 인증서가 만료되면 웹사이트 접속 시 보안 경고가 발생하여 접속에 문제가 발생할 수 있습니다.

도메인 리스트를 읽어 SSL 인증서의 만료 일자를 확인 후 만료가 임박한 인증서에 대해 이메일을 발송하는 스크립트를 소개합니다.

 

1. 기존 SSL 인증서 만료 체크 스크립트

우선 기본적인 SSL 인증서 만료 체크 스크립트를 살펴보겠습니다. 이 스크립트는 URL과 포트를 인자로 받아 SSL 인증서를 가져와 만료 일자를 확인하고, 만료일이 15일 이하로 남은 경우 이메일을 발송합니다.

checkSSL_Dday.sh 스크립트

#!/bin/bash

today="`date`"
date2nanosec="`date +%Y%m%d_%H%M%S_%N`"
URL=$1
PORT=$2
TMP_CRT=${URL}_${date2nanosec}.crt

date2stamp(){
    date --utc --date "$1" +%s
}

echo '##################### [ START ] #############################'
echo "-------------------------------"
echo "${URL}:${PORT}"
echo "-------------------------------"

# 인증서 얻기
echo "" | openssl s_client -connect ${URL}:${PORT} -servername ${URL} > ${TMP_CRT} 2>/dev/null

# 만료일 추출
enddate="`openssl x509 -noout -dates -in ${TMP_CRT} | grep notAfter | awk -F'=' '{print $2}'`"

stamp_enddate=$(date2stamp "$enddate")
stamp_today=`date +%s`
diffSec=$((stamp_enddate-stamp_today))

dday=$((diffSec/86400))
echo $dday

# 이메일 알림 발송
if [ $dday -lt 15 ]; then
    rtmp_url="smtps://smtp_server_address:465"
    rtmp_from="보내는사람 주소"
    rtmp_to1="받는사람 주소"
    rtmp_credentials="보내는사람계정:비번"
    mail_form_file="maildata_$1.txt"

    echo -n "From: " > "$mail_form_file"
    echo -n '"보내는사람 이름"' >> "$mail_form_file"
    echo " <${rtmp_from}>" >> "$mail_form_file"

    echo -n "To: " >>"$mail_form_file"
    echo -n '"받는사람 이름"' >> "$mail_form_file"
    echo " <${rtmp_to1}>" >> "$mail_form_file"

    echo "Subject: [SSL Expire] ${URL}:${PORT} expire D-Day is [$dday]" >> "$mail_form_file"
    echo "" >> "$mail_form_file"
    openssl x509 -noout -dates -text -in ${TMP_CRT} | egrep "Not Before|Not After" >> "$mail_form_file"

    curl --ssl-reqd --mail-from "$rtmp_from" --mail-rcpt "$rtmp_to1" "$rtmp_url" -T "$mail_form_file" -u "$rtmp_credentials"
    rm -f "$mail_form_file"
fi

rm -f ${TMP_CRT}
echo '##################### [ END ] #############################'
exit 0

이 스크립트는 URL과 포트를 통해 SSL 인증서를 가져와 만료 일자를 확인하고, 만료일까지 남은 일수(dday)를 계산합니다. dday가 15일 이하로 남은 경우 이메일 알림을 발송하는 방식입니다.

 

2. URL 리스트를 이용한 SSL 체크 스크립트

여러 개의 URL을 한 번에 체크하기 위해 도메인 리스트 파일을 작성하고, 이 리스트를 읽어 checkSSL_Dday.sh를 반복적으로 실행하는 스크립트를 만듭니다.

checkSSL_List.sh 스크립트

#!/bin/bash

LIST_FILE=/etc/zabbix/ssl_domain.list
# 스크립트 경로는 변경 될 수 있음(필자는 /etc/zabbix/ 아래에 적용

cat "$LIST_FILE" | grep '.' | grep -v ^# | while read LIST; do
    URL=`echo ${LIST} | awk '{print $1}'`
    PORT=`echo ${LIST} | awk '{print $2}'`

    /etc/zabbix/checkSSL_Dday.sh $URL $PORT
# 스크립트 경로는 변경 될 수 있음(필자는 /etc/zabbix/ 아래에 적용
    sleep 5
done
exit 0

이 스크립트는 ssl_domain.list 파일을 읽고, 각 도메인과 포트 정보를 추출하여 checkSSL_Dday.sh를 호출합니다.

 

ssl_domain.list 예시

samso.tistory.com 443
www.naver.com 443
www.google.com 8443
samsogood.tistory.com 9443

crontab 예시

30 9 * * * /etc/zabbix/checkSSL_List.sh
1. checkSSL_List.sh 을 실행하면
2. ssl_domain.list를 읽어서
3. checkSSL_Dday.sh 에서 계산하여 메일 발송

 

 

반응형

 


 

3. 개선된 통합 SSL 만료 체크 스크립트

모든 기능을 하나의 스크립트로 통합하고, 자격 증명을 .env 파일로 분리하여 보안성을 높였습니다.

통합 SSL 체크 스크립트 (checkSSL.sh)

#!/bin/bash

# 환경 변수 파일 로드
source /etc/zabbix/.env

# 파일 경로 설정
LIST_FILE="/etc/zabbix/ssl_domain.list"
LOG_FILE="/var/log/ssl_check.log"

# 로그 작성 함수
log_message() {
    echo "$(date '+%Y-%m-%d %H:%M:%S') - $1" >> "$LOG_FILE"
}

# 날짜 변환 함수
date2stamp() {
    date --utc --date "$1" +%s
}

# SSL 만료일 체크 및 메일 발송 함수
check_ssl_expiration() {
    URL=$1
    PORT=$2
    TMP_CRT="/tmp/${URL}_$(date +%Y%m%d_%H%M%S_%N).crt"

    log_message "Starting SSL check for ${URL}:${PORT}"

    # SSL 인증서 가져오기
    echo "" | openssl s_client -connect ${URL}:${PORT} -servername ${URL} > ${TMP_CRT} 2>/dev/null
    if [ $? -ne 0 ]; then
        log_message "Error: Failed to retrieve SSL certificate for ${URL}:${PORT}"
        rm -f ${TMP_CRT}
        return 1
    fi

    # 만료일 추출
    enddate="`openssl x509 -noout -dates -in ${TMP_CRT} | grep notAfter | awk -F'=' '{print $2}'`"
    stamp_enddate=$(date2stamp "$enddate")
    stamp_today=$(date +%s)
    diffSec=$((stamp_enddate - stamp_today))

    dday=$((diffSec / 86400))
    log_message "${URL}:${PORT} SSL Certificate D-Day: ${dday} days remaining."

    if [ $dday -lt 15 ]; then
        log_message "SSL certificate for ${URL}:${PORT} is close to expiration. Sending email notification."

        # 메일 폼 파일 생성
        mail_form_file="/tmp/maildata_${URL}.txt"
        {
            echo "From: \"보내는사람 이름\" <$SMTP_FROM>"
            echo "To: \"$SMTP_TO\""
            echo "Subject: [SSL Expire] ${URL}:${PORT} expires in [$dday] days"
            echo ""
            openssl x509 -noout -dates -in ${TMP_CRT} | grep "notAfter"
        } > "$mail_form_file"

        # 메일 전송
        curl --ssl-reqd --mail-from "$SMTP_FROM" --mail-rcpt "$SMTP_TO" "$SMTP_URL" -T "$mail_form_file" -u "$SMTP_CREDENTIALS"
        if [ $? -eq 0 ]; then
            log_message "Email sent successfully for ${URL}:${PORT}."
        else
            log_message "Error: Failed to send email for ${URL}:${PORT}."
        fi

        # 메일 폼 파일 삭제
        rm -f "$mail_form_file"
    fi

    # 임시 인증서 파일 삭제
    rm -f ${TMP_CRT}
    log_message "Completed SSL check for ${URL}:${PORT}"
}

# SSL 체크 시작
log_message "Starting SSL domain list check."

# 도메인 리스트 파일을 읽어 도메인별 SSL 체크
cat "$LIST_FILE" | grep '.' | grep -

4. .env 파일 설정

SMTP 자격 증명을 .env 파일에 저장합니다.

/etc/zabbix/.env 파일 내용 예시

SMTP_URL="smtps://smtp_server_address:465"
STMP_FROM="보내는사람 주소"
SMTP_TO="받는사람 주소"
SMTP_CREDENTIALS="보내는사람계정:비번"

이렇게 하면 스크립트 내에서 민감한 정보를 직접적으로 드러내지 않고, .env 파일만 적절히 보호하면 됩니다.

 

crontab 예시

30 9 * * * /etc/zabbix/checkSSL.sh

 

1. checkSSL.sh 을 실행하면
2. .env에서 환경설정파일을 읽어오고
3. ssl_domain.list의 도메인 포트를 읽어
4. check_ssl_expiration 함수가 만료일 계산 후 메일 발송

 

728x90
반응형