這是一份過後的總結。在經歷了調優過程踩的不少坑以後,咱們最終完善並實施了初步的性能測試方案,經過真實的測試數據概括出了 Laravel 開發過程當中的一些實踐技巧。php
最近有同事反饋 Laravel 寫的應用程序響應有點慢、20幾個併發把 CPU 跑滿... 爲了解決慢的問題,甚至一部分接口用 nodejs 來寫。前端
而個人第一反應是一個流行的框架怎麼可能會有這麼不堪?必定是使用上哪裏出現了問題。爲了一探究竟,因而開啓了此次 Laravel 應用性能調優之旅。node
此次性能測試方案中用到的優化技巧主要基於 Laravel 框架自己及其提供的工具。laravel
app.debug=false
php artisan config:cache
php artisan router:cache
php artisan optimize
composer dumpautoload
除了以上優化技巧以外,還有不少編碼上的實踐能夠提高 Laravel 應用性能,在本文中暫時不會作說明。(也能夠關注個人後續文章)數據庫
打開應用根目錄下的 .env 文件,把 debug 設置爲 false。json
APP_DEBUG=false
php artisan config:cache
運行以上命令能夠把 config 文件夾裏全部配置信息合併到一個 bootstrap/cache/config.php
文件中,減小運行時載入文件的數量。bootstrap
php artisan config:clear
運行以上命令能夠清除配置信息的緩存,也就是刪除 bootstrap/cache/config.php
文件瀏覽器
php artisan route:cache
運行以上命令會生成文件 bootstrap/cache/routes.php
。路由緩存能夠有效的提升路由器的註冊效率,在大型應用程序中效果越加明顯。緩存
php artisan route:clear
運行以上命令會清除路由緩存,也就是刪除 bootstrap/cache/routes.php
文件。服務器
php artisan optimize --force
運行以上命令可以把經常使用加載的類合併到一個文件中,經過減小文件的加載來提升運行效率。這個命令會生成 bootstrap/cache/compiled.php
和 bootstrap/cache/services.json
兩個文件。
經過修改 config/compile.php
文件能夠添加要合併的類。
在生產環境中不須要指定 --force
參數文件也能夠自動生成。
php artisan clear-compiled
運行以上命令會清除類映射加載優化,也就是刪除 bootstrap/cache/compiled.php
和 bootstrap/cache/services.json
兩個文件。
composer dumpautoload -o
Laravel 應用程序是使用 composer 來構建的。這個命令會把 PSR-0 和 PSR-4 轉換爲一個類映射表來提升類的加載速度。
注意:
php artisan optimize --force
命令裏已經作了這個操做。
Laravel 應用程序內置了並開啓了不少的中間件。每個 Laravel 的請求都會加載相關的中間件、產生各類數據。在 app/Http/Kernel.php
中註釋掉不須要的中間件(如 session 支持)能夠極大的提高性能。
HHVM 和 OPcache 都能輕輕鬆鬆的讓你的應用程序在不用作任何修改的狀況下,直接提升 50% 或者更高的性能。
只能說 PHP 7.x 比起以前的版本在性能上有了極大的提高。
嗯,限於你的真實企業環境,這個也許很長時間內改變不了,算我沒說。
咱們使用簡單的 Apache ab 命令僅對應用入口文件進行測試,並記錄和分析數據。
ab -t 10 -c 10 {url}
。該命令表示對 url 同時發起 10 個請求,並持續 10 秒鐘。命令中具體的參數設置須要根據要測試的服務器性能進行選擇。服務器環境說明
全部脫離具體環境的測試數據都沒有意義,而且只有在相近的條件下才能夠進行比較。
app\Http\routes.php
中定義了 85 個路由。以上的數據,你們在本身進行測試時能夠參考。
ab -t 10 -c 10 http://myurl.com/index.php
基礎檢查項
APP_DEBUG=true
bootstrap/cache/config.php
bootstrap/cache/routes.php
bootstrap/cache/compiled.php
和 bootstrap/cache/services.json
app/Http/Kernel.php
中開啓了大部分的中間件APP_DEBUG=false
。ab -t 10 -c 10 http://myurl.com/index.php
。與步驟 1 結果比較發現:關閉應用 debug 以後,每秒處理請求數從 26-34 上升到 33-35,請求響應時間從 大部分 300ms 以上降低到 290ms 左右,效果不太明顯,但確實有必定的提高。
注意:這部分與應用中的日誌等使用狀況有比較大的關聯。
php artisan config:cache
,確認生成 bootstrap/cache/config.php
。ab -t 10 -c 10 http://myurl.com/index.php
。與步驟 2 結果比較發現:開啓配置信息緩存以後,每秒處理請求數從 33-35 上升到 36-38,請求響應時間從 290ms 左右降低到 260ms 左右,效果不太明顯,但確實有必定的提高。
php artisan route:cache
,確認生成 bootstrap/cache/routes.php
。ab -t 10 -c 10 http://myurl.com/index.php
。與步驟 3 結果比較發現:開啓路由信息緩存以後,每秒處理請求數從 36-38 上升到 60 左右,請求響應時間從 260ms 降低到 160ms 左右,效果顯著,從 TPS 看,提高了 70%。
ab -t 10 -c 10 http://myurl.com/index.php
。注意:此次測試中我註釋掉了全部的中間件。實際狀況中應該儘可能只留下必要的中間件。
與步驟 4 結果比較發現:刪除了沒必要要的中間件以後,每秒處理請求數從 60 左右上升到 90 左右,請求響應時間從 160ms 降低到 110ms 左右,效果很是明顯,從 TPS 看,提高了 50%。
php artisan optimize --force
,確認生成 bootstrap/cache/compiled.php
和 bootstrap/cache/services.json
。ab -t 10 -c 10 http://myurl.com/index.php
。與步驟 5 結果比較發現:作了類映射加載優化以後,每秒處理請求數從 90 上升到 110,請求響應時間從 110ms 降低到 100ms 如下,效果仍是比較明顯的。
ab -t 10 -c 10 http://myurl.com/index.php
。與步驟 6 結果比較發現:關閉 OPcache 以後,每秒處理請求數從 110 降低到 15,請求響應時間從 100ms 如下上升到 650ms 以上。開啓與關閉 OPcache,數據上竟有幾倍的差異。
此後,我從新開啓了 PHP 的 OPcache,數據恢復到步驟 6 水平。
在運行 php artisan route:cache
命令時報這個錯誤。
緣由:路由文件中處理「/」時使用了閉包的方式。要運行該命令,路由的具體實現不能使用閉包方式。
修改方案:將路由的具體實現放到控制器中來實現。
在運行 php artisan route:cache
命令時報這個錯誤。
緣由:路由文件中定義了重複的路由。
修改方案:排查路由文件中的重複路由並修改。尤爲要注意 resource
方法極可能致使與其方法重複。
在運行 php artisan optimize --force
命名時報這個錯誤。
緣由:在加載須要編譯的類時沒有找到相應的文件。5.2 版本的 vendor/laravel/framework/src/Illuminate/Foundation/Console/Optimize/config.php
中定義了要編譯的文件路徑,但不知道爲何 /vendor/laravel/framework/src/Illuminate/Database/Eloquent/ActiveRecords.php
沒有找到,因此報了這個錯誤。
修改方案:暫時註釋掉了以上 config.php 中的 ../ActiveRecords.php
一行。
在運行 php artisan config:cache
以後,瀏覽器上訪問 Laravel 應用程序歡迎頁報這個錯誤。
緣由:Laravel 應用程序服務器是經過 Homestead 在虛擬機上搭建的。而這個命令我是在虛擬機以外運行的,致使生成的 config.php 中的路徑是本機路徑,而不是虛擬機上的路徑。因此沒法找到視圖文件。
修改方案:ssh 到虛擬機內部運行該命令。
坑也踩了,測試也作過了。這裏針對此次經歷作個實踐技巧的簡單總結。
app.debug=false
php artisan config:cache
php artisan router:cache
php artisan optimize
(包含自動加載優化 composer dumpautoload
)resouce
方法。以上的調優技巧及編碼注意事項主要針對框架自己,在真正的業務邏輯編碼中有不少具體的優化技巧,在此沒有討論。
後續的優化重點將會放在具體編碼實踐上:
網上看到不少框架性能對比的文章與爭論,也看到不少簡單貼出了數據。這些都不足以窺探真實的狀況,因此有了咱們此次的實踐,並在過程當中作了詳實的記錄。在各位讀者實踐過程當中提供參考、比較、反思之用。對於此次實踐有疑問的讀者,也歡迎提出問題和意見。
很少說了,要學習更多技術乾貨,請關注微信公衆號:up2048。
- EOF -