PDO 插入 MySQL 数据库不与另一个 PDO 查询一起工作
PDO insert into MySQL Database not working with another PDO query
(我不知道标题是不是描述性的,我不确定问题出在哪里,所以很难想出一个好的标题。)
事情是这样的。我想使用 PDO 将值(从 HTML 表单)插入到 MySQL 数据库中。
到目前为止一切顺利。我设法获得了 $_POST['xyz'] 值并成功地将它们插入到数据库中。但现在我想确保只有一行具有相同的电子邮件地址 ($email) 和相同的问题 ID ($qid)。正如您在代码中看到的那样,我通过检查行数来做到这一点。不确定这是否是一个好方法。
现在我可以成功地不插入具有相似电子邮件地址的两行,但由于某种原因我无法插入具有任何其他电子邮件地址的任何行。一直试图弄清楚我做错了什么,但不能。所以这是代码。希望你能看到我在那里做了什么(因为我看不到)。
try {
$cnnxn = new PDO("mysql:host=$db_host;dbname=$db_name", $db_username, $db_password);
} catch (PDOException $e2) {
die("ERROR: " . $e2->getMessage());
}
$query2 = $cnnxn->prepare("SELECT count(*) as cnt FROM grdj_replies WHERE email = :email AND question_id = :qid");
$query2->bindParam(':email', $email);
$query2->bindParam(':qid', $qid);
$isQueryOk = $query2->execute();
if ($isQueryOk) {
$count = $query2->fetchColumn();
} else {
trigger_error('Error executing statement.');
}
$query2->closeCursor();
if ($count > 0){
echo '<div class="tools-alert tools-alert-red"><p>Sähköpostiosoitteellasi <strong>'.$email.'</strong> löytyy jo tallennettu vastaus tähän tehtävään. Jos haluat muuttaa vastausta, seuraa sähköpostiosoitteeseesi lähetetyn viestin ohjeita.<p>';
echo '<p>(<a href="#">Klikkaa tästä, jos haluat lähettää ohjeet uudestaan osoitteeseen '.$email.'</a>.)</p></div>';
}
else {
$cnnxn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTIONS);
$cnnxn->exec("SET NAMES utf8");
$query = $cnnxn->prepare("INSERT INTO grdj_replies (question_id, last_name, first_name, email, question_number, answer, status, accesstoken) VALUES (:qid, :lastname, :firstname, :email, :questionnumber, :answer, :status, :accesstoken)");
$query->bindParam(':qid', $qid);
$query->bindParam(':lastname', $last_name);
$query->bindParam(':firstname', $first_name);
$query->bindParam(':email', $email);
$query->bindParam(':questionnumber', $question_number);
$query->bindParam(':answer', $answer);
$query->bindParam(':status', $status);
$query->bindParam(':accesstoken', $accesstoken);
$query->execute();
if ($query !== false)
{
print "<div class=\"tools-alert tools-alert-green\">Vastauksesi on tallennettu!</div>";
}
$query->closeCursor();
$cnnxn = null;
}
首先,您使用的是 ->bindParam(),其中 ->bindValue() 就足够了(也许更合适)。
你问你的输入处理是不是一个好的做事方式:我看不到那个代码。不要使用超全局变量,而是使用 filter_input() / filter_input_array()
您描述的问题可能不在 PHP 代码中:仔细查看数据库索引。您是否通过 qid 对 grdj_replies 进行了唯一索引(例如,您在 "qid" 上是否有主键)?对于同一个 qid,是否有任何其他不充分的索引阻止您将其他行插入 table?或许你应该通过qid、email联合唯一索引。
您将错误处理应用于创建 PDO 对象(数据库连接);在这种情况下,我经常发现将错误处理 (try/catch, $error->getMessage()) 应用于 SQL 语句的执行很有帮助(通过这种方式,您可以看到数据库正试图告诉你。它是否抛出一个 excuse/explanation 因为不是 运行 查询?)
我建议您使用 MySQL 唯一索引:
ALTER TABLE `grdj_replies`
ADD UNIQUE INDEX `UNIQUE_IDX` (`email`, `question_id`);
现在 MySQL 将确保没有其他行具有相同的电子邮件和 question_id 在插入新行之前,您不必检查它 "manually"。
如果已经有相同的数据,INSERT
请求将失败。
(我不知道标题是不是描述性的,我不确定问题出在哪里,所以很难想出一个好的标题。)
事情是这样的。我想使用 PDO 将值(从 HTML 表单)插入到 MySQL 数据库中。
到目前为止一切顺利。我设法获得了 $_POST['xyz'] 值并成功地将它们插入到数据库中。但现在我想确保只有一行具有相同的电子邮件地址 ($email) 和相同的问题 ID ($qid)。正如您在代码中看到的那样,我通过检查行数来做到这一点。不确定这是否是一个好方法。
现在我可以成功地不插入具有相似电子邮件地址的两行,但由于某种原因我无法插入具有任何其他电子邮件地址的任何行。一直试图弄清楚我做错了什么,但不能。所以这是代码。希望你能看到我在那里做了什么(因为我看不到)。
try {
$cnnxn = new PDO("mysql:host=$db_host;dbname=$db_name", $db_username, $db_password);
} catch (PDOException $e2) {
die("ERROR: " . $e2->getMessage());
}
$query2 = $cnnxn->prepare("SELECT count(*) as cnt FROM grdj_replies WHERE email = :email AND question_id = :qid");
$query2->bindParam(':email', $email);
$query2->bindParam(':qid', $qid);
$isQueryOk = $query2->execute();
if ($isQueryOk) {
$count = $query2->fetchColumn();
} else {
trigger_error('Error executing statement.');
}
$query2->closeCursor();
if ($count > 0){
echo '<div class="tools-alert tools-alert-red"><p>Sähköpostiosoitteellasi <strong>'.$email.'</strong> löytyy jo tallennettu vastaus tähän tehtävään. Jos haluat muuttaa vastausta, seuraa sähköpostiosoitteeseesi lähetetyn viestin ohjeita.<p>';
echo '<p>(<a href="#">Klikkaa tästä, jos haluat lähettää ohjeet uudestaan osoitteeseen '.$email.'</a>.)</p></div>';
}
else {
$cnnxn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTIONS);
$cnnxn->exec("SET NAMES utf8");
$query = $cnnxn->prepare("INSERT INTO grdj_replies (question_id, last_name, first_name, email, question_number, answer, status, accesstoken) VALUES (:qid, :lastname, :firstname, :email, :questionnumber, :answer, :status, :accesstoken)");
$query->bindParam(':qid', $qid);
$query->bindParam(':lastname', $last_name);
$query->bindParam(':firstname', $first_name);
$query->bindParam(':email', $email);
$query->bindParam(':questionnumber', $question_number);
$query->bindParam(':answer', $answer);
$query->bindParam(':status', $status);
$query->bindParam(':accesstoken', $accesstoken);
$query->execute();
if ($query !== false)
{
print "<div class=\"tools-alert tools-alert-green\">Vastauksesi on tallennettu!</div>";
}
$query->closeCursor();
$cnnxn = null;
}
首先,您使用的是 ->bindParam(),其中 ->bindValue() 就足够了(也许更合适)。
你问你的输入处理是不是一个好的做事方式:我看不到那个代码。不要使用超全局变量,而是使用 filter_input() / filter_input_array()
您描述的问题可能不在 PHP 代码中:仔细查看数据库索引。您是否通过 qid 对 grdj_replies 进行了唯一索引(例如,您在 "qid" 上是否有主键)?对于同一个 qid,是否有任何其他不充分的索引阻止您将其他行插入 table?或许你应该通过qid、email联合唯一索引。
您将错误处理应用于创建 PDO 对象(数据库连接);在这种情况下,我经常发现将错误处理 (try/catch, $error->getMessage()) 应用于 SQL 语句的执行很有帮助(通过这种方式,您可以看到数据库正试图告诉你。它是否抛出一个 excuse/explanation 因为不是 运行 查询?)
我建议您使用 MySQL 唯一索引:
ALTER TABLE `grdj_replies`
ADD UNIQUE INDEX `UNIQUE_IDX` (`email`, `question_id`);
现在 MySQL 将确保没有其他行具有相同的电子邮件和 question_id 在插入新行之前,您不必检查它 "manually"。
如果已经有相同的数据,INSERT
请求将失败。