php - mysqli_fetch_assoc()需要参数/调用成员函数bind_param()错误。如何获取并修复实际的mysql错误?

标签 php mysqli prepared-statement environment error-reporting

在我的本地/开发环境中,MySQLi查询执行正常。但是,当我将其上载到Web主机环境时,出现以下错误:


  致命错误:在...中的非对象上调用成员函数bind_param()


这是代码:

global $mysqli;
$stmt = $mysqli->prepare("SELECT id, description FROM tbl_page_answer_category WHERE cur_own_id = ?");
$stmt->bind_param('i', $cur_id);
$stmt->execute();
$stmt->bind_result($uid, $desc);


为了检查我的查询,我尝试通过控制面板phpMyAdmin执行查询,结果没有问题。

最佳答案

有时,您的mysqli代码会产生类似mysqli_fetch_assoc() expects parameter...Call to a member function bind_param()...之类的错误。甚至没有任何错误,但是查询不能完全一样。这意味着您的查询无法执行。

每次查询失败时,MySQL都会显示一条错误消息,说明原因。不幸的是,默认情况下,此类错误不会转移到PHP,而您所得到的只是上面提到的一个神秘的错误消息。因此,配置PHP和mysqli向您报告MySQL错误非常重要。一旦收到错误消息,对其进行修复将是小菜一碟。

如何在mysqli中获取错误消息

首先,在所有环境中mysqli连接之前,请始终使用以下行:

mysqli_report(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT);


之后,所有MySQL错误都会转移到PHP异常中。反过来,未捕获的异常会导致PHP致命错误。因此,在发生MySQL错误的情况下,您将获得常规的PHP错误。这将立即使您知道错误原因。堆栈跟踪将引导您到发生错误的确切位置。

如何在不同的环境中配置PHP

这是我关于PHP error reporting的文章的要旨:
开发服务器和实时服务器上的报告错误必须不同。在开发服务器上,将错误显示在屏幕上很方便,但是在实时服务器上,必须记录错误消息,因此您以后可以在错误日志中找到它们。

因此,必须将相应的配置选项设置为以下值


在开发服务器上


error_reporting应设置为E_ALL值;
log_errors应该设置为1(也可以在dev PC上记录日志)
display_errors应设置为1

在生产服务器上


error_reporting应设置为E_ALL值;
log_errors应设置为1
display_errors应设置为0



如何实际使用?

只需删除所有手动检查错误的代码,所有or die()if ($result)等。只需立即编写数据库交互代码:

$stmt = $this->con->prepare("INSERT INTO table(name, quantity) VALUES (?,?)");
$stmt->bind_param("si", $name, $quantity);
$stmt->execute();


再次,周围没有任何条件。如果发生错误,它将被视为代码中的任何其他错误。例如,在开发PC上,它只会显示在屏幕上,而在实时站点上,它将记录给程序员,而为了用户的方便,您可以使用错误处理程序(但这是一个不同的故事,对于mysqli,但您可以在上面链接的文章中了解它。

如何处理您收到的错误消息

得到错误消息后,您必须阅读并理解它。如果不屈尊,这听起来太明显了,但是学习者常常忽略了错误消息的极大帮助。但大多数情况下,它可以很直接地解释问题。说,如果它说不存在特定的表,则必须检查拼写,错别字,字母大小写,数据库凭据等。或者,如果显示SQL语法错误,则必须检查SQL。问题点就在错误消息中引用的查询部分之前。

如果您不明白该错误信息,请尝试使用Google进行搜索。在浏览结果时,请坚持使用能够解释错误的答案,而不是直截了当地给出解决方案。解决方案可能不适用于您的特定情况,但说明将帮助您理解问题并能够自己解决问题。

您还必须信任错误消息。如果说令牌的数量与绑定变量的数量不匹配,那就是。缺少的表或列也是如此。如果有选择,无论是您自己的错误还是错误消息是错误的,请始终坚持前者。再次听起来是屈尊的,但是这个站点上的数百个问题证明了此建议极为有用。

关于错误报告,您永远不应该做的事情清单


切勿使用错误抑制运算符(@)!这使程序员无法读取错误消息,因此无法修复错误
请勿使用die()echo或任何其他功能在屏幕上无条件地打印错误消息。 PHP可以自行报告错误,并根据环境正确地执行操作-因此,只需将其留给PHP。
不要添加条件来手动测试查询结果(例如if($result))。启用错误异常后,这种情况将毫无用处。
不要使用try..catch运算符回显错误消息。应该使用该运算符执行一些错误处理,例如事务回滚。但是,切勿仅将其用于报告错误-正如我们上文所述,PHP已经可以正确的方式做到这一点。


附言
有时没有错误,但也没有结果。这意味着数据库中没有符合您条件的数据。在这种情况下,即使您可以保证数据和标准都可以,也必须承认这一事实。他们不是。您必须再次检查它们。我有一篇文章可以帮助您解决这个问题,How to debug database interactions。尽管它是为PDO编写的,但原理是相同的。只需按照此说明逐步进行操作,即可解决您的问题或对堆栈溢出有一个可解答的问题。

关于php - mysqli_fetch_assoc()需要参数/调用成员函数bind_param()错误。如何获取并修复实际的mysql错误?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56069103/

相关文章:

php - foreach 循环中数组 undefined offset 通知

php - fatal error :调用未定义的方法 mysqli_stmt::get_result()

java - 将 PHP SoapClient 与 Java JAX-WS RI(Web 服务)结合使用

php - 动态内容选择不起作用

php - 如果 href 或 src 前面有一个点,则正则表达式需要不匹配

php - Opencart 1.4.9 从 mysql 到 mysqli

php - 将下拉菜单中的多个值保存到数据库中

php - 如何从mysql准备语句中的两个表中选择值

php - TCPDF 如何创建这个框?

php - 动态表单字段插入