天天看點

Kafka實戰(七) - 優雅地部署 Kafka 叢集1 作業系統 - OS2 磁盤3 帶寬總結參考

既然是叢集,必然有多個Kafka節點,隻有單節點構成的Kafka僞叢集隻能用于日常測試,不可能滿足線上生産需求。

真正的線上環境需要考量各種因素,結合自身的業務需求而制定。看一些考慮因素(以下順序,可是分了順序的哦)

1 作業系統 - OS

可能你會問Kafka不是JVM上的大資料架構嗎?Java又是跨平台的語言,把Kafka安裝到不同的作業系統上會有什麼差別嗎?

差別相當大!

确實,Kafka由Scala/Java編寫,編譯後源碼就是“.class”檔案。

本來部署到哪個OS應該一樣,但是不同OS的差異還是給Kafka叢集帶來了相當大的影響。

毋庸置疑,部署在Linux上的生産環境是最多的。

考慮作業系統與Kafka的适配性,Linux系統顯然要比其他兩個特别是Windows系統更加适合部署Kafka。可具體原因你能談笑風生嗎?

1.1 I/O模型

I/O模型可以近似認為I/O模型就是OS執行I/O指令的方法。

主流的I/O模型通常有5種類型:

  1. 阻塞式I/O

    e.g. Java中Socket的阻塞模式

  2. 非阻塞式I/O

    e.g. Java中Socket的非阻塞模式

  3. I/O多路複用

    e.g. Linux中的系統調用

    select

    函數
  4. 信号驅動I/O

    e.g. epoll系統調用則介于第三種和第四種模型之間

  5. 異步I/O

    e.g. 很少有Linux支援,反而Windows系統提供了一個叫IOCP線程模型屬于該類

我在這裡不詳細展開每一種模型的實作細節,因為那不是本文重點。

言歸正傳,I/O模型與Kafka的關系幾何?

Kafka Client 底層使用了Java的selector,而selector

  • 在Linux上的實作機制是epoll
  • 在Windows平台上的實作機制是select

是以在這一點上将Kafka部署在Linux上是有優勢的,能夠獲得更高效的I/O性能。

1.2 資料網絡傳輸效率

Kafka生産和消費的消息都是通過網絡傳輸的,而消息儲存在哪裡呢?

肯定是磁盤!

故Kafka需要在磁盤和網絡間進行大量資料傳輸。

Linux有個零拷貝(Zero Copy)技術,就是當資料在磁盤和網絡進行傳輸時避免昂貴核心态資料拷貝進而實作快速資料傳輸。Linux平台實作了這樣的零拷貝機制,但有些令人遺憾的是在Windows平台上必須要等到Java 8的60更新版本才能“享受”到。

一句話,在Linux部署Kafka能夠享受到零拷貝技術所帶來的快速資料傳輸特性帶來的極緻快感。

1.3 社群生态

社群目前對Windows平台上發現的Kafka Bug不做任何承諾。是以,Windows平台上部署Kafka隻适合于個人測試或用于功能驗證,千萬不要應用于生産環境。

2 磁盤

2.1 靈魂拷問:機械硬碟 or 固态硬碟

  • 前者便宜且容量大,但易壞!
  • 後者性能優勢大,但是貴!

建議是使用普通機械硬碟即可。

  • Kafka雖然大量使用磁盤,可多是順序讀寫操作,一定程度上規避了機械磁盤最大的劣勢,即随機讀寫慢。從這一點上來說,使用SSD并沒有太大性能優勢,機械磁盤物美價廉
  • 而它因易損壞而造成的可靠性差等缺陷,又由Kafka在軟體層面提供機制來保證

2.2 是否應該使用磁盤陣列(RAID)

使用RAID的兩個主要優勢在于:

  • 提供備援的磁盤存儲空間
  • 提供負載均衡

不過就Kafka而言

  • Kafka自己實作了備援機制提供高可靠性
  • 通過分區的設計,也能在軟體層面自行實作負載均衡

如此說來RAID的優勢也就沒有那麼明顯了。雖然實際上依然有很多大廠确實是把Kafka底層的存儲交由RAID的,隻是目前Kafka在存儲這方面提供了越來越便捷的高可靠性方案,是以線上上環境使用RAID似乎變得不是那麼重要了。

綜上,追求成本效益的公司可以不搭建RAID,使用普通磁盤組成存儲空間即可。使用機械磁盤完全能夠勝任Kafka線上環境。

2.3 磁盤容量

叢集到底需要多大?

Kafka需要将消息儲存在磁盤上,這些消息預設會被儲存一段時間然後自動被删除。

雖然這段時間是可以配置的,但你應該如何結合自身業務場景和存儲需求來規劃Kafka叢集的存儲容量呢?

假設有個業務

  • 每天需要向Kafka叢集發送1億條消息
  • 每條消息儲存兩份以防止資料丢失
  • 消息預設儲存兩周時間

現在假設消息的平均大小是1KB,那麼你能說出你的Kafka叢集需要為這個業務預留多少磁盤空間嗎?

計算:

  • 每天1億條1KB的消息,存兩份

    1億 * 1KB * 2 / 1000 / 1000 = 200GB

  • 一般Kafka叢集除消息資料還存其他類型資料,比如索引資料

    再為其預留10%磁盤空間,是以總的存儲容量就是220GB

  • 要存兩周,那麼整體容量即為

    220GB * 14,大約3TB

  • Kafka支援資料的壓縮,假設壓縮比是0.75

    那麼最後規劃的存儲空間就是0.75 * 3 = 2.25TB

總之在規劃磁盤容量時你需要考慮下面這幾個元素:

  • 新增消息數
  • 消息留存時間
  • 平均消息大小
  • 備份數
  • 是否啟用壓縮

3 帶寬

對于Kafka這種通過網絡進行大資料傳輸的架構,帶寬容易成為瓶頸。

普通的以太網絡,帶寬主要有兩種:1Gbps的千兆網絡和10Gbps的萬兆網絡,特别是千兆網絡應該是一般公司網絡的标準配置了

以千兆網絡為例,說明帶寬資源規劃。

真正要規劃的是所需的Kafka伺服器的數量。

假設機房環境是千兆網絡,即1Gbps,現在有業務,其目标或SLA是在1小時内處理1TB的業務資料。

那麼問題來了,你到底需要多少台Kafka伺服器來完成這個業務呢?

計算

帶寬1Gbps,即每秒處理1Gb資料

假設每台Kafka伺服器都是安裝在專屬機器,即每台Kafka機器上沒有混入其他服務

通常情況下你隻能假設Kafka會用到70%的帶寬資源,因為總要為其他應用或程序留一些資源。超過70%的門檻值就有網絡丢包可能性,故70%的設定是一個比較合理的值,也就是說單台Kafka伺服器最多也就能使用大約700Mb帶寬。

這隻是它能使用的最大帶寬資源,你不能讓Kafka伺服器正常性使用這麼多資源,故通常要再額外預留出2/3的資源,即

單台伺服器使用帶寬700Mb / 3 ≈ 240Mbps

這裡的2/3其實是相當保守的,可以結合機器使用情況酌情減少該值

有了240Mbps,可以計算1小時内處理1TB資料所需的伺服器數量了。

根據這個目标,每秒需要處理2336Mb的資料,除以240,約等于10台伺服器。

如果消息還需要額外複制兩份,那麼總的伺服器台數還要乘以3,即30台。

總結

與其盲目上馬一套Kafka環境然後事後費力調整,不如在一開始就思考好實際場景下業務所需的叢集環境。在考量部署方案時需要通盤考慮,不能僅從單個次元上進行評估。

參考

  • Linux核心模型架構
  • Kafka核心技術與實戰