我遇到PDO问题并提交多个查询。 这是我的PHP代码:
public function executeSql($multiQuery, $conn)
{
$arrQuery = mb_split(';\s*?(-- )?.*?\n', $multiQuery);
$conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$conn->beginTransaction();
try {
foreach ($arrQuery as $query) {
if (strlen(trim($query)) > 0) {
echo "<BR><BR>" . $query;
$conn->exec($query);
}
}
} catch (Exception $e) {
echo "<hr>RollBack";
$conn->rollback();
throw $e;
}
echo "<hr>Commit";
$conn->commit();
return true;
}
我的SQL:
INSERT INTO config_new SET nazwa='test', wartosc=123;
ALTER TABLE `koszty_rodzaje` DROP FOREIGN KEY `koszty_rodzaje_ibfk_2`,
ADD FOREIGN KEY (`temat_id`) REFERENCES `tematy` (`temat_id`)
ON DELETE CASCADE
ON UPDATE CASCADE;
第二个查询生成错误,但始终先插入:/
以下是我的回复:
INSERT INTO config_new
SET nazwa = 'dummy', wartosc = 1;
ALTER TABLE `koszty_rodzaje` DROP FOREIGN KEY `koszty_rodzaje_ibfk_2`,
ADD FOREIGN KEY (`temat_id`) REFERENCES `tematy` (
`temat_id`
)
ON DELETE CASCADE
ON UPDATE CASCADE;
INSERT INTO config_new SET nazwa='test', wartosc=123
ALTER TABLE `koszty_rodzaje` DROP FOREIGN KEY `koszty_rodzaje_ibfk_2`, ADD FOREIGN KEY (`temat_id`) REFERENCES `tematy` (`temat_id`) ON DELETE CASCADE ON UPDATE CASCADE;
RollBack
Fatal error: Uncaught exception 'PDOException' with message 'SQLSTATE[HY000]:
General error: 1025 Error on rename of
'./smaczny39/koszty_rodzaje' to './smaczny39/#sql2-3212-dafd68'
(errno: 152)' in /glowna/funkcje/klient.class.php:502
Stack trace: #0 /glowna/funkcje/klient.class.php(502):
PDO->exec('???ALTER TABLE ...') #1 /glowna/funkcje/klient.class.php(550):
cl_klient->executeSql('INSERT INTO con...', Object(PDO))
#2 /glowna/admin.php(41):
cl_klient->cron_aktualizuj_baze_klienta('1111', '2.0.0-pre.1')
#3 {main} thrown in /glowna/funkcje/klient.class.php on line 502
如您所见RollBack
已执行且Commit
已执行,为什么首先在DB中插入第一个查询?
如果我提出这样的查询:
INSERT INTO config_new SET nazwa='test', wartosc=123;
INSERT INTO config_new SET nazwa=testa, wartosc=123;
也出现了错误,没有插入新值,因此可以正常工作。
答案 0 :(得分:4)
MySQL总是在启动ALTER TABLE之前提交事务。因此,如果INSERT查询有效,无论ALTER TABLE是否有效,它都将继续。
此处有更多信息:https://dev.mysql.com/doc/refman/5.7/en/implicit-commit.html