logstash:使用自定义正则表达式模式(代码片段)

Elastic中国社区官方博客 Elastic中国社区官方博客     2023-04-03     249

关键词:

有时 Logstash Grok 没有我们需要的模式。 幸运的是我们有正则表达式库:Oniguruma。在很多时候,如果 Logstash 所提供的正则表达不能满足我们的需求,我们选用定制自己的表达式。

定义

  • Logstash 是一种服务器端数据处理管道,可同时从多个来源获取数据,对其进行转换,然后将其发送到 “存储”(如 Elasticsearch)。
  • Grok 是 Logstash 中的过滤器,用于将非结构化数据解析为结构化和可查询的内容。
  • Regular expression 是定义搜索模式的字符序列。

如果你已经在运行 Logstash,则无需安装额外的正则表达式库,因为 Grok 位于正则表达式之上,因此任何正则表达式在 grok 中也有效 —— Elastic 文档

语法

Grok

Grok 语法如下:

%SYNTAX:SEMANTIC
  • SYNTAX 是默认的 grok 模式
  • SEMANTIC 是 key

Oniguruma

oniguruma 语法如下:

(?<field_name>the pattern here)

Grok + Oniguruma

你可以像下面这样组合 Grok 和 Oniguruma:

%SYNTAX:SEMANTIC (?<field_name>the pattern here)

让我们开始吧

样本数据

为了演示我们如何将 Oniguruma 与 Grok 结合使用,我们将在示例中使用下面的日志数据。

production GET /v2/blacklist/ 200 24ms 5ba9e948801d34906b96e0c20 Panya/1.6.3 (com.sn.panya.host; build:1; iOS 10.3.3) Alamofire/4.66.0 \\"user_id\\":\\"5bd4c2f4569f470016bd8d55\\",\\"reason\\":\\"SPAMMER\\"

日志数据结构:

production == environment
GET == method
/v2/blacklist == url
200 == response_status
24ms == response_time
5bc6e716b5d6cb35fc9687c0 == user_id
Panya/1.6.3 (com.sn.panya.host; build:1; iOS 10.3.3) Alamofire/4.66.0 == user_agent
\\"user_id\\":\\"5bd4c2f4569f470016bd8d55\\",\\"reason\\":\\"SPAMMER\\" == req.body

目的:

目标是找到一种模式来构造非结构化日志数据。为此,我们将使用 Kibana 里的 Grok Debugger 来进行测试:

其中,我们的 Grok pattern 定义如下:

%WORD:environment %WORD:method %URIPATH:url %NUMBER:response_status %WORD:response_time %USERNAME:user_id

如上所示,上面的 Grok pattern 产生如下的结果:


  "environment": "production",
  "method": "GET",
  "response_status": "200",
  "user_id": "5ba9e948801d34906b96e0c20",
  "response_time": "24ms",
  "url": "/v2/blacklist/"

这是一个不错的开始,但还不完整。 没有 user_agent 和 req.body 的映射。要提取 user_agent 和 req.body,我们需要仔细检查其结构。

空格分隔符

值 production GET /v2/blacklist/ 200 24ms 5ba9e948801d34906b96e0c20 由空格分隔,这很容易使用。

但是,对于 user_agent,可以有动态数量的空格,具体取决于发送请求的硬件类型。

Panya/1.6.3 (com.sn.panya.host; build:1; iOS 10.3.3) Alamofire/4.66.0 

我们如何解释这种持续变化?

提示:看一下 req.body 的结构。

\\”user_id\\”:\\”5bd4c2f4569f470016bd8d55\\”,\\”reason\\”:\\”SPAMMER\\”

我们可以看到 req.body 是由花括号 组成的。

利用这些知识,我们可以构建一个自定义正则表达式模式来查找第一个左括号之前的所有内容,然后获取之后的所有内容。

 在上面,我们使用 Grok pattern:

(?<user_agent>[^]*) %GREEDYDATA:body

你可在这个链接中找到 “regex match everything until character”。

把所有的都放在一起

将其应用于 grok 调试器中的自定义正则表达式模式,我们得到了我们想要的结果:

我们的 Grok pattern 为:

%WORD:environment %WORD:method %URIPATH:url %NUMBER:response_status %WORD:response_time %USERNAME:user_id (?<user_agent>[^]*) %GREEDYDATA:body

 

创建 logstash.conf

为了能够测试我们的 Grok pattern 是否正确,我们创建如下的一个 logstash.conf 文件。我们可以参考之前的文章 “Logstash:在实施之前测试 Logstash 管道/过滤器”。

logstash.conf

input 
  generator 
    message => 'production GET /v2/blacklist/ 200 24ms 5ba9e948801d34906b96e0c20 Panya/1.6.3 (com.sn.panya.host; build:1; iOS 10.3.3) Alamofire/4.66.0 "user_id":"5bd4c2f4569f470016bd8d55","reason":"SPAMMER"'
    count => 1
  

 
filter 
  grok 
    match =>  "message" => "%WORD:environment %WORD:method %URIPATH:url %NUMBER:response_status %WORD:response_time %USERNAME:user_id1 (?<user_agent>[^]*) %GREEDYDATA:body"
  

  mutate 
    remove_field => ["message", "event", "host", "@version"]
   
 
 
output 
  stdout 
    codec => rubydebug
  

我们使用如下的命令来启动 Logstash pipeline:

./bin/logstash -f logstash.conf

从上面的输出中,我们可以看出来原始的数据已经变为结构化的数据了。我们可以看到美中不足的是 body 这个数据是一个 JSON 格式的数据,还没有被结构化。我们进一步修改我们的 logstash.conf 配置文件:

logstash.conf

input 
  generator 
    message => 'production GET /v2/blacklist/ 200 24ms 5ba9e948801d34906b96e0c20 Panya/1.6.3 (com.sn.panya.host; build:1; iOS 10.3.3) Alamofire/4.66.0 "user_id":"5bd4c2f4569f470016bd8d55","reason":"SPAMMER"'
    count => 1
  

 
filter 
  grok 
    match =>  "message" => "%WORD:environment %WORD:method %URIPATH:url %NUMBER:response_status %WORD:response_time %USERNAME:user_id1 (?<user_agent>[^]*) %GREEDYDATA:body"
  

  json 
    source => "body"
  

  mutate 
    remove_field => ["message", "event", "host", "@version", "body"]
  

 
 
output 
  stdout 
    codec => rubydebug
  

在上面,我们添加了 json 过滤器来处理 body,从而更进一步结构化数据。我们再次运行 Logstash。我们可以看到如下的结果:

 

从上面,我们可以看到 body 也被结果化了。我们可以看到 user_id 及 reason 两个字段。

elasticsearch-logstash-kibana(三)配置优化

...要对message进行解析。本文采用grok过滤器,使用match正则表达式解析,根据自己的log_format定制。nginx日志格式如下:对应日志如下:logstash中默认存在一部分正则让我们来使用,可以访问GrokDebugger来查看。基本定义在grok-patterns中... 查看详情

logstash使用笔记

参考技术ALogstash这东西就是正则表达式匹配,不过由于日志太大了,如果你这个正则从头写到尾估计写一半人就没了,所以人家预定义好了许多的正则表达式,那些%xxx本质上就是那些正则,一样的替代一下。内置的那些预定义... 查看详情

用于匹配单词的 javascript 正则表达式模式,具有自定义单词边界

】用于匹配单词的javascript正则表达式模式,具有自定义单词边界【英文标题】:javascriptregexpatterntomatchwords,withcustomwordboundary【发布时间】:2014-09-2909:04:53【问题描述】:我正在尝试使用javascript中的正则表达式匹配字符串中的单... 查看详情

用于忽略自定义转义字符的正则表达式模式

】用于忽略自定义转义字符的正则表达式模式【英文标题】:RegexPatternforignoringacustomescapecharacter【发布时间】:2012-09-0919:38:36【问题描述】:我正在尝试找到一个合适的正则表达式来匹配输入字符串中的一对自定义字符。这些自... 查看详情

自定义正则表达式不在客户端验证

】自定义正则表达式不在客户端验证【英文标题】:CustomRegularExpressionnotvalidatingontheclientside【发布时间】:2016-04-2516:27:59【问题描述】:我已经构建了一个自定义属性来在客户端验证正十进制值。问题是当我将正则表达式直接应... 查看详情

如何在自定义 grok 模式中引用正则表达式组?

】如何在自定义grok模式中引用正则表达式组?【英文标题】:HowdoIrefertoaregexgroupinsideacustomgrokpattern?【发布时间】:2017-08-0222:01:06【问题描述】:我想在我的日志行中添加特定URI参数的字段这是一个示例日志行:2017-03-1221:34:36W3SV... 查看详情

使用 QSqlTableModel 的正则表达式自定义 QAbstractItemDelegate

】使用QSqlTableModel的正则表达式自定义QAbstractItemDelegate【英文标题】:CustomQAbstractItemDelegatewithregexforQSqlTableModel【发布时间】:2015-03-1120:00:52【问题描述】:我正在尝试创建一个自定义委托,以便我可以使用Regex来验证正在输入到... 查看详情

Logstash grok 模式过滤自定义日志消息

】Logstashgrok模式过滤自定义日志消息【英文标题】:LogstashgrokpatterntofiltercustomLogmessage【发布时间】:2015-03-1608:40:25【问题描述】:我是logstash的新手,我想从日志消息中过滤文件。这是日志消息:[2015-03-1613:12:05,130]INFO-LogMediatorSe... 查看详情

简析正则表达式

...了处理基于标签的数据提取与数据填充大量的使用了正则表达式,在这里将我将正则表达式的语法和用法进行简单的描述,然后下篇中将介绍在c#中利用正则表达式的方法与代码实例。什么是正则表达式基本说来,正则表达式是... 查看详情

用于自定义电子邮件和域的 C# 正则表达式

】用于自定义电子邮件和域的C#正则表达式【英文标题】:C#Regexforcustomemailanddomain【发布时间】:2021-11-0920:35:14【问题描述】:我有一个带有使用此模式的输入的剃刀视图:pattern="^[a-zA-Z0-9._+-]+&#64mydomain.com"它用作前端验证非... 查看详情

正则表达式

正则表达式1.简单的介绍正则表达式a) 正则表达式就是描述字符串排列模式的一种自定义语法规则b) 如果可以使用字符串函数处理完成的任务,就不要使用正则表达式c) 有一些复杂性的操作,只能用正则表达式来完成d... 查看详情

logstash使用操作部分

1.logstash的概念及特点。概念:logstash是一个数据采集、加工处理以及传输(输出)的工具。特点:  -所有类型的数据集中处理  -不同模式和格式数据的正常化  -自定义日志格式的迅速扩展  -为自定义数据源轻松添加插件... 查看详情

Grafana - 在查询中使用自定义变量作为正则表达式

】Grafana-在查询中使用自定义变量作为正则表达式【英文标题】:Grafana-usecustomvariableasregexinquery【发布时间】:2019-08-1019:16:37【问题描述】:我们有普罗米修斯数据源,我一直在尝试使用具有少量值的自定义变量作为逗号分隔值... 查看详情

flask自定义转换器,实现路由匹配正则表达式参数(代码片段)

...自定义转换器来实现了,而不能向Django那样直接使用正则表达式1#路由传递的参数默认当做string处理2#这里指定int,尖括号中冒号后面的内容是动态的34@app.route(‘/user/<int:id>‘)5defhello_itcast(id):6r 查看详情

自定义正则表达式 [关闭]

】自定义正则表达式[关闭]【英文标题】:CustomRegularExpressions[closed]【发布时间】:2013-03-2419:03:58【问题描述】:如何使用正则表达式来分隔BCT34385Z0000N07518ZBCT34395Z0000N07518Z转换成BCT343格式?我正在使用这个magento将2种类型的序列... 查看详情

正则表达式实战(代码片段)

使用正则表达式正则表达式相关知识在编写处理字符串的程序或网页时,经常会有查找符合某些复杂规则的字符串的需要,正则表达式就是用于描述这些规则的工具,换句话说正则表达式是一种工具,它定义了字符串的匹配模式... 查看详情

markdown尖叫青蛙自定义提取的正则表达式cheatsheet(代码片段)

查看详情

一个可以使用多个正则表达式进行多次尝试匹配,并进行替换的excelvba自定义函数(ufd)

以下代码可使用多个正则表达式对目标单元格进行多次匹配尝试,如匹配成功,将停止尝试匹配其他正则表达式,并且使用该正则表达式相对应的替换表达式进行替换,返回替换结果。使用前需要做EarlyBinding。即在VBE编辑器中,... 查看详情