1. 起因

由于yii2项目cache的unserialize( )函数报了notice的错,具体报错内容和报错参数无法得知,所以需要捕捉到该具体内容。

  1. 报错内容只有简单的提示项目代码报错行数
  2. 由于yii2框架的cache函数内部使用了serialize( )和unserialize( )来处理缓存内容,而unserialize( )报错无法得知是哪个cache使用的时候报错(无法知道是哪个key,就无法知道是哪个业务)

    2. 解决办法

    2.1 定义

  3. 调用原理:

    php内置 set_error_handler() 函数设置用户自定义的错误处理函数。

  1. <?
  2. function set_error_handler ($error_handler, $error_types = E_ALL | E_STRICT) {}
  1. 处理方法解释:
    <?php
    function error_function(error_level, error_message, error_file, error_line, error_context) {}
    
参数 描述
error_level
必需的。规定用户自定义的错误的错误报告级别。必须是值数字。可能的错误报告级别详见下面的表格。
error_message 必需的。规定用户自定义的错误的错误消息。
error_file 可选。规定发生错误的文件名。
error_line 可选。规定发生错误的行号。
error_context 可选。规定指向活跃符号表中发生错误的数组。换句话说,error_context 将包含一个说明每个变量引发错误的存在范围的数组。

2.2 具体实现

<?

// 在需要捕捉的地方之前调用
set_error_handler('low_level_error');

/**
 * 排查 notice 和 warning 错误使用
 * @param string $type
 * @param string $message
 * @param string $file
 * @param string $line
 * @param null $errcontext
 * @throws \Throwable
 */
function low_level_error($type, $message, $file, $line, $errcontext = NULL)
{
    !is_string($errcontext) && $errcontext = json_encode($errcontext);

    $time = date('Y-m-d H:i:s');
    $str = "\n ".$time.' set_error_handler: ' . $type . ' : ' . $message . ' in ' . $file . ' on ' . $line . ' line .' . ' [params:][' . $errcontext . '] .';
    $str = addslashes($str);

    Debug::log($str, '20210115_debug.log');
}