一、impala + kudu一些優化心得
用了幾次impala + kudu做大資料實時計算場景,一路踏坑過來,這裡分享踏坑經驗
- 一開始需要全量導入kudu,這時候我們先用sqoop把關系資料庫資料導入臨時表,再用impala從臨時表導入kudu目标表
由于sqoop從關系型資料直接以parquet格式導入hive會有問題,這裡預設hive的表都是txt格式;每次導完到臨時表,需要做invalidate metadata 表操作,不然後面直接導入kudu的時候會查不到資料
- 除了查詢,建議所有impala操作都在impala-shell而不在hue上面執行
- impala并發寫入kudu的時候,資料量比較大的時候
這時候kudu配置參數 --memory_limit_hard_bytes能大點就大點,因為kudu寫入首先儲存再記憶體裡面,到一定閥值才溢寫到磁盤,這個是直接最能提高寫的方法;
當然不是所有機器都有那麼多資源,可以把--maintenance_manager_num_threads 這個參數稍微調大,需要調試,提高資料從記憶體寫入磁盤的效率
- impala查詢kudu
首先所有表做完全量的etl操作,必須得執行compute stats 表名,不然impala執行sql生成的計劃執行數評估的記憶體不準确,容易評估錯誤導緻實際執行不了
kudu表最好不要做任何壓縮,保證原始掃描性能發揮最好;假如對查詢性能要求比存儲要求高的話;大部分企業對實時查詢效率要求高,而且存儲成本畢竟低;
kudu針對大表要做好分區,最好range和hash一起使用,前提是主鍵列包含能hash的id,但range分區一定要做好,經驗告訴我一般是基于時間;
查詢慢的sql,一般要拿出來;友善的話做下explain,看下kudu有沒有過濾部分資料關鍵字kudu predicates;假如sql沒問題,那在impala-shell執行這個sql,最後執行summray指令,重點檢視單點峰值記憶體和時間比較大的點,對相關的表做優化,解決資料傾斜問題
- kudu資料删除
大表不要delete,不要猶豫直接drop,在create吧;磁盤空間會釋放的
- 關于impala + kudu 和 impala + parquet
網上很多分析impala + kudu 要比 impala + parquet 優越很多;誰信誰XB;
首先兩個解決的場景不一樣,kudu一般解決實時,hive解決的是離線(通常是T + 1或者 T -1)
hive基于hdfs,hdfs已經提供一套較為完善的存儲機制,底層資料和檔案操作便利;安全性,可擴充性都比kudu強很多,最重要parquet + impala效率要比kudu高,數倉首選是它
kudu最大優勢是能做類似關系型資料庫一樣的操作,insert, update, delete,這樣熱點的資料可以存儲在kudu裡面并随時做更新
- 最後談到的實時同步工具
同步工具我們這裡使用streamsets,一個拖拉拽的工具,非常好用;但記憶體使用率高,通過jconsole我們發現,所有任務同時啟動;JVM新生代的内容幾乎都跑到老年代了,GC沒來的及,就記憶體溢出了;後面單獨拿幾台伺服器出來做這個ETL工具,jvm配置G1垃圾回收器
二、問題分析-kudu資料庫
1.問題聚焦到kudu資料庫上,從資料庫原理,特别是kudu處理請求的入手
[[email protected] ~]# ps aux | grep 145440
kudu 145440 202 37.2 34052208 24452396 ? Sl Feb28 52555:59 /usr/lib/kudu/sbin/kudu-tserver --server_dump_info_path=/var/run/kudu/kudu-tserver-kudu.json --flagfile=/etc/kudu/conf/tserver.gflagfile
2.kudu用LSM 索引檔案,組織資料,存儲。寫入過程先寫記憶體,再刷磁盤。data+log 形式。WAL。
3.kudu 先把資料寫記憶體(髒資料),再寫log(WAL)。随着記憶體中髒資料不斷增加,kudu有一套機制會刷髒資料。
4.大量資料寫入kudu,kudu處理不及時,造成寫入失敗和寫入慢,一定出在kudu寫資料 的瓶頸上,寫資料的吞吐量不高。
5.寫入吞吐量達到瓶頸,需要找出瓶頸點。 從系統架構上看,一個是軟體問題,一個是硬體問題。
6.檢視kudu資料和log目錄,發現 兩個目錄(檔案),都存放到了ssd磁盤上。
7.檢視該ssd盤,iostat 發現 磁盤吞吐量沒有達到其極限。io有的是資源,隻是kudu沒有充分利用到ssd寫入能力。
8.因為ssd(sas接口,eMLC),随機iops和順序iops性能很高,随機和順序讀寫 吞吐量 非常大。 而現在寫入量很低,util%也非常低。
[[email protected] ~]# iostat -x 1 100
Linux 3.10.0-514.el7.x86_64 (realtime-1) 03/17/2020 _x86_64_ (64 CPU)
avg-cpu: %user %nice %system %iowait %steal %idle
2.66 0.00 0.46 0.04 0.00 96.84
Device: rrqm/s wrqm/s r/s w/s rkB/s wkB/s avgrq-sz avgqu-sz await r_await w_await svctm %util
sdb 0.00 5.00 0.00 2.00 0.00 28.00 28.00 0.00 0.00 0.00 0.00 0.00 0.00
sda 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00
sdc 0.00 0.00 0.00 6.00 0.00 24.00 8.00 0.00 0.00 0.00 0.00 0.00 0.00
sdd 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00
9.顯然,kudu系統,沒有充分利用完系統硬體性能。
大量資料寫入,記憶體中dirty data堆積,不能flush到磁盤。(kudu刷髒資料中也很複雜,這裡不詳述)。記憶體使用量超過配置參數限制,導緻kudu拒絕寫入新資料。
可是ssd盤的處理能力,沒用被kudu充分利用到 %util 基本都是0。
三、問題解決-kudu調優
1,Kudu Tablet Servers 參數調節
Flag | Default | Modify After | 描述 |
---|---|---|---|
–block_cache_capacity_mb | 512 | 12G | 配置設定給Kudu Tablet伺服器塊緩存的最大記憶體量。(雖然較高的值有助于提高讀寫性能,但是不要将 block_cache_capacity_mb 提高到記憶體壓力門檻值以上,因為這将導緻即使寫吞吐量很低,Kudu也會頻繁重新整理,建議将block_cache_capacity_mb保持在記憶體壓力門檻值的50%以下) 提高讀寫性能, 改值建議為 memory_limit_hard_bytes 的 30% 到 50%. |
–-memory_limit_hard_bytes | 4294967296 | 42G | 寫性能,控制kudu最多使用多少記憶體,在開始拒絕所有輸入的寫之前,Tablet Server 可以消耗的最大記憶體量。(根據機器記憶體去調整,如果主機有更多的記憶體可供Kudu使用,那麼建議設定大一點。根據系統總記憶體自動調整大小的值為0,值-1禁用所有記憶體限制,機關:bytes),,Tablet Server在批量寫入資料時并非實時寫入磁盤,而是先Cache在記憶體中,在flush到磁盤。這個值設定過小時,會造成Kudu資料寫入性能顯著下降。對于寫入性能要求比較高的叢集,建議設定更大的值 建議是機器總記憶體的百分之80,master的記憶體量建議是2G, 因為Kudu 的4台主機均為網絡增強性,而Kudu本身對網絡IO要求較高,應将這4台主機應均服務于Kudu,是以将2/3的記憶體配置設定給kudu使用。後期PRO環境在修改hostname時,移除其他節點,對節點進行調整。 |
–maintenance_manager_num_threads | 1 | 24 | 維護管理器線程池的大小。對于旋轉磁盤,線程數不應超過裝置數。(官網建議的維護管理器線程數是資料目錄的3倍) 預設為1,調成24 (我們雖然是單塊盤,但是ssd) (機械盤:一個資料盤,配置設定一個1,幾個資料盤配幾個) |
–default_num_replicas | 3 | 每個tablet的預設副本數 | |
–log_dir | /tmp | 存放Tablet Server 日志檔案 | |
–memory_pressure_percentage | |||
–flush_threshold_mb | 這個在低版本可以作為調優依據,現在系統預設也是可以的,不用調也可以。 | ||
–memory_limit_soft_percentage | 可使用記憶體比例,如果髒資料特别大,kudu總記憶體超過一定限制,kudu就拒絕寫入了,因為他有太多髒資料要刷磁盤了,但是髒資料太多,超過,或者即将超過允許使用的記憶體總數,那麼就拒絕寫入了 | ||
max_clock_sync_error_usec | 10000000 | 20000000 | 設定ntp伺服器的時間誤差不超過20s(預設是10s) |
2,Kudu實體記憶體背壓解決
官網:https://kudu.apache.org/docs/troubleshooting.html#memory_limits
盡管官網給出了參數調節的說明,但在實際情況中, 當出現Kudu背壓時, 所有業務均停掉, 而Kudu占用記憶體并沒有及時下降, 導緻資料無法寫入使業務癱瘓.
這一原因目前并沒有得到很好的解決方案, 但對以上參數的調節可盡量避免該錯誤的發生, 後期持續更新.
不成熟的方案: 檢視各tablet server 上tablet 的記憶體使用情況, 查找記憶體使用較多的tablet 下的 table, 将該table 資料備份後删除, 使記憶體快速降低, 避免影響全局業務.
jbd2引起IO過高,導緻KUDU 平均負載超載,隻有重新開機kudu
3.根據生産環境主機配置和實際業務需求參考 (調優),調大後重新開機kudu,再看效果,
4.調大後,再看kudu利用ssd硬體能力,寫入吞吐量達到152MB,是之前的100倍。
Device: rrqm/s wrqm/s r/s w/s rkB/s wkB/s avgrq-sz avgqu-sz await r_await w_await svctm %util
sdb 0.00 8380.00 427.00 3078.00 6988.00 152704.00 91.12 31.13 8.88 20.23 7.30 0.25 86.30
sda 0.00 0.00 1.00 1.00 4.00 4.00 8.00 0.00 1.00 2.00 0.00 1.00 0.20
sdc 0.00 0.00 1.00 6.00 40.00 24.00 18.29 0.01 0.86 0.00 1.00 0.86 0.60
sdd 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00
dm-0 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00
dm-1 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00 0.00
5.初略估計,每秒 5-10萬 并發沒問題,對應處理事件數/s 是之前 100倍以上,吞吐率 100倍。
6.再次打開zepplin後,實時資料立刻出來的,前端顯示正常。
四、kudu問題延續分析
查這個問題,看了官網和google了幾個case。
1.kudu重新開機後需要做一些redo和undo操作,特别是需要重新組織(整理)資料,啟動會非常慢。有兩個參數特别重要:
num_tablets_to_delete_simultaneously 預設為1,調成 24
num_tablets_to_open_simultaneously 預設為1,調成 24
可以看看這個 https://www.mail-archive.com/[email protected]/msg00307.html
2.針對kudu寫入能力的性能測試,通過幾個參數觀察 qps,latency,error_rate
https://kudu.apache.org/2016/04/26/ycsb.html
裡面特别提到 flush_threshold_mb 調成20G,效果顯著,但是我沒有測過。
3.寫入性能差,寫入失敗,有的同學說是記憶體不足的問題,需要加記憶體100G。
這個思路完全錯誤,如果是讀性能差,加記憶體,寫入差要分析kudu寫入資料過程,分析軟體、硬體。
加記憶體有用,但是加完記憶體後,隻會将髒資料在記憶體中堆積的越來越多。并沒有落盤。
完整的思路是,軟體->作業系統->硬體 這三層來展開分析。軟體本身差,作業系統(比如核心參數問題)問題,硬體瓶頸。這麼去分析。