1.es
ElasticSearch是?一個(gè)基于Lucene的開源分布式搜索和分析引擎服務(wù)器?。它的特點(diǎn)有:分布式,零配
置,?自動(dòng)發(fā)現(xiàn),索引?自動(dòng)分?片,索引副本機(jī)制,restful?風(fēng)格接?口,多數(shù)據(jù)源,?自動(dòng)搜索負(fù)載等。ElasticSearch這個(gè)詞由Elastic和search組成,前者代表可動(dòng)態(tài)擴(kuò)容,后者代表其功能,當(dāng)集群環(huán)境下es節(jié)點(diǎn)數(shù)需要擴(kuò)容時(shí)基本能做到只要花錢買兩臺(tái)機(jī)器,加入集群,就可以直接使用,非常的方便.我們?cè)谑裁礃拥膱?chǎng)景下需要es?
- 當(dāng)我們的sql存在過多l(xiāng)ike的時(shí)候可以考慮用es來代替mysql
- **數(shù)據(jù)過大,需要分布式存儲(chǔ)時(shí).
- 搜索,如日志,商品等等
- 對(duì)數(shù)據(jù)要求不那么嚴(yán)謹(jǐn)?shù)呐幚砗土魇接?jì)算.
- free-schema比較適合中臺(tái)的應(yīng)用
2.概念
1.1 lucene
一個(gè)開放源代碼的全文檢索引擎工具包,但它不是一個(gè)完整的全文檢索引擎,而是一個(gè)全文檢索引擎的架構(gòu),提供了完整的查詢引擎和索引引擎,部分文本分析引擎
1.1.1 索引數(shù)據(jù)結(jié)構(gòu)
對(duì)一段文章或者記錄進(jìn)行切割分詞,記錄單個(gè)詞條到文檔的映射關(guān)系,如,【doc1:我是中國人,doc2:我愛中國?!咳绻胑s提供的標(biāo)準(zhǔn)分詞器按照單個(gè)中文拆開,則記錄如下
| term | 頻率 | 記錄 |
|---|---|---|
| 我 | 2 | doc1,doc2 |
| 是 | 1 | doc1 |
| 中 | 2 | doc1,doc2 |
| 國 | 2 | doc1,doc2 |
| 人 | 1 | doc1 |
| 愛 | 1 | doc2 |
這樣就可以通過對(duì)詞條的搜索來找到包含記錄的文檔。
1.1.2 搜索
| term | doc1 | doc2 | doc3 | doc4 |
|---|---|---|---|---|
| 人工 | 1 | 1 | 1 | 0 |
| 智能 | 1 | 1 | 1 | 0 |
| 成為 | 1 | 0 | 0 | 0 |
| 互聯(lián)網(wǎng) | 1 | 0 | 1 | 0 |
| 大會(huì) | 1 | 0 | 0 | 0 |
| 焦點(diǎn) | 1 | 0 | 0 | 0 |
| 谷歌 | 0 | 1 | 0 | 1 |
| 推出 | 0 | 1 | 0 | 0 |
| 開源 | 0 | 1 | 0 | 1 |
| 工具 | 0 | 1 | 0 | 1 |
搜索谷歌,開源但是不包含大會(huì)的文檔:
谷歌:0 1 0 1
開源:0 1 0 1
大會(huì):0 1 1 1(不包含大會(huì),則取反)
對(duì)這個(gè)三個(gè)數(shù)做與運(yùn)算-->0101即文檔2和文檔四包含此次搜索要求。
1.1.3 segment
段是lucene存儲(chǔ)的最小單元,每一次寫入都會(huì)將當(dāng)前線程索引的數(shù)據(jù)寫入到一個(gè)新的segment中,防止多線寫入對(duì)于同一個(gè)句柄文件產(chǎn)生的競(jìng)爭(zhēng),但是在搜索時(shí)為了防止遍歷所有的段,又需要將segement合并到一個(gè)大的文件當(dāng)中去,刪除操作和更新都是記錄刪除的標(biāo)識(shí),在重新寫入一個(gè)新的段,后面再合并的時(shí)候在去做真正的刪除操作。
1.2 es
1.2.1 基本概念
| mysql | es |
|---|---|
| 庫 | index |
| 表 | type |
| 行 | document |
| 字段 | field |
| schema | mapping |
1.2.2 分片-副本

分片和副本是做數(shù)據(jù)高可用的時(shí)候必不可少的一個(gè)概念,無論是hdfs還是kafka或者是其他的分布式中間件都會(huì)有這樣的概念,只是叫法不一樣,數(shù)據(jù)過于大,一臺(tái)機(jī)器放不下,需要將數(shù)據(jù)切分,也就是分片,可能也有別的中間件叫法不一樣,比如kafak叫分區(qū), 副本的作用有兩個(gè)一個(gè)是備份,另外一個(gè)是它本身也能提供主分片的功能。這兩個(gè)功能如果和mysql進(jìn)行類比,可以類型分片是搞分庫,而副本則是主從,在es中,一個(gè)索引默認(rèn)有5個(gè)主分片,1個(gè)副本,同一個(gè)分片的主分片和副本不能落在同一個(gè)node上,防止因?yàn)闄C(jī)器宕機(jī),而丟失該分片的所有數(shù)據(jù),在機(jī)器允許的情況下,提高副本分片的數(shù)量也能提高系統(tǒng)的qps,分片的丟失也是es常見的報(bào)紅報(bào)黃的問題。
1.2.2 節(jié)點(diǎn)
| 類型 | 描述 |
|---|---|
| Master | 主節(jié)點(diǎn) |
| Data Node | 存儲(chǔ)數(shù)據(jù)節(jié)點(diǎn) |
| Coordinating Node | 客戶端節(jié)點(diǎn) |
| Ingest Node | 索引文當(dāng)前可以做些預(yù)處理的工作 |
1.2.4 zen
zen是es7.0前默認(rèn)的選舉算法,類似于bully算法,基于二階段提交,假設(shè)在完美的情況下有五個(gè)機(jī)器,3臺(tái)作為master節(jié)點(diǎn),首先節(jié)點(diǎn)啟動(dòng),es會(huì)根據(jù)自己的ip和端口號(hào)計(jì)算出一個(gè)id,并與另外兩臺(tái)簡(jiǎn)歷長(zhǎng)連接,當(dāng)檢測(cè)到長(zhǎng)連接的數(shù)量已經(jīng)達(dá)到可以選舉,并且集群中沒有主節(jié)點(diǎn)的情況下,開始正式選舉,假設(shè)a,b,c生成的三個(gè)id分別為1,2,3,此時(shí)a得知b和c分別為2,3,知道集群中最小id為節(jié)點(diǎn)本身,而b,c也知道集群中最小節(jié)點(diǎn)為a,以最小id作為評(píng)判的標(biāo)準(zhǔn),此時(shí)a,作為候選節(jié)點(diǎn),則等待b,c加入自己,而b,c則主動(dòng)發(fā)送信息,告知要加入a,如果加入成功,并且加入的數(shù)量是大于法定人數(shù),則選舉成功,當(dāng)然這個(gè)是理想情況,實(shí)際情況非常復(fù)雜,要考慮消息超時(shí),選舉輪次等等因素。
1.2.5 分詞器
1.2.5.1 內(nèi)置分詞器
GET _analyze
{
"analyzer": "standard",
"text": "不轉(zhuǎn)不是中國人"
}
es內(nèi)部?jī)?nèi)置了些分詞器,我們也可以根據(jù)自己的需求來置頂一些分詞器,如果是對(duì)于業(yè)務(wù)開發(fā),常見的分詞器就是ik,ik分兩種分詞,一種是standard分詞,就是按照中文一個(gè)一個(gè)割開,另外一個(gè)是smart分詞,就是可以根據(jù)一些常見的語義來進(jìn)行分詞,在ik目錄下有一個(gè)分詞字典,把常用的詞寫進(jìn)去,就能達(dá)到智能分詞的目的,ik也內(nèi)置了很多詞條。
1.2.5.2 自定義分詞器
分詞器分詞主要是經(jīng)過三個(gè)步驟
1.character filter,這個(gè)是處理串的第一個(gè)過程,可以對(duì)整個(gè)串進(jìn)行處理。
2.tokenizer:按照規(guī)則進(jìn)行分詞,如按照空格分開
3.token filter:這個(gè)是最后的一個(gè)步驟,可以對(duì)每個(gè)term進(jìn)行處理。
GET _analyze
{
"tokenizer" : "whitespace",
"filter" : ["lowercase"],
"char_filter" : ["html_strip"],
"text" : "this is A <b>test</b>"
}
這個(gè)過程就是先對(duì)text文本內(nèi)容先去掉html標(biāo)簽,在按空格切開,最后把所有的串變成小寫,也可以在filter指定去掉停用詞,去掉this is等用法。
1.2.6 寫入
1.客戶端向協(xié)調(diào)協(xié)調(diào)節(jié)點(diǎn)發(fā)送請(qǐng)求,協(xié)調(diào)節(jié)點(diǎn)將寫請(qǐng)求轉(zhuǎn)發(fā)直master節(jié)點(diǎn).
2.master節(jié)點(diǎn)根據(jù)id確定主分片的位置,如果沒有id此時(shí)會(huì)生成id,會(huì)并將數(shù)據(jù)請(qǐng)求轉(zhuǎn)發(fā)至主分片所在的節(jié)點(diǎn)
3.主分片進(jìn)行寫操作,先是進(jìn)行雙寫操作,寫translog后在寫buffer,后面會(huì)有一個(gè)sync線程定期將內(nèi)存的數(shù)據(jù)刷到磁盤上(refresh_interval),而刷到磁盤時(shí)只是將數(shù)據(jù)刷到系統(tǒng)的oscache中,后面就是操作系統(tǒng)的事情了,所以線上在部署es時(shí),假如32g內(nèi)存的機(jī)器,至少要留一半的大小給系統(tǒng)緩存,不僅能加速寫的過程,也會(huì)加速讀的過程.
4.當(dāng)主節(jié)點(diǎn)寫入成功后,需要將數(shù)據(jù)轉(zhuǎn)發(fā)至副本節(jié)點(diǎn),進(jìn)行寫入,副本寫入成功數(shù)受quorum( int( (primary + number_of_replicas) / 2 ) + 1 )的影響,這個(gè)也是一個(gè)法定人數(shù)的概念,寫入超過一半認(rèn)為此次寫入成功.
5.每次寫入會(huì)生成一個(gè)segment,然后后面會(huì)有一個(gè)purge線程,定期合并segment.
1.2.7 搜索
1.將搜索的語句用索引時(shí)相同的分詞器進(jìn)行分詞.
2.協(xié)調(diào)節(jié)點(diǎn)將請(qǐng)求轉(zhuǎn)發(fā)至每個(gè)主分片或者副本分片
3.每個(gè)分片進(jìn)行搜索的操作和打分,并將執(zhí)行結(jié)果的id和排序值返回給協(xié)調(diào)節(jié)點(diǎn),協(xié)調(diào)節(jié)點(diǎn)在進(jìn)行排序(query_then_fetch),協(xié)調(diào)節(jié)點(diǎn)在根據(jù)負(fù)載均衡策略,去分片上回取數(shù)據(jù).
4.每個(gè)分片進(jìn)行搜索的操作和打分,并將執(zhí)行結(jié)果的文檔返回給協(xié)調(diào)節(jié)點(diǎn),協(xié)調(diào)節(jié)點(diǎn)在進(jìn)行排序(query_and_fetch)
query_and_fetch和query_then_fetch
3.語法
3.1 查詢語法
3.1.1 term
term查詢應(yīng)該是最好理解的,就是搜索語句剛好是一個(gè)term,可以直接在倒排序索引中搜索.如:
PUT test/uk/1
{
"word":"我是中國人"
}
PUT test/uk/2
{
"word":"我來自江蘇"
}
GET test/uk/_search
{
"query": {
"term": {
"word": {
"value": "我"
}
}
}
}
##返回
"hits": {
"total": 2,
"max_score": 0.2876821,
"hits": [
{
"_index": "test",
"_type": "uk",
"_id": "2",
"_score": 0.2876821,
"_source": {
"word": "我來自江蘇"
}
},
{
"_index": "test",
"_type": "uk",
"_id": "1",
"_score": 0.2876821,
"_source": {
"word": "我是中國人"
}
}
]
3.1.2 match
match相對(duì)term多做了個(gè)動(dòng)作,就是會(huì)對(duì)搜索語句進(jìn)行分詞,屬于全文搜索.如
GET test/uk/_search
{
"query": {
"match": {
"word": "我是"
}
}
}
###返回
"hits": [
{
"_index": "test",
"_type": "uk",
"_id": "1",
"_score": 0.5753642,
"_source": {
"word": "我是中國人"
}
},
{
"_index": "test",
"_type": "uk",
"_id": "2",
"_score": 0.2876821,
"_source": {
"word": "我來自江蘇"
}
}
]
這個(gè)時(shí)候,只要分完詞后只要包含這幾個(gè)分詞結(jié)果的文檔就都出來了,是or的關(guān)系,也可以指定要滿足與的關(guān)系,如
GET test/uk/_search
{
"query": {
"match": {
"word": {
"query": "我是",
"operator": "and"
}
}
}
}
###返回
"hits": [
{
"_index": "test",
"_type": "uk",
"_id": "1",
"_score": 0.5753642,
"_source": {
"word": "我是中國人"
}
}
]
另外es在生成文檔的時(shí)候幫我們生成了一個(gè)keyword關(guān)鍵字,我們可以用keyword關(guān)鍵字做精確查詢,如:
GET test/uk/_search
{
"query": {
"match": {
"word.keyword": "我是中國人"
}
}
}
###返回
"hits": [
{
"_index": "test",
"_type": "uk",
"_id": "1",
"_score": 0.2876821,
"_source": {
"word": "我是中國人"
}
}
]
3.1.3 match_phrase
match_phrase 是另外一種玩法,它可以控制分詞后詞條之間間隔的距離,如:
GET test/uk/_search
{
"query": {
"match_phrase": {
"word": {
"query": "我國",
"slop":1
}
}
}
}
因?yàn)榇藭r(shí)我和國之間的間隔為2,當(dāng)指定為1時(shí),無法查出.
3.1.4 bool
bool語法可以實(shí)現(xiàn)多級(jí)的or和and和not的關(guān)系,比如我現(xiàn)在查詢這樣一段話:這個(gè)語句中必須要包含我和中國,但是不能包含江這個(gè)term,語法如下:
GET test/uk/_search
{
"query": {
"bool": {
"must": [
{"term": {
"word": {
"value": "我"
}
}},{
"match": {
"word": "中國"
}
}
],
"must_not": [
{"term": {
"word": {
"value": "江"
}
}}
]
}
}
}
3.1.5 filter
filter語法和query的語法差不多,把最外層的query換成filter即可,如:
GET test/uk/_search
{
"post_filter": {
"match": {
"word.keyword": "我是中國人"
}
}
}
##返回
"hits": [
{
"_index": "test",
"_type": "uk",
"_id": "1",
"_score": 1,
"_source": {
"word": "我是中國人"
}
}
但是可以和上面那一條對(duì)比下,這條的score得分為1,而上面是一個(gè)小于1的數(shù),所以filter是不會(huì)走打分機(jī)制的,正因?yàn)椴恍枰蚍?es也能將這部分?jǐn)?shù)據(jù)直接緩存,當(dāng)我們不需要使用打分的時(shí)候,建議多用filter.
3.1.6 paninless
painless是es內(nèi)置的腳本語言,可以用painless進(jìn)行批量處理,多次聚合等操作,語法和java類似,如,將只要包含我這個(gè)語句的替換成我特么黑化
POST test/uk/_update_by_query
{
"query":{
"match":{
"word":"我"
}
},
"script": {
"lang": "painless",
"inline": "ctx._source.word = params.word;",
"params":{
"word":"我特么黑化"
}
}
}
3.2 聚合語法
聚合是es提供的另外一個(gè)功能,可以根據(jù)term進(jìn)行做分組,而且可以多次下鉆,然后做min,max等操作,聚合總共分為指標(biāo)聚合,桶聚合, 矩陣聚合 , 管道聚合 ,前面兩種用的比較多,指標(biāo)聚合的意思就是計(jì)算分組和的min,max值,而桶聚合的意思是將分組后的數(shù)據(jù)進(jìn)行分析,可以算各個(gè)分組里面的一些指標(biāo)和數(shù)據(jù).聚合使用的不是倒排序索引,而是正排序索引,如果需要對(duì)text字段進(jìn)行聚合需要打開fielddata功能,不然無法使用.
例子來與極客時(shí)間(Elasticsearch核心技術(shù)與實(shí)戰(zhàn))
DELETE /employees
PUT /employees/
{
"mappings" : {
"properties" : {
"age" : {
"type" : "integer"
},
"gender" : {
"type" : "keyword"
},
"job" : {
"type" : "text",
"fields" : {
"keyword" : {
"type" : "keyword",
"ignore_above" : 50
}
}
},
"name" : {
"type" : "keyword"
},
"salary" : {
"type" : "integer"
}
}
}
}
PUT /employees/_bulk
{ "index" : { "_id" : "1" } }
{ "name" : "Emma","age":32,"job":"Product Manager","gender":"female","salary":35000 }
{ "index" : { "_id" : "2" } }
{ "name" : "Underwood","age":41,"job":"Dev Manager","gender":"male","salary": 50000}
{ "index" : { "_id" : "3" } }
{ "name" : "Tran","age":25,"job":"Web Designer","gender":"male","salary":18000 }
{ "index" : { "_id" : "4" } }
{ "name" : "Rivera","age":26,"job":"Web Designer","gender":"female","salary": 22000}
{ "index" : { "_id" : "5" } }
{ "name" : "Rose","age":25,"job":"QA","gender":"female","salary":18000 }
{ "index" : { "_id" : "6" } }
{ "name" : "Lucy","age":31,"job":"QA","gender":"female","salary": 25000}
{ "index" : { "_id" : "7" } }
{ "name" : "Byrd","age":27,"job":"QA","gender":"male","salary":20000 }
{ "index" : { "_id" : "8" } }
{ "name" : "Foster","age":27,"job":"Java Programmer","gender":"male","salary": 20000}
{ "index" : { "_id" : "9" } }
{ "name" : "Gregory","age":32,"job":"Java Programmer","gender":"male","salary":22000 }
{ "index" : { "_id" : "10" } }
{ "name" : "Bryant","age":20,"job":"Java Programmer","gender":"male","salary": 9000}
{ "index" : { "_id" : "11" } }
{ "name" : "Jenny","age":36,"job":"Java Programmer","gender":"female","salary":38000 }
{ "index" : { "_id" : "12" } }
{ "name" : "Mcdonald","age":31,"job":"Java Programmer","gender":"male","salary": 32000}
{ "index" : { "_id" : "13" } }
{ "name" : "Jonthna","age":30,"job":"Java Programmer","gender":"female","salary":30000 }
{ "index" : { "_id" : "14" } }
{ "name" : "Marshall","age":32,"job":"Javascript Programmer","gender":"male","salary": 25000}
{ "index" : { "_id" : "15" } }
{ "name" : "King","age":33,"job":"Java Programmer","gender":"male","salary":28000 }
{ "index" : { "_id" : "16" } }
{ "name" : "Mccarthy","age":21,"job":"Javascript Programmer","gender":"male","salary": 16000}
{ "index" : { "_id" : "17" } }
{ "name" : "Goodwin","age":25,"job":"Javascript Programmer","gender":"male","salary": 16000}
{ "index" : { "_id" : "18" } }
{ "name" : "Catherine","age":29,"job":"Javascript Programmer","gender":"female","salary": 20000}
{ "index" : { "_id" : "19" } }
{ "name" : "Boone","age":30,"job":"DBA","gender":"male","salary": 30000}
{ "index" : { "_id" : "20" } }
{ "name" : "Kathy","age":29,"job":"DBA","gender":"female","salary": 20000}
# Metric 聚合,找到最低的工資
POST employees/_search
{
"size": 0,
"aggs": {
"min_salary": {
"min": {
"field":"salary"
}
}
}
}
# Metric 聚合,找到最高的工資
POST employees/_search
{
"size": 0,
"aggs": {
"max_salary": {
"max": {
"field":"salary"
}
}
}
}
# 一個(gè)聚合,輸出多值
POST employees/_search
{
"size": 0,
"aggs": {
"stats_salary": {
"stats": {
"field":"salary"
}
}
}
}
#Salary Ranges 分桶,可以自己定義 key
POST employees/_search
{
"size": 0,
"aggs": {
"salary_range": {
"range": {
"field":"salary",
"ranges":[
{
"to":10000
},
{
"from":10000,
"to":20000
},
{
"key":">20000",
"from":20000
}
]
}
}
}
}
3.2.1 聚合不準(zhǔn)確
1.cardinality等一些操作采用近似的算法,提升性能
2./假設(shè)我們有一個(gè)索引,被分了三個(gè)shard,分布在三個(gè)不同的機(jī)器上,文檔中某一個(gè)字段為英文字母A,B,C等等,現(xiàn)在對(duì)這個(gè)字段進(jìn)行聚合,找出文檔中數(shù)量排名前五的聚合結(jié)果:
| 分片1 | 分片2 | 分片三 |
|---|---|---|
| A(25) | A(30) | A(45) |
| B(18) | B(25) | C(44) |
| C(6) | F(17) | Z(36) |
| D(3) | Z(16) | G(30) |
| D(2) | G(15) | E(29) |
| F(2) | H(14) | H(28) |
| G(2) | I(10) | Q(2) |
| H(2) | Q(6) | D(1) |
| I(1) | J(8) | |
| J(1) | C(4) |
然后在每個(gè)分片中取前五個(gè),在協(xié)調(diào)節(jié)點(diǎn)中再次聚合:
| 分片1 | 分片2 | 分片三 |
|---|---|---|
| A(25) | A(30) | A(45) |
| B(18) | B(25) | C(44) |
| C(6) | F(17) | Z(36) |
| D(3) | Z(16) | B(30) |
| D(2) | G(15) | E(29) |
聚合結(jié)果
| 排名 | term |
|---|---|
| 1 | A(100) |
| 2 | Z(52) |
| 3 | C(50) |
| 4 | G(45) |
| 5 | B(43) |
實(shí)際情況中,C有6+4+44=54個(gè),這是因?yàn)樵跀?shù)據(jù)節(jié)點(diǎn)返回的時(shí)候,并未將排名第六以后的數(shù)據(jù)返回給協(xié)調(diào)節(jié)點(diǎn),我們也可以通過調(diào)大shard_size的參數(shù)返回更多的數(shù)據(jù),從而提高數(shù)據(jù)的準(zhǔn)確性,但是過大的size會(huì)增加集群的負(fù)擔(dān),降低集群性能,所以如果對(duì)數(shù)據(jù)的準(zhǔn)確性要求沒那么高的情況下,可以使用es的聚合功能,如果數(shù)據(jù)準(zhǔn)確性很高,請(qǐng)考慮hadoop或者flink這類工具.
4.狀態(tài)檢查
# 集群健康
GET /_cat/health?v
# 查詢文檔總數(shù)
GET /_cat/count?v
#查詢某個(gè)索引的
GET /_cat/count/movies?v
# 查看索引
GET /_cat/indices
#查看某一個(gè)索引
GET /_cat/indices/movies?v
#查看yellow狀態(tài)的索引
GET /_cat/indices?v&health=yellow
#根據(jù)文本數(shù)進(jìn)行倒排序
GET /_cat/indices?v&s=docs.count:desc
es在使用過程中,經(jīng)常會(huì)遇到狀態(tài)變黃變紅的情況,變黃的原因是副本分片的丟失,此時(shí)不影響寫入和查詢,變紅是因?yàn)橹鞣制瑏G失,會(huì)影響寫入,常見的狀態(tài)原因如下:
# 查看所有分片
GET _cat/shards
#根據(jù)索引正則
GET _cat/shards/m*?v
#unassigned.reason可以查看未分配的原因
GET _cat/shards?h=index,shard,prirep,state,unassigned.reason
state狀態(tài)描述:
INDEX_CREATED Unassigned as a result of an API creation of an index.
CLUSTER_RECOVERED Unassigned as a result of a full cluster recovery.
INDEX_REOPENED Unassigned as a result of opening a closed index.
DANGLING_INDEX_IMPORTED Unassigned as a result of importing a dangling index引入危險(xiǎn)索引()
NEW_INDEX_RESTORED Unassigned as a result of restoring into a new index.
EXISTING_INDEX_RESTORED Unassigned as a result of restoring into a closed index.
REPLICA_ADDED Unassigned as a result of explicit addition of a replica.
ALLOCATION_FAILED Unassigned as a result of a failed allocation of the shard.
NODE_LEFT Unassigned as a result of the node hosting it leaving the cluster.
REROUTE_CANCELLED Unassigned as a result of explicit cancel reroute command.
REINITIALIZED When a shard moves from started back to initializing, for example, with shadow replicas.
REALLOCATED_REPLICA A better replica location is identified and causes the existing replica allocation to be cancelled.
#查看unassigned.reason具體解讀
GET /_cluster/allocation/explain
{
"index": "myindex",
"shard": 0,
"primary": true
}
變紅或者變黃在短暫時(shí)間內(nèi)是正?,F(xiàn)象,但是持續(xù)時(shí)間很長(zhǎng)的時(shí)候就需要注意了,我之前遇到es變紅的比較多的原因主要有兩個(gè).一個(gè)是磁盤被打滿,數(shù)據(jù)寫不進(jìn)去,另外一個(gè)是節(jié)點(diǎn)宕機(jī),所以這兩種情況需要找運(yùn)維同學(xué)協(xié)助排查問題.
5.使用技巧
1.esjar包沖突比較嚴(yán)重,也不僅僅是es的問題,底層netty包經(jīng)常會(huì)和別的jar包進(jìn)行沖突,而且jar包要和線上es版本一致,es客戶端版本兼容問題很頭疼,主要原因是Lucene升級(jí)不兼容,Lucene有一個(gè)類專門用來記錄版本號(hào),密密麻麻,這種情況可以在idea里面安裝個(gè)maven analyzer,可以方便排查沖突.
2.語法,es語法比較復(fù)雜,熟記我們常用的就行了,再不會(huì)的去翻翻文檔,這里面有個(gè)小技巧,就是可以利用kibana,可以搜索完看下kibana發(fā)的請(qǐng)求,然后去構(gòu)造這個(gè)json.自己寫完構(gòu)造請(qǐng)求,可以輸出下toString方法,看是不是一樣.
3.可視化客戶端,es有很多可視化客戶端,如果沒有監(jiān)控啥需求,僅僅是看看數(shù)據(jù),可以在chrome安裝個(gè)head插件即可.
6.推薦環(huán)節(jié)
1.官方文檔
2.極客時(shí)間- Elasticsearch核心技術(shù)與實(shí)戰(zhàn)
3.Elasticsearch頂尖高手系列-核心知識(shí)篇 + 高手進(jìn)階篇,bilibili有(順便安利一波,bilibili真的是碼農(nóng)的好網(wǎng)站)
4.elasticsearch源碼解析與優(yōu)化實(shí)戰(zhàn)
5.Lucene實(shí)戰(zhàn)
6.es中文網(wǎng)站,可以訂閱