公司的系統是面向商戶營銷的CRM系統,採用的是saas模式而非獨立部署,使用者表200W,日活3W,日增長5000+,每天的請求量總量目前是200多W次,其中服務端的請求量主要來自前端API請求+商戶ERP資料同歩+微信事件回撥。以下均在拋去系統設計的問題不討論,小公司的產品活下去才是第一要素,只能現有的情況下儘量優化,一步步摸著石頭過河。
服務配置:
-
單臺阿里雲ECS伺服器 - 12核24G (redis/nginx/php7.1/laravel5.7)
-
單臺阿里雲RDS資料庫 - 2核4G (mysql)
-
Supervisor開多個程式跑佇列任務
-
php的woker程式設為100個
-
跟據laravel優化文件做了優化https://learnku.com/articles/2020/ten-laravel-5-program-optimization-techniques
-
php-fpm實際併發如下(siege壓測-2核4G測試環境):
-
大部分簡單邏輯介面1秒300QPS
-
資料庫操作多的介面併發1秒70QPS
-
全查快取介面介面併發1秒550QPS
存在問題
當三個十萬粉絲的同時商家發推文和多個商家線下門店做促銷活動時,一秒點選人數過多或線下ERP消費小票、積分回傳過多,伺服器就會崩潰掉,伺服器崩潰的時間如果超過幾分鐘不能響應介面,就會觸發微信事件的3次重推機制和ERP回傳5次重推機制,觸發重推機制的情況下我們是可能關閉erp的回傳,但無法停止80家商戶的微信事件重推,這個時侯系統一般就會癱瘓1個多小時,癱瘓結束後又會面臨資料找回的問題
引入Laravel-S,利用swoole的長駐記憶體的機制, 常駐記憶體後每個請求減少了一大堆的初始化開銷,能一定程度的增加併發數,實測要連線資料庫的介面中的併發數提升了35% ~ 50%,不連線資料庫的介面中的併發數提升400% ~ 500%,整體的請求失敗率大幅度降低,正式環境下每天200多W個請求整體是正常的,沒有發現有記憶體洩漏,在整體修改不大的情況下得到這個提升是很值得滿意的。在此感謝Laravel-S作者和swoole社群,以下是Laravel-S作者對資料庫連線提升不大的解釋
laravel-s文件
https://github.com/hhxsv5/laravel-s
在此swoole實際併發如下(siege壓測-2核4G測試環境):
- 大部分簡單邏輯介面1秒600QPS
- 資料庫操作多的介面併發1秒96QPS
- 全查快取介面介面併發1秒2000QPS
存在問題
資料庫會不定時出現這個報錯 General error: 2006 MySQL server has gone away,正式和測試都出現過,要重啟laravel-s程式就能解決報錯,但問題的起因暫未查明
在swoole的基礎上引入負載均衡做伺服器叢集和分離專案內的模組(獨立ERP模組、微信模組),用堆機器來提高總的併發數
負載均衡存在問題
- 檔案如何同步 - 半解決,大部分檔案已上雲,小部分用nginx換髮到有存在檔案的特定伺服器
- 日誌如何收集 - 未解決
- session、快取如何同步 - 已解決,全域性切換redis
- 程式碼如何自動更新 - 未解決,手動更新多臺伺服器
分離模組存在問題
- 模型、佇列、事件監聽器高度藕合如何分離 - 半解決,多個伺服器程式碼相同,只是不同業務訪問特定伺服器
以上的問題附了程式碼如何自動更新外,其實都可以在專案開始前設計好,希望各位如果開新專案不妨直接考慮上負載均衡會遇到的問題,儘量檔案上雲,不要用本地檔案快取,在一開始分離模組。如果認為專案做不大的不用考慮。
3臺機器搭好了負載均衡,同時程式碼層和業務層也做了很多的優化,能上快取的上快取,能走非同步的不走同步,在全解決二階段方案現有的問題後,相信在現有的下架構是可以撐半年時間來開發業務的了。laravel能做的優化應該是到頭了,後面就是資料庫的優化、引入mq佇列、引入Elasticsearch、用協程的swoole框架重構(swoole框架支援微服務,微服務+k8s會是目前看來的最終解了)。
關於負載均衡的問題上,如何更自動化地部署程式碼和日誌收集?各位真實解決方案是如何實現的?在這拋磚引玉一下,大家有好的解決方案望在下方評論
本作品採用《CC 協議》,轉載必須註明作者和本文連結