linux指令碼監控應用且通過郵件報警異常
一、背景
最近接到監控應用並通過郵件報警的任務,由於需求比較簡單,故沒有使用springboot那套,而是採用linux指令碼的方式進行監控。
二、思路
通過linux自帶的定時功能,定時執行一個linux指令碼,通過指令碼訪問應用的介面,若介面不通,進行重試,達到一定重試次數則重啟tomcat併發送告警郵件。若無法重啟tomcat,則重試,達到一定次數停止重啟併發送告警郵件。
三、安裝sendmail並配置sendmail
在安裝配置sendmail的時候遇到不少坑,在配置sendmail的時候,需要修改/etc/mail/sendmail.mc檔案和/etc/mail.rc檔案,網上很多部落格都是配置了其中一個,導致無法傳送郵件成功,因此在配置的時候需要特別注意。具體的
指令碼檔案如下,將傳送郵箱等資訊改成自己的,直接放到linux伺服器(centos)執行該指令碼檔案即可安裝且配置完成.
1 #! /bin/bash 2 3 # 傳送郵箱 4 $from=$1 5 # 協議 6 $smtp=$2 7 # 傳送使用者,一般與傳送郵箱一致 8 $user=$3 9 # 授權碼(非郵箱密碼) 10 $password=$4 11 12 # 安裝sendmail 13 yum install -y sendmail 14 yum install -y sendmail-cf 15 16 # 安裝salauthd 17 # 使用smtp認證,需要安裝saslauthd18 yum install -y saslauthd 19 20 # 啟動saslauthd服務 21 service saslauthd start 22 23 # 設定saslauthd開機自動啟動 24 chkconfig saslauthd on 25 26 # 安裝perl,不然無法使用下面的命令查詢檔案內容並替換 27 yum install -y perl perl-devel 28 29 # 安裝mailx 30 yum install -y mailx 31 32 # 配置sendmail 33 # 設定外網可訪問 34 # 實際是將DAEMON_OPTIONS(`Port=smtp,Addr=127.0.0.1, Name=MTA')dnl 替換成 DAEMON_OPTIONS(`Port=smtp,Addr=0.0.0.0, Name=MTA')dnl35 find /etc/mail -name 'sendmail.mc' | xargs perl -pi -e 's|Addr=127.0.0.1|Addr=0.0.0.0|g' 36 37 # 設定傳送郵箱相關資訊 38 echo "set ssl-verify=ignore">>/etc/mail.rc 39 echo "set nss-config-dir=/etc/pki/nssdb">>/etc/mail.rc 40 # 傳送郵箱 41 echo "set from=$from">>/etc/mail.rc 42 # 協議 43 echo "set smtp=$smtp">>/etc/mail.rc 44 # 傳送郵箱使用者,一般與傳送郵箱一致 45 echo "set smtp-auth-user=$user">>/etc/mail.rc 46 # 授權碼(非郵箱密碼) 47 echo "set smtp-auth-password=$password">>/etc/mail.rc 48 echo "set smtp-auth=login">>/etc/mail.rc 49 50 # sendmail開機啟動 51 chkconfig sendmail on 52 53 # 啟動sendmail 54 service sendmail start
四、編寫監控指令碼
該指令碼用來訪問應用介面,以此來確定應用是否正常,並通過sendMail傳送異常郵件。具體邏輯如下指令碼
1 #! /bin/bash 2 3 # tomcat啟動指令碼 4 startTomcat=$1 5 6 # 日誌地址 7 tomcatMonitorLog=$2 8 9 # 郵件地址,多個逗號隔開 10 email_address=$3 11 12 # 請求介面 13 webUrl=$4 14 15 # 重試次數 16 retryCount=$5 17 18 # 最大重啟次數 19 maxRestartCount=$6 20 21 # 計數器檔案位置 22 restartCountTxt=$7 23 24 # tomcat停止指令碼 25 stopTomcat=$8 26 27 # 判斷容器是否存在的指令碼 28 isExist=$9 29 30 # 用來計數重啟tomcat的次數 31 restartCount=0 32 33 # 正確的請求返回值 34 statusCode=200 35 36 time=$(date "+%Y-%m-%d %H:%M:%S") 37 echo "=======================$time=======================">>$tomcatMonitorLog 38 39 # 日誌輸出 40 if [ -f $tomcatMonitorLog ]; then 41 echo "日誌檔案已建立">>$tomcatMonitorLog 42 else 43 echo "日誌檔案未建立,馬上建立">>$tomcatMonitorLog 44 touch $tomcatMonitorLog 45 fi 46 47 # 初始化計數器 48 if [ -f $restartCountTxt ]; then 49 while read line 50 do 51 restartCount=$((line)) 52 done < $restartCountTxt 53 else 54 touch $restartCountTxt 55 echo "0" > $restartCountTxt 56 fi 57 58 # 判斷是否已達到最大重啟次數 59 if [[ "$restartCount" -eq "$maxRestartCount" ]]; then 60 tomcatServiceCodeTry=$(curl -s -m 10 -o /dev/null --connect-timeout 10 $webUrl -w %{http_code}) 61 62 # 重置重啟計數器(因手動重啟應用而沒有重置計數器) 63 if [[ "$tomcatServiceCodeTry" -eq "$statusCode" ]]; then 64 echo '【info】tomcat執行正常,訪問系統介面正常,重置計數器'>>$tomcatMonitorLog 65 true > $restartCountTxt 66 echo "0" > $restartCountTxt 67 exit 0 68 else 69 echo "已超過最大重啟次數,不再自動重啟">>$tomcatMonitorLog 70 echo '已超過最大重啟次數,不再自動重啟,請手動重啟' | mail -v -s '系統告警' $email_address 71 true > $restartCountTxt 72 count=$[restartCount+1] 73 echo $count > $restartCountTxt 74 exit 0 75 fi 76 fi 77 if [[ "$restartCount" -ge "$maxRestartCount" ]]; then 78 tomcatServiceCodeTry=$(curl -s -m 10 -o /dev/null --connect-timeout 10 $webUrl -w %{http_code}) 79 # 重置重啟計數器(因手動重啟應用而沒有重置機器) 80 if [[ "$tomcatServiceCodeTry" -eq "$statusCode" ]]; then 81 echo '【info】tomcat執行正常,訪問系統介面正常,重置計數器'>>$tomcatMonitorLog 82 true > $restartCountTxt 83 echo "0" > $restartCountTxt 84 exit 0 85 else 86 echo "已超過最大重啟次數,不再自動重啟">>$tomcatMonitorLog 87 exit 0 88 fi 89 fi 90 91 # 獲取tomcat程序id 92 tomcatId=$($isExist) 93 # 重啟 94 function restart() { 95 if [ -n "$tomcatId" ]; then 96 echo "tomcat開始關閉" 97 $stopTomcat 98 fi 99 sleep 10 100 # 迴圈100次,直到程序已經被關閉,否則認為關閉不成功,主動關閉程序 101 for((i=1;i<100;i++)); 102 do 103 tomcatId=$($isExist) 104 if [ -n "$tomcatId" ]; then 105 sleep 10 106 echo "tomcat還沒關閉,繼續阻塞等待關閉完成" 107 else 108 break 109 fi 110 done 111 echo 'tomcat開始重啟...' 112 $startTomcat # 啟動tomcat 113 } 114 115 # 監控服務是否正常 116 function monitor() { 117 118 # 判斷tomcat程序是否存在 119 if [ -n "$tomcatId" ]; then 120 tomcatServiceCodeTry=$(curl -s -m 10 -o /dev/null --connect-timeout 10 $webUrl -w %{http_code}) 121 if [[ "$tomcatServiceCodeTry" -eq "$statusCode" ]]; then 122 echo '【info】tomcat執行正常,訪問系統介面正常......' 123 true > $restartCountTxt 124 echo "0" > $restartCountTxt 125 exit 0 126 else 127 sleep 10 128 for((i=0;i<$retryCount;i++)) 129 do 130 tomcatServiceCodeTry=$(curl -s -m 10 -o /dev/null --connect-timeout 10 $webUrl -w %{http_code}) 131 if [[ "$tomcatServiceCodeTry" -eq "$statusCode" ]]; then 132 echo '【info】tomcat執行正常,訪問系統介面正常......' 133 true > $restartCountTxt 134 echo "0" > $restartCountTxt 135 echo "執行完成" 136 exit 0 137 else 138 echo '【error】重新訪問系統介面失敗' 139 sleep 30 140 fi 141 done 142 echo '【error】訪問系統接口出錯,請注意......開始重啟tomcat' 143 echo '【error】傳送告警郵件' 144 echo '【info】由於訪問系統接口出錯,tomcat開始自動重啟' 145 true > $restartCountTxt 146 count=$[restartCount+1] 147 echo $count > $restartCountTxt 148 # 傳送告警郵件 149 echo "由於訪問系統接口出錯,tomcat開始自動重啟,地址:$webUrl" | mail -v -s "系統告警" $email_address 150 restart # 重啟 151 fi 152 else 153 echo '【error】tomcat程序不存在!tomcat開始自動重啟...' 154 echo '【error】$startTomcat,請稍候......' 155 echo '【error】傳送告警郵件' 156 echo "由於tomcat沒有啟動,tomcat開始自動重啟,地址:$webUrl" | mail -v -s "系統告警" $email_address 157 true > $restartCountTxt 158 count=$[restartCount+1] 159 echo $count > $restartCountTxt 160 restart # 重啟 161 fi 162 } 163 monitor>>$tomcatMonitorLog
五、新增定時器
首先編寫一個指令碼,用來存放初始化資訊,如啟動tomcat的命令、日誌地址、郵件地址、訪問介面、重試次數、停止tomcat命令等,具體如下
1 #! /bin/bash 2 3 # tomcat啟動指令碼 4 startTomcat=/usr/local/apache-tomcat-7.0.92/bin/startup.sh 5 6 # 日誌地址 7 tomcatMonitorLog=/usr/local/monitorApplication.log 8 9 # 郵件地址,多個逗號隔開 10 email_address=你的傳送郵箱地址 11 12 # 請求介面 13 webUrl=你的應用介面 14 15 # 重試次數,每次間隔30秒 16 retryCount=5 17 18 # 最大重啟次數 19 maxRestartCount=3 20 21 # 計數器檔案位置 22 restartCountTxt=/usr/local/restartCountTxt.txt 23 24 # tomcat停止指令碼 25 stopTomcat=/usr/local/kill.sh 26 27 # 判斷容器是否存在的指令碼 28 isExist=/usr/local/isExistTomcat.sh 29 30 # 執行監控指令碼 31 monitorApplicationProcessId=$(ps -ef |grep monitorApplication |grep -w /usr/local |grep -v 'grep'|awk '{print $2}') 32 if [[ $monitorApplicationProcessId ]]; then 33 time=$(date "+%Y-%m-%d %H:%M:%S") 34 echo "=======================$time=======================">>$tomcatMonitorLog 35 echo "monitorApplication.sh指令碼正在試行,此次定時任務不執行該指令碼,直接退出,等待下一次定時任務">>$tomcatMonitorLog 36 exit 0 37 else 38 sh /usr/local/monitorApplication.sh $startTomcat $tomcatMonitorLog $email_address $webUrl $retryCount $maxRestartCount $restartCountTxt "$stopTomcat" "$isExist" 39 fi
其次,定義一個定時器,使用crontab -e命令,插入以下程式碼,表示一分鐘執行一次check.sh指令碼
*/1 * * * * /usr/local/check.sh
到此,定時監控應用的指令碼就完成了。
參考部落格:https://blog.csdn.net/thinkthewill/article/details/80868442
所有指令碼github地址:https://github.com/1053531172/monitorApplication