如何使用PDO和bindParam将数组插入mysql?

时间:2012-03-25 05:12:35

标签: mysql multidimensional-array pdo

我正在使用以下代码。代码有效,但我想更改它以便它使用bindparam

try {
    $dbh = new PDO("mysql:host=$hostname;dbname=$dbname", $username, $password);
$stqid=array();

    for ($i=0; $i<$array_count; $i++){
    $stqid[$i][0]=$lastInsertValue;
    $stqid[$i][1]=$qid[$i][0];
    $stqid[$i][2]=$qid[$i][1];
    }

$values = array();
    foreach ($stqid as $rowValues) {
        foreach ($rowValues as $key => $rowValue) {
        $rowValues[$key] = $rowValues[$key];  
        }

    $values[] = "(" . implode(', ', $rowValues) . ")";
    }

$count = $dbh->exec("INSERT INTO qresults(instance, qid, result) VALUES  ".implode (', ', $values)); 
$dbh = null;
}
catch(PDOException $e){
    echo $e->getMessage();
}

我替换了以下

$count = $dbh->exec("INSERT INTO qresults(instance, qid, result) VALUES  ".implode (', ', $values)); 

$sql = "INSERT INTO qresults (instance, qid, result) VALUES (:an_array)";
$stmt = $dbh->prepare($sql);
$stmt->bindParam(':an_array', implode(',', $values),PDO::PARAM_STR);
$stmt->execute();

但插入不再起作用了(虽然我没有收到任何错误消息)。

问题:我做错了什么?如何重写代码以使用bindParam?

1 个答案:

答案 0 :(得分:3)

您正在尝试创建一个语句并绑定一个参数。

语句很棒,因为它可能会使任何类型的SQL注入无效。它通过删除仅被视为字符串的查询的概念来实现。 SQL查询被视为带有参数列表的字符串,以及作为绑定变量的关联数据。 所以查询不仅是文本,还有文本+数据。

我的意思是:

这个简单的查询:

SELECT * FROM A WHERE val="$param"

这不安全,因为查询只被视为字符串。如果没有检查$ param,那就是SQLi漏洞。

但是在创建语句时,您的查询将变为:

SELECT * FROM A WHERE val=:param

然后使用bindparam指定值a:param。这意味着该值不会附加到查询字符串,但已经解析了查询并提供了数据。

在你的情况下,你绑定到param:数组一个内爆数组(我假设“data1”,“data2”等)。这只是一个参数,其值为字符串(“data1,data2,data3 ...”),因此它只会导致一次插入,而不会导致多次插入。

您可以通过生成具有足够参数来处理数组的查询来更改语句生成

$sql = "INSERT INTO qresults (instance, qid, result) VALUES ( :val0, :val1, :val2, ...)";

然后在数组上循环并为每个参数调用bindparam方法。

$count = 0;
foreach($values as $val)
{
   $stmt->bindParam(":val$count", $val,PDO::PARAM_STR);
   $count++;

}

这样可行。

编辑:此解决方案展示了它如何适用于一维数组,但可以通过调整语句查询生成并修改bindparam循环轻松扩展到您的问题。

您的陈述应如下:

$sql = "INSERT INTO qresults (instance, qid, result) VALUES (:val0, :val1, :val2) , (:val3, :val4, :val5), ...";

您只需要计算基础数组中元素的数量。