ElasticSearch筆記-5.X版本若干變化
寫在前面:去年寫的有關Elastic的一些知識是基於2.x版本的,目前最新的版本是5.6(2017-10),一些重要的API與用法已經發生改變。這篇文章在之前系列的基礎上,重點從API角度講講變化的部分。
一、對映的變化
string型別變為為text/keyword
變化最大的是ES的基本型別string。目前string型別已標為廢棄的,取而代之的變成了 text/keyword。text表示全文分析的string(即之前預設的string),keyword為不經分析的string(即not_analyzed的string)。
目前預設的字串對映為
{
"type": "text" ,
"fields": {
"keyword": {
"type": "keyword",
"ignore_above": 256
}
}
}
即表明預設的字串型別為分詞的,可進行全文搜尋等;其子關鍵字欄位是未分析的,可進行精確查詢、聚合及排序等。
如有個欄位名為title為字串型別。自動對映後,
title
可用於全文搜尋,而title.keyword
欄位可進行聚合、排序等操作。
二、document API 變化
為演示方便,這裡往ES新增一些資料。
POST /cars/sale/_bulk
{ "index": {} }
{ "price" : 10000, "color" : "red", "make" : "honda", "sold" : "2014-10-28" }
{ "index": {}}
{ "price" : 20000, "color" : "red", "make" : "honda", "sold" : "2014-11-05" }
{ "index": {}}
{ "price" : 30000, "color" : "green", "make" : "ford", "sold" : "2014-05-18" }
{ "index": {}}
{ "price" : 15000, "color" : "blue", "make " : "toyota", "sold" : "2014-07-02" }
{ "index": {}}
{ "price" : 12000, "color" : "green", "make" : "toyota", "sold" : "2014-08-19" }
{ "index": {}}
{ "price" : 20000, "color" : "red", "make" : "honda", "sold" : "2014-11-05" }
{ "index": {}}
{ "price" : 80000, "color" : "red", "make" : "bmw", "sold" : "2014-01-01" }
{ "index": {}}
{ "price" : 25000, "color" : "blue", "make" : "ford", "sold" : "2014-02-12" }
現在我們有了關於汽車銷售的有關資料。
_update_by_query
5.x版本ES添加了_update_by_query
API,可以根據查詢到的結果進行更新。
目前我們有個需求是,所有福特(ford)汽車決定降價1000元。這正好可以使用_update_by_query
完成。
POST /cars/sale/_update_by_query
{
"query":{
"term":{
"make":"ford"
}
},
"script":{
"inline":"ctx._source.price=ctx._source.price-1000",
"lang":"painless" ①
}
}
① painless
為ES最新預設的指令碼語言,相關資料可參考painless指令碼語言。
_delete_by_query
_delete_by_query
與上面提到的_update_by_query
類似。它是根據查詢刪除某些文件。繼續上面的示例。
刪除所有寶馬(bmw)車系。
POST /cars/sale/_delete_by_query
{
"query":{
"term":{
"make":"bmw"
}
}
}
reindex
_reindex
功能為將文件從一個索引複製到另一個索引。利用它可以實現資料索引級別的無痛遷移,其中重要的是,在遷移時我們可以改變目標索引的某些欄位型別。即平滑地升級我們的索引型別。
在我們的資料中,color
和make
都是text型別,意味著可用於全文檢索,可在實際應用中,我們總是需要精確匹配他們,沒必要分詞,而ES的欄位型別一旦確定又無法修改。
之前的做法是重建一個索引,然後利用_bulk
把資料批量匯入新索引中。現在利用_reindex
,可以實現一步匯入。
首先需要重建一個索引,設定為需要的型別。
PUT /cars_new
{
"mappings": {
"sale": {
"properties": {
"color": {
"type": "keyword"
},
"make": {
"type": "keyword"
},
"price": {
"type": "integer"
},
"sold": {
"type": "date"
}
}
}
}
}
新索引cars_new
的color
和make
為keyword型別,price
修改為了integer
型別(之前為long
)。
使用_reindex
遷移索引。
POST /_reindex
{
"source":{
"index":"cars"
},
"dest":{
"index":"cars_new"
}
}
檢視新索引cars_new
確實建立成功,檢視cars_new對映。
GET /cars_new/_mappings/
{
"cars_new": {
"mappings": {
"sale": {
"properties": {
"color": {
"type": "keyword"
},
"make": {
"type": "keyword"
},
"price": {
"type": "integer"
},
"sold": {
"type": "date"
}
}
}
}
}
}
關於過濾 filtered
目前過濾的API已經不支援filtered
的語法了。實現過濾使用constant_score
或在bool
子句下filter
實現。這兩者都不會計算文件得分,使查詢更高效。
如只獲取綠色的汽車
POST /cars_new/sale/_search
{
"query":{
"constant_score":{
"filter":{
"term":{
"color":"green"
}
}
}
}
}
或
{
"query":{
"bool":{
"filter":{
"term":{
"color":"green"
}
}
}
}
}
一般bool
下的過濾往往結合其他查詢進行,若只有一個過濾,使用constant_score
即可,它會將每個文件的評分都置為1。
三、其他變化
- 5.x中取消了
search_type = count
語法,使用size:0
的方式來代替。 - 添加了
profile
API,可以獲取具體在查詢時過濾,使可以有目的性的優化。