Elasticsearch系列 實戰搜尋語法

2022-07-04 11:45:12 字數 3675 閱讀 7477

空查詢

最簡單的搜尋命令,不指定索引和型別的空搜尋,它將返回集群下所有索引的所有文件(預設顯示10條):

get /_search

{}

搜尋多個索引
get /index1,index2/_doc/_search

{}

指定分頁搜尋
get /_search

get帶request body

http協議,get請求帶body是不規範的做法,但由於es搜尋的複雜性,加上http協議get/post方法表述的語義,get更適合用來表述查詢的動作,雖然不規範,但還是這麼用了。現在大多數瀏覽器也支援get+request body,如果遇到不支援的,換成post即可。了解一下就行,不用太慌張。

query dsl是一種非常靈活、可讀性高的查詢語言,body為json格式,絕大部分功能都可以用它來展現,並且這種查詢語句更純粹,讓學習者更專注於本身的功能,避免client api的干擾。

get /_search

}}

基本語法
# 查詢語句結構

}# 針對某個欄位的查詢

}}

合併查詢語句

再複雜的查詢語句,也是由乙個乙個的查詢條件疊加而成的,查詢語句有兩種形式:

舉個例子:

},

"must_not": },

"should": },

"filter": } }

}}

復合語句可以巢狀,來實現更複雜的查詢需求,在上面的例子上簡單延伸一下:

"bool": },

"must_not": },

"should": [

},},

"must_not": }

}}],

"filter": } }

}

復合語句相關性分數計算

每乙個子查詢都獨自地計算文件的相關性得分。一旦他們的得分被計算出來,bool 查詢就將這些得分進行合併並且返回乙個代表整個布林操作的得分,得分高的顯示在前面,filter內的條件不參與分數計算。

我們還是以英文兒歌的索引為案例,看乙個搜尋需求:歌詞內容包含friend,同時歌長大於30秒的記錄

get /music/children/_search}],

"filter": }}

}}}

filter與query

僅按照搜尋條件把需要的資料篩選出來,不計算相關度分數。

匹配條件的資料,會根據搜尋條件的相關度,計算每個document的分數,然後按照分數進行排序,這個才是全文搜尋的情況。

效能差異

filter只做過濾,不作排序,並且會快取結果到記憶體中,效能非常高。

query匹配條件,要做評分,沒有快取,效能要低一些。

應用場景

filter乙個非常重要的作用就是減少不相關資料對query的影響,提公升query的效能,二者常常搭配在一起使用。

組合使用的時候,把期望符合條件的document的搜尋條件放在query裡,把要濾掉的條件放在filter裡。

如果乙個查詢只有filter過濾條件,可以用constant_score來替代bool查詢,這樣的查詢語句更簡潔、更清晰,只是沒有評分,示例如下:

get /music/children/_search}}

}}

filter內不支援terms語法,注意一下。

再複雜的查詢語句,也是由最基礎的查詢變化而來的,而最常用的查詢其實也就那麼幾個。

match_all查詢

查詢簡單的匹配所有文件

get /_search

}}

match查詢

無論是全文搜尋還是精確查詢,match查詢是最基本的標準

# 全文搜尋例子

}# 精確搜尋}}

}}

對於精確值的查詢,我們可以使用filter來替代,filter有快取的效果。

multi_match查詢

可以在多個欄位上執行相同的match查詢

}

range查詢

查詢指定區間內的數字或時間,query和filter都支援,一般是filter用得多,允許的操作符如下:

}}

term查詢

用於精確值匹配,精確值可以是數字,日期,boolean或keyword型別的字串

}}}

}

terms查詢

跟term類似,只是允許一次指定多個值進行匹配,只要有任何乙個匹配上,都滿足條件

}
複雜的查詢語句,可能會有幾百行,可以先使用除錯工具檢測一下查詢語句,定位不合法的搜尋及原因,完整語法如下:

get /index/type/_validate/query?explain

}

explain引數可以提供更詳細的查詢不合法的資訊,便於問題定位。寫乙個錯誤的例子,比如使用中文標點符號:

get /music/children/_validate/query?explain

}}

錯誤提示如下:

valid關鍵字,true為驗證通過,false為不通過,如上提示資訊,會指明3行33列錯誤,原因是使用了中文的引號。將語法修正後,得到的正確響應如下:

,

"valid": true,

"explanations": [

]}

查詢請求得到的結果,預設排序是相關性得分降序。如果我們只使用filter過濾,符合filter條件的文件,評分都是一樣的(bool的filter得分是null,constant_score得分是1),結果文件還是隨機返回,顯然這樣的排序不符合我們的預期。

sort排序規則

為此,我們可以使用sort屬性,對文件進行排序,sort的用法與mysql如出一轍,示例如下:

get /music/children/_search

} } }

},"sort": [

}]}

sort內可以同時指定多個排序字段,一旦使用sort排序後,_score得分將變成null,因為我們指定了排序規則,_score沒有實際意義了,就不用耗費精力再去計算它。

字串排序問題

}},

"name": }}

}}

}}}

例如name欄位,有乙個text型別的,裡面fields還有乙個型別為keyword,名稱也為keyword的字段,所以在排序的場景中,我們應該使用name.keyword,示例如下:

get /music/children/_search

}]}

本篇介紹query dsl的語法及基礎實戰內容,順帶點了一下filter與query的區別,面對複雜查詢語句時,建議先用驗證工具進行排查,最後介紹了一下排序方面的知識,基礎語法、上機案例多實踐即可。

elasticsearch啟動報錯系列

wget 解壓tar zxvf elasticsearch 6.2.4.tar.gz 在啟動過程 中會遇到這兩個問題 1 max file descriptors 4096 for elasticsearch process is too low,increase to at least 65536...

Elasticsearch系列九 Bool 查詢

案例書籍推薦 bool查詢對應lucenne中的booleanquery,它由乙個或者多個子句組成,match 分詞匹配,下面的例子會對查詢盡心分詞,分為 寶馬 多少 馬力 那麼所有包含這三個詞中的乙個或者多個文件就會被搜尋出來.match phrase 針對上面的例子,乙個文件 我的保時捷也不錯 ...

ElasticSearch系列04 核心概念

一 es配置檔案詳解 elasticsearch.yml es的基本配置檔案 詳見elasticsearch中文.yml logging.yml 日誌配置檔案,es也是使用log4j來記錄日誌的,所以logging.yml裡的設定按普通log4j配置來設定就行了。二 es中的核心概念 cluster...