过滤日志目录中所有日志里最近1小时的错误记录及上下5行


这里假设日志文件中的时间标准格式为:[YYYY-mm-ddTHH:MM:SS.ZZZ]
例如,日志格式:

1
2
3
4
5
[2019-12-11T15:15:05.533] [INFO] default - Executing (default): SELECT count(*) AS `count` FROM `watch` AS `watch` WHERE `watch`.`fmid` = 25;
{
"i": "am",
"a": "json file"
}

命令:

1
find ./ -type f -mmin -60 |xargs awk '$1~/[0-9]{4}-[0-9]{2}-[0-9]{2}/ {t=substr($1,2,19); h=strftime("%Y-%m-%dT%T", systime()-3600); if(t>h){print $0; curline=NR}} curline>0&&NR>curline&&NR<=curline+999 {if (FNR==1) {curline=0} else {print $0}}' | grep "ERROR" -A 5 -B 5

解释:

  • find ./ -type f -mmin -60 找到一小时以内修改过的文件
  • '$1~/[0-9]{4}-[0-9]{2}-[0-9]{2}/ 匹配日期行,对于日期行执行后面大括号的动作
  • t=substr($1,2,19); 取中括号中的日期
  • h=strftime("%Y-%m-%dT%T", systime()-3600); 取当前时间一个小时前的日期
  • if(t>h){print $0; curline=NR} 比较日期,如果在一小时内,则打印该行,并记录当前行号
  • curline>0&&NR>curline&&NR<=curline+999 匹配上一次打印的日期行后面的行,尽量覆盖直至下一个日期行,匹配到就执行后面的大括号里的动作
  • if (FNR==1) {curline=0} else {print $0} 如果切换了下一个文件,就重置匹配日期行记录(不然后面的文件假如开头不是符合条件的行也都会打印出来),否则就继续打印当前文件的剩余行
  • grep "ERROR" -A 5 -B 5 在前面打印的所有行中将ERROR前后5行过滤出来