PHP执行MySQL查询遇异常错误求助:mysqli_query相关报错
嘿,我之前也碰到过类似的mysqlnd驱动EOF包错误,结合你的情况——单独在MySQL命令行执行查询完全正常,但用PHP的mysqli_query就报Premature end of data和EOF packet shorter than expected——问题大概率出在PHP的mysqlnd驱动和MySQL服务器之间的连接传输环节,而不是SQL语句本身。给你几个实用的排查和解决方向:
先确认数据库连接是否还活着
有可能在执行这条查询前,数据库连接已经因为超时、网络波动或者MySQL服务器主动断开失效了。你可以在执行mysqli_query前加个连接存活检查,必要时重新建立连接:// $conn是你的数据库连接对象 if (!mysqli_ping($conn)) { // 关闭失效连接 mysqli_close($conn); // 重新建立连接 $conn = mysqli_connect('你的主机', '用户名', '密码', '数据库名'); } // 再执行目标查询 $result = mysqli_query($conn, "select ifnull(count(nid),0) from likes where nid=18578");调整mysqlnd的网络超时配置
这类EOF错误经常和mysqlnd的网络超时设置过短有关。如果有权限修改php.ini,可以调整这两个参数:mysqlnd.net_read_timeout = 60(延长读取数据的超时时间,单位秒)mysqlnd.net_write_timeout = 60(延长写入数据的超时时间)
修改后记得重启PHP-FPM或者你的Web服务器(比如Nginx/Apache)。
检查脚本的执行上下文
看看这条查询是不是在一个长时间运行的脚本里执行的?之前有没有执行过大量查询或者占用资源的操作?如果是,可能之前的查询结果没释放导致内存堆积,或者连接被耗尽。可以在执行这条查询前,先释放之前的查询结果:// 假设之前有查询结果$prev_result if (isset($prev_result)) { mysqli_free_result($prev_result); }也可以把这条查询单独抽出来写个小脚本测试,看看是不是脚本其他部分影响了连接。
检查MySQL服务器的超时设置
MySQL服务器端的wait_timeout和interactive_timeout参数如果设置太小,会主动断开长时间闲置的连接。你可以先在MySQL命令行临时调整测试:SET GLOBAL wait_timeout = 3600; SET GLOBAL interactive_timeout = 3600;如果调整后问题解决了,记得修改MySQL的配置文件(比如my.cnf或my.ini),把这两个参数永久设置为合适的值,然后重启MySQL服务。
试试用预处理语句替代直接查询
有时候直接用mysqli_query执行查询会有兼容性问题,换成mysqli的预处理语句试试,说不定能绕开这个驱动层面的bug:$stmt = mysqli_prepare($conn, "select ifnull(count(nid),0) from likes where nid=?"); // 绑定参数,"i"表示整数类型 mysqli_stmt_bind_param($stmt, "i", $nid); $nid = 18578; mysqli_stmt_execute($stmt); // 绑定结果变量 mysqli_stmt_bind_result($stmt, $count); mysqli_stmt_fetch($stmt); // 输出结果 echo $count; // 关闭语句 mysqli_stmt_close($stmt);
按照上面的步骤逐一排查,应该能解决这个问题。
内容的提问来源于stack exchange,提问作者Linux Pro

