[英]Simple PHP Select with Prepared Statements Displays No Results
I am trying to create a simple PHP script that selects data using prepared statements. 我正在尝试创建一个简单的PHP脚本,该脚本使用准备好的语句选择数据。 Currently, I am using this tutorial as a source. 当前,我正在使用本教程作为源。 When I call my script, I have no errors in the error.log, but no data is displayed. 当我调用脚本时,error.log中没有错误,但是没有数据显示。 Here is my script: 这是我的脚本:
<?php
$servername = "xxx";
$username = "xxx";
$password = "xxx";
$dbname = "xxx";
// Create connection
$conn = new mysqli($servername, $username, $password, $dbname);
// Check connection
if ($conn->connect_error) {
die("Connection failed: " . $conn->connect_error);
}
$stmt = $conn->prepare("SELECT * FROM Regions WHERE id=?");
$stmt->bind_param("i", $_POST['id']);
$stmt->execute();
$result = $stmt->get_result();
if($result->num_rows > 0) {
while($row = $result->fetch_assoc()) {
$name[] = $row['name'];
$center[] = $row['center'];
$content_string[] = $row['content_string'];
}
}
$stmt->close();
echo $name;
echo $center;
echo $content_string;
$conn->close();
?>
My structure looks like this: 我的结构如下所示:
I have tried to access the output by calling http://URL/php/protected.php?id=1 and http://URL/php/protected.php to no avail. 我试图通过调用http://URL/php/protected.php?id = 1和http://URL/php/protected.php来访问输出,但无济于事。 I've narrowed down that the error is happening because if($result->num_rows > 0)
never gets evaluated. 我缩小了错误发生的范围,因为if($result->num_rows > 0)
从未得到评估。 From that, I figure that the error must be in my SQL statement. 由此,我认为该错误必须在我的SQL语句中。
I am actually the author of that tutorial lol. 我实际上是该教程的作者。 Did you check the section on error handling? 您是否检查了有关错误处理的部分? You should be able to get a meaningful message by following that. 通过遵循该步骤,您应该能够获得有意义的消息。
For instance 例如
if ( !$stmt = $conn->prepare("SELECT * FROM Regions WHERE id=?") )
echo "Prepare Error: ($conn->errno) $conn->error";
if ( !$stmt->bind_param("i", $_POST['id']) )
echo "Binding Parameter Error: ($conn->errno) $conn->error";
if ( !$stmt->execute() )
echo "Execute Error: ($stmt->errno) $stmt->error";
if ( !$stmt->get_result() ) //Only for select with get_result()
echo "Getting Result Error: ($conn->errno) $conn->error";
if ( !$stmt->store_result() ) //Only for select with bind_result()
echo "Storing Result Error: ($conn->errno) $conn->error";
$stmt->close();
Edit: A more elegant way to do this would be with exception handling. 编辑:一种更优雅的方法是使用异常处理。 Keep in mind that if mysqli_report()
is used before creating the connection, then it will output your database password on errors. 请记住,如果在创建连接之前使用mysqli_report()
,则它将在错误时输出数据库密码。 You should be using either a try/catch
or custom exception handler printing to your error log anyway, but it's worth pointing out. 无论如何,您应该使用try/catch
或自定义异常处理程序打印到错误日志,但这是值得指出的。 Also, make sure to do display_errors = Off
and log_errors = On
in your php.ini 另外,请确保在php.ini中执行display_errors = Off
和log_errors = On
mysqli_report(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT);
$stmt = $conn->prepare("SELECT * FROM Regions WHERE id=?");
$stmt->bind_param("i", $_POST['id']);
$stmt->execute();
$result = $stmt->get_result();
if($result->num_rows > 0) {
while($row = $result->fetch_assoc()) {
$name[] = $row['name'];
$center[] = $row['center'];
$content_string[] = $row['content_string'];
}
}
$stmt->close();
But as RichGoldMd pointed out, you also should be doing something like the following, which is a very common reason for errors in my experience. 但是正如RichGoldMd指出的那样,您还应该执行以下操作,这是导致我的经验出错的非常普遍的原因。
$id = (!empty($_POST['id']) ? $_POST['id'] : '');
Do you own the server this is running on (VPS or dedicated), or is this a shared hosting environment? 您是否拥有运行该服务器的服务器(VPS或专用服务器),或者这是共享托管环境? When I tried running your code, I got this error: 当我尝试运行您的代码时,出现以下错误:
PHP Fatal error: Call to undefined method mysqli_stmt::get_result()
A fatal error on the get_result
line would certainly prevent if($result->num_rows > 0)
from being evaluated. get_result
行上的致命错误肯定会阻止评估if($result->num_rows > 0)
get_result
if($result->num_rows > 0)
。 That error message led me to this question , which suggests that you can't use get_result
without the the mysqlnd extension installed. 该错误消息使我想到了这个问题 , 该问题表明如果未安装mysqlnd扩展名,则无法使用get_result
。 With PHP 5 on Debian/Ubuntu, this would be the php5-mysqlnd
package. 在Debian / Ubuntu上使用PHP 5时,它将是php5-mysqlnd
软件包。
If you aren't able to install that extension, and this is indeed your problem, you won't be able to use get_result
, meaning you'll need to use the far uglier bind_result method, which would look something like this: 如果您无法安装该扩展程序,而这确实是您的问题,那么您将无法使用get_result
,这意味着您将需要使用难看的bind_result方法,该方法看起来像这样:
<?php
$servername = "xxx";
$username = "xxx";
$password = "xxx";
$dbname = "xxx";
// Create connection
$conn = new mysqli($servername, $username, $password, $dbname);
// Check connection
if ($conn->connect_error) {
die("Connection failed: " . $conn->connect_error);
}
$stmt = $conn->prepare("SELECT name, center, content_string FROM Regions WHERE id=?");
$stmt->bind_param("i", $_POST['id']);
$stmt->execute();
$stmt->bind_result($row_name, $row_center, $row_content_string);
if($result->num_rows > 0) {
while($row = $result->fetch_assoc()) {
$name[] = $row_name;
$center[] = $row_center;
$content_string[] = $row_content_string;
}
}
$stmt->close();
echo $name;
echo $center;
echo $content_string;
$conn->close();
?>
It's highly advisable to not use SELECT *
when using bind_result
, since the order of columns returned by the database matters. 强烈建议在使用bind_result
时不要使用SELECT *
,因为数据库返回的列顺序很重要。
Personally, I'd recommend looking into using PDO instead of mysqli, because I think the syntax is a lot friendlier than mysqli's and there's a lot less "gotchas" like the one I described above. 就个人而言,我建议您使用PDO代替mysqli,因为我认为该语法比mysqli友好得多,并且“陷阱”比我上面描述的要少得多。 Here's a decent tutorial to introduce you to PDO. 这是一个不错的教程,向您介绍PDO。
You are calling you script with a query parameter - which is probably a GET if you are doing it in the browser, but retrieving the value from $_POST - Furthermore, you should ensure that the array index exists before you bind it - that is likely the problem, that $_POST['id'] doesn't exist when you call bind_param(). 您正在使用查询参数调用脚本-如果在浏览器中执行脚本,则可能是GET,但是从$ _POST检索值-此外,在绑定数组索引之前,应确保存在数组索引-这很可能问题是,当您调用bind_param()时,$ _POST ['id']不存在。
Before running the query you should test it: 在运行查询之前,您应该对其进行测试:
if (isset($_POST['id']) {
// ... do the query...
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.