智能地将一个文本日志文件与另一个文本日志文件“减去”

智能地将一个文本日志文件与另一个文本日志文件“减去”

示例:应用程序生成包含许多不同消息的大型文本日志文件。当无法正常运行时,A它也会生成类似的大型日志文件。B

我想查看文件中哪些消息B本质上是新的,即从中过滤掉所有内容A

简单原型是:

  1. 对两个文件进行排序 | uniq
  2. 连接文件
  3. 排序 | uniq-c
  4. grep -v "^2"

这样就产生了对称差异,很不方便。如何做得更好?(包括非对称差异和保留消息顺序B

程序应该首先分析A了解哪些消息是常见的,然后分析B显示需要注意的消息。

理想情况下,它应该自动忽略时间戳、行号或其他易变的东西。

例如。答:

0:00:00.234  Received buffer 0x324234
0:00:00.237     Processeed buffer 0x324234
0:00:00.238     Send buffer 0x324255
0:00:03.334  Received buffer 0x324255
0:00:03.337     Processeed buffer 0x324255
0:00:03.339     Send buffer 0x324255
0:00:05.171  Received buffer 0x32421A
0:00:05.173     Processeed buffer 0x32421A
0:00:05.178     Send buffer 0x32421A

乙:

0:00:00.134  Received buffer 0x324111
0:00:00.137     Processeed buffer 0x324111
0:00:00.138     Send buffer 0x324111
0:00:03.334  Received buffer 0x324222
0:00:03.337     Processeed buffer 0x324222
0:00:03.338     Error processing buffer 0x324222 
0:00:03.339     Send buffer 0x3242222
0:00:05.271  Received buffer 0x3242FA
0:00:05.273     Processeed buffer 0x3242FA
0:00:05.278     Send buffer 0x3242FA
0:00:07.280     Send buffer 0x3242FA failed

结果:

0:00:03.338     Error processing buffer 0x324222 
0:00:07.280     Send buffer 0x3242FA failed

解决这个问题的方法之一可能是这样的:

  1. 将每行拆分为逻辑单元:0:00:00.134 Received buffer 0x3241110:00:00.134Receivedbuffer0x324111324111Received buffer\d:\d\d:\d\d\.\d\d\d\d+:\d+:\d+.\d+0x[0-9A-F]{6}... 它应该找到单个单词、数字中的简单模式、常见布局(例如“某些日期比文本比数字比文本比行尾”),还可以处理上述组合。由于这不是一项简单的任务,因此应该支持(但不是必需的)用户帮助(添加具有明确“忽略那个”、“作为主要因素”、“不要拆分为部分”、“视为日期/数字”、“注意此类消息的顺序/数量”规则的正则表达式)。
  2. 查找重复的单元并“分类”行,过滤掉过于不稳定的内容,例如时间戳、地址或行号。
  3. 分析第二个文件,找到具有新逻辑单元(一次性或重复性)的东西,或者任何会让已经习惯第一个文件的系统“惊奇”的东西。

手动执行一些此类操作的示例:

$ cat A | head -n 1
0:00:00.234  Received buffer 0x324234

$ cat A | egrep -v "Received buffer" | head -n 1
0:00:00.237     Processeed buffer 0x324234

$ cat A | egrep -v "Received buffer|Processeed buffer" | head -n 1
0:00:00.238     Send buffer 0x324255

$ cat A | egrep -v "Received buffer|Processeed buffer|Send buffer" | head -n 1

$ cat B | egrep -v "Received buffer|Processeed buffer|Send buffer"
0:00:03.338     Error processing buffer 0x324222 
0:00:07.280     Send buffer 0x3242FA failed

这是一件很无聊的事情(有很多消息类型);而且我可能会不小心包含一些太宽泛的模式。而且它无法处理消息之间的相互关系等复杂的事情。

我知道这是与人工智能相关的。可能已经开发出工具了?

答案1

diff(及其各种选项)将向您显示两种方式的差异,并保留消息顺序。但是,它不会删除差异的重复项(因为您可以uniq在之后应用)或处理不同的顺序。这样够好吗?

答案2

使用diff(在正常输出模式下,即没有-c-u)。新行将以 为前缀>

diff A B | sed -ne 's/> //p'

如果日志包含时间戳,则必须先将其删除。

有时,在上下文中查看新/更改的部分会更好,突出显示差异并导航不同的块。Emacs 有一个不错的界面(工具 | 比较菜单,M-x ediff-files)。还有许多独立工具(名称中通常带有“diff”或“compare”)。

顺便说一句,如果您对行的顺序不感兴趣,那么对两个文件进行排序comm会比您在问题中给出的过程更容易、更漂亮。

答案3

这是一个难题,从某种意义上说,也是一个活跃的研究问题。我认为目前还没有一个程序只需要插入几个正则表达式即可。

我会将您的程序表述为尝试比较网络程序的踪迹。我怀疑比较网络或并发程序踪迹的人遇到过这个问题并编写了自己的工具,但我脑子里没有具体的例子。

相关内容