OLAP | 京東 OLAP 實踐之路

分享嘉賓:李陽 京東 資深研發(fā)工程師
編輯整理:連志鵬
出品社區(qū):DataFunTalk
導讀:本文主要介紹京東在構建OLAP從無到有各環(huán)節(jié)考慮的重點,由需求場景出發(fā),剖析當前存在的問題,并提供解決方案,最后介紹OLAP的發(fā)展過程。
▌需求場景
1. 京東數(shù)據(jù)入口

① 業(yè)務數(shù)據(jù):訂單
京東作為一家電商企業(yè),擁有自營商品銷售平臺和全鏈路物流通道。首先第一數(shù)據(jù)入口就是訂單,針對不同訂單進行多維度分析,比如:對訂單分析、對店鋪分析、對商品品類分析等等。
展開對訂單維度來說,因為我們作為電商,訂單是非常重要的一個維度分析和數(shù)據(jù)支撐,所以常結合訂單SKU,計算品類下單轉化率。
② 行為數(shù)據(jù):點擊和搜索
用戶在京東商城的操作,比如點擊和搜索,我們會將用戶的這些行為結合訂單信息,來做一些分析,比如分析商品的熱銷和滯銷程度,以及轉化情況,最常見的就是漏斗分析,來計算轉化率。
③ 廣告和推薦
基于用戶下單情況,我們會推送廣告和推薦給到用戶,然后進行計算,分析廣告觸達相關情況。
④ 監(jiān)控指標
對于監(jiān)控指標,是我們一個巨大的場景,因為在我們這里,除了用戶行為數(shù)據(jù),還有很多運維的數(shù)據(jù)也需要管理起來。
2. 京東數(shù)據(jù)出口

京東的數(shù)據(jù)出口,主要分類兩大類:離線和實時
① 離線
月報和周報
典型離線場景:財務報表經(jīng)常需要月報周報。
機器學習
會用到大量的一些訓練數(shù)據(jù),這些數(shù)據(jù)的生成也會用到OLAP的一些特性來把數(shù)據(jù)進行分析,產(chǎn)生一些訓練的數(shù)據(jù)。
② 實時
交互式查詢
非研發(fā)同事,比如營運分析人員,經(jīng)常需要臨時查詢業(yè)務數(shù)據(jù),比如查詢最近一周訂單的匯總以及明細數(shù)據(jù),對這些數(shù)據(jù)進行分析,輔助決策。
實時大屏展示
平臺做大促或者實時監(jiān)控運營情況,會依照大屏的指標,實時動態(tài)調(diào)整資源。比如營銷策略、廣告費投入、供應鏈庫存。尤其重要的是,在大促銷的時候,可以進行動態(tài)資源的調(diào)整,比如車輛資源調(diào)度、根據(jù)促銷效果決策活動是否需要進行調(diào)整等。
▌問題與解決方案
以上是京東的部分業(yè)務場景,和大多數(shù)闡述數(shù)據(jù)架構不同,我們本次將數(shù)據(jù)搭建的過程分為4個方面:數(shù)據(jù)怎么寫進來;寫進來以后怎么進行存儲;存儲以后又怎么進行取用;最后是如何管理前3個環(huán)節(jié)。
1. 寫

① 數(shù)據(jù)源及數(shù)據(jù)結構多樣性
現(xiàn)狀:
數(shù)據(jù)源來源多樣化:文件系統(tǒng)(本地文件&分布式系統(tǒng)文件)& MQ
本地文件,比如說服務器本地的數(shù)據(jù),直接導入進來
數(shù)據(jù)量比較大時,在用戶本地存不了這么大的數(shù)據(jù)量,會將數(shù)據(jù)存儲在HDFS上
Kafka或者MQ數(shù)據(jù),上游將產(chǎn)生的數(shù)據(jù)直接存儲到消息隊列中,在京東內(nèi)部,這種MQ的系統(tǒng)有多個,但是我們需要統(tǒng)一進行接入
數(shù)據(jù)結構的多樣化,最常見:CSV、TSV、JSON、AVRO、PARQUET、BINLOG等
問題:
多種數(shù)據(jù)源及數(shù)據(jù)類型,對于開發(fā)人員來說,進行數(shù)據(jù)分析的成本相對比較高,我們希望分析人員,只需要專注于業(yè)務邏輯本身,直接進行SQL查詢,而無需關心數(shù)據(jù)來源。
解決方案:
建立統(tǒng)一導入數(shù)據(jù)服務,將多樣化的數(shù)據(jù)源和數(shù)據(jù)類型進行封裝,通過給用戶配置權限,用戶只需要在可視化界面直接進行操作,即可完成數(shù)據(jù)的導入操作,具體的操作也是比較簡單,以MQ數(shù)據(jù)源舉例:
選擇數(shù)據(jù)源的topic
指定導入的目標源
選擇數(shù)據(jù)格式
選擇對應的數(shù)據(jù)字段類型等等
② 數(shù)據(jù)的時效性
現(xiàn)狀:
實時的數(shù)據(jù)需要實時進行計算和展示;離線的數(shù)據(jù),可以定時的推送并計算一次,對時效的要求比較低。
問題:
如何保證實時和離線數(shù)據(jù)的時效性,且不會相互影響?
解決方案:
對實時集群和離線集群進行物理隔離,防止互相干擾,這樣做的好處有:
實時和離線對于資源的需求不同,實時數(shù)據(jù)寫入非常頻繁,而離線的數(shù)據(jù)只是在指定運行的時間點比較多,區(qū)分開便于管理。
③ 數(shù)據(jù)的更新和刪除
問題:
對于OLAP的架構來說,如何做到既要查詢搜索又要更新呢?
解決方案:
數(shù)據(jù)更新,采用覆蓋寫的方案。以訂單為例,用戶下了一個訂單1,此時下單狀態(tài)為1,后面用戶進行了支付操作,訂單狀態(tài)為2,那么我們會重新推送一條全量的數(shù)據(jù),只是狀態(tài)的字段值發(fā)生看變化。
數(shù)據(jù)刪除,采用刪除分區(qū)然后重新導入這個分區(qū)數(shù)據(jù),或者采用版本管理方式,因為通過新版本的數(shù)據(jù)會覆蓋原來的版本,起到刪除的作用。
③ 高吞吐
問題:
以京東現(xiàn)在的體量,每天的數(shù)據(jù)是很大的,如何解決高吞吐問題呢?
解決方案:
機房配置萬兆網(wǎng)絡,另外對于實時場景,配備SSD;離線場景,配備HDD。
2. 存

① 海量數(shù)據(jù)
問題:
京東的數(shù)據(jù),TB數(shù)據(jù)量是非常常見的,有些時候會達到PB級別,那么采用單機的方式肯定是行不通的,那么如何解決數(shù)據(jù)存儲的問題呢?
解決方案:
采用分布式解決大規(guī)模數(shù)據(jù)的問題。
為了提高效率,采用了列式存儲,對后續(xù)指標的計算效率也有提升,其實在OLAP的架構中,大多數(shù)都是列式存儲。
采用不同類別的壓縮方式,比如snappy等。
② 容錯性
問題:
數(shù)據(jù)現(xiàn)在是科技類企業(yè)非常重要的資產(chǎn),那么如何保障數(shù)據(jù)的安全性性呢?
解決方案:
其一:多副本的容錯方式,我們的OLAP采用三副本的方式,所以其中1個或2個副本損壞或遷移時做擴容都比較容易處理。
其二:RAID獨立磁盤冗余陣列(RAID,redundant array of independent disks),因為磁盤金屬機器經(jīng)常會壞,加上有一些機器過保存在損壞的風險,所以我們也通過raid解決一部分數(shù)據(jù)容錯性的問題,防止磁盤壞掉之后整個機器不能提供服務的情況。
③ 一致性
解決方案:
解決數(shù)據(jù)的一致性的問題,需要使用到分布式協(xié)調(diào)和本地事務機制。
分布式協(xié)調(diào),比如zookeeper
本地事務機制:對于本地的提交,是否通過事務來保證數(shù)據(jù)的一致性
通過兩者的結合,來實現(xiàn)數(shù)據(jù)的一致性。
3. 讀

① 查詢速度
問題:
數(shù)據(jù)存儲到系統(tǒng)中以后,如何高效的進行取用呢?
解決方案:
通用方式,數(shù)據(jù)進行分區(qū)分片,在很多場景,對數(shù)據(jù)的分析都是按照時間進行分區(qū),分區(qū)以后,再進行分片或者分桶。
比如:訂單信息,我們可能按天查詢,那么就可以按照實際日期進行分區(qū);比如,存儲10年的數(shù)據(jù),不可能全部查詢,我們按照統(tǒng)計則按月進行分區(qū)。
預聚合,提前進行預計算,減少一次性計算的數(shù)據(jù)量,提高性能。
索引,大部分場景下會使用索引,比如做明細查詢,可能會到hash索引、betree、范圍查詢或者倒排。
物化視圖,其實和預聚合的功能類似,數(shù)據(jù)進入到物化視圖中時,提前進行一些預計算。
② 易用性
問題:
如何實現(xiàn)系統(tǒng)的易用性?
解決方案:
需要OLAP系統(tǒng)兼容JDBC和ODBC,同時支持標準的SQL。
提供界面化的操作,這種方式可以避免所有的運營分析人員都具備Mysql等數(shù)據(jù)庫的環(huán)境,可以直接登入圖形化界面進行查詢的操作。
③ QPS
問題:
如何提高QPS?
解決方案:
緩存,使用doris時,增加比如partitioncache,或者結果級緩存,或者分區(qū)緩存機制來提升查詢效率。
多副本,設置多副本的方式,通過犧牲部分存儲空間,來提升QPS,但是這個效果有限。
提升機器的規(guī)模。
4. 管理

現(xiàn)狀:
早期我們碰到磁盤壞了,搞得手忙腳亂,替換磁盤或者是下機器操作時間很長,而且這個操作完成之后還涉及重新平衡數(shù)據(jù)或者數(shù)據(jù)遷移,這個過程非常麻煩。
問題:
如何降低運維成本?
解決方案:
建設監(jiān)控和報警機制,進行提前預防。
優(yōu)化節(jié)點的下線,在京東系統(tǒng)中,有兩種方式:
方式1:通過黑名單的方式,如果監(jiān)控到某個節(jié)點經(jīng)常不健康,我們會把它納入黑名單,并將他踢下線了。
方式2:通過腳本操作,但是從最開始我們需要替換一個節(jié)點,估計從發(fā)現(xiàn)到替換完成得三小時,現(xiàn)在通過一些比較自動化的東西,現(xiàn)在大概十分鐘左右能做到一個節(jié)點的替換。
▌發(fā)展歷程
1.0時代

1.0時代的場景比較少,數(shù)據(jù)量也比較少,主要是訂單相關的一些數(shù)據(jù),分析通過關系型數(shù)據(jù)庫就能搞定,比如說oracle或者mysql。
可通過數(shù)據(jù)儲備同步到備庫做分析,或者mysql一個是slave庫,主庫做一些利用線上業(yè)務,然后備庫對存貨的一些分析和查詢。
2.0時代

到了2.0場景,不再是簡單處理訂單問題,還要處理物流、供應鏈、客服、支付等等場景。
場景大增,數(shù)據(jù)量也爆發(fā)式增長,從原來的G到現(xiàn)在的TB甚至PB級別。傳統(tǒng)關系性數(shù)據(jù)庫,已經(jīng)不能滿足需求了。
這個時候我們開始搭建了離線數(shù)倉,在數(shù)倉中進行分析,主要用Hive和Spark進行計算,數(shù)據(jù)都是T-1,臨時查詢數(shù)據(jù)的體驗非常差,需要耗時分鐘級別且還是昨天的數(shù)據(jù)。
3.0時代

為提升查詢數(shù)據(jù)的速度和數(shù)據(jù)的時效性,開始做實時查詢。我們現(xiàn)在使用統(tǒng)一OLAP服務,從最開始使用Kylin處理一些離線的業(yè)務,到現(xiàn)在我們用了doris和clickhouse結合起來,同時處理實時和離線,統(tǒng)一服務接口,對用戶和開發(fā)人員開放。
同時針對不同的業(yè)務,提供不同的計算引擎,我們現(xiàn)在提供一個整體打包解決方案,業(yè)務只需要在OLAP的服務上,進行統(tǒng)一部署到數(shù)據(jù)技術平臺即可,大大減少了開發(fā)成本。
未來規(guī)劃

① 管理平臺優(yōu)化
ClickHouse的動態(tài)伸縮。
智能化運維。智能優(yōu)化節(jié)點上下線或者數(shù)據(jù)均衡這些方面的工作。主要想要通過減少人工干預操作,降低時間的浪費。在京東的系統(tǒng)中,現(xiàn)在擁有上千臺的服務器,如果一直由人工來處理的話,那么成本非常高。
② 優(yōu)化查詢速度
優(yōu)化實時計算緩存。在doris中,使用partitioncacahe或者sqlcache在離線場景中比較有效,后續(xù)將考慮在實時計算中引入緩存進行優(yōu)化。
索引智能化管理。索引的引擎有非常多種,如果需要開發(fā)人員了解所有的引擎,學習成本是比較高的,我們能不能做成智能化的索引引擎呢?這樣的話用戶不需要再去關心類似的一個索引怎么建的問題,而是我們在通過用戶的一些查詢行為分析,自動的來給他做索引的創(chuàng)建,這樣簡化工作成本,讓開發(fā)人員有更多的心思去做好運營和分析。
▌問答環(huán)節(jié)
Q1:請問老師貴司有用過druid引擎嗎?
A1:沒有,我們調(diào)研發(fā)現(xiàn),第一,druid對sql的支持不是很友好;第二,druid擅長于持續(xù)性的數(shù)據(jù)場景,但是京東訂單是一個頻繁發(fā)生狀態(tài)變化的一個場景,它是不太好處理的,所以當時我們也沒有選druid。
Q2:clickhouse和doris如何根據(jù)業(yè)務場景選型,有哪些坑?
A2:
第一,查詢性能:在查詢表不多即沒有太多表關聯(lián)情況下,clickhouse查詢速度比較快,但是在做大表關聯(lián)查詢時,doris的性能會好于clickhouse。
第二,QPS:clickhouse是在極限使用CPU的性能,但是doris的QPS性能在某些場景下會比clickhouse好。
第三,運維成本:doris的運維成本會小于clickhouse,至少現(xiàn)在對我們來看,因為它會有節(jié)點自動上下線擴容收容會很方便,但是clickhouse做這個方面比較麻煩。
第四,數(shù)據(jù)更新:clickhouse數(shù)據(jù)更新的引擎有三種,用戶在使用的時候比較麻煩,但是doris,它直接進行數(shù)據(jù)覆蓋,就能做到一個更新,操作更方便。
Q3:doris和clickhouse是自動選擇,還是需要用戶自己去選,如果是自動選的話,識別機制是什么樣的?
A3:目前還沒有做到自動選。當前先整體提供解決方案,我們?yōu)橛脩籼峁┘夹g支撐,未來可能會想著如何去打通統(tǒng)一化,因為它的模型創(chuàng)建不太一樣,它的sql是有差異的。
Q4:數(shù)據(jù)接入CK方面,京東目前是什么樣的方案?
A4:目前有兩條路線。
一個是用戶自己業(yè)務側接入,因為有些歷史原因,用戶他已經(jīng)用了很久的clickhouse,他自己有比較成熟的一套接入系統(tǒng)。
一個是使用clickhouse來接入,不管是從離線還是從kafka中,這種方式是我們在平臺側,在平臺側開發(fā)了統(tǒng)一的OLAP服務,用戶可以上面操作。就如前面所說,用戶選擇數(shù)據(jù)源,再選一個目標源,點擊它執(zhí)行導入,就可以完成。
在文末分享、點贊、在看,給個3連擊唄~

李陽
京東 | 資深研發(fā)工程師
關于我們:
DataFunTalk 專注于大數(shù)據(jù)、人工智能技術應用的分享與交流。發(fā)起于2017年,在北京、上海、深圳、杭州等城市舉辦超過100場線下沙龍、論壇及峰會,已邀請近600位專家和學者參與分享。其公眾號 DataFunTalk 累計生產(chǎn)原創(chuàng)文章300+,百萬+閱讀,10萬+精準粉絲。
