我需要扫描日志文件并从中提取相关部分到另一个文件。 日志格式为:
[hh:mm:ss] Header
[hh:mm:ss] irrelevant text
[hh:mm:ss] irrelevant text
[hh:mm:ss]Error text
[hh:mm:ss] some details
[hh:mm:ss] end_error;
[hh:mm:ss] irrelevant text
[hh:mm:ss] Warning text
[hh:mm:ss] some details
[hh:mm:ss] end_warning;
[hh:mm:ss] irrelevant text
[hh:mm:ss] irrelevant text
[hh:mm:ss]Error text
[hh:mm:ss] some details
[hh:mm:ss] end_error;
我需要出现所有错误和警告并捕获以下文本:
[hh:mm:ss]Error text
[hh:mm:ss] some details
[hh:mm:ss] end_error;
[hh:mm:ss] Warning text
[hh:mm:ss] some details
[hh:mm:ss] end_warning;
[hh:mm:ss]Error text
[hh:mm:ss] some details
[hh:mm:ss] end_error;
在bash上实现此目的的最简单方法是什么?
答案 0 :(得分:1)
$ awk '/^(Error|Warning)/{f=1} f; /;/{f=0}' file
Error text
end_error;
Warning text
end_warning;
您的原始输入文件在每行的开头显示错误和警告,因此我的上面的脚本中有一个行首锚(^)。使用您最新发布的样本输入文件和所需的输出,您需要:
$ awk '
/^[[:space:]]*\[[^]]+\][[:space:]]*(Error|Warning)/ { found=1 }
found { sub(/^[[:space:]]+/,""); print }
/;/ { found=0 }
' file
[hh:mm:ss]Error text
[hh:mm:ss] some details
[hh:mm:ss] end_error;
[hh:mm:ss] Warning text
[hh:mm:ss] some details
[hh:mm:ss] end_warning;
[hh:mm:ss]Error text
[hh:mm:ss] some details
[hh:mm:ss] end_error;
正则表达式的复杂性是为了避免错误匹配,如果输入文件中的其他位置出现错误或警告字。
答案 1 :(得分:1)
使用GNU sed
范围运算符和-n
以及-r
选项分别禁止默认打印和启用扩展正则表达式。 p
标志打印与条件匹配的行。
$ sed -nr '/^(Error|Warning)/,/;/p' file
Error text
end_error;
Warning text
end_warning;
您也可以在awk
中执行相同操作。但是几乎总是建议使用Ed's方法。
$ awk '/^(Error|Warning)/,/;/' file
Error text
end_error;
Warning text
end_warning;
答案 2 :(得分:0)
尝试:
cat file | awk '/^(Error|Warning)/,/;$/ { print $0 }' > output
这将通过awk传输文件,awk将打印以Error
或Warning
开头的行,直到以;
结尾的第一行,结果将保存在{{1 }}