如果在unserialize生成错误时如何捕获PHP上的异常?
答案 0 :(得分:12)
一个简单的方法是:
$ret = @unserialize($foo);
if($ret === null){
//Error case
}
但它不是最现代化的解决方案。
如前所述,最好的方法是拥有自定义错误/异常处理程序(不仅适用于此情况)。但是,根据你正在做的事情,这可能是过度的。
答案 1 :(得分:11)
不,你无法抓住它,unserialize()
不会抛出异常。
如果传递的字符串不可反序列化,则返回FALSE并发出E_NOTICE。
您可以设置自定义异常处理程序来处理所有错误:
function exception_error_handler($errno, $errstr, $errfile, $errline ) {
throw new ErrorException($errstr, $errno, 0, $errfile, $errline);
}
set_error_handler("exception_error_handler");
答案 2 :(得分:4)
完整的解决方案如下所示:
<?php
// As mentioned in the top answer, we need to set up
// some general error handling
function exception_error_handler($errno, $errstr, $errfile, $errline ) {
throw new ErrorException($errstr, $errno, 0, $errfile, $errline);
}
set_error_handler("exception_error_handler");
// Note, there are two types of way it could fail,
// the fail2 fail is when try to unserialise just
// false, it should fail. Also note, what you
// do when something fails is up to your app.
// So replace var_dump("fail...") with your
// own app logic for error handling
function unserializeSensible($value) {
$caught = false;
try {
$unserialised = unserialize($value);
} catch(ErrorException $e) {
var_dump("fail");
$caught = true;
}
// PHP doesn't have a try .. else block like Python
if(!$caught) {
if($unserialised === false && $value !== serialize(false)) {
var_dump("fail2");
} else {
var_dump("pass");
return $unserialised;
}
}
}
unserializeSensible('b:0;'); // Should pass
unserializeSensible('b:1;'); // Should pass
unserializeSensible('a:2:{s:1:"a";b:0;s:1:"b";s:3:"foo";}'); // Should pass
unserializeSensible('a:2:{s:1:"a";b:0;s:1:"b";s:3:1111111111111111;}'); // Should fail
unserializeSensible(123); // Should fail
unserializeSensible("Gday"); // Should fail
unserializeSensible(false); // Should fail2
unserializeSensible(true); // Should fail
答案 3 :(得分:3)
将所有PHP错误(警告通知等)转换为异常。示例是here。
答案 4 :(得分:1)
正如Mihai Iorga所说,unserialize
不会抛出任何东西。您可以通过将返回值与false
进行比较来检查错误,但是如果序列化的值为布尔值false
,它将失败。下面的解决方案无需使用缓慢而麻烦的技术(例如设置自定义错误处理程序)即可解决此问题。
如果序列化值InvalidArgumentException
无效,以下代码将引发$v
,否则$x
将包含未序列化的值。
要特别注意区分:
unserialize()
返回false
表示无效的序列化值false
。$x = @unserialize ($v);
if ($x === false && $v != 'b:0;')
throw new InvalidArgumentException;