Bash - 提取两个模式之间的行并在两个模式内包含匹配项

问题描述 投票:0回答:1

我在 Oracle Service Bus 中处理大型日志文件。它们是具有两种硬编码模式的消息列表。我需要从它们中提取硬编码模式之间的几行,并以会话 id (uuid) 作为输入。

具有以下特点:

  • 提取的消息始终以“[YYYY-MM-DD09THH:MM:SS...”开头
  • 该消息具有会话 ID 参考(例如:[@uuid:274defb0-d02b-49fe-aeb2-92d8a5fab518])
  • 消息以 ]] 作为最后一行结束

这里是日志文件的示例:

[2023-10-09T09:08:38.995+02:00] [...not useful information...][...not useful information...] [@uuid:274defb0-d02b-49fe-aeb2-92d8a5fab518]  

Body:<soapenv:Body xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">[[ 

....soap message...

...final lines 

</soapenv:Body>  

]] 

我从给定的 uuid 开始提取消息。

在主机上我只能使用 bash 脚本

我尝试了 sed 或 awk 但无法解决问题

bash unix awk sed osb
1个回答
0
投票

你可以这样做:

declare should_write=no
while read -r line; do
  if [[ "$line" =~ ^\[[0-9]{4}-[0-9]{2}-[0-9]{2}T[0-9]{2}:[0-9]{2}:[0-9]{2}\.[0-9]{3}[^]]*\] ]]; then
    should_write=yes
    echo "$line"
  elif [[ "$line" =~ ^[ \t]*\]\][ \t]*$ ]]; then # or "$line" == ']]'
    should_write=no
    echo "$line"
  elif [[ "$should_write" == yes ]]; then
    echo "$line" 
  fi
done < file

正则表达式可能需要一些调整,或者您可以避免它(尤其是]])。

您还可以在之前调用添加一些 rtrim 功能,具体取决于空间是否重要:

while .. do ... done < <(sed -E -e 's@[ \t]+$@@g' "$file")
© www.soinside.com 2019 - 2024. All rights reserved.