最近想寫一篇es的索引的一個設計,由於設計的東西特別多,當然,elasticsearch的模板和動態映射也是其中的一個設計點,所以乾脆先來聊聊索引的模板和動態映射,模板,聽這個名字就相當於一些公共可用的東西可以作爲所有索引的一個設置,
本文爲博客園作者所寫: 一寸HUI,個人博客地址:https://www.cnblogs.com/zsql/
一、elasticsearch模板
2.1、elasticsearch模板介紹
這裏說明下,elasticsearch7.8的模板接口發生了一些變化,_template接口將在後期被廢棄(雖然還能使用,不推薦),所以本文不介紹這個接口。既然有廢棄的那肯定有新的方式來玩模板了。
最詳細接介紹看官網:https://www.elastic.co/guide/en/elasticsearch/reference/7.8/index-templates.html
現在模板分爲兩種模板,一個索引模板(index templates ),一個是組件模板(component templates),索引模板是告訴Elasticsearch如何在創建索引時配置索引的一種方法。模板是在創建索引之前配置的,當手動或通過索引文檔創建索引時,模板的基礎設置將用作創建索引。組件模板是可重用的構建塊,用於配置映射、設置和別名。使用組件模板來構造索引模板,組件模板不能直接應用於索引。索引模板可以包含組件模板的集合,也可以直接指定設置、映射和別名。組件模板的接口是:_component_template,而索引模板的接口是:_index_template,下面來個官方的例子,可以明顯的看出來組件模板component_template1和other_component_template被索引模板通過參數composed_of被引用,所以索引模板template_1既包括自己的設置,又包括了兩個組件模板的設置,這樣就可以輕鬆靈活的做組合,降低耦合性。
PUT _component_template/component_template1
{
"template": {
"mappings": {
"properties": {
"@timestamp": {
"type": "date"
}
}
}
}
}
PUT _component_template/other_component_template
{
"template": {
"mappings": {
"properties": {
"ip_address": {
"type": "ip"
}
}
}
}
}
PUT _index_template/template_1
{
"index_patterns": ["te*", "bar*"],
"template": {
"settings": {
"number_of_shards": 1
},
"mappings": {
"_source": {
"enabled": false
},
"properties": {
"host_name": {
"type": "keyword"
},
"created_at": {
"type": "date",
"format": "EEE MMM dd HH:mm:ss Z yyyy"
}
}
},
"aliases": {
"mydata": { }
}
},
"priority": 10,
"composed_of": ["component_template1", "other_component_template"],
"version": 3,
"_meta": {
"description": "my custom"
}
}
通過上面的接收,應該就清楚了這兩個模板之間的關係,可以用來幹嘛了。接下來一一介紹下這兩個模板。
2.2、Component templates(組件模板)
先上官網:https://www.elastic.co/guide/en/elasticsearch/reference/7.8/indices-templates-v1.html
組件模板是構建索引模板的構建塊。比如指定索引映射、設置和別名等。
使用語法:
PUT /_component_template/<component-template>
索引模板可以由多個組件模板組成。要使用組件模板,請在索引模板通過參數composed_of指定。組件模板僅作爲匹配索引模板的一部分。在任何的索引或者索引模板中定義的一些內容(設置,mapping等)都會覆蓋組件模板中與之相同的內容,也就是說組件模板等級最低了,容易被取代。組件模板的只會在索引創建的時候生效,修改組件模板不會對現有的索引有影響。下面介紹下組件模板請求體的一些參數:
參數名 | 參數介紹 |
template | 必須配置,表名是要應用的模板,可以選擇包括映射、設置或別名配置 |
aliases | 配置可選,配置index的別名 |
mappings | 配置可選,配置index的mapping |
settings | 配置可選,配置index的一些通用配置 |
version | 配置可選,用於外部管理組件模板的版本號 |
_meta | 配置可選,用於配置一些介紹信息,比如用戶元數據 |
舉個例子,一看就懂:
PUT _component_template/template_1
{
"template": {
"settings": {
"number_of_shards": 1
},
"aliases": {
"alias1": {},
"alias2": {
"filter": {
"term": {
"user.id": "kimchy"
}
},
"routing": "shard-1"
},
"{index}-alias": {}
}
},
"version": 123,
"_meta": {
"description": "set number of shards to one",
"serialization": {
"class": "MyComponentTemplate",
"id": 10
}
}
}
3.3、index templates(索引模板)
先看官網:https://www.elastic.co/guide/en/elasticsearch/reference/7.8/indices-put-template.html
使用語法:
PUT /_index_template/<index-template>
索引模板定義可以定義設置、映射和別名等,然後通過匹配自動應用於新建的索引。Elasticsearch基於與索引名稱匹配的通配符模式將模板應用於新索引,也就是說通過索引進行匹配,看看新建的索引是否符合索引模板,如果符合,就將索引模板的相關設置應用到新的索引,如果同時符合多個索引模板呢,這裏需要對參數priority進行比較,這樣會選擇priority大的那個模板進行創建索引。在創建索引模板時,如果匹配有包含的關係,或者相同,則必須設置priority爲不同的值,否則會報錯。索引模板也是隻有在新創建的時候起到作用,修改索引模板對現有的索引沒有影響。同樣如果在索引中設置了一些設置或者mapping都會覆蓋索引模板中相同的設置或者mapping。接下來看看創建索引模板請求體的一些參數:
參數名稱 | 參數介紹 |
index_patterns | 必須配置,用於在創建期間匹配索引名稱的通配符(*)表達式數組 |
template | 可選配置,可以選擇包括別名、映射或設置配置 |
composed_of | 可選配置,組件模板名稱的有序列表。組件模板按指定的順序合併,這意味着最後指定的組件模板具有最高的優先級 |
priority | 可選配置,創建新索引時確定索引模板優先級的優先級。選擇具有最高優先級的索引模板。如果未指定優先級,則將模板視爲優先級爲0(最低優先級) |
version | 可選配置,用於外部管理索引模板的版本號 |
_meta | 可選配置,關於索引模板的可選用戶元數據。可能有任何內容 |
看這些,好像很複雜,舉個例子就容易了:(匹配所有te開頭的新建索引,分片爲1,優先級爲10)
PUT /_index_template/template_1
{
"index_patterns": [
"te*"
],
"template": {
"settings": {
"number_of_shards": 1
},
"aliases": {
"alias1": {},
"alias2": {
"filter": {
"term": {
"user.id": "kimchy"
}
},
"routing": "shard-1"
},
"{index}-alias": {}
},
"mappings": {
"_source": {
"enabled": true
}
}
},
"version": 123,
"priority": 10,
"_meta": {
"description": "set number of shards to three",
"serialization": {
"class": "MyIndexTemplate",
"id": 17
}
}
}
這裏沒有說組合索引的使用,請看第一節介紹部分,這兩種索引的關係,還有就是組合索引被引用順序,後者更具有更高的優先級,會覆蓋前面的一些組合索引的一些相同的設置,然而組件索引不同的部分將會疊加在一起成爲索引模板的設置。語法確實不難,但是怎麼應用好呢,比如在elk中使用索引模板寫數據到es,比如索引設計,怎麼把索引自動滾動呢,這塊後期會有文章介紹,盡請期待。當然還有動態模板沒有介紹,繼續往下走。
二、Dynamic Mapping(動態映射)
注意:其實個人覺得把動態模板寫這裏是爲了區分索引模板和動態模板,因爲個人混淆過,所以寫這裏比較好區別,其實動態模板不是索引模板,這裏不要誤會,其實動態模板就是可以配置在索引中或者配置在索引模板中,作用是elasticsearch對數據探索自發現添加,可以指定匹配,並映射成指定類型。這裏要記住elasticsearch只有組合模板和索引模板,動態模板時動態映射的一種實現。動態模板定義了索引創建後新添加字段的映射規則,而索引模板是在創建索引時默認爲索引添加的別名、配置和映射等信息。索引模板包含該模板適用索引的模式或規則,以及索引創建時默認包含的別名、配置和映射關係等。它們分別通過index_patterns、aliases、settings和mappings等四個參數設置
在說動態模板之前,先要說說動態映射。
Elasticsearch最重要的功能之一就是可以自動探索數據。要爲文檔編制索引,不必首先創建索引、定義映射類型和定義字段,只需爲文檔編制索引,索引、類型和字段就會自動生成。
自動檢測和添加新字段以及字段類型稱爲動態映射,主要分爲動態字段和動態模板。這裏引出動態字段和動態模板,所以先看看動態字段。
2.1、Dynamic field mapping(動態字段映射)
先看官網:https://www.elastic.co/guide/en/elasticsearch/reference/7.8/dynamic-field-mapping.html
默認情況下,當在文檔中找到索引沒有定義的字段時,Elasticsearch會將新字段添加到類型映射中。通過將參數dynamic設置爲false(忽略新字段)或strict(遇到未知字段時引發異常),可以在文檔和對象級別禁用此行爲。
假設啓用了動態字段映射,則使用一些簡單規則來確定字段應具有的數據類型:當然不是所有的類型都可以自動映射的,只有field data types這些可以動態的探索映射,所以其他的數據類型需要顯示的指定。例如:
說起來可能比較有點不好理解,那就需要例子說明了:
PUT my-index-000001/_doc/1
{
"create_date": "2015/09/02"
}
GET my-index-000001/_mapping
這樣就自動把create_date在映射中添加了,並且字段類型爲date,這就是動態字段映射,也就是elasticsearch的一個特色,這樣就不要給所有的字段提前定義好,但是雖然方便了,但是不利於索引的管理,如果出現了一條異常的數據插入到索引中,這樣就會導致索引中的mapping中出現很多不必要的字段,動態字段映射可以更具需求對其進行配置。
2.2、Dynamic templates(動態模板)
詳情見官網:https://www.elastic.co/guide/en/elasticsearch/reference/7.8/dynamic-templates.html
動態模板(Dynamic Template)用於自定義動態添加字段時的映射規則,可通過索引映射類型的dynamic_templates參數設置。該參數接收一組命名的動態模板,每一個模板由匹配條件和映射規則組成。匹配條件定義了新字段是否可以使用當前模板,可根據新字段的數據類型、名稱和路徑來定義條件;而映射規則由參數mapping定義,它需要給出新字段要使用哪些參數,可使用type定義新字段數據類型。
使用規則如下:
- 匹配規則可使用關鍵字match_mapping_type匹配新字段數據類型,這可以用於將一種默認類型轉換爲其他類型或者設置其他特性。
- 還可使用match、match_pattern和unmatch匹配新字段名稱。其中match和unmatch可以使用星號“*”做名稱匹配,而match_pattern則支持正則表達式
- 匹配新字段路徑可使用path_match和path_unmatch,路徑與名稱的區別是其中包含點“.”。在mapping參數中,還可以使用{name}和{dynamic_type}代表新字段名稱和類型。
使用語法:
"dynamic_templates": [
{
"my_template_name": { //這裏可以隨便寫,便於辨別就好,
... match conditions ... //這裏就是上面說的規則,比如match_mapping_type
"mapping": { ... } //匹配字段使用的映射,意思就是把匹配到的內容映射爲你想要設置的內容
}
},
...
]
這裏只舉例說明一個規則或者說是條件:match_mapping_type
PUT my-index-000002
{
"mappings": {
"dynamic_templates": [
{
"integers": {
"match_mapping_type": "long",
"mapping": {
"type": "integer"
}
}
},
{
"strings": {
"match_mapping_type": "string",
"mapping": {
"type": "text",
"fields": {
"raw": {
"type": "keyword",
"ignore_above": 256
}
}
}
}
}
]
}
}
PUT my-index-000002/_doc/1
{
"my_integer": 5,
"my_string": "Some string"
}
查看結果
其實靜下心來看也不難,其他的規則可以看官網的例子。