我试图创建一个包含多个条件的INSERT语句作为PHP函数的一部分 - 到目前为止,这是我的代码:
public function insertData($data)
{
try
{
$stmt = $this->con->prepare('
INSERT IGNORE INTO tblProductData(
strProductCode,
strProductName,
strProductDesc,
smintStockLevel,
dblPrice,
dtmDiscontinued,
dtmAdded)
SELECT :strProductCode,
:strProductName,
:strProductDesc,
:smintStockLevel,
:dblPrice,
(CASE WHEN :dtmDiscontinued = "yes" then NOW();
ELSE SET dtmlDiscontinued = "NULL";
END CASE),
NOW()
FROM dual
WHERE not (:dblPrice < 5.0 and :smintStockLevel < 10)
and not (:dblPrice > 1000.0) ');
$length = count($data);
for ($x=0; $x < $length; $x++) {
$params = array(':strProductCode' => $data[$x][0],
':strProductName' => $data[$x][1],
':strProductDesc' => $data[$x][2],
':smintStockLevel' => $data[$x][3],
':dblPrice' => $data[$x][4] );
$stmt->execute($params);
}
return $stmt;
} catch(PDOException $e) {
echo 'ERROR: ' . $e->getMessage();
}
}
}
条件如下
dblPrice
的值小于5且smintStockLevel的值小于10,则不会插入该行。dblPrice
的值大于1000 - 请勿插入该行NULL
此查询作为PHP预处理语句的一部分执行,迭代包含所有值的多维数组。
我是否需要创建多个CASE
?有人可以就解决这个问题的最佳方法提供建议。
需要进一步的信息,请告诉我。
更新
输入上面的代码是为了显示完整的背景,并包含了戈登的建议。但是,我目前在执行时收到错误ERROR: SQLSTATE[HY093]: Invalid parameter number: number of bound variables does not match number of tokens
。
有人能看出原因吗?谢谢
解决方案
:dtmlDiscontinued
需要添加到$params
以解决错误:
示例
$params = array(':strProductCode' => $data[$x][0], ':strProductName' => $data[$x][1], ':strProductDesc' => $data[$x][2],
':smintStockLevel' => $data[$x][3], ':dblPrice' => $data[$x][4], ':dtmDiscontinued' => $data[$x][5] );
答案 0 :(得分:1)
您不能将where
子句与values
一起使用。您可以在SQL中实现逻辑,如下所示:
INSERT INTO tblProductData(strProductCode, strProductName, strProductDesc, smintStockLevel,
dblPrice, dtmDiscontinued, dtmAdded
)
SELECT :strProductCode, :strProductName, :strProductDesc, :smintStockLevel,
:dblPrice,
(case when :dtmDiscontinued = 'Yes' then NOW() end),
NOW()
FROM dual
WHERE not (:dblPrice < 5.0 and :smintStockLevel < 10) and
not (:dblPrice > 1000.0);
(注意from dual
实际上并没有做任何事情,但有些数据库在使用from
时需要where
子句。)
我不知道dtmDiscontinued = 'yes'
是什么意思。但是像上面这样的东西应该有效。
也就是说,您可能会发现将逻辑放在应用程序层而不是数据库中更容易。如果您总是想检查这些条件,请考虑触发器。
答案 1 :(得分:0)
Mysql没有检查约束,因此您必须在触发器中实现它们。 为了让ypu成为一个先机:
DELIMITER $$
CREATE TRIGGER product_cond BEFORE INSERT ON tblProductData
FOR EACH ROW
BEGIN
declare message VARCHAR(255);
declare hasError BIT;
IF new.dblPrice < 5 AND new.smintStockLevel < 10 THEN
SET hasError := 1;
SET message := 'If price is less then 5 stock has to be more then 10';
END IF;
IF new.dblPrice > 1000 THEN
SET hasError := 1;
SET message := 'Price can not be over 1000';
END IF;
/* create the other ckecks in the same way
If check failed signal an error */
IF hasError = 1 THEN
SIGNAL SQLSTATE '45000'
SET MESSAGE_TEXT = message;
END IF;
END$$
DELIMITER ;
请注意,使用SIGNAL
需要MYSQL 5.5+当然,您也可以在应用程序层进行这些检查