特定的MySQL PDO日期时间插入[HY0093]错误

时间:2014-02-15 20:05:21

标签: php mysql datetime pdo

我花了很多时间试图弄清楚这里有什么问题,我很难过。 这是失败的特定PHP代码:

//Handy function I use to do all my bound queries - yes you can have it.
function prepareBindAndExecute($pdo, $qry, $aParams) {
    if (!$stmt = $pdo->prepare($qry)) {
        setSessionError("Failed to prepare $qry");
        return false;
    }
    foreach ($aParams as $aParam) {
        // $aParam[0] = ":labelToBind"
        // $aParam[1] = value to Bind
        // $aParam[2] = PDO::PARAM_TYPE
        if (strpos($qry, $aParam[0]) !== false) {  // skip binding if label isn't in query.  This allows built up queries to not fail if parts were not created for a parameter.
            if (!$stmt->bindParam($aParam[0], $aParam[1], $aParam[2])) {
                setSessionError("Failed to bind $aParam[1] as $aParam[0] to $qry Error Info:".print_r($stmt->errorInfo()));
                return false;
            }
        }
    }
    if (!$stmt->execute()) {
        setSessionError("Failed to execute $qry bound with ".json_encode($aParams).' Error Info:'.print_r($stmt->errorInfo()));
        return false;
    }
    return $stmt;
}
// Here's the problem call: The member_login is a VARCHAR(32) receiving an email address string 
// and the submission_date is a DateTime column receiving the current date.
        $stmt = prepareBindAndExecute($pdoRW,
                                      'INSERT INTO videosubmissions (member_login, submission_date) VALUES (:login, :submission-date)',
                                      [ [ ':login',           $info['login'],   PDO::PARAM_STR ], 
                                        [ ':submission-date', $submission_date->format(DateTime::ISO8601), PDO::PARAM_STR ] ]);

以下是我使用此代码获得的结果:

  

无法执行

     
    

INSERT INTO videosubmissions(member_login,submission_date)VALUES     (:login,:submission-date)绑定     [[ “:登录”, “xTst2@gmail.com”,2],     [ “:提交日期”, “2014-02-15T20:37:01 + 0100”,2]]

  

错误日志中包含相关的PHP错误:

  

PHP警告:PDOStatement :: execute():SQLSTATE [HY093]:参数无效   number:参数未在......中定义。

这个简单的情况并非不匹配的参数数量,因为只有两个标签要绑定。我的帮助函数一直在处理比这个更复杂的查询。 有一段时间我以为我通过引用:label标签 - >来解决这个问题。 VALUES(“:label”,:submission_date ...... 这让调用成功但导致sting“:label”被插入到DB中,实际上,根据我的理解,会导致真正的参数计数不匹配。 PDO :: PARAM_常量不提供DATE或DATETIME风格。 (见http://www.php.net/manual/en/pdo.constants.php) 我已经验证我的帮助函数没有跳过绑定任何参数 - 我们可以从返回的错误消息中播种。

我还尝试将submission_date与DateTime PHP对象而不是字符串绑定,我尝试了各种数据/时间格式化字符串。 我想知道登录参数中的@是否以某种方式搞砸了绑定。 如果PDO能提供发送到mySql的实际查询的内容会很好,但这可能会隐藏在驱动程序中。

希望我只是缺少一些愚蠢的东西。 感谢!!!

2 个答案:

答案 0 :(得分:0)

Dunno这个特殊代码的问题是什么,但如果要取出所有无用的部分,可以归结为这个,我很确定会工作

function query($pdo, $qry, $aParams) {
    $stmt = $pdo->prepare($qry);
    $stmt->execute($aParams);
    return $stmt;
}
$sql = 'INSERT INTO videosubmissions (member_login, submission_date) VALUES (?, ?)';
query($pdoRW, $sql, [$info['login'], $submission_date->format(DateTime::ISO8601)]);

答案 1 :(得分:0)

占位符名称中不能包含-

INSERT INTO [...snip...] (:login, :submission-date)',
                                            ^---

-不是占位符名称中的有效字符,MySQL会将其解释为

 ... :submission MINUS date

由于您没有绑定submission的值,因此会出现无效的参数编号错误。即使您偶然拥有另一个名为WAS :submission的占位符,由于MySQL中使用了未定义/不存在的date字段,您仍然会得到SQL解析器错误。作为减法操作。