php - 尝试,捕获并重试

时间:2014-07-28 18:47:34

标签: php try-catch

有时我的代码会中断并且不受我的控制

我如何做以下事情?

try {
//do my stuff
}
catch {
//sleep and try again
}

代码不是那么多,所以它只是一个功能,所以如果我没有必要,我就不想制作和调用另一个功能

6 个答案:

答案 0 :(得分:52)

您可以尝试这样的事情:

function exception_error_handler($errno, $errstr, $errfile, $errline ) {
    throw new ErrorException($errstr, 0, $errno, $errfile, $errline);
}
set_error_handler("exception_error_handler");

$NUM_OF_ATTEMPTS = 5;
$attempts = 0;

do {

    try
    {
        executeCode();
    } catch (Exception $e) {
        $attempts++;
        sleep(1);
        continue;
    }

    break;

} while($attempts < $NUM_OF_ATTEMPTS);

function executeCode(){
    echo "Hello world!";
}

在这里,我们执行do...while循环,以便代码至少执行一次。如果executeCode()函数遇到错误,它将抛出Exception块将捕获的try...catch。然后catch块将变量$attempt递增1并调用continue以测试下一次迭代的while条件。如果已经有五次尝试,则循环将退出并且脚本可以继续。如果没有错误,即continue块中的catch语句未执行,则循环将break,从而完成脚本。

请注意使用here中的set_error_handler函数。我们这样做是为了捕捉executeCode()函数中的所有错误,即使我们不自己手动抛出错误。

如果您认为您的代码可能会多次失败,sleep()函数可能会在continue语句之前发挥作用。 “减慢”可能无限循环将有助于降低CPU Usage

让脚本无限运行直到成功是不是一个好主意,因为在循环的前100次迭代中出现的错误不太可能被解决,从而导致脚本“冻结”起来。更重要的是,最好重新评估您希望在出现错误时多次运行的代码,并改进它以正确处理任何错误。

答案 1 :(得分:3)

简单地说:

function doSomething($params, $try = 1){
    try{
        //do something
        return true;
    }
    catch(Exception $e){
        if($try <5)
             sleep(10);
             //optionnaly log or send notice mail with $e and $try
             doSomething($params, $try++);
        else 
             return false;
    }
}

答案 2 :(得分:1)

这是一个简单的算法:

    do{
        try {
            $tryAgain = false;
            /* Do everything that throws error here */

        }
        catch(Exception $e) {
            $tryAgain = true;
            /* Do error reporting/archiving/logs here */

        }
    } while($tryAgain);

答案 3 :(得分:0)

我不完全理解为什么你会这么想,因为你很有可能创造一个无限循环。但是,如果代码很可能在小睡眠后成功,无论出于何种原因,下面是一个解决方案

while(true){
    // execute the code you are attempting
    if(some condition to signal success){
        break; // exit the loop
    }

    sleep(2); // 2 seconds
}

答案 4 :(得分:0)

这个库看起来很酷,它具有不同的退避策略,您可以选择它们,并且每次都无法实现重试逻辑。

https://github.com/stechstudio/backoff

示例代码:

$result = backoff(function() {
    return doSomeWorkThatMightFail();
});

答案 5 :(得分:-1)

为了能够捕获异常,你必须先抛出一个异常。 像这样的东西。

<?php
function inverse($x) {
    if (!$x) {
        throw new Exception('Division by zero.');
    }
    return 1/$x;
}

try {
    echo inverse(5) . "\n";
    echo inverse(0) . "\n";
} catch (Exception $e) {
    echo 'Caught exception: ',  $e->getMessage(), "\n";
}

// Continue execution
echo "Hello World\n";
?>

有一些内置的例外情况:http://php.net/manual/en/spl.exceptions.php