TairSearch是集緩衝與計算於一體的即時全記憶體檢索系統,其核心的倒排索引機制既能滿足詞根的模糊比對查詢,也能作為熱資料存放區裝置,實現儲存計算一體化,加速任意、多列索引的聯集查詢效率。
背景資訊
互連網及傳統行業應用服務的關鍵資料通常儲存在MySQL等關係型資料庫中。為緩解資料庫訪問壓力,通常會引入Redis等Key-value緩衝系統(KV緩衝系統)承擔熱資料的查詢,以提升查詢效能。然而,當業務情境需要在資料庫中進行多列索引聯集查詢或LIKE
模糊比對查詢時,普通的KV緩衝系統無法較好地獨立支撐以上情境,往往需要引入Lua指令碼或外部計算等額外的過濾匹配機制實現聯集查詢。
KV緩衝系統在多列索引聯集查詢情境的局限性
在將資料匯入至KV緩衝系統時,以Redis為例,通常會將關係型資料庫的行資料匯入至Redis的Hash結構:以行資料中主鍵欄位的值作為Redis Hash的Key,其他欄位名作為Hash的Field,其欄位的值作為對應Field的Value。
如果僅涉及查詢主鍵索引,則在Redis中可以直接通過HMGET
的方式擷取指定欄位的資訊。但在關係型資料庫中,不僅可以存在主鍵索引,還可以設定多個二級索引以及多種聯合索引等,用於提高查詢效率。然而Redis在如下情境中存在明顯局限性:
二級索引查詢:Redis不支援以Hash結構中的field內容進行查詢,因此只能在Redis中建立2層Hash結構來儲存關係型資料庫中的二級索引。此方案不僅增加了匯入資料的複雜度,也因資料冗餘造成記憶體空間浪費。
聯合索引查詢:Redis不支援對Hash結構進行多Key聯集查詢,使用者只能通過Lua指令碼或外部計算實現聯集查詢。
本文以TairSearch支撐流量洪峰時的機票搜尋業務為例,介紹如何通過TairSearch,加速任意、多列索引的聯集查詢效率。
關於TairSearch的詳細介紹及命令樣本,請參見Search。
精準搜尋機票樣本
在暑期、國慶、春節等中長假期時,熱門旅遊度假區的航班查詢容易造成流量洪峰。在該情境下,可以將所有的待飛航班資訊儲存至TairSearch中。
建立文檔索引
以某服務平台的機票搜尋介面為例,精準搜尋機票涉及幾個關鍵條件:出發地、目的地、出行日期、艙位、是否帶兒童或嬰兒等。
本樣本以出發地、目的地拼接作為TairSearch的Key(departure_destination
),例如zhuhai_hangzhou
。建立如下索引欄位:出發地(departure
)、目的地(destination
)、出行日期(date
)、艙位(seat
)、是否帶兒童或嬰兒(with
)、航班號(flight_id
)、價格(price
)、起飛時間(departure_time
)、降落時間(destination_time
)。
如需增加或調整欄位,可直接執行TFT.UPDATEINDEX
。
程式碼範例如下:
TFT.CREATEINDEX zhuhai_hangzhou '{
"mappings":{
"properties":{
"departure":{"type":"keyword"},
"destination":{"type":"keyword"},
"date":{"type":"keyword"},
"seat":{"type":"keyword"},
"with":{"type":"keyword"},
"flight_id":{"type":"keyword"},
"price":{"type":"double"},
"departure_time":{"type":"long"},
"destination_time":{"type":"long"}
}
}
}'
預計輸出:
OK
寫入資料
整理航班資訊,寫入TairSearch文檔,程式碼範例如下:
TFT.ADDDOC zhuhai_hangzhou '{
"departure":"zhuhai",
"destination":"hangzhou",
"date":"2022-09-01",
"seat":"first",
"with":"baby",
"flight_id":"CZ1000",
"price":986.1,
"departure_time":1661991010,
"destination_time":1661998210
}'
預計輸出:
"{"_id":"16615908912020060"}"
# 返迴文檔ID,格式為JSON。
精準搜尋
搜尋2022年09月01日珠海至杭州,頭等艙座位的航班,且按照航班的出發時間進行排序,程式碼範例如下。
TFT.Search zhuhai_hangzhou '{"sort":["departure_time"],"query":{"bool":{"must":[{"term":{"date":"2022-09-01"}},{"term":{"seat":"first"}}]}}}'
預計輸出:
"{
"hits": {
"hits": [
{
"_id": "16615908912020060",
"_index": "zhuhai_hangzhou",
"_score": 0.433955,
"_source": {
"departure": "zhuhai",
"destination": "hangzhou",
"date": "2022-09-01",
"seat": "first",
"with": "baby",
"flight_id": "CZ1000",
"price": 986.1,
"departure_time": 1661991010,
"destination_time": 1661998210
}
}
],
"max_score": 0.433955,
"total": {
"relation": "eq",
"value": 1
}
}
}"