EQueue 2.0 性能測試報告


前言

最近用了幾個月的時間,一直在對EQueue做性能優化。到現在總算告一段落了,現在把一些優化的結果分享給大家。EQueue是一個分布式的消息隊列,設計思路基本和阿里的RocketMQ一致,只是是用純C#寫的,這點大家應該都知道了。

  1. EQueue開源地址:https://github.com/tangxuehua/equeue
  2. EQueue相關文檔:http://www.cnblogs.com/netfocus/category/598000.html
  3. EQueue Nuget地址:http://www.nuget.org/packages/equeue

之前EQueue 1.*版本,消息持久化是使用SQLServer的,之前也想做性能測試,但發現效果不理想。所以放棄了測試,轉為專心對消息持久化這塊進行優化。之前的持久化設計是通過Sql Bulk Copy的方式異步批量持久化消息。但是當數據庫服務器和Broker本身部署在不同的服務器上時,持久化消息也會走網卡,消耗帶寬,影響消息的發送和消費的TPS。而如果數據庫服務器部署在Broker同一台服務器上,則因為SQLServer本身也會消耗CPU以及內存,也會影響Broker的消息發送和消費的TPS。所以,經過考慮后,最終決定狠下心來,采用終極方案來持久化消息,就是通過本地順序寫文件的方式來持久化消息。支持異步刷盤和同步刷盤兩種方式。采用文件存儲后,EQueue可以輕易的支持大量消息的堆積,你的硬盤有多大,就能堆積多少量的消息。

到現在為止,經過不斷的測試,功能上我認為已經比較穩定了,性能也基本滿足我的要求。另外,EQueue單純的消息持久化模塊(MessageStore)以及TCP通信層的性能是非常高的。MessageStore我設計時,盡量獨立一些,因為我發現寫文件和讀文件的設計是通用的,以后可以被復用到其他項目,所以我設計時,確保持久化模塊的通用性;而TCP通信層,也是也是一樣,通用和高效。目前我自己寫的通信層(在ECommon類庫中)可以輕松把網卡壓滿。

關於EQueue 2.0文件持久化版本的具體設計,我下一篇文章會具體介紹,本文主要是想分享一下EQueue 2.0的性能測試結果。為大家在使用到線上環境前做架構選型給出性能方面的參考。

測試目的

測試單個EQueue Broker服務器的發送消息、消費消息的性能。

硬件環境

全部采用UCloud雲主機進行測試。一台Broker,4台Client機器。Broker的配置為8核16G內存,120G的SSD硬盤,Client的配置為4核8G內存,普通硬盤。所有服務器操作系統均為Windows Server 2012。具體如下圖所示:

測試場景1

1台生產者、1台消費者、1台Broker,異步刷盤,每隔100ms刷一次盤。

消息大小(字節)  發送TPS  消費TPS  發送網絡吞吐量  消費網絡吞吐量 Broker磁盤寫入吞吐量  Broker CPU Broker內存 Producer CPU Producer內存 Consumer CPU Consumer內存
 128  56400  56400  10MB  13MB  13MB  35%  35%  30%  12%  30%  13%
 512  41000  41000  22MB  25MB  25MB  32%  35%  30%  13%  30%  13%
 1024  29000  29000  30MB  34MB  34MB  32%  35%  27%  12%  25%  13%
 2048  20000  20000  41MB  43MB  43MB  30%  35%  27%  12%  25%  13%

測試場景2

2台生產者、2台消費者、1台Broker,異步刷盤,每隔100ms刷一次盤。

消息大小(字節)  發送總TPS  消費總TPS  發送總網絡吞吐量  消費總網絡吞吐量 Broker磁盤寫入吞吐量  Broker CPU Broker內存 Producer CPU Producer內存 Consumer CPU Consumer內存
 128  50000  50000  8.6MB  11MB  11MB  46%  35%  19%  13%  19%  13%
 512  40000  40000  21MB  24MB  24MB  48%  35%  19%  13%  19%  13%
 1024  31200  31200  32MB  35MB  35MB  47%  35%  19%  13%  19%  13%
 2048  23000  23000  48MB  51MB  51MB  45%  35%  19%  13%  19%  13%

結束語

一些說明

  1. 因為EQueue的Producer發送消息時,本地會有緩存隊列。所以Producer發送消息采用的線程數對發送TPS並無什么影響。所以,我上面的測試中並沒有考慮發送線程數;
  2. Broker的內存使用我們是可以控制的,我測試時配置為當內存使用到達40%時,開始自動清理內存,所以上面的測試結果,內存使用都不會超過40%;
  3. 因為消費者從Broker拉取消息時,EQueue的設計在內存足夠的情況下,總是會將需要消費的消息緩存在非托管內存,所以消費者拉取消息時,總是從內存獲取消息的。所以Broker沒有磁盤的讀取;且由於這個設計,消費者消費消息不會成為瓶頸,假設當前Broker上存在大量消息可以被消費,然后我們開一個Consumer,那消費速度是非常快的,1K大小的消息,10W TPS沒有問題。所以,消息的消費不會成為瓶頸,除非消費者自己內部處理消息的代碼太慢。這種情況下,消費者需要增加Consumer機器,確保消費速度跟得上發送速度。
  4. 上面的測試結果是基於UCloud的虛擬機,由於我沒有物理機,所以不知道物理機上的性能。有條件的朋友我非常希望能幫忙測試下哦。像這種重要的分布式消息隊列服務器,是應該部署在物理機上的。另外,我測試時,Producer和Consumer服務器使用的是普通的虛擬機,盡量真實的模仿一般應用的虛擬機配置。

測試結論

從上面的測試結果可知:

  1. 隨着消息體的不斷增大,發送消息的TPS不斷降低,一般我們的消息大小為1KB,在有兩個發送者客戶端時,EQueue的發送消息TPS大概為31000。我覺得性能上應該滿足大部分需求場景了。如果一個系統平均每秒產生31200個消息,一天是86400秒。那一天的消息量是27億。這個數字已經很大了,呵呵。相信國內大部分網站都沒有這么大的規模。當然我們不能這么簡單的來算,實際的系統肯定有高峰期的,實際大家要根據自己的系統的高峰期發送消息的TPS來衡量具體要部署多少台EQueue Broker服務器。線上環境使用時,我們不能把Broker壓滿的,要給其有足夠的處理余量,比如高峰期發送TPS為10W,每台Broker最大能承受3W,那我們至少要分配6台機器,確保應付可能出現的高峰。這樣才能應付特別高的高峰。
  2. 大家可以看到上面的數據中,開兩個生產者,兩個消費者,消息大小為2KB時,Broker的進出總網絡流量為99MB,這個數據還沒有到達千兆網卡的總流量(125MB)。目前,我只申請了5台機器,4個客戶端機器。但實際我們的應用的集群,客戶端機器應該會更多,我不知道當客戶端機器增加時,能否把Broker的網卡壓滿,如果壓不滿,則說明Broker本身的設計實現已經到達瓶頸了,也就是說EQueue Broker本身設計上可能還有性能優化的空間。
  3. 在上面的性能數據情況下,所有服務器的CPU,內存使用穩定,符合預期。在穩定性方面,我在個人筆記本上同時發送和消費消息,連續運行1天沒有問題;也有其他網友幫忙測試了穩定性,運行幾天也沒有問題。各項指標均正常。所以我認為目前EQueue的穩定性應該問題不大了。
  4. Broker的消息持久化,采用的是順序寫文件的方式;目前的測試結果來看,完全還沒達到寫文件的瓶頸;如果我們單獨測試寫文件模塊的性能,可以輕松達到300MB每秒,而我們的千兆網卡最大流量也只有125MB。所以,消息持久化不會再成為很大的瓶頸了,但寫文件的響應時間本身也會影響Broker對外的TPS,目前的響應時間為60ms,我感覺是比較慢的,不知道是否是虛擬機的原因,不知道物理機上會如何。我覺得SSD硬盤,寫入文件的響應時間不會這么慢的。
  5. 最后一點,當Broker的客戶端增加時,Broker的CPU的使用也會相應增加一點。這個可以理解,因為TCP長連接的數量多了一倍。而生產者和消費者服務器的CPU內存的使用都非常穩定,符合預期。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM