【问题标题】:Looping through MySQL results from stored procedure循环访问存储过程的 MySQL 结果
【发布时间】:2015-07-20 23:24:16
【问题描述】:

为了简单起见,我有以下 SQL 查询:

"SELECT id,name FROM employees WHERE birthdate<'$dymd'"

如果我想使用标准(非存储过程)查询中的记录,代码如下所示:

$sql="SELECT id,name FROM employees WHERE birthdate<'$dymd'";

$rst=$mysqli->query($sql);

while($row=$rst->fetch_assoc())
{
  ...
}

$rst->free();

但如果我将查询存储到存储过程中:

CREATE PROCEDURE GetEmployees(IN dymd DATE)
  READS SQL DATA
BEGIN
  SELECT id,name FROM employees WHERE birthdate<dymd;
END;

我无法使用之前的循环(我收到错误消息:“命令不同步;您现在无法运行此命令”)。我必须像这样循环:

$sql="CALL GetEmployees('$dymd')";

$rst=$mysqli->query($sql);

if($rst->num_rows)
{
  do
  {
    $row=$rst->fetch_assoc();
    ...
  }
  while($mysqli->next_result());
  $rst->free();
}

问题是为什么我需要显式推送记录指针以防存储过程中的记录!?为什么 fetch_assoc() 不像以前那样为我做这件事?

更重要的是,上面的代码仅适用于从每个 PHP 页面的存储过程中检索到的一个结果集。如果我在第二个存储过程的同一 PHP 页面上有两个存储过程(例如 CALL YoungEmployees() 和 CALL OldEmployees()),我会收到已经提到的错误消息。如果我使用标准查询(不是来自存储过程),那么它工作正常 - 两个结果集都正确显示在一个页面上!

【问题讨论】:

  • 据我所知,从标准查询和存储过程中检索的结果集的区别在于存储过程返回多个结果集,mysqli需要以不同方式处理它们。
  • @JurgisGregov 非常感谢 - 这就是解决方案!只需在每次检索存储过程后放置 $mysqli->next_result() !虽然与 PHP 手册中关于存储过程 (php.net/manual/en/mysqli.quickstart.stored-procedures.php) 的规定相反,不能使用 $msqli->query(),但这对我有用。

标签: php mysql stored-procedures mysqli


【解决方案1】:

根据@JurisGregov 的评论,解决方案是;

//first stored procedure

$sql1="CALL YoungEmployees('$dymd')";

if($rst1=$mysqli->query($sql1))
{
  while($row1=$rst1->fetch_row())
  {
    ...
  }
  $rst1->close();
  $mysqli->next_result(); //!!!
}

//second stored procedure

$sql2="CALL OldEmployees('$dymd')";

if($rst2=$mysqli->query($sql2))
{
  while($row2=$rst2->fetch_row())
  {
    ...
  }
  $rst2->close();
  $mysqli->next_result(); //!!!
}

【讨论】:

  • 注意:别忘了数据库用户必须有EXECUTE权限才能运行(调用)存储过程!
猜你喜欢
  • 2013-08-05
  • 1970-01-01
  • 2013-11-13
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-05-05
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多