目錄
1Kafka持久化機制
Kafka數據存儲目錄由log.dirs參數配置。 Kafka的消息數據是基於磁盤進行數據存儲的。
每個partition都會對應一個文件夾。Partition中可以包含一個或者多個segment, 消息的失效是以segment爲單位的。 默認情況下, 每個片段包含1GB或者1周的數據, 以較小的那個爲準。 當前正在寫入數據的分區稱爲活躍分區, 活躍分區是不會被刪除的。
Kafka的消息可以進行壓縮, 在客戶端CPU充足的情況下, 可以有效的增加吞吐量。 即如果通過網絡傳輸文件, 只需要在內核內存空間裏有一個內存緩衝區。
消息保留的時間可以配置:
- log.retention.bytes: 空間限制
- log.retention.hours, log.retention.minutes, log.retention.ms: 時間限制
1.1 如何使用磁盤達到較高的吞吐量?
- 順序讀寫: 磁盤的順序讀寫遠比隨機讀寫要快;
- RAID陣列;
- 分佈式讀寫;
1.2 寫磁盤的過程
一般的操作系統在寫磁盤時, 不會直接往磁盤寫, 而是先寫到內存中的page cache, 然後再一定時間之後, 才把數據複製到磁盤上。 如下:
kafka可以通過log.flush.*這些參數進行沖刷磁盤相關的配置。
2 Producer 攔截器
可以向producer註冊攔截器, 執行一些橫切邏輯。 可以同時註冊多個攔截器, 它們之間以職責鏈的模式來寫作。
攔截器的接口的接口爲ProducerInterceptor, 其中方法定義爲:
- configure(configs): 初始化時調用;
- onSend(ProducerRecord): 方法的出入參時ProducerRecord, 運行在用戶主線程中, 在確定分區和消息被序列化之前調用;
- onAcknowledgement(Recordmetadata, Exeption): 消息處理結果的回調, 運行在IO線程中, 所以不要在這個方法中執行過重的邏輯, 以免影響消息的發送。
- close();
需要由用戶來保證多線程的安全性。
3 Kafka Partitionor
可以通過實現Partitionor來實現自己的分區規則。
其中的一個使用場景是,保證消息的順序, 當partition的數量變多時, 通過Partition讓相同key的消息還是發送在原來的partition上。
4 Kafka調優參考
4.1 吞吐量
通過增大消息發送和消費的批次可以提高吞吐量。 在客戶端機器CPU充足的情況下可以開啓壓縮, 也可以提高吞吐量。
相關配置:
- Producer:
- batch.size 設置成一個比較大的值。
- linger.ms 100或者更大的值
- compression.type lz4是壓縮率最大的算法
- acks=1
- retries=0
- buffer.memory 適當增加緩衝區的大小, 增加可以同時處理的batch的數量
- Consumer:
- fetch.min.bytes 增加單個request的最小字節數
4.2 延遲
吞吐量是和延遲相互矛盾的一個參數,對於需要低延遲的情況, 可以適量調低吞吐量的參數來調整。
4.3 可用性
可以通過增加partition的副本數量來提高kafka的可用性。
- Broker
- replication.factor >= 3
5 Leader的選舉
Partition的leader的選舉, 如下圖:
Broker中有一個節點存在着一個controller, 當要選舉一個partition的leader時, 由controller根據某種策略決定哪一個ISR 節點成爲新的broker。ISR, 是指和leader節點保持一致的節點, 由兩個配置參數界定:
- replica.lag.time.max.ms
- replica.lag.max.messages
決定的策略: 是搶佔性的嗎?
(acks爲all時, 實際上是同步了所有的ISR就返回)