0%

PHP程序调试与性能分析

性能分析是衡量应用程序在代码级别的相对性能,性能分析将捕捉的事件包括:CPU的使用,内存的使用,函数的调用时长和次数,以及调用图等。另外,性能分析的行为本身也会影响应用性能。

一、程序调试

  1. 使用xdebug:作为全世界最好的开发语言,基本上使用echo、print_r()、var_dump()等就可以完成各种开发工作了。不过既然作为一门编程语言,肯定少不了断点调试,xdebug功能之一便是提供断点调试,此处仅以vs code为例。

    • 安装xdebug【php7.3】

      • 下载php对应版本(本人php7.3,下载2.8.0)

      • 解压 tar -zxvf xdebug-2.8.0.tgz

      • cd xdebug-2.8.0

      • sudo /usr/local/php/7.3/bin/phpize

      • sudo ./configure –with-php-config=/usr/local/php/7.3/bin/php-config

      • sudo make && sudo make install

      • 修改php.ini,zend_extension=/path/xdebug.so

        • 注意此处写的是zend_extension,不能写extension,否则PHP Warning: Xdebug MUST be loaded as a Zend extension in Unknown...
      • 通过脚本phpinfo();或命令查看php -m

        1
        2
        [Zend Modules]
        Xdebug
      • 继续修改php.ini,加入以下内容:

        • 网上各种各样的配置都有,最准确的配置为通过phpinfo()查看xdebug模块下的配置
        • 官方配置
        1
        2
        3
        4
        5
        6
        7
        8
        9
        10
        11
        12
        13
        14
        15
        16
        17
        18
        19
        20
        21
        22
        23
        24
        25
        26
        27
        28
        29
        30
        zend_extension=xdebug.so
        zend_debugger.allow_hosts=127.0.0.1
        zend_debugger.expose_remotely=always
        zend_debugger.httpd_uid=-1
        xdebug.collect_params = on
        xdebug.collect_return = on
        #profile
        xdebug.auto_profile = on
        xdebug.profiler_enable = 1
        xdebug.profiler_output_dir=your path #自定义路径
        xdebug.profiler_output_name=cachegrind.out.%s
        ;xdebug.profiler_enable_trigger=on
        #trace
        xdebug.auto_trace = on
        xdebug.show_exception_trace = on
        xdebug.trace_format = 1
        xdebug.trace_output_dir = your path #自定义路径
        xdebug.trace_output_name = trace.%c.%p
        xdebug.show_local_vars = 0
        xdebug.dump.POST = *
        xdebug.dump.COOKIE = *
        xdebug.dump.SESSION = *
        xdebug.var_display_max_data = 4056
        xdebug.var_display_max_depth = 5
        xdebug.remote_enable=on
        xdebug.remote_handler=dbgp
        xdebug.remote_host=127.0.0.1
        xdebug.remote_port=9010 #不能用9000,php-fpm默认监听端口
        xdebug.remote_autostart=1
        xdebug.cli_color=1
      • 重启php-fpm进程

    • vs code设置

      • 安装PHP Debug插件,直接在商店搜索安装即可

      • Mac下fn+f5开启调试,默认会提示创建launch.json

        1
        2
        3
        4
        5
        6
        7
        8
        9
        10
        11
        12
        13
        14
        15
        16
        17
        18
        19
        20
        21
        22
        23
        24
        25
        26
        27
        28
        29
        30
        31
        32
        33
        34
        35
        36
        37
        38
        39
        40
        41
        42
        43
        44
        45
        {
        "version": "0.2.0",
        "configurations": [
        {
        "name": "Listen for Xdebug",
        "type": "php",
        "request": "launch",
        "port": 9010 //和xdebug.remote_port保持一致
        },
        {
        "name": "Launch currently open script",
        "type": "php",
        "request": "launch",
        "program": "${file}",
        "cwd": "${fileDirname}",
        "port": 9010,//和xdebug.remote_port保持一致
        "runtimeArgs": [
        "-dxdebug.start_with_request=yes"
        ],
        "env": {
        "XDEBUG_MODE": "debug,develop",
        "XDEBUG_CONFIG": "client_port=${port}"
        }
        },
        {
        "name": "Launch Built-in web server",
        "type": "php",
        "request": "launch",
        "runtimeArgs": [
        "-dxdebug.mode=debug",
        "-dxdebug.start_with_request=yes",
        "-S",
        "localhost:0"
        ],
        "program": "",
        "cwd": "${workspaceRoot}",
        "port": 9010,
        "serverReadyAction": {
        "pattern": "Development Server \\(http://localhost:([0-9]+)\\) started",
        "uriFormat": "http://localhost:%s",
        "action": "openExternally"
        }
        }
        ]
        }
    • 编写代码index.php

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      <?php
      $a = 1;
      $b = 2;
      $c = 3;
      $d = 4;

      echo sum(1,2),PHP_EOL;
      function sum($a, $b) {
      return add($a, $b);
      }
      function add($a, $b){
      return $a + $b;
      }
    • 设置断点,如echo sum(1,2),PHP_EOL;

    • 请求/usr/local/php/7.1/bin/php index.php

      xdebug

  2. debug_print_backtrace()和debug_backtrace()

二、性能分析

  1. 使用xdebug

    • 修改php.ini

      1
      2
      3
      4
      5
      6
      #profile
      xdebug.auto_profile = on
      xdebug.profiler_enable = 1
      xdebug.profiler_output_dir=your path #自定义路径
      xdebug.profiler_output_name=cachegrind.out.%s
      ;xdebug.profiler_enable_trigger=on
    • 安装图形化工具qcachegrind

      • brew install graphviz
      • brew install qcachegrind
      • csrutil disable
      • sudo mount -uw /
      • sudo ln -s /usr/local/bin/dot /usr/bin/dot
      • csrutil enable
    • 启动qcachegrind或直接命令行使用

xdebug

  1. 使用xhprof(需要自己集成到框架内部)

    • 安装xhprof扩展(依赖哪些扩展依次安装即可)

      • cd /usr/local/src
      • wget https://pecl.php.net/get/xhprof-2.3.5.tgz
      • tar -zxvf xhprof-2.3.5.tgz
      • cd xhprof-2.3.5/extension
      • /usr/local/php/7.3/bin/phpize
      • ./configure –with-php-config=/usr/local/php/7.3/bin/php-config
      • sudo make && sudo make install
      • vim /usr/local/php/7.3/php.ini
      1
      2
      3
      4
      extension_dir = "/usr/local/php/7.3/lib/php/extensions/no-debug-non-zts-20160303/"
      extendion = xhprof.so
      #可选项,主要存放每次运行生成的文件,默认在`/var/tmp/`目录下
      xhprof.output_dir = "自定义目录"
      • 重启php-fpm
    • 使用

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      server {
      listen 80;
      server_name phpweb.com;
      location / {
      root your_path;
      index index.php index.html index.htm;
      }
      location ~ \.php$ {
      root your_path;
      fastcgi_pass 127.0.0.1:9000;
      fastcgi_index index.php;
      fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_na me;
      include fastcgi_params;
      }
      }
      • 直接访问地址http://phpweb.com/xhprof/examples/sample.php

        • xhprof_enable(XHPROF_FLAGS_NO_BUILTINS | XHPROF_FLAGS_CPU | XHPROF_FLAGS_MEMORY);
          • XHPROF_FLAGS_NO_BUILTINS:设置这个常量后,将不统计PHP内置函数。
          • XHPROF_FLAGS_CPU:设置这个常量后,会统计进程占用CPU时间。
            • 由于CPU时间是通过调用系统调用getrusage获取,导致性能比较差。开启这个选项后,大概性能下降一半。因此,如果对cpu耗时不是特别敏感的情况下,建议不要启用这个选项。
          • XHPROF_FLAGS_MEMORY:设置这个常量后,将会统计内存占用情况。
            • 由于获取内存情况,使用的是zend_memory_usage和zend_memory_peak_usage,并不是系统调用。因此对性能影响不大。如果需要对内存使用情况进行分析的情况下,可以开启。
        • 输出说明
          • ct:表示调用的次数
          • wt:表示函数方法执行的时间耗时。
            • 相当于在调用前记录一个时间,函数方法调用完毕后计算时间差。
          • cpu:表示函数方法执行消耗的cpu时间。
            • 和wt的差别在于当进程让出cpu使用权后,将不再计算cpu时间。
            • 通过调用系统调用getrusage获取进程的占用cpu数据。
          • mu:表示函数方法所使用的内存。
            • 相当于在调用前记录一个内存占用,函数方法调用完毕后计算内存差。
            • 调用的是zend_memory_usage获取内存占用情况。
          • pmu:表示函数方法所使用的内存峰值。
            • 调用的是zend_memory_peak_usage获取内存情况。
      • 查看性能分析http://phpweb.com/xhprof/xhprof_html/index.php

        • 单个报告http://phpweb.com/xhprof/xhprof_html/index.php?run=619e04f147635&source=index

          • Function Name: 函数名

          • Calls: 调用次数

          • Calls%: 调用次数的百分比(图中带有百分比符号的字段皆表示百分比的意思,所以后面不在介绍)

          • Incl. Wall Time: 包含子函数执行的所有花费时间,单位:微秒(下同)

          • Excl. Wall Time: 函数本身执行所花费的时间。

          • Incl. CPU: 包含子函数执行的所花费的CPU时间。

          • Excl. CPU: 函数本身执行所花费的CPU时间。

          • Incl.MemUse: 包含子函数执行的所占用的内存,单位:字节(下同)

          • Excl.MemUse: 函数本身执行所占用的内存。

          • Incl.PeakMemUse: 包含子函数执行,所占用内存的峰值。

          • Excl.PeakMemUse: 函数本身执行所占用内存的峰值。

            • Incl. 表示Including(包含)的缩写

            • Excl. 表示Excluding(不包含)的缩写

              debug1

              debug2

        • 对比报告http://phpweb.com/xhprof/xhprof_html/index.php?run1=619e04f147635&run2=619e02ed47c0e&source=index

        • 汇总报告http://phpweb.com/xhprof/xhprof_html/index.php?run=619e04f147635,619e02ed47c0e,619e020eb9791&source=index

三、参考

  1. 参考一
  2. 参考二
  3. 参考三
  4. 参考四
  5. 参考五
  6. 参考六
  7. 参考七
  8. 参考八