Apache Doris 在美聯物業的資料倉庫應用實踐,助力傳統行業數字化革新!

語言: CN / TW / HK

導讀: 傳統行業面對數字化轉型往往會遇到很多困難,比如缺乏資料管理體系、資料需求開發流程冗長、煙囪式開發、過於依賴紙質化辦公等,美聯物業也有遇到類似的問題。本文主要介紹美聯物業基於 Apache Doris 在資料體系方面的建設,以及對資料倉庫搭建經驗進行的分享和介紹,旨在為資料量不大的傳統企業提供一些數倉思路,實現資料驅動業務,低成本、高效的進行數倉改造。

作者|美聯物業數倉負責人 謝幫桂

美聯物業屬於香港美聯集團成員,於 1973 年成立,並於 1995 年在香港聯合交易所掛牌上市(香港聯交所編號:1200),2008 年美聯工商鋪於主機板上市(香港聯交所編號:459), 成為擁有兩家上市公司的地產代理企業。擁有 40 餘載房地產銷售行業經驗,業務涵蓋中、小型住宅、豪宅及工商鋪,提供移民顧問、金融、測量、按揭轉介等服務,業務遍佈中國香港地區、中國澳門地區和中國內地等多個重要城市。

本文主要介紹關於美聯物業在資料體系方面的建設,以及對資料倉庫搭建經驗進行的分享和介紹,旨在為資料量不大的傳統企業提供一些數倉思路,實現資料驅動業務,低成本、高效的進行數倉改造。

考慮隱私政策,本文不涉及公司任何具體業務資料。

業務背景

美聯物業早在十多年前就已深入各城市開展房地產中介業務,資料體系的建設和發展與大多數傳統服務型公司類似,經歷過幾個階段時期,如下圖所示。

我們的資料來源於大大小小的子業務系統和部門手工報表資料等,存在歷史存量資料龐大,資料結構多樣複雜,資料質量差等普遍性問題。此外,早期業務邏輯處理多數是使用關係型資料庫 SQL Server 的儲存過程來實現,當業務流程稍作變更,就需要投入大量精力排查儲存過程並進行修改,使用及維護成本都比較高。

基於此背景,我們面臨的挑戰可以大致歸納為以下幾點:

  • 缺乏資料管理體系,統計口徑統一,已有資料無法降本複用。多部門、多系統、多欄位,命名隨意、表違反正規化結構混亂;對同一業務來源資料無法做到多份報表複用,反覆在不同報表編寫同一套計算邏輯。
  • 海量資料下效能不足,查詢響應慢。歷史大多數業務資料儲存在關係型資料庫中,分表分庫已無法做到上億資料秒級分析查詢。
  • 資料需求開發流程冗長、煙囪式開發。每當業務部門提出一個數據需求,資料開發就需要在多個系統之間進行資料相容編寫儲存過程,從而導致儲存過程的可移植性和可讀性都非常差。
  • 部門之間嚴重依賴文字文件處理工作,效率低下。由於長期的手工統計,使用者已形成習慣,導致對資訊系統的信任程度也比較低。

早期架構

針對上述的⼏個需求,我們在平臺建設的初期選⽤了 Hadoop、Hive、Spark 構建最初的離線數倉架構,也是比較普遍、常見的架構,運作原理不進行過多贅述。

我們資料體系主要服務物件以內部員工為主,如房產經紀人、後勤人員、行政人事、計算機部門,房產經紀在全國範圍內分佈廣泛,也是我們的主要服務物件。當前資料體系還無需面向 C 端使用者,因此在資料計算和資源方面的壓力並不大,早期基於 Hadoop 的架構可以滿足一部分基本的需求。但是隨著業務的不斷髮展、內部人員對於資料分析的複雜性、分析的效率也越來越高,該架構的弊端日益越發的明顯,主要體現為以下幾點:

  • 過於笨重:傳統公司的計算量和資料量並不大,使用 Hadoop 過於浪費。
  • 效率低下:T+1 的排程時效和指令碼,動輒需要花費 1 小時的計算時間匯入匯出,效率低、影響資料的開發工作。
  • 維護成本高:元件過多,排查故障鏈路過長,運維成本也很高,且部門同事之間熟悉各個元件需要大量學習和溝通成本。

新數倉架構

基於上述業務需求及痛點,我們開始了架構升級,並希望在這次升級中實現幾個目標:

  • 初步建立資料管理體系,搭建資料倉庫。
  • 搭建報表平臺和報表快速開發流程體系。
  • 實現資料需求能夠快速反應和交付(1小時內),查詢延遲不超過 10s。
  • 最小成本原則構建架構,支援滾動擴容。

技術選型

經過調研瞭解以及朋友推薦,我們瞭解到了 Apache Doris ,並很快與社群取得了聯絡,Apache Doris 的幾大優勢吸引了我們:

足夠簡單

美聯物業及大部分傳統公司的資料人員除了需要完成資料開發工作之外,還需要兼顧運維和架構規劃的工作。因此我們選擇數倉元件的第一原則就是"簡單",簡單主要包括兩個方面:

  • 使用簡單:Apache Doris 相容 MySQL 協議,支援標準 SQL,有利於開發效率和共識統一,此外,Doris 的 ETL 編寫指令碼主要使用 SQL進行開發,使用 MySQL 協議登陸使用,相容多數 MySQL 語法,提供豐富的資料分析函式,省去了 UDF 開發工作。
  • 架構簡單:Doris 的元件架構由 FE+BE 兩類程序組成,不依賴其他系統,升級擴容非常方便,故障排查鏈路非常清晰,有利於運維成本的降低。

極速效能

Doris 依託於列式儲存引擎、自動分割槽分桶、向量計算、多方面 Join 優化和物化檢視等功能的實現,可以覆蓋眾多場景的查詢優化,海量資料也能可以保證低延遲查詢,實現分鐘級或秒級響應。

極低成本

降本提效已經成為現如今企業發展的常態,免費的開源軟體就比較滿足我們的條件,另外基於 Doris 極簡的架構、語言的相容、豐富的生態等,為我們節省了不少的資源和人力的投入。並且 Doris 支援 PB 級別的儲存和分析,對於存量歷史資料較大、增量資料較少的公司來說,僅用 5-8 個節點就足以支撐上線使用。

社群活躍

截止目前,Apache Doris 已開源數年,並已支援全國超 1500 企業生產使用,其健壯性、穩定性不可否認。另外社群非常活躍,SelectDB 為社群組建了專職的技術支援團隊,任何問題均能快速反饋,提供無償技術支援,使用起來沒有後顧之憂。

執行架構

在對 Apache Doris 進一步測試驗證之後,我們完全摒棄了之前使用 Hadoop、Hive、Spark 體系建立的數倉,決定基於 Doris 對架構進行重構,以 Apache Doris 作為數倉主體進行開發:

  • 資料整合:利用 DataX、Flink CDC 和 Apache Doris 的 Multi Catalog 功能等進行資料整合。
  • 資料管理:利用 Apache Dolphinscheduler 進行指令碼開發的生命週期管理、多租戶人員的許可權管理、資料質量監察等。
  • 監控告警:採用 Grafana + Prometheus + Loki 進行監控告警,Doris 的各項監控指標可以在上面執行,解決了對元件資源和日誌的監控問題。
  • 資料服務:使用帆軟 Report 為使用者提供資料查詢和分析服務,帆軟支援表單製作和資料填報等功能,支援自助取數和自助分析。

資料模型

1)縱向分域

房地產中介行業的大資料主題大致如下,一般會根據這些主題進行數倉建模。建模主題域核心圍繞"企業使用者"、"客戶"、"房源"、"組織"等幾個業務實體展開,進行維度表和事實表的建立。

我們從前線到後勤,對業務資料匯流排進行了梳理,旨在整理業務實體和業務活動相關資料,如多個系統之間存在同一個業務實體,應統一為一個欄位。梳理業務匯流排有助於掌握公司整體資料結構,便於維度建模等工作。

下圖為我們簡單的梳理部分房地產中介行業的業務匯流排:

2)橫向分層

資料分層是最常見的 5 層結構主要是利用 Apache Doris + Apache DolphinScheduler 進行層級資料之間 DAG 指令碼排程。

儲存策略: 我們在 8 點到 24 點之間採用增量策略,0 點到 8 點執行全量策略。採用增量 + 全量的方式是為了在ODS 表因為記錄的歷史狀態欄位變更或者 CDC 出現數據未完全同步的情況下,可以及時進行全量補數修正。

3)增量策略

  1. where >= "業務時間-1天或-1小時"

增量的 SQL 語句不使用 where="業務時間當天"的原因是為了避免資料漂移情況發生,換言之,排程指令碼之間存在時間差,如 23:58:00 執行了指令碼,指令碼的執行週期是 10 分鐘/次,但是源庫最後一條資料 23:59:00 才進來,這時候 where="業務時間當天"就會將該資料漏掉。

  1. 每次跑增量指令碼前獲取表中最大的主鍵 ID 存入輔助表,where >= "輔助表記錄ID"

如果 Doris 表使用的是 Unique Key 模型,且恰好為組合主鍵,當主鍵組合在源表發生了變化,這時候 where >=" 業務時間-1天"會記錄該變化,把主鍵發生變化的資料 Load 進來,從而造成資料重複。而使用這種自增策略可有效避免該情況發生,且自增策略只適用於源表自帶業務自增主鍵的情況。

  1. 表分割槽

如面對日誌表等基於時間的自增資料,且歷史資料和狀態基本不會變更,資料量非常大,全量或快照計算壓力非常大的場景,這種場景需要對 Doris 表進行建表分割槽,每次增量進行分割槽替換操作即可,同時需要注意資料漂移情況。

4)全量策略

  1. Truncate Table 清空表插入

先清空表格後再把源表資料全量匯入,該方式適用於資料量較小的表格和凌晨沒有使用者使用系統的場景。

  1. ALTER TABLE tbl1 REPLACE WITH TABLE tbl2表替換

這種方式是一種原子操作,適合資料量大的全量表。每次執行指令碼前先 Create 一張資料結構相同的臨時表,把全量資料 Load 到臨時表,再執行表替換操作,可以進行無縫銜接。

應用實踐

業務模型

  • 業務模型是分鐘級排程 ETL
  • 初次部署建議配置:8 節點 2FE * 8BE 混合部署
  • 節點配置:32C * 60GB * 2TB SSD
  • 對於存量資料 TB 級、增量資料 GB 級的場景完全夠用,如有需要可以進行滾動擴容。

具體應用

  1. 離線資料和日誌資料整合利用 DataX 進行增量和全量排程,Datax 支援 CSV 格式和多種關係型資料庫的Redear,而 Doris 在很早之前就提供了 DataX Doris writer 聯結器。

  1. 實時統計部分藉助了 Flink CDC 對源表進行實時同步,利用 Doris 的物化檢視或者 Aggregate 模型表進行實時指標的彙總處理,因我們只有部分指標需要實時處理,不希望產生過多的資料庫連線和 Flink Job,因此我們使用 Dinky 的多源合併和整庫同步功能,也可以自己簡單實現一個Flink DataStream 多源合併任務,只通過一個 Job 可對多個 CDC 源表進行維護。值得一提的是, Flink CDC 和 Apache Doris 新版本支援 Schema Change 實時同步,在成本允許的前提下,可完全使用 CDC 的方式對 ODS 層進行改造。
EXECUTE CDCSOURCE demo_doris WITH (
  'connector' = 'mysql-cdc',
  'hostname' = '127.0.0.1',
  'port' = '3306',
  'username' = 'root',
  'password' = '123456',
  'checkpoint' = '10000',
  'scan.startup.mode' = 'initial',
  'parallelism' = '1',
  'table-name' = 'ods.ods_*,ods.ods_*',
  'sink.connector' = 'doris',
  'sink.fenodes' = '127.0.0.1:8030',
  'sink.username' = 'root',
  'sink.password' = '123456',
  'sink.doris.batch.size' = '1000',
  'sink.sink.max-retries' = '1',
  'sink.sink.batch.interval' = '60000',
  'sink.sink.db' = 'test',
  'sink.sink.properties.format' ='json',
  'sink.sink.properties.read_json_by_line' ='true',
  'sink.table.identifier' = '${schemaName}.${tableName}',
  'sink.sink.label-prefix' = '${schemaName}_${tableName}_1'
);
  1. 指令碼語言採用 Shell + SQL 或純 SQL 的形式,我們在 Apache DolphinScheduler 上進行指令碼生命週期管理和釋出,如 ODS 層,可以編寫通用的 DataX Job 檔案,通過傳參的方式將 DataX Job 檔案傳參執行源表匯入,無需在每一個源表編寫不同的DataX Job ,支援統一配置引數和程式碼內容,維護起來非常方便。另外我們在 DolphinsSheduler 上對 Doris 的 ETL 指令碼進行管理,還可以進行版本控制,能有效控制生產環境錯誤的發生,進行及時回滾。

  1. 釋出 ETL 指令碼後匯入資料,可直接在帆軟 Report 進行頁面製作,基於登陸賬號來控制頁面許可權,如需控制行級別、欄位級別許可權,可以製作全域性字典,利用 SQL 方式進行控制。Doris 完全支援對賬號的庫表許可權控制,這一點和 MySQL 的設定完全一樣,使用起來非常便捷。

除以上之外,在容災恢復、叢集監控、資料安全等方面也有應用,比如利用 Doris 備份實現容災恢復、Grafana+Loki 對叢集進行指標規則告警、Supervisor 對節點元件進行守護程序監控,開啟 Doris 審計日誌對執行 SQL 效率進行監控等,因篇幅限制,此處不進行詳細說明。

優化經驗

  1. 資料匯入

我們使用 DataX 進行離線資料匯入,DataX 採用的是 Stream Load 方式匯入,該方式可以通過引數控制匯入批次流量,DataX 匯入不需要藉助計算引擎,開箱即用的特點非常方便。另外,Stream Load 匯入是同步返回結果的,其他匯入方式一般是非同步返回結果,針對我們的架構來說,在 Dolphinscheduler上執行非同步匯入資料會誤以為該指令碼已經執行成功,影響其正常執行。如採用其他非同步匯入方式,建議在 Shell 指令碼中 執行show load 再利用正則過濾狀態進行判斷。

  1. 資料模型

我們所有層級的表模型大部分採用 Unique Key 模型,該模型可有效保證資料指令碼的結果冪等性,Unique Key 模型可以完美解決上游資料重複的問題,大家可以根據業務模式來選擇不同的模型建表。

  1. 外部資料來源讀取

Catalog 方式可以使用 JDBC 外表連線,還可以對 Doris 生產叢集資料進行讀取,便於生產資料直接 Load 進測試伺服器進行測試。另外,新版支援多資料來源的 Catalog,可以基於 Catalog 對 ODS 層進行改造,無需使用 DataX 對ODS 層進行匯入。

  1. 查詢優化

儘量把非字元型別(如 int 型別、where 條件)中最常用的欄位放在前排 36 個位元組內,在點查表過程中可以快速過濾這些欄位(毫秒級別),可以充分利用該特性進行資料表輸出。

  1. 資料字典

利用 Doris 自帶的 information_schema 元資料製作簡單的資料字典,這在還未建立資料治理體系前非常重要,當部門人數較多的時候,溝通成本成為發展過程中最大的“攔路虎”,利用資料字典可快速對錶格和欄位的全域性查詢和釋義,最低成本形成數倉人員的資料規範,減少人員溝通成本,提高開發效率。

架構收益

  • 自動取數導數:資料倉庫的明細表可以定時進行取數、導數,自助組合維度進行分析。
  • 效率提升:T+1 的離線時效從小時計降低至分鐘級
  • 查詢延遲降低:面對上億行資料的表,利用 Doris 在索引和點查方面的能力,實現即席查詢 1 秒內響應,複雜查詢 5 秒內響應。
  • 運維成本降低:從資料整合到資料服務,只需維護少陣列件就可以實現整體鏈路高效管理。
  • 資料管理體系:Doris 數倉的搭建,使得資料管理體系初步形成,資料資產得以規範化的沉澱。
  • 資源節省:只用了少數伺服器,快速搭建起一套資料倉庫,成功實現降本賦能。同時 Doris 超高的壓縮比,將資料壓縮了 70%,相較於 Hadoop 來說,儲存資源的消耗大幅降低。

總結與規劃

目前我們已經完成數倉建設的初期目標,未來我們有計劃基於 Apache Doris 進行中臺化的改造,同時 Apache Doris在使用者畫像和人群圈選場景的能力十分強悍,支援 Bitmap 等格式進行匯入和轉換,提供了豐富的 Bitmap 分析函式等,後續我們也將利用這部分能力進行客戶群體分析,加快數字化轉型。

最後,感謝 Apache Doris 社群和 SelectDB 團隊對美聯物業的快速響應和無償支援,希望 Doris 發展越來越好,也希望更多的企業可以嘗試使用 Apache Doris。

「其他文章」