解析日志并在1个命令中输出2个字符串

时间:2011-11-29 14:58:53

标签: parsing awk grep logging

178.139.20.52 - - [26/Nov/2011:08:21:13 +0000] "POST /test/LinkTest.cgi?e=PATTERN&t3=0:010015&t4=1322295671:587875&l=178.139.20.174&n=149 HTTP/1.1" 200 17 "-" "BOT/1.26"

以上是我要解析的日志条目类型。

我喜欢输出命令:

178.139.20.52 PATTERN

关于如何实现这一目标的任何想法?

谢谢。

感谢您的回答,我将会这样做:

cat access_log | grep "LinkTest.cgi" | grep "26\/Nov\/2011" | awk -v FS="[ =&]" '{ print $1,$8 }' | sort -u

5 个答案:

答案 0 :(得分:2)

使用GNU sed的方法怎么样?

sed -r 's/^(\S+).*e=([^&]+)&.*/\1 \2/'

答案 1 :(得分:2)

如何使用awk

注意 - 如果您的pattern不包含=space&,这将有效。

awk -v FS="[ =&]" '{ print $1,$8 }' file

[jaypal:~/Temp] cat file
178.139.20.52 - - [26/Nov/2011:08:21:13 +0000] "POST /test/LinkTest.cgi?e=PATTERN&t3=0:010015&t4=1322295671:587875&l=178.139.20.174&n=149 HTTP/1.1" 200 17 "-" "BOT/1.26"


[jaypal:~/Temp] awk -v FS="[ =&]" '{ print $1,$8 }' file
178.139.20.52 PATTERN

答案 2 :(得分:2)

我认为grep不适合这个,它只根据模式过滤行。您可以使用-o开关仅打印与该模式匹配的文本,但我不知道如何在grep中提取/打印多个子字符串。

这个perl one liner怎么样?

perl -ne 'm/^\s*(\d+\.\d+\.\d+\.\d+).+?\?e=([^&]+)/ and print "$1 $2\n"'

答案 3 :(得分:2)

这个问题似乎没有具体说明,因为我们不知道PATTERN中的内容。这是一个起点:

sed -e 's/ .*LinkTest.cgi?e=/ /' -e 's/&.*//'

答案 4 :(得分:1)

使用awk:

'infile'的内容

178.139.20.52 - - [26/Nov/2011:08:21:13 +0000] "POST /test/LinkTest.cgi?e=PATTERN&t3=0:010015&t4=1322295671:587875&l=178.139.20.174&n=149 HTTP/1.1" 200 17 "-" "BOT/1.26"

我的linux机器中的awk命令:

awk 'BEGIN { FS = "=" } { ip = substr( $1, 0, index( $1, " " ) - 1 ); pattern = substr( $2, 0, index( $2, "&" ) - 1 ); printf "%s %s\n", ip, pattern }' infile

结果:

178.139.20.52 PATTERN