天天看點

Go 網絡庫并發對比

本文主要測試 ​​gev​​ 網絡庫和其他三方 Go 網絡庫以及标準庫的吞吐量對比。

測試對象

  • ​​gev​​ :一個輕量、快速的基于 Reactor 模式的非阻塞 TCP 網絡庫
  • ​​eviop​​ :evio 的優化版本
  • ​​evio​​ :Fast event-loop networking for Go
  • ​​gnet​​ :eviop 的網絡模型替換版本
  • net 标準庫

測試方法

采用陳碩測試 muduo 使用的 ping pong 協定來測試吞吐量。

簡單地說,ping pong 協定是用戶端和伺服器都實作 echo 協定。當 TCP 連接配接建立時,用戶端向伺服器發送一些資料,伺服器會 echo 回這些資料,然後用戶端再 echo 回伺服器。這些資料就會像乒乓球一樣在用戶端和伺服器之間來回傳送,直到有一方斷開連接配接為止。這是用來測試吞吐量的常用辦法。

測試的用戶端代碼: ​​https://github.com/Allenxuxu/gev/blob/master/benchmarks/client/main.go​​

測試腳本: ​​https://github.com/Allenxuxu/gev/blob/master/benchmarks/bench-pingpong.sh​​

主要做兩項測試:

  • 單線程單個 work 協程測試,測試并發連接配接數為 10/100/1000/10000 時的吞吐量
  • 4 線程 4 個 work 協程測試,測試并發連接配接數為 10/100/1000/10000 時的吞吐量

所有測試中,ping pong 消息的大小均為 4096 bytes,用戶端始終是 4 線程運作。

測試結果

Go 網絡庫并發對比
Go 網絡庫并發對比

總結與思考

無論是單線程,還是多線程模式下,gev 都比其他網絡庫吞吐量略高出一些。

evio 因為 epoll 使用一些 bug 和可優化之處,是以在 linux 環境中的吞吐量遠不如優化版本 eviop。

eviop 是我對 evio bug 修複和優化的版本,是以其性能也是比 evio 提升不少。我曾嘗試在 eviop 中替換 evio 的網絡模型( evio 利用 accpet 的驚群現象工作),但是因為其代碼耦合度過高,修改成本過大,最終決定一邊完善 eviop (維持網絡模型不變)一邊自己借鑒 muduo 的網絡模型重新撸一個新的 -- gev。

繼續閱讀