電商搜索引擎的架構(gòu)設(shè)計和性能優(yōu)化

「 OneAPM 技術(shù)公開課」由應(yīng)用性能管理第一品牌 OneAPM 發(fā)起画切,內(nèi)容面向 IT 開發(fā)和運維人員东涡。云集技術(shù)牛人隆嗅、知名架構(gòu)師错忱、實踐專家共同探討技術(shù)熱點儡率。本文系「OneAPM 技術(shù)公開課」第一期演講嘉賓前當當網(wǎng)高級架構(gòu)師吳英昊的演講整理:

首先,非常感謝 OneAPM 技術(shù)公開課舉辦的這次活動以清。首先喉悴,我想說的是電商搜索引擎和普通的搜索引擎有很大的差別,因為電商搜索引擎主要是解決用戶要「買什么」玖媚,而通用搜索引擎主要是解決用戶「搜什么」箕肃。比如同樣搜索一個詞「百年孤獨」,電商的搜索肯定是給你推薦這本書的商家今魔,而百度主要是告訴你:《百年孤獨》是一本書勺像。

電商搜索引擎的特點

眾所周知,標準的搜索引擎主要分成三個大的部分错森,第一步是爬蟲系統(tǒng)吟宦,第二步是數(shù)據(jù)分析,第三步才是檢索結(jié)果涩维。首先殃姓,電商的搜索引擎并沒有爬蟲系統(tǒng)袁波,因為所有的數(shù)據(jù)都是結(jié)構(gòu)化的,一般都是微軟的數(shù)據(jù)庫或者 Oracle 的數(shù)據(jù)庫蜗侈,所以不用像百度一樣用「爬蟲」去不斷去別的網(wǎng)站找內(nèi)容篷牌,當然,電商其實也有自己的「爬蟲」系統(tǒng)踏幻,一般都是抓取友商的價格枷颊,再對自己進行調(diào)整。

第二點该面,就是電商搜索引擎的過濾功能其實比搜索功能要常用夭苗。甚至大于搜索本身。什么是過濾功能隔缀?一般我們網(wǎng)站買東西的時候题造,搜了一個關(guān)健詞,比如尿不濕猾瘸,然后所有相關(guān)品牌或者其他分類的選擇就會呈現(xiàn)在我們面前界赔。對百度而言,搜什么詞就是什么詞须妻,如果是新聞的話仔蝌,可能在時間上會有一個過濾的選項泛领。

第三點荒吏,電商搜索引擎支持各種維度的排序,包括支持好評渊鞋、銷量绰更、評論、價格等屬性的排序锡宋。而且對數(shù)據(jù)的實時性的要求非常高儡湾。對一般的搜索引擎,只有非常重要的網(wǎng)站执俩,比如一些重量級的門戶網(wǎng)站徐钠,百度的收錄是非常快的役首,但是對那些流量很小的網(wǎng)站尝丐,可能一個月才會爬一次。電商搜索對數(shù)據(jù)的實時性要求主要體現(xiàn)在價格和庫存兩個方面衡奥。

電商搜索引擎另一個特點就是不能丟品爹袁,比如我們在淘寶、天貓開了個店鋪矮固,然后好不容易搞了一次活動失息,但是卻搜不到了,這是無法忍受的。除此之外盹兢,電商搜索引擎與推薦系統(tǒng)和廣告系統(tǒng)是相互融合的邻梆,因為搜素引擎對流量的貢獻是最大的,所以大家都希望把廣告系統(tǒng)能跟其融合蛤迎。當然确虱,還有一點非常重要,就是要保證絕對的高可用替裆,而且不能宕機校辩。

電商搜索引擎的架構(gòu)

因為電商搜索引跟一般的搜索引擎區(qū)別很大,所以在架構(gòu)的設(shè)計上也獨具特色辆童。首先宜咒,搜索引擎的實現(xiàn)方式有很多種,有谷歌把鉴、百度故黑、搜狗這種非常大的公司,也有京東庭砍、淘寶场晶、當當這樣的電商搜索引擎,很多中小型的電商可能更喜歡用一個開源的搜索引擎怠缸。所以總的來說诗轻,主要包括以下這幾種方式:

電商搜索引擎的架構(gòu)設(shè)計和性能優(yōu)化

第一種是「Lucene+自己封裝」,只用來做檢索揭北,然后封裝扳炬,后面所有的 ES,這兩個是完整的解決方案搔体,而且包括索引所有的東西恨樟,只需要部署好業(yè)務(wù)邏輯,然后查找結(jié)果就可以了疚俱。

第二種就是 Solr劝术,這是一個高性能,采用 Java5 開發(fā)呆奕,基于 Lucene 的全文搜索服務(wù)器养晋。同時對其進行了擴展,提供了比 Lucene 更為豐富的查詢語言登馒,同時實現(xiàn)了可配置匙握、可擴展并對查詢性能進行了優(yōu)化,并且提供了一個完善的功能管理界面陈轿,是一款非常優(yōu)秀的全文搜索引擎圈纺。

第三種是 ElasticSearch秦忿,這是一個基于 Lucene 的搜索服務(wù)器。它提供了一個分布式多用戶能力的全文搜索引擎蛾娶,基于 RESTful web 接口灯谣。Elasticsearch 是用 Java 開發(fā)的,并作為 Apache 許可條款下的開放源碼發(fā)布蛔琅,目前使用的也非常多胎许。

這里提一下,當當?shù)乃阉饕媸亲约簩崿F(xiàn)的罗售,」家ぃ現(xiàn)在,新興的互聯(lián)網(wǎng)公司大部分都是使用第一種或者第二種寨躁,數(shù)據(jù)量比較大的一般采用第三種穆碎。

電商搜索引擎標配模塊

電商搜索引擎的架構(gòu)設(shè)計和性能優(yōu)化

接下來我想講一下,如果我們自己做一個搜索引擎的話需要實現(xiàn)哪些功能(上圖是電商搜索引擎的標準模塊)职恳,其實不止是電商搜索引擎所禀,除了通搜的搜索引擎,其他的搜索引擎也是使用這樣的標配放钦。

電商搜索引擎的架構(gòu)設(shè)計和性能優(yōu)化

對檢索模塊而言色徘,首先是對用戶的意圖進行分析,根據(jù)用戶的搜索詞來進行純算法的實現(xiàn)操禀。比如用戶的搜索詞是「黑包包」褂策,其實用戶的本意就是買一個黑色的包,但是這個「包」可以跟別的詞組合在一起床蜘,甚至在搜索結(jié)果中會出現(xiàn)「包子」辙培。所以蔑水,這就需要 query 分析系統(tǒng)來做邢锯,告訴檢索系統(tǒng),你需要主要在服裝鞋帽中的分類去找搀别,而不是生鮮食品類丹擎。

設(shè)計到技術(shù)層面,當當網(wǎng)使用的是 C++歇父。如果構(gòu)建一個性能好的系統(tǒng)蒂培,一些老一點的公司,大家都是在使用 C++ 或者是 C 語言榜苫。不止是當當網(wǎng)护戳,其實很多公司都是使用的 C 或者 C++ 實現(xiàn)的搜索引擎。

數(shù)據(jù)更新模塊

電商搜索引擎的架構(gòu)設(shè)計和性能優(yōu)化

第二個模塊就是數(shù)據(jù)更新模塊垂睬,該模塊負責生成索引媳荒。而數(shù)據(jù)中心模塊主要做的事情抗悍,就是將原始的結(jié)構(gòu)化數(shù)據(jù),變成一個可供檢索系統(tǒng)使用的搜索數(shù)據(jù)庫钳枕。當然缴渊,數(shù)據(jù)更新模塊和檢索模塊是分開還是合并呢?其實從本質(zhì)上講鱼炒,都是一堆代碼衔沼,完全可以寫在一個進程里。當然昔瞧,也可以分開指蚁,通過網(wǎng)絡(luò)往外輸入,各自都有道理自晰。第一種是簡單粗暴型的欣舵,如果是普通電商,像生鮮電商缀磕,數(shù)據(jù)量不大缘圈,實時性、季節(jié)性很強袜蚕,就可以把兩個系統(tǒng)用一個進程來完成糟把。但是如果到了百萬、千萬甚至上億級別的話牲剃,就不可能部在一臺機器上了遣疯。

電商搜索引擎的架構(gòu)設(shè)計和性能優(yōu)化

上圖就是當兩個系統(tǒng)合并在一起的時候,紅色部分就是檢索系統(tǒng)凿傅,黃色部分是上游產(chǎn)生數(shù)據(jù)的系統(tǒng)缠犀,如果是淘寶的話,對接就是淘寶的商戶聪舒,當當網(wǎng)對接是市場部的人員辨液,他們將數(shù)據(jù)錄入系統(tǒng),推到數(shù)據(jù)庫箱残,然后向下進行傳送滔迈,最終建立一個索引。

上圖中的藍色部分就是業(yè)務(wù)邏輯被辑,因為電商的搜索引擎業(yè)務(wù)需求量非常高燎悍,尤其是現(xiàn)在大家都喜歡用手機進行購物,像手機專享價就是一個新的業(yè)務(wù)盼理,這也意味著需要一個專用的模塊來處理這些商用的邏輯谈山。

此外,就是用戶行為的分析宏怔,我們搜集到的日志還有其他相關(guān)的數(shù)據(jù)都會存到 Hadoop 集群上去奏路,通過離線計算抗蠢,然后傳給商業(yè)模塊或者排序模塊進行排序和打分,并提供給用戶更好的使用體驗思劳。

出問題是不可避免的迅矛!如何解決?

雖然整理來看潜叛,設(shè)計的思路是非常合理的秽褒,但是還是會出現(xiàn)問題。一般而言威兜,一個成熟的電商搜索系統(tǒng)销斟,它的問題都很集中,要這幾種情況:首先就是 Bug椒舵,當然這是所有系統(tǒng)都會遇到的問題蚂踊;第二個就是并發(fā),但是搜索系統(tǒng)是沒辦法進行分庫分表笔宿,所以能做的就是索引切分犁钟;最后一點就是監(jiān)控,包括問題追蹤泼橘、日志系統(tǒng)和監(jiān)控系統(tǒng)涝动,那么為了解決這些問題,我們應(yīng)該怎么做炬灭?

首先醋粟,針對 Bug 問題,只能靠自動化運維去解決(這里也推薦使用 OneAPM 工具)重归;第二個就是高并發(fā)的問題米愿,目前主要是靠緩存和橫向擴展。而緩存和橫向擴展怎么應(yīng)用到系統(tǒng)中去鼻吮,這個很關(guān)鍵育苟。很多人也說可以換一種語言,比如講 Python 換成 C++狈网,但實際情況下宙搬,換語言并不能解決并發(fā)的問題笨腥,好的數(shù)據(jù)結(jié)構(gòu)的設(shè)計比換一種語言更能提高性能拓哺,所以一般解決高并發(fā)問題的也就是緩存和橫向擴展。

第三個就是使用用 FLUME 日志系統(tǒng)(Flume 是 Cloudera 提供的一個高可用的脖母,高可靠的士鸥,分布式的海量日志采集、聚合和傳輸?shù)南到y(tǒng)谆级,F(xiàn)lume 支持在日志系統(tǒng)中定制各類數(shù)據(jù)發(fā)送方烤礁,用于收集數(shù)據(jù)讼积;同時,F(xiàn)lume 提供對數(shù)據(jù)進行簡單處理脚仔,并寫到各種數(shù)據(jù)接受方(可定制)的能力)勤众。其實,F(xiàn)lume 會把集群上每一個節(jié)點的日志全都收集起來鲤脏,這樣做起來有兩個好處们颜,第一是現(xiàn)場出問題,可以先回滾出 Bug猎醇,然后進行查詢窥突。第二個就是對日志進行搜集,然后做用戶行為分析硫嘶,查看用戶點擊了多少次阻问,從何處導入的流量等等,從而便于更好的進行排序沦疾。

電商搜索引擎的架構(gòu)設(shè)計和性能優(yōu)化

然后講一下緩存的問題称近。一般搜索的緩存可能分為兩級緩存,據(jù)我觀察哮塞,像搜狗可能是使用頁面級緩存煌茬,而百度可能用的是索引級的緩存。比如在搜狗搜索一個詞彻桃,開始時可能需要 40 毫秒坛善,然后再搜的話,就可能一下子降到 1 毫秒邻眷。這就是頁面級緩存眠屎。而百度可能第一次搜索用了 40 毫秒,第二次就是 25 毫秒肆饶,它并不是把頁面給緩存下來改衩,而是將索引的倒排鏈緩存,級別其實是不一樣的驯镊。

電商搜索很多使用的是兩級緩存葫督,對于特別熱門的詞匯,我們可以做頁面級緩存板惑,而頁面級緩存的時間只有 15 秒到 20 秒橄镜。但是像價格這樣的東西不能緩存,需要前臺頁面去反拉價格冯乘。第二級就是索引級別的緩存洽胶,實際上也是自建的一個緩存系統(tǒng)。另外裆馒,排序也有緩存姊氓,因為排序的結(jié)果不太會有太大的變化丐怯。

電商搜索引擎的架構(gòu)設(shè)計和性能優(yōu)化

上圖是當當?shù)乃阉骷軜?gòu),這里有一個集群是做數(shù)據(jù)分析的翔横,上面?zhèn)錆M了數(shù)據(jù)读跷。

首先,集群之間采用什么樣的通訊方式禾唁?我們主要使用 ZMQ(這是一個簡單好用的傳輸層舔亭,像框架一樣的一個 socket library,使得 Socket 編程更加簡單蟀俊、簡潔和性能更高钦铺。是一個消息處理隊列庫,可在多個線程肢预、內(nèi)核和主機盒之間彈性伸縮)矛洞。原因其實只有一個,就是快烫映,非痴颖荆快,比較適合數(shù)據(jù)量比較大的業(yè)務(wù)锭沟。

如何避免冷啟動抽兆?

最后就是冷啟動的問題,這個問題是很多電商網(wǎng)站都很頭疼的問題族淮。尤其是隨著電商網(wǎng)站的商品數(shù)量達到一定量級的時候辫红,比如已經(jīng)上億了,像淘寶祝辣、天貓的話應(yīng)該更多贴妻。如果重建了一次索引需要啟動,或者新上線了一個業(yè)務(wù)模塊蝙斜,需要重啟系統(tǒng)名惩,是很麻煩的。

當然孕荠,當集群大了以后有很多方法娩鹉,比如分開啟動之類的,至于技術(shù)嘛稚伍,一般索引的加載都是使用 Lunix 標準的 MMAP(MMAP 將一個文件或者其它對象映射進內(nèi)存弯予。文件被映射到多個頁上,如果文件的大小不是所有頁的大小之和槐瑞,最后一個頁不被使用的空間將會清零熙涤。MMAP 在用戶空間映射調(diào)用系統(tǒng)中作用很大),這樣啟動速度會很快困檩,但是系統(tǒng)會有預(yù)熱時間祠挫,前面一些時間的查詢會比較慢

如果數(shù)據(jù)量不是特別大的話,而且現(xiàn)在內(nèi)存也那么便宜悼沿,完全可以將數(shù)據(jù)一次性讀入內(nèi)存等舔,因為 mmap 的操作畢竟性能沒有直接內(nèi)存來得快。

第三種的話糟趾,就是盡量減少做全量數(shù)據(jù)的頻率慌植,避免整個系統(tǒng)的重啟,這需要定期做一下索引的優(yōu)化义郑,把沒用的索引干掉蝶柿。

如果是新上了一個業(yè)務(wù)模塊需要重啟集群,這樣的事情最好不要發(fā)生非驮,這就是架構(gòu)有問題了交汤,將業(yè)務(wù)模塊變成外部的模塊或者插件進行上線才是正確的,不然每上線一個模塊需要重啟集群劫笙,這誰都受不了芙扎。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市填大,隨后出現(xiàn)的幾起案子戒洼,更是在濱河造成了極大的恐慌,老刑警劉巖允华,帶你破解...
    沈念sama閱讀 211,376評論 6 491
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件圈浇,死亡現(xiàn)場離奇詭異,居然都是意外死亡靴寂,警方通過查閱死者的電腦和手機汉额,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,126評論 2 385
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來榨汤,“玉大人蠕搜,你說我怎么就攤上這事∈蘸荆” “怎么了妓灌?”我有些...
    開封第一講書人閱讀 156,966評論 0 347
  • 文/不壞的土叔 我叫張陵,是天一觀的道長蜜宪。 經(jīng)常有香客問我虫埂,道長,這世上最難降的妖魔是什么圃验? 我笑而不...
    開封第一講書人閱讀 56,432評論 1 283
  • 正文 為了忘掉前任掉伏,我火速辦了婚禮,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘斧散。我一直安慰自己供常,他們只是感情好,可當我...
    茶點故事閱讀 65,519評論 6 385
  • 文/花漫 我一把揭開白布鸡捐。 她就那樣靜靜地躺著栈暇,像睡著了一般。 火紅的嫁衣襯著肌膚如雪箍镜。 梳的紋絲不亂的頭發(fā)上源祈,一...
    開封第一講書人閱讀 49,792評論 1 290
  • 那天,我揣著相機與錄音色迂,去河邊找鬼香缺。 笑死,一個胖子當著我的面吹牛歇僧,可吹牛的內(nèi)容都是我干的图张。 我是一名探鬼主播,決...
    沈念sama閱讀 38,933評論 3 406
  • 文/蒼蘭香墨 我猛地睜開眼馏慨,長吁一口氣:“原來是場噩夢啊……” “哼埂淮!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起写隶,我...
    開封第一講書人閱讀 37,701評論 0 266
  • 序言:老撾萬榮一對情侶失蹤倔撞,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后慕趴,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體痪蝇,經(jīng)...
    沈念sama閱讀 44,143評論 1 303
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 36,488評論 2 327
  • 正文 我和宋清朗相戀三年冕房,在試婚紗的時候發(fā)現(xiàn)自己被綠了躏啰。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 38,626評論 1 340
  • 序言:一個原本活蹦亂跳的男人離奇死亡耙册,死狀恐怖给僵,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情详拙,我是刑警寧澤帝际,帶...
    沈念sama閱讀 34,292評論 4 329
  • 正文 年R本政府宣布,位于F島的核電站饶辙,受9級特大地震影響蹲诀,放射性物質(zhì)發(fā)生泄漏。R本人自食惡果不足惜弃揽,卻給世界環(huán)境...
    茶點故事閱讀 39,896評論 3 313
  • 文/蒙蒙 一脯爪、第九天 我趴在偏房一處隱蔽的房頂上張望则北。 院中可真熱鬧,春花似錦痕慢、人聲如沸尚揣。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,742評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽惑艇。三九已至蒿辙,卻和暖如春拇泛,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背思灌。 一陣腳步聲響...
    開封第一講書人閱讀 31,977評論 1 265
  • 我被黑心中介騙來泰國打工俺叭, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人泰偿。 一個月前我還...
    沈念sama閱讀 46,324評論 2 360
  • 正文 我出身青樓熄守,卻偏偏與公主長得像,于是被迫代替她去往敵國和親耗跛。 傳聞我的和親對象是個殘疾皇子裕照,可洞房花燭夜當晚...
    茶點故事閱讀 43,494評論 2 348

推薦閱讀更多精彩內(nèi)容