嗯,我有一个表,有2个唯一的索引字段:email
和doc
。当检测到重复的密钥插入时,我需要提醒用户。我可以使用:
...
catch(PDOException $e) {
if($e->getCode() == 1062)
...
}
但是我不知道是哪个索引触发了这个错误。有办法知道吗?
我在谷歌上发现,你可以通过getMessage()
函数做到这一点,但似乎MySQL的某些版本返回类似key 1
的东西,而其他人返回name_of_key
,这使得这很难工作。在插入之前我需要做一个选择吗?它看起来很丑。
谢谢。
为了实现这个跨版本,您确实需要在INSERT之前放置一个SELECT。只要创建了适当的锁,就可以在插入之前安全地执行select操作,而不需要竞争。
为获得最佳性能,使用InnoDB和"SELECT…"FOR UPDATE",因为它具有行级锁定。SELECT…如果行存在,FOR UPDATE将锁定该行;如果行不存在,则锁定该行的"gap"。不要使用SELECT…在共享模式下锁定,因为这会创建读锁,必须升级为写锁,并且可能发生死锁。
- http://dev.mysql.com/doc/refman/5.0/en/innodb-locking-reads.html
如果使用MyISAM,请使用LOCK TABLE来锁定表,这样只有一个线程可以访问它。——http://dev.mysql.com/doc/refman/4.1/en/lock-tables.html