index API在特定索引中添加或更新JSON類型化文檔,使其可搜索,下面的示例將JSON文檔插入到「twitter」索引中,其類型名爲「_doc」,id爲1:數據庫
PUT twitter/_doc/1 { "user" : "kimchy", "post_date" : "2009-11-15T14:12:12", "message" : "trying out Elasticsearch" }
以上索引操做的結果是:segmentfault
{ "_shards" : { "total" : 2, "failed" : 0, "successful" : 2 }, "_index" : "twitter", "_type" : "_doc", "_id" : "1", "_version" : 1, "_seq_no" : 0, "_primary_term" : 1, "result" : "created" }
_shards
報頭提供了關於索引操做的複製過程的信息。api
total
- 指示應該對多少碎片副本(主碎片和副本碎片)執行索引操做。successful
- 指示成功執行索引操做的碎片副本的數量。failed
- 當副本碎片上的索引操做失敗時,包含與複製相關錯誤的數組。索引操做成功的狀況下,successful
至少是1。數組
當索引操做成功返回時,副本碎片可能不會所有啓動(默認狀況下,只須要主碎片,可是這種行爲能夠更改),在這種狀況下,total
將等於基於number_of_replicas
設置的總碎片,successful
將等於啓動的碎片數(主碎片加副本),若是沒有失敗,則failed
爲0。
若是以前沒有建立索引,則索引操做將自動建立索引(查看用於手動建立索引的create index API),而且若是尚未建立特定類型,還會自動爲該類型建立動態類型映射(請參閱put mapping API以手動建立類型映射)。併發
映射自己很是靈活,而且沒有模式,新的字段和對象將自動添加到指定類型的映射定義中,查看映射部分以得到關於映射定義的更多信息。app
能夠經過在全部節點的配置文件中設置action.auto_create_index
爲false
禁用自動索引建立,能夠經過將index.mapper.dynamic
爲每一個索引設置爲false
來禁用自動映射建立。異步
自動索引建立能夠包括基於白/黑名單列表的模式,例如,將action.auto_create_index
設置爲+aaa*
、-bbb*
、+ccc*
、-*
(+
表示容許,-
表示不容許)。elasticsearch
每一個索引的文檔都有一個版本號,關聯的version
做爲對index API請求的響應的一部分返回,當指定version
參數時,index API可選的容許樂觀鎖併發控制,這將控制要對其執行操做的文檔的版本。版本控制用例的一個很好的例子是執行事務讀 - 而後更新,指定一個從最初讀取的文檔中的version
,能夠確保在此期間沒有發生任何更改(當讀是爲了更新時,建議將preference
設置爲_primary
),例如:函數
PUT twitter/_doc/1?version=2 { "message" : "elasticsearch now has versioning support, double cool!" }
注意:版本控制是徹底實時的,而且不受搜索操做的接近實時方面的影響,若是沒有提供版本,則在不進行任何版本檢查的狀況下執行操做。oop
默認狀況下,內部版本控制從1
開始,每次更新時遞增,包括刪除。可選地,版本號能夠用外部值進行補充(例如,若是維護在數據庫中),要啓用該功能,應該將version_type
設置爲external
。提供的值必須是一個數值,大於或等於0的long
值,並小於9.2e+18
。在使用外部版本類型時,系統檢查傳遞給索引請求的版本號是否大於當前存儲文檔的版本號,而不是檢查匹配的版本號,若是爲true
,則對文檔進行索引並使用新的版本號,若是提供的值小於或等於存儲文檔的版本號,將發生版本衝突,索引操做將失敗。
外部版本控制支持將值
0
做爲有效的版本號,這容許版本與版本號是從0開始而不是從1開始的外部版本控制系統同步。它的反作用是,版本號爲0的文檔既不能使用Update By Query API進行更新,也不能使用Delete By Query API進行刪除,只要它們的版本號爲0。
一個好的反作用是,只要使用了源數據庫的版本號,就不須要維護因爲更改源數據庫而執行的異步索引操做的嚴格順序。若是使用外部版本控制,那麼即便使用數據庫中的數據更新Elasticsearch索引的簡單狀況也會獲得簡化,由於若是索引操做因爲某種緣由出現故障,則只使用最新版本。
除了上面介紹的internal
和external
版本類型以外,Elasticsearch還爲特定的用例支持其餘類型,下面是不一樣版本類型及其語義的概述。
internal
external
或external_gt
long
數字。external_gte
long
數字。external_gte
版本類型用於特殊的用例,應該當心使用,若是使用不當,可能致使數據丟失,還有另外一個選項,force
,它被廢棄了,由於它會致使主碎片和副本碎片分離。
索引操做還接受op_type
,可用於強制一個create
操做,容許「put-if-absent」的行爲,使用create
時,若是該id文檔已經存在於索引中,則索引操做將失敗。
下面是一個使用op_type
參數的示例:
PUT twitter/_doc/1?op_type=create { "user" : "kimchy", "post_date" : "2009-11-15T14:12:12", "message" : "trying out Elasticsearch" }
指定create
的另外一個選項是使用如下uri:
PUT twitter/_doc/1/_create { "user" : "kimchy", "post_date" : "2009-11-15T14:12:12", "message" : "trying out Elasticsearch" }
能夠在不指定id的狀況下執行索引操做,在這種狀況下,將自動生成id,此外,op_type
將被自動設置爲create
,下面是一個例子(注意使用的是POST而不是PUT):
POST twitter/_doc/ { "user" : "kimchy", "post_date" : "2009-11-15T14:12:12", "message" : "trying out Elasticsearch" }
以上索引操做的結果是:
{ "_shards" : { "total" : 2, "failed" : 0, "successful" : 2 }, "_index" : "twitter", "_type" : "_doc", "_id" : "W0tpsmIBdwcYyG50zbta", "_version" : 1, "_seq_no" : 0, "_primary_term" : 1, "result": "created" }
默認狀況下,碎片放置(或routing
)是經過使用文檔的id
值的hash來控制的,爲了實現更顯式的控制,可使用routing
參數直接在每一個操做的基礎上指定路由器使用的hash函數的值,例如:
POST twitter/_doc?routing=kimchy { "user" : "kimchy", "post_date" : "2009-11-15T14:12:12", "message" : "trying out Elasticsearch" }
在上面的示例中,「_doc」文檔根據提供的routing
參數「kimchy」被路由到一個碎片。
在設置顯式映射時,能夠選擇使用_routing
字段指導索引操做,從文檔自己提取路由值,這確實須要額外的文檔解析傳遞的成本(很是低),若是定義了_routing
映射並設置爲required
,若是沒有提供或提取到路由值,索引操做將失敗。
索引操做根據其路由(請參閱上面的路由部分)定向到主碎片,並在包含此碎片的實際節點上執行,主碎片完成操做後,若是須要,更新將分發給合適的副本。
爲了提升對系統的寫操做的彈性,能夠將索引操做配置爲在繼續操做以前等待必定數量的活動碎片副本,若是必需的活動碎片副本數量不可用,那麼寫操做必須等待並重試,直到必要的碎片副本啓動或超時。默認狀況下,寫操做只等待主碎片處於活動狀態後再繼續(即wait_for_active_shards=1
),經過設置index.write.wait_for_active_shards
,能夠在索引設置中動態覆蓋此默認值,要更改每一個操做的這種行爲,可使用wait_for_active_shards
請求參數。
有效值是all
或索引中每一個碎片中配置的副本總數的任意正整數(即number_of_replicas+1
),指定一個負數或一個大於碎片副本數量的數字會拋出錯誤。
例如,假設咱們有一個由三個節點組成的集羣,A
、B
和C
,咱們建立一個索引,index
將副本的數量設置爲3(結果是4個碎片副本,比節點多一個副本)。若是咱們嘗試索引操做,默認狀況下,操做只會在繼續以前確保每一個碎片的主副本可用,這意味着,即便B
和C
宕機,而且A
託管主碎片副本,索引操做仍然只處理數據的一個副本。若是將wait_for_active_shards
設置爲3
(全部3個節點都已啓動),那麼在繼續以前,索引操做將須要3個活動碎片副本,這一要求應該獲得知足,由於集羣中有3個活動節點,每一個節點都持有碎片的副本。可是,若是咱們將wait_for_active_shards
設置爲all
(或4
,這是相同的),索引操做將不會繼續,由於索引中沒有每一個活動碎片的全部4個副本,除非集羣中出現一個新節點來承載碎片的第四個副本,不然操做將超時。
須要注意的是,這個設置大大減小了寫操做不寫入到所需碎片副本數量的機會,但它並無徹底排除這種可能性,由於這種檢查發生在寫操做開始以前,一旦寫操做開始,複製仍然可能在任何數量的碎片副本上失敗,但在主副本上仍然成功,寫操做響應的_shards
部分顯示覆製成功/失敗的碎片副本的數量。
{ "_shards" : { "total" : 2, "failed" : 0, "successful" : 2 } }
控制什麼時候該請求所作的更改對搜索可見,參閱?refresh。
在使用索引api更新文檔時,即便文檔沒有更改,也老是會建立文檔的新版本,若是這是不可接受的,使用_update
api將detect_noop
設置爲true
,這個選項在索引api上不可用,由於索引api不會獲取舊源,而且沒法將其與新源進行比較。
對於無操做的更新何時不可接受,並無硬性規定,它是許多因素的組合,好比數據源發送其實是無操做的更新的頻率,以及每秒鐘Elasticsearch在正在接收更新的碎片上運行多少查詢。
當執行索引操做時,分配給執行索引操做的主碎片可能不可用,其中的一些緣由多是主碎片正在從網關中恢復或正在經歷重定位。默認狀況下,索引操做將等待主碎片變得可用1分鐘,而後失敗並響應錯誤,可使用timeout
參數顯式地指定它的等待時間,這裏有一個將其設置爲5分鐘的例子:
PUT twitter/_doc/1?timeout=5m { "user" : "kimchy", "post_date" : "2009-11-15T14:12:12", "message" : "trying out Elasticsearch" }