介紹
logstash擁有豐富的filter插件,它們擴展了進入過濾器的原始數據,進行復雜的邏輯處理,甚至可以無中生有的添加新的 logstash 事件到后續的流程中去!Grok 是 Logstash 最重要的插件之一。也是迄今為止使蹩腳的、無結構的日志結構化和可查詢的最好方式。Grok在解析 syslog logs、apache and other webserver logs、mysql logs等任意格式的文件上表現完美。
使用grok前注意
grok 模式是正則表達式,因此這個插件的性能受到正則表達式引擎嚴重影響。盡管知道 grok 模式與日志條目可以多快匹配非常重要,但是了解它在什么時候匹配失敗也很重要。匹配成功和匹配失敗的性能可能會差異很大。
grok基礎
grok模式的語法如下:
%{SYNTAX:SEMANTIC}
1
SYNTAX:代表匹配值的類型,例如3.44可以用NUMBER類型所匹配,127.0.0.1可以使用IP類型匹配。
SEMANTIC:代表存儲該值的一個變量名稱,例如 3.44 可能是一個事件的持續時間,127.0.0.1可能是請求的client地址。所以這兩個值可以用 %{NUMBER:duration} %{IP:client} 來匹配。
你也可以選擇將數據類型轉換添加到Grok模式。默認情況下,所有語義都保存為字符串。如果您希望轉換語義的數據類型,例如將字符串更改為整數,則將其后綴為目標數據類型。例如%{NUMBER:num:int}將num語義從一個字符串轉換為一個整數。目前唯一支持的轉換是int和float。
例子: 通過這種語法和語義的思想,我們可以從一個示例日志中抽出有用的字段,就像這個虛構的http請求日志:
55.3.244.1 GET /index.html 15824 0.043
可以使用如下grok pattern來匹配這種記錄:
%{IP:client} %{WORD:method} %{URIPATHPARAM:request} %{NUMBER:bytes} %{NUMBER:duration}
我們在logstash.conf中添加過濾器配置:
filter {
grok {
match => {
"message" => "%{IP:client} %{WORD:method} %{URIPATHPARAM:request} %{NUMBER:bytes} %{NUMBER:duration}" }
}
}
以下是filter結果:
● client:
55.3.244.1
● method: GET
● request: /index.html
● bytes:
15824
● duration:
0.043
Logstash附帶約120個模式。你可以在這里找到它們
https://github.com/logstash-plugins/logstash-patterns-core/tree/master/patterns
正則表達式
Grok位於正則表達式之上,所以任何正則表達式在grok中都是有效的。正則表達式庫是Oniguruma,您可以在
Oniguruma網站上看到完整支持的regexp語法。
中文學習正則表達式網站:
http://www.runoob.com/regexp/regexp-tutorial.html
自定義類型
更多時候logstash grok沒辦法提供你所需要的匹配類型,這個時候我們可以使用自定義
第一種
直接使用Oniguruma語法來命名捕獲,它可以讓你匹配一段文本並保存為一個字段:
(?<field_name>the pattern here)
1
例如,日志有一個queue_id 為一個長度為10或11個字符的十六進制值。使用下列語法可以獲取該片段,並把值賦予queue_id
(?<queue_id>[
0-9A-F]{10,11})
1
第二種
創建自定義 patterns 文件。
①創建一個名為patterns其中創建一個文件postfix (文件名無關緊要,隨便起),在該文件中,將需要的模式寫為模式名稱,空格,然后是該模式的正則表達式。例如:
#contents of ./patterns/postfix:
POSTFIX_QUEUEID [
0-9A-F]{10,11}
②然后使用這個插件中的patterns_dir設置告訴logstash目錄是你的自定義模式。這是一個完整的示例的示例日志:
Jan
1 06:25:43 mailserver14 postfix/cleanup[21403]: BEF25A72965: message-id=<20130101142543.5828399CCAF@mailserver14.example.com>
1
filter {
grok {
patterns_dir => [
"./patterns"]
match => {
"message" => "%{SYSLOGBASE} %{POSTFIX_QUEUEID:queue_id}: %{GREEDYDATA:syslog_message}" }
}
}
匹配結果如下:
● timestamp: Jan
1 06:25:43
● logsource: mailserver14
● program: postfix/cleanup
● pid:
21403
● queue_id: BEF25A72965
● syslog_message: message-id=<
20130101142543.5828399CCAF@mailserver14.example.com>
Grok過濾器配置選項
break_on_match
● 值類型是布爾值
● 默認是true
● 描述:match可以一次設定多組,預設會依照順序設定處理,如果日志滿足設定條件,則會終止向下處理。但有的時候我們會希望讓Logstash跑完所有的設定,這時可以將break_on_match設為false。
keep_empty_captures
● 值類型是布爾值
● 默認值是 false
● 描述:如果為true,捕獲失敗的字段將設置為空值
match
● 值類型是數組
● 默認值是 {}
● 描述:字段⇒值匹配
例如:
filter {
grok { match => {
"message" => "Duration: %{NUMBER:duration}" } }
}
#如果你需要針對單個字段匹配多個模式,則該值可以是一組,例如:
filter {
grok { match => {
"message" => [ "Duration: %{NUMBER:duration}", "Speed: %{NUMBER:speed}" ] } }
}
named_captures_only
● 值類型是布爾值
● 默認值是 true
● 描述:If true, only store named captures from grok.(暫不清楚有什么用)
overwrite
● 值類型是 array
● 默認是[]
● 描述:覆蓋字段內容
例如:
filter {
grok {
match => {
"message" => "%{SYSLOGBASE} %{DATA:message}" }
overwrite => [
"message" ]
}
}
如果日志是May 29 16:37:11 sadness logger: hello world經過match屬性match => { “message” => “%{SYSLOGBASE} %{DATA:message}” }處理后,message的值變成了hello world。這時如果使用了overwrite => [ “message” ]屬性,那么原來的message的值將被覆蓋成新值。
pattern_definitions
● 值類型是 數組
● 默認值是 {}
● 描述:模式名稱和模式正則表達式,也是用於定義當前過濾器要使用的自定義模式。匹配現有名稱的模式將覆蓋預先存在的定義。可以將此視為僅適用於grok定義的內聯模式,patterns_dir是將模式寫在外部。
例如:
filter {
grok {
patterns_dir =>
"/usr/local/elk/logstash/patterns"
pattern_definitions => {
"MYSELFTIMESTAMP" => "20%{YEAR}-%{MONTHNUM}-%{MONTHDAY} %{HOUR}:?%{MINUTE}(?::?%{SECOND})"}
match => {
"message" => ["%{MYSELFTIMESTAMP:timestamp} %{JAVACLASS:message}","%{MYSELF:content}"]}
}
}
patterns_dir
● 值類型是數組
● 默認值是 []
● 描述:一些復雜的正則表達式,不適合直接寫到filter中,可以指定一個文件夾,用來專門保存正則表達式的文件,需要注意的是該文件夾中的所有文件中的正則表達式都會被依次加載,包括備份文件。
patterns_dir => [
"/opt/logstash/patterns", "/opt/logstash/extra_patterns"]
1
正則文件以文本格式描述:
NAME PATTERN
#空格前是正則表達式的名稱,空格后是具體的正則表達式
例如:這是一個數字的表達式
NUMBER \d+
patterns_file_glob
● 屬性值的類型:string
● 默認值:“*”
● 描述:針對patterns_dir屬性中指定的文件夾里哪些正則文件,可以在這個filter中生效,需要本屬性來指定。默認值“*”是指所有正則文件都生效。
tag_on_failure
● 值類型是數組
● 默認值是 [“_grokparsefailure”]
●描述:沒有成功匹配時,將值附加到字段
tag_on_timeout
● 值類型是字符串
● 默認值是 “_groktimeout”
● 描述:如果Grok正則表達式超時,則應用標記。
timeout_millis
● 值類型是數字
● 默認值是 30000
● 描述: 嘗試在這段時間后終止正則表達式。如果應用了多個模式,則這適用於每個模式。這將永遠不會提前超時,但超時可能需要一些時間。實際的超時時間是基於250ms量化的近似值。設置為0以禁用超時。
常用選項
所有過濾器插件都支持以下配置選項:
add_field
● 值類型是散列
● 默認值是 {}
● 描述:在匹配日志中增加一個 field,可以通過%{field}動態命名field名或field的值。例如:
filter {
grok {
add_field => {
"foo_%{somefield}" => "Hello world, from %{host}" }
}
}
# 你也可以一次添加多個字段
filter {
grok {
add_field => {
"foo_%{somefield}" => "Hello world, from %{host}"
"new_field" => "new_static_value"
}
}
}
add_tag
● 值類型是數組
● 默認值是 []
● 描述:如果此過濾器成功,請向該事件添加任意標簽。標簽可以是動態的,並使用%{field} 語法包含事件的一部分。
例如:
filter {
grok {
add_tag => [
"foo_%{somefield}" ]
}
}
# 你也可以一次添加多個標簽
filter {
grok {
add_tag => [
"foo_%{somefield}", "taggedy_tag"]
}
}
enable_metric
● 值類型是布爾值
● 默認值是 true
● 描述:禁用或啟用度量標准
id
● 值類型是字符串
● 此設置沒有默認值。
● 描述:向插件實例添加唯一ID,此ID用於跟蹤插件特定配置的信息。
例如:
filter {
grok {
id =>
"ABC"
}
}
periodic_flush
● 值類型是布爾值
● 默認值是 false
● 描述:如果設置為ture,會定時的調用filter的更新函數(flush method)
remove_field
● 值的類型:array
● 默認值:[]
● 描述:刪除當前文檔中的指定filted
filter {
grok {
remove_field => [
"foo_%{somefield}" ]
}
}
# 你也可以一次移除多個字段:
filter {
grok {
remove_field => [
"foo_%{somefield}", "my_extraneous_field" ]
}
}
remove_tag
● 值類型是數組
● 默認值是 []
● 描述:如果此過濾器成功,請從該事件中移除任意標簽。標簽可以是動態的,並使用%{field} 語法包括事件的一部分。
例如:
filter {
grok {
remove_tag => [
"foo_%{somefield}" ]
}
}
# 你也可以一次刪除多個標簽
filter {
grok {
remove_tag => [
"foo_%{somefield}", "sad_unwanted_tag"]
}
}