从“mysqli-> prepare”导出“查询”

时间:2012-07-16 16:44:09

标签: php mysqli prepared-statement

是否可以导出由mysqli::prepare::bind_param格式化的查询?

示例:

<?php
$mysqli = new mysqli('host', 'user', 'pass', 'table');
if(mysqli_connect_errno()){
    printf('Connect failed: %s\n', mysqli_connect_error());
    exit;
}

$data=7290;

if ($stmt = $mysqli->prepare('SELECT `id`,`info` FROM `propertys` WHERE id>?')){
    $stmt->bind_param('i',$data);
    $stmt->execute();
    $stmt->bind_result($id,$info);
    while($q=$stmt->fetch()){
        echo $id,': ',$info,'<br>';
    }
    $stmt->close();
}
$mysqli->close();
?>

我想导出QUERYmysql::prepare执行的bind_param个功能 所以(这是一个虚构的例子):

if ($stmt = $mysqli->prepare('SELECT `id`,`info` FROM `propertys` WHERE id>?')){
    $stmt->bind_param('i',$data);
    $stmt->execute();
    echo $stmt->exportQuery();//Function does not exist, just for example

函数::exportQuery将打印如下:

SELECT `id`,`info` FROM `propertys` WHERE id>7290

有什么解决方案吗?

感谢。

3 个答案:

答案 0 :(得分:6)

我知道这对调试很有用,但它不是预处理语句的工作方式。参数不与客户端的预准备语句组合。 PHP永远不应该访问与其参数结合的查询字符串。

执行prepare()时,SQL语句将发送到数据库服务器,执行execute()时会单独发送参数。 MySQL的常规查询日志确实显示了在执行()后插值的最终SQL。以下是我的常规查询日志的摘录。我从mysql CLI运行查询,而不是从PHP运行,但原理是相同的。

081016 16:51:28 2 Query       prepare s1 from 'select * from foo where i = ?'
                2 Prepare     [2] select * from foo where i = ?
081016 16:51:39 2 Query       set @a =1
081016 16:51:47 2 Query       execute s1 using @a
                2 Execute     [2] select * from foo where i = 1

重新评论:

@Baily是正确的,MySQL没有客户端解决方案来返回插入参数的完整查询。这不是PHP的错。

要启用上面提到的日志记录,请在MySQL客户端中使用此命令,或通过API从PHP提交:

SET GLOBAL general_log = ON;

您应该在完成收集信息后关闭日志,因为记录每个查询会花费一些开销。

SET GLOBAL general_log = OFF;

PS:动态更改日志记录设置需要MySQL 5.1或更高版本。在早期版本中,您必须在更改日志记录时重新启动mysqld。

答案 1 :(得分:0)

准备好的声明不会像那样工作,这是你无法看到声明的原因,因为它应该能够在没有操作的情况下传递到数据库。

因此,唯一的解决方案是将数据附加到字符串,并回显或保存到变量。

编辑以包含您评论过的安全问题..

//Assume you're using $_GET to get the id
$data = mysql_real_escape_string($_GET['yourID']);

$yourStatement = 'SELECT `id`,`info` FROM `propertys` WHERE id>';
$savedStatement = $yourStatement.$data;

echo $savedStatement;
//Will return 'SELECT `id`,`info` FROM `propertys` WHERE id>4'

if ($stmt = $mysqli->prepare($yourStatement.'?')){
$stmt->bind_param('i',$data);
$stmt->execute();
  }

答案 2 :(得分:-1)

您可以重复回显线上的查询字符串,并将变量手动放入字符串中,如下所示:

if ($stmt = $mysqli->prepare('SELECT `id`,`info` FROM `propertys` WHERE id>?')){
    $stmt->bind_param('i',$data);
    if($stmt->execute()){
        echo 'SELECT `id`,`info` FROM `propertys` WHERE id>'.$data;
    };
}

您发布的大部分评论表明您的问题实际上是:

How to show the last queries executed on MySQL?