로그의 오류/경고를 이메일로 보내는 스크립트를 만들고 있습니다. 30분마다 전송되기를 원하지만 새 항목이 있을 때만 전송되기를 원합니다. 지난 30분 동안만 무엇이 문제인지 어떻게 알 수 있나요?
로그의 타임스탬프는 다음 형식을 따릅니다.
<2016년 8월 1일 오후 2시 15분 29초 MDT> <오류 내용...>
지금까지의 스크립트는 다음과 같습니다.
#!/bin/bash
cat /var/log/logfile.log | egrep -i "error|warning" | tee -a /tmp/log.tmp
"get only last 30 min of errors" | mail -s "Errors/Warning" [email protected]
타임스탬프(2016년 8월 1일 오후 2:15:29 MDT)를 epoch 시간으로 변환한 다음 현재 epoch 시간과 비교할 수 있습니까? 아니면 sed/awk/perl을 사용하여 지난 30분을 얻을 수 있는 방법이 있습니까? ?
답변1
시대로 변환하려면 다음 명령문을 사용할 수 있습니다.
# date +%s -d"Aug 1, 2016 2:15:29 PM MDT"
1470082529
Epoch를 UTC로 변환하려면 다음을 사용할 수 있습니다.
# date -d @1470082529
Tue Aug 2 00:45:29 IRDT 2016 #### on Linux Box
# date -r 1470082529
Tue Aug 2 00:45:29 IRDT 2016 ###on BSD box
답변2
내가 사용할 perl
모듈은 File::Tail
. 지금은 예제를 작성할 시간이 없지만 Perlish 의사 코드에서는 다음과 같습니다.
#! /usr/bin/not-actually-perl
use strict;
use File::Tail;
use Net::SMTP or Mail::Mailer or one of the squillion other
perl mail sending modules;
open a File::Tail file handle to your log file
my $now=time();
my @lines = ();
while (read the File::Tail handle) {
push @lines, $_;
if (time() > ($now + 1800 seconds) ) {
$now=time();
email the @lines array to [email protected];
@lines=();
}
}
실제 작업 스크립트는 아마도 위의 스크립트보다 10줄 미만일 것입니다. 대부분은 이메일 헤더를 설정하는 것입니다.
일시 중지하거나 종료하기 전에 현재 @lines에 있는 내용을 이메일로 보내기 위해 다양한 신호를 포착하는 몇 줄도 있습니다.
File::Tail
정확한 세부사항 Net::SMTP
은 및(또는 다른 곳)의 매뉴얼 페이지를 참조하십시오.
답변3
좋은 아이디어입니다. 가장 간단한 방법은 @MelBurslan이 제안한 대로 파일을 비교하는 것입니다.
#!/bin/sh
[email protected]
OFILE=/var/tmp/alerts.tmp
LOG30=/var/tmp/LOG30
LOGNOW=/var/tmp/LOGNOW
HOST=`hostname`
# setup file
if [ -f ${OFILE} ]; then
cat /dev/null > ${OFILE}
else
touch ${OFILE}
fi
cat /var/log/logfile.log | egrep -i "error|warning" | tee -a ${LOGNOW}
diff ${LOG30} ${LOGNOW} | tee -a ${OFILE}
if [ -f ${OFILE} ]; then
echo "Errors" | cat - ${OFILE} > temp && mv temp ${OFILE}
mailx -r [email protected] -s "Errors" ${MAILTO} < ${OFILE}
fi
rm ${LOG30}
mv ${LOGNOW} /var/tmp/LOG30
rm ${OFILE}