php調試排錯技巧大全

做php開發時間不短了,在這裏總結下平時常用的調試方法,希望對大家有所幫助。

1 代碼調試

1.1 打印輸出

使用echo、var_dump 、print_r等方法在需要調試地方進行打印輸出,通過輸出特定變量的值可以判斷程序執行是否正確。

1.2 使用debug_backtrace 函數打印調用棧信息:

debug_print_backtrace();exit;

#0  cli_rakuten->getOrders(1)
#1  call_user_func_array(Array ([0] => cli_rakuten Object (),[1] => getOrders), Array ([0] => 1)) called at [/data/project/***/include/of/of.php:79]
#2  of::cliDispatch(cli_rakuten, getOrders, 1, Array ([0] => 1)) called at [/data/project/***/cli.php:17]

1.3 使用xdebug調試代碼

PHP xdebug 調試工具安裝與使用

Xdebug是一個開放源代碼的PHP程序調試器(即一個Debug工具),可以用來跟蹤,調試和分析PHP程序的運行狀況。

配置好phpstorm+xdebug後,可很方便的對代碼進行斷點調試:

除了生成調用棧信息外,xdebug還能生成性能分析報告,windows上可使用WinCacheGrind來查看性能分析報告。

1.4 使用xhprof調試分析代碼

XHProf是facebook 開發的一個測試php性能的擴展。

對於本地開發環境來說,進行性能分析xdebug是夠用了,但如果是線上環境的話,xdebug消耗較大,配置也不夠靈活,因此線上環境建議使用xhprof進行PHP性能追蹤及分析。

xhprof安裝很簡單,可直接去搜索安裝文檔。

在代碼中加入生成xhprof分析報告代碼:

xhprof_enable(
        XHPROF_FLAGS_MEMORY|XHPROF_FLAGS_CPU,
        [
            'ignored_functions'    => [
                'call_user_func',
                'call_user_func_array'
            ]
        ]);

//這裏是業務代碼
//...


$xhprofData = xhprof_disable();
require '/data/soft/xhprof/xhprof_lib/utils/xhprof_lib.php';
require '/data/soft/xhprof/xhprof_lib/utils/xhprof_runs.php';
$xhprofRuns = new XHProfRuns_Default();
$runId = $xhprofRuns->save_run($xhprofData, 'xhprof_test');
echo 'http://192.168.52.129:8888/xhprof_html/index.php?run=' . $runId . '&source=xhprof_test'.PHP_EOL;

查看報告:

圖形報告:

 

2 日誌分析

log日誌,通常是系統或軟件、應用的運行記錄。通過log的分析,可以方便用戶瞭解系統或軟件、應用的運行情況;如果你的應用log足夠豐富,也可以分析以往用戶的操作行爲、類型喜好、地域分佈或其他更多信息;如果一個應用的log同時也分了多個級別,那麼可以很輕易地分析得到該應用的健康狀況,及時發現問題並快速定位、解決問題,補救損失。

2.1 PHP日誌

2.1.1 php錯誤日誌

php錯誤日誌可在配置文件php.ini中設置:

log_errors = On

error_log = /var/log/php-fpm/php_errors.log

也可在php-fpm配置文件php-fpm.conf中設置:

php-fpm進程日誌,記錄php-fpm進程相關日誌信息

error_log = /var/log/php-fpm/error.log

php-fpm.conf中也可以設置錯誤日誌,會覆蓋掉php.ini中的相關設置

php_admin_value[error_log] = /var/log/php-fpm/www-error.log

php_admin_flag[log_errors] = on

2.1.2 php慢日誌

slowlog = /var/log/php-fpm/www-slow.log

#執行時間超過request_slowlog_timeout 設置時間將會記錄到slowlog中

request_slowlog_timeout = 1s

慢日誌文件中會記錄執行時間較長的函數信息:

[19-Sep-2018 11:00:55] [pool www] pid 80603

script_filename = /data/project/test//slow.php

[0x00007f4e0a7ed568] sleep() /data/project/test/slow.php:5

2.2 業務日誌

php內置error_log、syslog函數功能強大且性能極好,但由於各種缺陷(error_log無錯誤級別、無固定格式,syslog不分模塊、與系統日誌混合),靈活度降低了很多,不能滿足應用需求。

當然我們可以自己封裝實現一個符合PHP PSR-3 日誌接口規範 所要求的模塊、級別、清晰、易用等特點的日誌庫,但通常不建議這樣做,因爲已經有一些非常好的第三方日誌庫了,我們可直接用。

這裏挑選3款應用比較廣的日誌庫進行比較:

log4php

文檔:http://logging.apache.org/log4php/quickstart.html

log4php是apche組織維護項目,是log4xx系列日誌組件之一,log4j在JAVA中可算是大名鼎鼎的日誌開發包。log4php也作爲一個單獨的子項目存在,可以很方便的加載使用。

優點:

最爲著名、設計精良、格式完美、文檔完善、功能強大、擴展方便

缺點:

只支持TRACE、DEBUG、INFO、WARN、ERROR、FATAL共6個日誌級別,不完全符合psr-3日誌規範
停止維護了,目前最新版本還是更新於2012-12-13日v2.3.0
性能較差

Monolog

github地址:https://github.com/Seldaek/monolog

使用方法:https://www.jianshu.com/p/59ce6d70f801

Monolog是一款強大的日誌處理類庫,應用非常廣泛,目前有包括Symfony 、Laravel、 CakePHP、YII等諸多知名php框架都內置了Monolog。Monolog可以發送你的日誌到文件、到sockets、到郵箱、到數據庫或(和)者其他網路存儲服務(雲)。這裏用了,因爲Monolog的確可以做到同時保存到一個或多個存儲介質。

優點:

功能強大、應用廣泛、安裝方便、設計優秀,使用靈活、擴展方便、更新活躍

缺點:性能較差

SeasLog

github地址:https://github.com/Neeke/SeasLog

使用方法:https://blog.csdn.net/u011120720/article/details/51474488

SeasLog是一個C語言編寫的PHP擴展,提供一組規範標準的功能函數,在PHP項目中方便、規範、高效地寫日誌,以及快速地讀取和查詢日誌。

優點:高性能、功能完善

缺點:

安裝配置較麻煩,如編譯PHP擴展

擴展不方便

比較

從功能上比較:

Monolog > SeasLog > log4php

從性能上比較:

SeasLog > Monolog > log4php

3 進程跟蹤

3.1 使用lsof查看進程打開的文件句柄

Linux平臺提供了lsof工具可以查看某個進程打開的文件句柄,可以用於跟蹤進程所有打開的socket、file、資源。

lsof -p 2901

3.2 使用strace跟蹤進程中的系統調用

strace常用來跟蹤進程執行時的系統調用和所接收的信號。 在Linux世界,進程不能直接訪問硬件設備,當進程需要訪問硬件設備(比如讀取磁盤文件,接收網絡數據等等)時,必須由用戶態模式切換至內核態模式,通過系統調用訪問硬件設備。strace可以跟蹤到一個進程產生的系統調用,包括參數,返回值,執行消耗的時間。

跟蹤可執行程序:

strace -T -tt -s 512 php /data/project/***/cli.php test

跟蹤服務程序

strace -T -tt -s 512 -p 1123

默認返回的結果每一行代表一條系統調用,規則爲“系統調用的函數名及其參數=函數返回值”。

3.3 gdb調試php進程

一般的php問題通過以上的這些方法排查出來了。但還有死循環、進程異常退出等問題可通過gdb分析core dump文件來排查原因。

//修改core file size
ulimit -c unlimited

//修改core dump文件生成位置
echo "/tmp/core-%e.%p" > /proc/sys/kernel/core_pattern

//用gdb調試core dump文件
gdb php -c core.31656
 

4 網絡抓包

4.1 使用tcpdump抓包

在調試網絡通信程序是tcpdump是必備工具。tcpdump很強大,可以看到網絡通信的每個細節。如TCP,可以看到3次握手,PUSH/ACK數據推送,close4次揮手,全部細節。包括每一次網絡收包的字節數,時間等。

tcpdump -i any tcp port 80  

  • 18:01:37.968224 時間帶有精確到微妙
  • 192.168.52.1.64504 > T1.http 表示通信的流向,64504是客戶端,T1.http是服務器端80端口
  • [S] 表示這是一個SYN請求
  • [.] 表示這是一個ACK確認包,(client)SYN->(server)SYN->(client)ACK 就是3次握手過程
  • [P] 表示這個是一個數據推送,可以是從服務器端向客戶端推送,也可以從客戶端向服務器端推
  • [F] 表示這是一個FIN包,是關閉連接操作,client/server都有可能發起
  • [R] 表示這是一個RST包,與F包作用相同,但RST表示連接關閉時,仍然有數據未被處理。可以理解爲是強制切斷連接
  • win 2053是指滑動窗口大小
  • length 7300指數據包的大小

4.2 使用ngrep抓包

tcpdump能抓到網絡通信細節,但如果只想看傳輸的數據等簡單信息可以用ngrep命令

ngrep -pqt -W byline port 80 -d ens33

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章