我对这段代码没有任何问题,令人惊讶地工作正常,但我真的不明白它是如何工作的,甚至是正确的,所以:
我使用mysqli查询ajax帖子或获取电话是这样的:
$con = mysqli_connect('localhost','root','','db') or die(header('Location: ./404.php'));
$add = "INSERT INTO table (id, id2, id3) VALUES('','$fid','')";
if(mysqli_query($con, $add)){
echo "added";
}
$remove = "DELETE FROM table WHERE id2='$fid'";
if(mysqli_query($con, $remove)){
echo "removed";
}
$getInfo = "SELECT * FROM table";
$result = $con->query($getInfo);
if($result->num_rows > 0) {
while($row = $result->fetch_assoc()){
//do something
}
}
适用于$_POST or $_GET values I used mysqli_real_escape_string
这里转换为PDO:
try{
$con = new PDO('mysql:host=localhost;dbname=db;charset=utf8mb4', 'root', '', array(PDO::ATTR_EMULATE_PREPARES => false, PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION));
$get = $con->query("SELECT * FROM table");
foreach($get->fetchAll(PDO::FETCH_ASSOC) as $row){
$data['0'] = $row['name'];
$data['1'] = $row['email'];
return $data;
}
$add = $con->prepare("INSERT INTO table (id, id2, id3) VALUES(:f1,:f2,:f3)");
$add->execute(array(':f1' => '', ':f2' => $fid, ':f3' => ''));
echo "added";
$remove = $con->prepare("DELETE FROM table WHERE id2=:f1");
$remove->bindValue(':f1', $fid, PDO::PARAM_STR);
$remove->execute();
echo "removed";
}catch(PDOException $ex){
echo "error";
}
现在这个有效,但是我真的不知道它是用pdo写的,我不需要像mysqli那样使用mysqli_real_escape_string之类的东西。 我在网上找到的就是现在如何编写代码的哪一部分正在做什么,例如我在mysqli中使用插入,更新或删除时使用
if(mysqli_query($con, $sql)){echo "success";}else echo 'fail';
我怎么能用pdo做到这一点? 而且对于使用try和catch我不知道我是否需要在每个查询中使用它或者我在上面添加它?
再说一次我是pdo的新手,我不太了解它并且上面的代码有效,但我不知道是不是以正确的方式编写了?
答案 0 :(得分:1)
首先,我要祝贺你加入PDO。在我认识的所有经验丰富的PHP开发人员中,他们一致认为PDO更喜欢mysqli。
我强烈建议您read through this guide使用PDO。它应该回答你所有的问题,甚至回答你将来可能会遇到的一些问题。
针对您的具体问题:
只要您使用带有占位符的预准备语句,就不再需要转义任何内容了。转义的存在恰恰是因为人们将变量插入到SQL语句中,这可能会混淆您需要的引号来包含字符串。
使用准备好的语句不再存在问题,这也意味着不再存在SQL注入的危险。 SQL注入利用字符串连接将原始SQL语句转换为完全不同的语句,再次使用引号,这就是为什么从用户输入接受的非转义字符串是SQL注入的攻击向量。使用参数和预处理语句解决了这两个问题。
对于使用PDO的错误处理,您希望使用in the manual here讨论的PDO::ERRMODE_EXCEPTION
。
不幸的是,PDO的默认值是PDO::ERRMODE_SILENT
,这实际上忽略了数据库错误,只是设置了你必须自己检查的PDO对象变量。
话虽如此,您可以通过在创建PDO连接对象时或之后添加错误模式来解决此问题。示例在我链接的PDO错误模式页面上。
对于Try-Catch块,一般情况下,除非您有一些功能代码来解决错误,否则您不希望特别捕获异常。从DRY和反模式的角度来看,包装每个sql调用只是为了报告错误信息是不好的。使用正确的错误模式,SQL错误将抛出您可以在错误处理程序中处理的异常,并且通常是您不应该吃东西并继续进行的事情。
您的错误处理程序应该(在生产中)将错误记录到磁盘/通过电子邮件发送给系统管理员或站点所有者,并显示一个专业的非特定错误消息,通知用户该问题以及所有异常应该发生的错误消息。