抑制PDO警告

5
我正在尝试显示服务器状态,基于数据库是否可以连接。使用旧的 mysql_connect()mysqli_connect() 很容易实现。我想保持现代性,所以使用 PDO,但我不知道如何抑制默认警告。据我所知,您需要使用 getMessage() 函数才能打印出 PDO 警告,但我没有使用它。
以下是我的代码:
8  $dbstatus = 1;
9  try {
10  $db = new PDO($dbms . ':host=' . $dbhost . ';port=' . $dbport . ';dbname=' . $dbname, $dbuser, $dbpasswd);
11  $db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
12 } catch(PDOException $e) {
13  $dbstatus = 0;
14 }
15 if($dbstatus == 1) {
16  echo '<span style="color: green">DB Up</span>';
17 } else {
18  echo '<span style="color: red">DB Down</span>';
19  exit;
20 }

所有的连接变量都已经提供并且正确,除了故意破坏的$dbhost。现在它产生了期望的结果,但同时也打印了一个警告消息:

警告:PDO::__construct():php_network_getaddresses:getaddrinfo失败:没有这样的主机。在C:\xampp\htdocs\cd\includes\dbconnect.php 的第10行。

如果我更正$dbhost变量,它可以正常工作,所以我知道问题不在于可用的PDO语句。
你有什么想法吗? 解决方案 我使用了jeroen提供的变体。
if(filter_var(gethostbyname($dbhost), FILTER_VALIDATE_IP)) {
 $dbstatus = 1;
 try {
  $db = new PDO($dbms . ':host=' . $dbhost . ';port=' . $dbport . ';dbname=' . $dbname, $dbuser, $dbpasswd, array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION));
 } catch(PDOException $e) {
  $dbstatus = 0;
 }
} else {
 $dbstatus = 0;
}
if($dbstatus == 1) {
 echo '<span style="color: green">DB Up</span>';
} else {
 echo '<span style="color: red">DB Down</span>';
 exit;
}

感谢你的帮助,希望这对其他人有所帮助!^^

在返回JSON的AJAX调用中,警告(似乎无法捕获)正在使我过去两天的工作毫无意义。这太糟糕了。 - Daniel Dolz
1个回答

2

这里唯一我能看到的问题就是你在尝试打开连接之后才告诉PDO抛出异常,那很可能太晚了。

相反,你可以直接使用第四个参数将该选项发送到构造函数中:

try {
  $opts = array(PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION);
  $db = new PDO($dbms . ':host=' . $dbhost . ';port=' . $dbport . ';dbname=' . $dbname,
                $dbuser, $dbpasswd, $opts);
} catch(PDOException $e) {
...

我想这可能会解决你的问题。

编辑:如果主机名是由用户提供的,你可以在将其发送到PDO构造函数之前进行验证。

例如使用:

if (filter_var(gethostbyname($user_provided_host_name), FILTER_VALIDATE_IP)) {
  // valid hostname / ip address
}

这适用于域名、localhost和IP地址。


更改属性声明并没有阻止警告加载。 - Christopher Esbrandt
@AoN 奇怪,我没有测试过完全相同的内容,但是我在这里得到了异常(使用google.com的IP地址...):http://codepad.viper-7.com/dLZi8R - jeroen
我想我知道它出了什么问题。我在地址中间添加了一个空格,从而断开了连接,这导致了错误。当我输入正确的域名(google.com)或IP地址时,它不会产生警告。使用拼写错误的“localhost”或IP会产生警告。对于技术人员来说很好,但对于只想知道数据库是否正常的用户来说就不那么好了。有没有什么方法可以弥补这个问题?我尝试在$dbhost变量上使用rawurlencode(),但对警告没有任何作用。:S - Christopher Esbrandt
@AoN 你忘记了在筛选函数中过滤有效IP地址的部分:http://codepad.viper-7.com/fuHEeF。如果你不使用它,那么你会筛选一个字符串,所以 l ocalhost 仍然是 l ocalhost - jeroen
哦,现在我感觉太蠢了!谢谢你的耐心和帮助!它非常好用,即使我最初把 try catch 包装在 if 语句中也可以。 :) - Christopher Esbrandt
显示剩余4条评论

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接