1. 程式人生 > >Impala中的invalidate metadata和refresh

Impala中的invalidate metadata和refresh

來源:

http://blog.csdn.net/yu616568/article/details/72780346

前言

Impala採用了比較奇葩的多個impalad同時提供服務的方式,並且它會由catalogd快取全部元資料,再通過statestored完成每一次的元資料的更新到impalad節點上,Impala叢集會快取全部的元資料,這種快取機制就導致通過其他手段更新元資料或者資料對於Impala是無感知的,例如通過hive建表,直接拷貝新的資料到HDFS上等,Impala提供了兩種機制來實現元資料的更新,分別是INVALIDATE METADATA和REFRESH操作,本文將詳細介紹這兩個操作。

使用方式

INVALIDATE METADATA是用於重新整理全庫或者某個表的元資料,包括表的元資料和表內的檔案資料,它會首先清楚表的快取,然後從metastore中重新載入全部資料並快取,該操作代價比較重,主要用於在hive中修改了表的元資料,需要同步到impalad,例如create table/drop table/alter table add columns等。

INVALIDATE METADATA 語法:

INVALIDATE METADATA;                   //重新載入所有庫中的所有表
INVALIDATE METADATA [table]            //重新載入指定的某個表
  • 1
  • 2
  • 3

REFRESH是用於重新整理某個表或者某個分割槽的資料資訊,它會重用之前的表元資料,僅僅執行檔案重新整理操作,它能夠檢測到表中分割槽的增加和減少,主要用於表中元資料未修改,資料的修改,例如INSERT INTO、LOAD DATA、ALTER TABLE ADD PARTITION、LLTER TABLE DROP PARTITION等,如果直接修改表的HDFS檔案(增加、刪除或者重新命名)也需要指定REFRESH重新整理資料資訊。

REFRESH 語法:

REFRESH [table]                             //重新整理某個表
REFRESH [table] PARTITION [partition]       //重新整理某個表的某個分割槽
  • 1
  • 2
  • 3

INVALIDATE METADATA原理

對於INVALIDATE METADATA操作,由客戶端將查詢提交到某個impalad節點上,執行如下的操作:

  • 1.獲取需要執行INVALIDATE METADATA的表,如果沒指定表則不設定表示全部表(不考慮這種情況)。
  • 2.請求catalogd執行resetMetadata操作,並將isFresh引數設定為false。
  • 3.catalogd接收到該請求之後執行invalidateTable操作,將該表的快取清除,然後重新生成該表的快取物件,新生成的物件只包含表名+庫名的資訊,為新生成的表物件生成一個新的catalog版本號(假設新的version=1),將這部分資訊返回給呼叫方(impalad),然後非同步執行元資料和資料的載入。
  • 4.impalad收到catalogd的返回值,返回值是更新之後的表快取物件+版本號,但是這是一個不完整的表元資料,impalad將這個元資料應用到本地元資料快取。
  • 5.INVALIDATE METADATA執行完成。

INVALIDATE METADATA操作帶來的副作用是生成一個新的未完成的元資料物件,對於操作請求的impalad(稱它為impalad-A),能夠立馬獲取到該物件,對於其它的impalad需要通過statestored同步,因此執行完該操作,處理該操作的impalad對於該表的快取是一個新的但是不完整的物件,其餘的impalad儲存的是舊的元資料。

對於後續的該表查詢操作,分為如下四種情況:

  • 如果catalogd已經完成該表所有元資料載入,會對該表生成一個新的版本號(假設version=2),然後更新到statestored,由statestored廣播到各個impalad節點上,此時所有的查詢都查詢到最新的元資料和資料。
  • 如果catalogd尚未完成表的元資料載入或者statestored未廣播完成,並且接下來請求到impalad-A(之前執行INVALIDATE METADATA的節點),此時impalad在執行語義分析的時候能夠檢測到表的元資料不完整(因為當前只有表名和庫名,沒有任何其餘的元資料),impalad會直接請求catalogd獲取該表最新的元資料,如果catalogd尚未完成元資料載入,則該請求會等到直到catalogd載入完成並返回impalad最新的元資料。
  • 如果catalogd尚未完成表的元資料載入或statestored未廣播完成,接下來請求到了其他的impalad節點,如果接受請求的impalad尚未通過statestored同步新的不完整的表元資料(version=1),則該impalad中快取的關於該表的元資料是執行INVALIDATE METADATA之前的,因此根據舊的元資料處理該查詢(可能因為檔案被刪除導致錯誤)。
  • 如果catalogd尚未完成表的元資料載入,接下來請求到了其他的impalad節點,如果接受請求的impalad已經通過statestored同步新的不完整的表元資料(version=1),那麼接下來會像第二種情況一樣處理。

從INVALIDATE METADATA的實現來看,該操作不僅僅會全量載入表的元資料和分割槽、檔案元資料,還會影響後面關於該表的查詢。

REFRESH原理

對於REFRESH操作,由客戶端將查詢提交到某個impalad節點上,執行如下的操作:

  • 1.獲取需要執行REFRESH的表和分割槽資訊。
  • 2.請求catalogd執行resetMetadata操作,並將isFresh引數設定為true。
  • 3.catalogd接收到該請求之後判斷是否指定分割槽,如果指定了分割槽則執行reload partition操作,如果未指定則執行reload table操作,對於reloadPartition則從metastore中讀取partition最新的元資料,然後重新整理該partition擁有的所有檔案的元資料(大小,許可權,資料分佈等);對於reloadTable則從metadata中讀取全部的partition資訊,然後和快取中的partition進行比對判斷是否有分割槽需要增加和刪除,對於其餘的分割槽則執行元資料的更新。
  • 4.impalad收到catalogd的返回值,返回值是更新之後該表的快取資料,impalad會將該資料更新到自己的快取中。因此接受請求的impalad能夠將當前元資料快取。
  • 5.REFRESH執行完成。

對於後續的查詢,分為如下兩種情況:

  • 如果查詢提交到到執行REFRESH的impalad節點,那麼查詢能夠使用最新的元資料。
  • 如果查詢提交到其他impalad節點,需要依賴於該表0更新後的快取是否已經同步到impalad中,如果已經完成了同步則可以使用最新的元資料,如果未完成則使用舊的元資料。

可以看出REFRESH操作較之於INVALIDATE METADATA是輕量級的操作,如果更改只涉及到一個分割槽設定可以只重新整理一個分割槽的元資料,並且它是同步的,對於之後查詢的影響較小。

使用原則

如果在使用過程中涉及到了元資料或者資料的更新,則需要使用這兩者中的一個操作完成,具體如何選擇需要根據如下原則:

  • invalidate metadata操作比refresh要重量級
  • 如果涉及到表的schema改變,使用invalidate metadata [table]
  • 如果只是涉及到表的資料改變,使用refresh [table]
  • 如果只是涉及到表的某一個分割槽資料改變,使用refresh [table] partition [partition]
  • 禁止使用invalidate metadata什麼都不加,寧願重啟catalogd。

總結

REFRESH和INVALIDATE METADATA對於impala而言是比較重要的兩個操作,分別處理資料和元資料的修改,其中REFRESH操作是同步的,INVALIDATE METADATA是非同步的,本文詳細介紹了兩種語句的適用場景和執行原理,以及可能造成的影響,最重要的是,需要謹記這兩種查詢使用場景。

參考

INVALIDATE METADATA語句 
REFRESH語句 
Impala原始碼