在mysql死亡时捕获异常 - 苗条并防止在这种情况下记录到php_error日志

时间:2017-12-21 08:20:18

标签: php slim

您好我有以下代码:

try {
    $sth = $this->container->db->prepare("select  x from table");
    $sth->execute();
    $result = $sth->fetchAll(PDO::FETCH_ASSOC);
    return $result;
} catch (\PDOException $e) {
    throw new ServerException("Could not get data");
} catch (\Exception $e) {
    return false;
}

使用苗条3与wamp 问题是当我指向API(每1秒轮询一次)时出现以下错误:

Fatal error: Call to a member function prepare() on boolean in /

2个问题:它向客户端抛出错误 它在wamp下的php_error.log中抛出一个错误,文件变大了

如何防止和捕获这些错误

PDO课程:

public function getConnection($dsn, $username, $password) {

    $conn = null;
    try {
        $conn = new PDO($dsn, $username, $password);
        //Set common attributes
        $conn->setAttribute(\PDO::ATTR_ERRMODE, \PDO::ERRMODE_EXCEPTION);

        return $conn;

    } catch (PDOException $e) {
        return false;
        //TODO: flag to disable errors?
        throw $e;

    }
    catch(Exception $e) {
        die();
        //TODO: flag to disable errors?
        throw $e;

    }
}

2 个答案:

答案 0 :(得分:1)

Like many learners, you are taking this matter upside down

你永远不应该真正捕捉到这样的例外。

  

它向客户端抛出错误

在实时服务器上为整个站点禁用。无论是PHP异常还是文件系统错误,都不应向用户显示单个PHP错误消息。将display_errors设置为负值并忘记所有问题。

  

如何防止和捕获这些错误

同样,你永远不应该做这样的事情,直截了当地捕捉每一个错误,只是解雇它。这就像使用臭名昭着的@运算符

  

它在wamp下的php_error.log中抛出一个错误,文件变大了

好的,只有这个才有意义。有两种可能的解决方案:

  1. 最好的一个:正确配置你的mysql服务器,这样就不会像1 RPS那样轻负载。
  2. 好吧,你真正想要的是什么,但我仍然不建议,因为扫除地毯下的污垢永远不会付出代价:抓住异常,然后验证它是否是你想要的,然后做一些事情(即尝试在短暂的超时后重新连接),但重新抛出异常,这样你就可以知道别的东西会出错。为此,您应该在try..catch块中添加一个条件,该条件应该验证错误,如果它是您期望的那个,则处理它,否则只是再次抛出它。
  3. 当然,为了捕获PDOException,您必须为PDO启用它。

答案 1 :(得分:0)

1)在Slim中,您使用容器(服务工厂)来构建PDO对象。例如:

$container['db'] = function (Container $container) {
    $settings = $container->get('settings');

    $host = $settings['db']['host'];
    $dbname = $settings['db']['database'];
    $username = $settings['db']['username'];
    $password = $settings['db']['password'];
    $charset = $settings['db']['charset'];
    $collate = $settings['db']['collate'];
    $dsn = "mysql:host=$host;dbname=$dbname;charset=$charset";

    $options = [
        PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
        PDO::ATTR_PERSISTENT => false,
        PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_ASSOC,
        PDO::MYSQL_ATTR_INIT_COMMAND => "SET NAMES $charset COLLATE $collate"
    ];

    return new PDO($dsn, $username, $password, $options);
};

2)您必须将PDO选项设置为构造函数才能使其正常工作。例如:

$options = [
    PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
];

$pdo = new PDO($dsn, $username, $password, $options);