hbase構建二級索引解決方案

大資料技術派發表於2021-12-28

hbase構建二級索引

關注公眾號:大資料技術派,回覆“資料”,領取1024G資料。

1 為什麼需要二級索引

HBase的一級索引就是rowkey,我們僅僅能通過rowkey進行檢索。假設我們相對Hbase裡面列族的列列進行一些組合查詢,就只能全表掃描了。表如果較大的話,代價是不可接受的,所以要提出二級索引的方案。

二級索引的思想:簡單理解就是,根據列族的列的值,查出rowkey,再按照rowkey就能很快從hbase查詢出資料,我們需要構建出根據列族的列的值,很快查出rowkey的方案。

2 常見的二級索引方案

  1. MapReduce方案;
  2. Coprocessor方案;
  3. elasticsearch+hbase方案;
  4. Solr+hbase方案;

2.1 MapReduce方案

IndexBuilder:利用MR的方式構建Index
長處:併發批量構建Index
缺點:不能實時構建Index

舉例:
原表:

row  1      f1:name  zhangsan
row  2      f1:name  lisi
row  3      f1:name  wangwu

索引表:

row     zhangsan    f1:id   1
row     lisi        f1:id   2
row     wangwu      f1:id   3

這種方式的思想是再構建一張hbase表,列族的列這裡的name作為索引表的rowkey,根據rowkey查詢出資料hbase是很快的,拿到id後,也就拿到了原表的rowkey了,因為源表的rowkey就是id,每次查詢一共需要查詢兩張表。

2.2 Coprocessor方案

有關協處理器的講解,Hbase官方文件是最好的,這裡大體說一下它的作用與使用方法。

  1. Coprocessor提供了一種機制可以讓開發者直接在RegionServer上執行自定義程式碼來管理資料。
    通常我們使用get或者scan來從Hbase中獲取資料,使用Filter過濾掉不需要的部分,最後在獲得的資料上執行業務邏輯。但是當資料量非常大的時候,這樣的方式就會在網路層面上遇到瓶頸。客戶端也需要強大的計算能力和足夠大的記憶體來處理這麼多的資料,客戶端的壓力就會大大增加。但是如果使用Coprocessor,就可以將業務程式碼封裝,並在RegionServer上執行,也就是資料在哪裡,我們就在哪裡跑程式碼,這樣就節省了很大的資料傳輸的網路開銷。
  2. Coprocessor有兩種:Observer和Endpoint
    EndPoint主要是做一些計算用的,比如計算一些平均值或者求和等等。而Observer的作用類似於傳統關係型資料庫的觸發器,在一些特定的操作之前或者之後觸發。學習過Spring的朋友肯定對AOP不陌生,想象一下AOP是怎麼回事,就會很好的理解Observer了。Observer Coprocessor在一個特定的事件發生前或發生後觸發。在事件發生前觸發的Coprocessor需要重寫以pre作為字首的方法,比如prePut。在事件發生後觸發的Coprocessor使用方法以post作為字首,比如postPut。
    Observer Coprocessor的使用場景如下:
    2.1. 安全性:在執行Get或Put操作前,通過preGet或prePut方法檢查是否允許該操作;
    2.2. 引用完整性約束:HBase並不直接支援關係型資料庫中的引用完整性約束概念,即通常所說的外來鍵。但是我們可以使用Coprocessor增強這種約束。比如根據業務需要,我們每次寫入user表的同時也要向user_daily_attendance表中插入一條相應的記錄,此時我們可以實現一個Coprocessor,在prePut方法中新增相應的程式碼實現這種業務需求。
    2.3. 二級索引:可以使用Coprocessor來維持一個二級索引。正是我們需要的

索引設計思想

關鍵部分來了,既然Hbase並沒有提供二級索引,那如何實現呢?先看下面這張圖

Coprocessor

我們的需求是找出滿足cf1:col2=c22這條記錄的cf1:col1的值,實現方法如圖,首先根據cf1:col2=c22查詢到該記錄的行鍵,然後再通過行健找到對應的cf1:col1的值。其中第二步是很容易實現的,因為Hbase的行鍵是有索引的,那關鍵就是第一步,如何通過cf1:col2的值找到它對應的行鍵。很容易想到建立cf1:col2的對映關係,即將它們提取出來單獨放在一張索引表中,原表的值作為索引表的行鍵,原表的行鍵作為索引表的值,這就是Hbase的倒排索引的思想。

2.3 elasticsearch+hbase方案

比如說你現在有一行資料

id name age ….30 個欄位

但是你現在搜尋,只需要根據 id name age 三個欄位來搜尋

如果你傻乎乎的往 es 裡寫入一行資料所有的欄位,就會導致說 70% 的資料是不用來搜尋的,結果硬是佔據了 es 機器上的 filesystem cache 的空間,單挑資料的資料量越大,就會導致 filesystem cahce 能快取的資料就越少

僅僅只是寫入 es 中要用來檢索的少數幾個欄位就可以了,比如說,就寫入 es id name age 三個欄位就可以了,然後你可以把其他的欄位資料存在 mysql 裡面,我們一般是建議用 es + hbase 的這麼一個架構。

hbase 的特點是適用於海量資料的線上儲存,就是對 hbase 可以寫入海量資料,不要做複雜的搜尋,就是做很簡單的一些根據 id 或者範圍進行查詢的這麼一個操作就可以了

從 es 中根據 name 和 age 去搜尋,拿到的結果可能就 20 個 doc id,然後根據 doc id 到 hbase 裡去查詢每個 doc id 對應的完整的資料,給查出來,再返回給前端。

img

你最好是寫入 es 的資料小於等於,或者是略微大於 es 的 filesystem cache 的記憶體容量

然後你從 es 檢索可能就花費 20ms,然後再根據 es 返回的 id 去 hbase 裡查詢,查 20 條資料,可能也就耗費個 30ms,可能你原來那麼玩兒,1T 資料都放 es,會每次查詢都是 5 ~ 10 秒,現在可能效能就會很高,每次查詢就是 50ms。

四個字總結的話,我覺得就是“各司其職”,HBase 就用來儲存,ES 就用來做索引,況且目前的實際情況跟文章中說的也很像,要查詢的欄位就幾個,而其他的欄位又很大又沒用,沒必要都丟到 ES 中,浪費查詢效率

2.4 Solr+hbase方案

Solr是一個獨立的企業級搜尋應用server,它對並提供相似幹Web-service的API介面。使用者能夠通過http請求,向搜尋引擎server提交一定格式的XML檔案,生成索引。也能夠通過Http Get操作提出查詢請求,並得到XML格式的返回結果。

Solr是一個高效能。採用Java5開發。基幹Lucene的全文搜尋server。同一時候對其進行了擴充套件。提供了比Lucene更為豐富的查詢語言,同一時候實現了可配置、可擴充套件並對查詢效能進行了優化,而且提供了一個完好的功能節理介面。是一款非常優秀的全文搜尋引擎。

HBase無可置疑擁有其優勢,但其本身僅僅對rowkey支援毫秒級的高速檢索,對於多欄位的組合查詢卻無能為力。基於Solr的HBase多條件查詢原理非常easy。將HBase表中涉及條件過濾的欄位和rowkey在Solr中建立索引,通過Solr的多條件查詢高速獲得符合過濾條件的rowkey值,拿到這些rowkey之後在HBASE中通過指定rowkey進行查詢。

img

網上其它還有根據Phoenix構建的,redismysql等都是可以嘗試的。

交流群

加我微信:ddxygq,回覆“加群”,我拉你進群。

猜你喜歡
數倉建模—指標體系
數倉建模—寬表的設計
Spark SQL知識點與實戰
Hive計算最大連續登陸天數
Flink計算pv和uv的通用方法

相關文章