PHP 异常任重而道远-阿里云开发者社区

开发者社区> 周梦康> 正文

PHP 异常任重而道远

简介: 这几天观察错误日志发现有一个数据反序列化的notice错误,实际情况我是从缓存中读取数据然后反序列化,因为反序列化失败,所以实际每次都是去数据库取的值。背后性能影响还是挺大的。
+关注继续查看

背景

这几天观察错误日志发现有一个数据反序列化的notice错误,实际情况我是从缓存中读取数据然后反序列化,因为反序列化失败,所以实际每次都是去数据库取的值。背后性能影响还是挺大的。

缺失的异常

刚开始写代码的时候一直不明白为什么要用异常,感觉if else就能搞定了,为什么还要多此一举,现在反而觉得 php 的异常太少。

对比两种序列化场景,一个是json,另一个是serialize

json

json encode/decode的时候,如果出现异常,可以通过json_last_error()来获取。

https://www.php.net/manual/en/function.json-last-error.php

这样的设计够用,但不太符合面向对象的套路。

serialize/unserialize

在使用自带的序列化和反序列化的时候,相比json的处理,则更加简单粗暴,没有函数能拿到最后的错误,只会通过自定义的error handler来接管,然后自己去做出一些相应的处理。

为什么要捕获异常

比如我的代码比较乱,有的 key 是 json 序列化,有的 key 是 serialize。我们可以将 key 分类。不能确保其他人配置的对应关系是对的,或者有的人忘记了,所以我需要用捕获异常的方式来兜底,这样我们的代码更加健壮一些。unserialize失败之后,我们可以尝试去json_decode,而不是立即返回一个false,从而把请求传递到数据库。(不要说代码设计的烂,很多时候祖传代码才能让我们更快的成长。。)

代码演示

error_reporting(E_ALL);

$a = ["a" => 1];

class UnSerializeException extends ErrorException
{

}

set_error_handler(function ($severity, $message, $file, $line) {
    $info = explode(":", $message);

    if ($severity == E_NOTICE) {
        if ($info[0] == "unserialize()") {
            throw new UnSerializeException($message);
        }
        return true;
    } else {

        throw new ErrorException($message, 0, $severity, $file, $line);;
    }
});


try {
    $b = unserialize(json_encode($a));
} catch (ErrorException $exception) {
    var_dump(get_class($exception), $exception->getMessage(), $exception->getTraceAsString()); // 捕获到了
} finally {
    restore_error_handler();
}

try {
    $b = unserialize(json_encode($a));
} catch (ErrorException $exception) {
    var_dump(get_class($exception), $exception->getMessage(), $exception->getTraceAsString()); // 无法捕获
}

输出结果

string(20) "UnSerializeException"
string(43) "unserialize(): Error at offset 0 of 7 bytes"
string(181) "#0 [internal function]: {closure}(8, 'unserialize(): ...', '/Users/mengkang...', 34, Array)
#1 /Users/mengkang/PhpstormProjects/xxx/test.php(34): unserialize('{"a":1}')
#2 {main}"

Notice: unserialize(): Error at offset 0 of 7 bytes in /Users/mengkang/PhpstormProjects/xxx/test.php on line 42

后记

所以 php 代码的异常设计还是任重而道远的,而这些已经设定的“旧的规范”要推翻,需要“勇气”,毕竟会影响所有的使用者。

很多群里老是有语言之争的聊天,我一般都看看罢了,也不参与。类似的例子,不胜枚举,后面我会持续输出一些 php 自黑的博客,希望 php 代码更加健壮、安全。也希望大家不要只看到 php 干活快,快的背后隐藏着无数的潜在风险。

版权声明:本文内容由阿里云实名注册用户自发贡献,版权归原作者所有,阿里云开发者社区不拥有其著作权,亦不承担相应法律责任。具体规则请查看《阿里云开发者社区用户服务协议》和《阿里云开发者社区知识产权保护指引》。如果您发现本社区中有涉嫌抄袭的内容,填写侵权投诉表单进行举报,一经查实,本社区将立刻删除涉嫌侵权内容。

相关文章
异常信息: ResultSet can not re-read row data for column 2
解决方法:下面的解决方案是网上高人说的:                    (1)如果采用jdbc-odbc驱动,那么就必须按照查询顺序来一次读取(不论有没有image或text类型)           (2)如果采用微软提供的ms sql server jdbc driver,...
554 0
阿里云服务器怎么设置密码?怎么停机?怎么重启服务器?
如果在创建实例时没有设置密码,或者密码丢失,您可以在控制台上重新设置实例的登录密码。本文仅描述如何在 ECS 管理控制台上修改实例登录密码。
10095 0
异常之: The server time zone value '�й���׼ʱ��' is unrecognized or represents more than one time zone.
在 MySQL 中执行命令试下:  set global time_zone=’+8:00’   设置为东8区 就不报错了。 show variables like '%time_zone%';   解释:在访问数据库时出现时区无法识别问题,在通过在数据库连接URL后,加上?serverTimezone=UTC , 时区是确认了但是这默认是0市区,导致在存入数据库时,JDBC会将当前系统市区东8区,减去8个小时,最终导致时间不匹配。
1598 0
Swagger异常定位纪实,是用的不对,还是Swagger本身设计问题
swagger ui是一个采用注解驱动的接口文档工具,目前已支持标准的open api v3规范协议,所以不仅可以在java项目里使用,每个语言都有相应的open api实现。项目集成swagger后,可以生成导出open api v3格式化的元数据集,有了这个接口元数据,你可以在任何支持v3协议的ui上展示你的api信息。在前后端分离的项目中,swagger ui的出现,大大提高了前后端联调的效率。swagger ui在解析注解标注的元数据信息时,特别场景下会抛异常,而且抛的异常没有直观的有价值的异常信息,所以深入的debug了一番,虽然最后问题解决很简单,但是过程非常曲折。故将bug定位过
604 0
阿里云服务器如何登录?阿里云服务器的三种登录方法
购买阿里云ECS云服务器后如何登录?场景不同,阿里云优惠总结大概有三种登录方式: 登录到ECS云服务器控制台 在ECS云服务器控制台用户可以更改密码、更换系.
13893 0
强悍的异常处理-处理多个异常 | 带你学《Java面向对象编程》之七十七
当try块中出现多个异常,而catch块中捕获的只有有限个时,有时会出现无法捕获导致程序异常终止的情况,此时我们可以用多个catch块来解决。
566 0
ASP.NET Core 异常和错误处理 - ASP.NET Core 基础教程 - 简单教程,简单编程
原文:ASP.NET Core 异常和错误处理 - ASP.NET Core 基础教程 - 简单教程,简单编程 ASP.NET Core 异常和错误处理 上一章节中,我们学习了 ASP.
939 0
Java连接池你用对了吗?一次Unexpected end of stream异常的排查
Apache连接池参数调优、Redis连接关闭机制、Linux网络抓包
655 0
Java 编程中关于异常处理的 10 个最佳实践
异常处理是Java 开发中的一个重要部分。它是关乎每个应用的一个非功能性需求,是为了处理任何错误状况,比如资源不可访问,非法输入,空输入等等。
755 0
+关注
周梦康
十年前从 LNMP 开始个人站长 mengkang.net 生涯。 分享各种线上故障复盘笔记,关注我,防止采坑。
116
文章
70
问答
来源圈子
更多
PHP学习资料大全
+ 订阅
文章排行榜
最热
最新
相关电子书
更多
《2021云上架构与运维峰会演讲合集》
立即下载
《零基础CSS入门教程》
立即下载
《零基础HTML入门教程》
立即下载