项目需要做一个shell程序,用来查找指定日志文件中某段字符串str,再根据该字符串str所在的行,找到对应的某个字段str1($*)再以此str1找出str上下若干包含str1的行,主要内容用awk实现,还用到了getopts进行参数的判断:
#!/bin/bash # File: Fmsg.sh # Author: xiaoleyu@gmail.com # Update: 2008-07-30 while getopts "m:k:l:f:" flag do case $flag in m) MSG=$OPTARG #各个参数后面的值都保存在OPTARG 这个默认参数里面 ;; l) BUFL=$OPTARG ;; k) KEY=$OPTARG ;; f) FileName=$OPTARG ;; ?) echo "-f FileName -m SearchMsg -k Key -l BufferLenght " ;; *) echo "something wrong" ;; esac done echo Searching MSG is $MSG echo BufferLenght is $BUFL echo FileName is $FileName if [ -n "$BUFL" ] #说明:如果BUFL( -l 参数)为空 则BUFLEN=3 表示显示与str相关的上下3行的记录 then BUFLEN=$BUFL else BUFLEN="3" # 需要引号 fi if [ -n "$FileName" ] then File=$FileName else File="" fi if [ -n "$KEY" ] then KEY1=$KEY grep $KEY1 $File > filter.out #如果File 为空则可通过管道输入 File="filter.out" else File=$FileName fi REQFILE=$MSG awk -F " " ' #-F " "表示以空格作为不同参数($*)的分隔符 BEGIN { m='$BUFLEN';n='$BUFLEN';i=1;nr_up=0;nr_down=0; } { for(i=1;i<=m;i++) { up[$3,i]=up[$3,i+1];#二维数组表示特点[,] } { if(flag>0) { if( temp2==$3) print $0; flag --; } } up[$3,m+1]=$0; } /'$REQFILE'/{ # { 需要接在/后面,否则可能出现判断失效 temp2=$3; if(nf_up==0) nr_up=NR; else { if(nr_down!=0) nr_up=nr_down; nr_down=NR; } if(nr_down!=0 && nr_up!=0 && nr_down-nr_up<=m+n) { for(i=1;i<=m+n-(nr_down-nr_up-1);i++) { delete up[$3,i]; } } for(j=1;j<=m;j++) { print up[$3,j] } print $0; flag=n; next; }' $File
#调用方法1:cat fileName | sh Fmsg.sh -m str -l bufLen #调用方法2:sh Fmsg.sh -m str -l bufLen -f fileName -k 关键字
说明: 文件名 "fileName" 文件内容如下: aaaa a bbbbbbbb cccccccccdd ddddddddd eeee fffffffff ddddddddddd hhhh a bbbbbbbb ddddddddddd eeeeeeeee aaaa ccccccccc lkkkkksadas afsd a 22222222 ddsfsafdsdd sadsfsafa dfas dfasdfasd safsdfsafsf aaaa a 22222222 asdasdsdsdd ddddddddd eeee fffffffff ddddddddddd hhhh a 22222222 ddddddddddd eeeeeeeee aaaa ccccccccc lkkkkksadas afsd a 22222222 this_is_msg sadsfsafa dfas dfasdfasd safsdfsafsf aaaa a 22222222 cccccccccdd ddddddddd eeee fffffffff ddddddddddd hhhh a 22222222 ddddddddddd eeeeeeeee aaaa ccccccccc lkkkkksadas afsd a 22222222 ddsfsafdsdd sadsfsafa dfas dfasdfasd safsdfsafsf aaaa a bbbbbbbb cccccccccdd ddddddddd eeee fffffffff ddddddddddd hhhh a bbbbbbbb ddddddddddd eeeeeeeee aaaa ccccccccc lkkkkksadas afsd a asfasdfs ddsfsafdsdd sadsfsafa dfas dfasdfasd safsdfsafsf aaaa a bbbbbbbb cccccccccdd ddddddddd eeee fffffffff ddddddddddd hhhh a bbbbbbbb ddddddddddd eeeeeeeee aaaa ccccccccc lkkkkksadas afsd a asfasdfs ddsfsafdsdd sadsfsafa dfas dfasdfasd safsdfsafsf 我们输入要找的msg是:‘this_is_msg’ 通过这个msg 找到$2="22222222" 然后我们找出该行前后包括"22222222"的若干行(值为BUFLEN) 命令为: sh Fmsg.sh -m this_is_msg -l 3 -f fileName 打印结果为: afsd a 22222222 ddsfsafdsdd sadsfsafa dfas dfasdfasd safsdfsafsf aaaa a 22222222 asdasdsdsdd ddddddddd eeee fffffffff ddddddddddd hhhh a 22222222 ddddddddddd eeeeeeeee aaaa ccccccccc lkkkkksadas afsd a 22222222 this_is_msg sadsfsafa dfas dfasdfasd safsdfsafsf aaaa a 22222222 cccccccccdd ddddddddd eeee fffffffff ddddddddddd hhhh a 22222222 ddddddddddd eeeeeeeee aaaa ccccccccc lkkkkksadas afsd a 22222222 ddsfsafdsdd sadsfsafa dfas dfasdfasd safsdfsafsf